X-Git-Url: https://git.libre-soc.org/?a=blobdiff_plain;f=src%2Fmesa%2Fdrivers%2Fdri%2Fi965%2Fbrw_fs.h;h=748069e7b000fe01fae54d7b41afae4d8f1406fe;hb=467077b834eff4a38eb7a298826baddc44a298b8;hp=506f3ad4b392d5a9632c038cf19a72f3f3e27d61;hpb=246211d366feeff03e1ffa1756e718a1a5e2a6d5;p=mesa.git diff --git a/src/mesa/drivers/dri/i965/brw_fs.h b/src/mesa/drivers/dri/i965/brw_fs.h index 506f3ad4b39..748069e7b00 100644 --- a/src/mesa/drivers/dri/i965/brw_fs.h +++ b/src/mesa/drivers/dri/i965/brw_fs.h @@ -28,6 +28,7 @@ #pragma once #include "brw_shader.h" +#include "brw_ir_fs.h" extern "C" { @@ -39,19 +40,17 @@ extern "C" { #include "program/prog_parameter.h" #include "program/prog_print.h" #include "program/prog_optimize.h" -#include "program/register_allocate.h" -#include "program/sampler.h" +#include "util/register_allocate.h" #include "program/hash_table.h" #include "brw_context.h" #include "brw_eu.h" #include "brw_wm.h" -#include "brw_shader.h" #include "intel_asm_annotation.h" } #include "glsl/glsl_types.h" #include "glsl/ir.h" - -#define MAX_SAMPLER_MESSAGE_SIZE 11 +#include "glsl/nir/nir.h" +#include "program/sampler.h" struct bblock_t; namespace { @@ -62,142 +61,6 @@ namespace brw { class fs_live_variables; } -class fs_reg : public backend_reg { -public: - DECLARE_RALLOC_CXX_OPERATORS(fs_reg) - - void init(); - - fs_reg(); - fs_reg(float f); - fs_reg(int32_t i); - fs_reg(uint32_t u); - fs_reg(struct brw_reg fixed_hw_reg); - fs_reg(enum register_file file, int reg); - fs_reg(enum register_file file, int reg, enum brw_reg_type type); - fs_reg(class fs_visitor *v, const struct glsl_type *type); - - bool equals(const fs_reg &r) const; - bool is_valid_3src() const; - bool is_contiguous() const; - - fs_reg &apply_stride(unsigned stride); - /** Smear a channel of the reg to all channels. */ - fs_reg &set_smear(unsigned subreg); - - /** - * Offset in bytes from the start of the register. Values up to a - * backend_reg::reg_offset unit are valid. - */ - int subreg_offset; - - fs_reg *reladdr; - - /** Register region horizontal stride */ - uint8_t stride; -}; - -static inline fs_reg -retype(fs_reg reg, enum brw_reg_type type) -{ - reg.fixed_hw_reg.type = reg.type = type; - return reg; -} - -static inline fs_reg -offset(fs_reg reg, unsigned delta) -{ - assert(delta == 0 || (reg.file != HW_REG && reg.file != IMM)); - reg.reg_offset += delta; - return reg; -} - -static inline fs_reg -byte_offset(fs_reg reg, unsigned delta) -{ - assert(delta == 0 || (reg.file != HW_REG && reg.file != IMM)); - reg.subreg_offset += delta; - return reg; -} - -/** - * Get either of the 8-component halves of a 16-component register. - * - * Note: this also works if \c reg represents a SIMD16 pair of registers. - */ -static inline fs_reg -half(const fs_reg ®, unsigned idx) -{ - assert(idx < 2); - assert(idx == 0 || (reg.file != HW_REG && reg.file != IMM)); - return byte_offset(reg, 8 * idx * reg.stride * type_sz(reg.type)); -} - -static const fs_reg reg_undef; -static const fs_reg reg_null_f(retype(brw_null_reg(), BRW_REGISTER_TYPE_F)); -static const fs_reg reg_null_d(retype(brw_null_reg(), BRW_REGISTER_TYPE_D)); -static const fs_reg reg_null_ud(retype(brw_null_reg(), BRW_REGISTER_TYPE_UD)); - -class ip_record : public exec_node { -public: - DECLARE_RALLOC_CXX_OPERATORS(ip_record) - - ip_record(int ip) - { - this->ip = ip; - } - - int ip; -}; - -class fs_inst : public backend_instruction { - fs_inst &operator=(const fs_inst &); - -public: - DECLARE_RALLOC_CXX_OPERATORS(fs_inst) - - void init(enum opcode opcode, const fs_reg &dst, fs_reg *src, int sources); - - fs_inst(enum opcode opcode = BRW_OPCODE_NOP, const fs_reg &dst = reg_undef); - fs_inst(enum opcode opcode, const fs_reg &dst, const fs_reg &src0); - fs_inst(enum opcode opcode, const fs_reg &dst, const fs_reg &src0, - const fs_reg &src1); - fs_inst(enum opcode opcode, const fs_reg &dst, const fs_reg &src0, - const fs_reg &src1, const fs_reg &src2); - fs_inst(enum opcode opcode, const fs_reg &dst, fs_reg src[], int sources); - fs_inst(const fs_inst &that); - - void resize_sources(uint8_t num_sources); - - bool equals(fs_inst *inst) const; - bool overwrites_reg(const fs_reg ®) const; - bool is_send_from_grf() const; - bool is_partial_write() const; - int regs_read(fs_visitor *v, int arg) const; - bool can_do_source_mods(struct brw_context *brw); - - bool reads_flag() const; - bool writes_flag() const; - - fs_reg dst; - fs_reg *src; - - uint8_t sources; /**< Number of fs_reg sources. */ - - /* Chooses which flag subregister (f0.0 or f0.1) is used for conditional - * mod and predication. - */ - uint8_t flag_subreg; - - uint8_t regs_written; /**< Number of vgrfs written by a SEND message, or 1 */ - bool eot:1; - bool header_present:1; - bool shadow_compare:1; - bool force_uncompressed:1; - bool force_sechalf:1; - bool pi_noperspective:1; /**< Pixel interpolator noperspective flag */ -}; - /** * The fragment shader front-end. * @@ -206,6 +69,9 @@ public: class fs_visitor : public backend_visitor { public: + const fs_reg reg_null_f; + const fs_reg reg_null_d; + const fs_reg reg_null_ud; fs_visitor(struct brw_context *brw, void *mem_ctx, @@ -214,12 +80,24 @@ public: struct gl_shader_program *shader_prog, struct gl_fragment_program *fp, unsigned dispatch_width); + + fs_visitor(struct brw_context *brw, + void *mem_ctx, + const struct brw_vs_prog_key *key, + struct brw_vs_prog_data *prog_data, + struct gl_shader_program *shader_prog, + struct gl_vertex_program *cp, + unsigned dispatch_width); + ~fs_visitor(); void init(); fs_reg *variable_storage(ir_variable *var); - int virtual_grf_alloc(int size); + fs_reg vgrf(const glsl_type *const type); + fs_reg vgrf(int num_components); void import_uniforms(fs_visitor *v); + void setup_uniform_clipplane_values(); + void compute_clip_distance(); void visit(ir_variable *ir); void visit(ir_assignment *ir); @@ -241,8 +119,9 @@ public: void visit(ir_emit_vertex *); void visit(ir_end_primitive *); - uint32_t gather_channel(ir_texture *ir, uint32_t sampler); - void swizzle_result(ir_texture *ir, fs_reg orig_val, uint32_t sampler); + uint32_t gather_channel(int orig_chan, uint32_t sampler); + void swizzle_result(ir_texture_opcode op, int dest_components, + fs_reg orig_val, uint32_t sampler); fs_inst *emit(fs_inst *inst); void emit(exec_list list); @@ -308,13 +187,19 @@ public: const fs_reg &varying_offset, uint32_t const_offset); - bool run(); + bool run_fs(); + bool run_vs(); + void optimize(); + void allocate_registers(); void assign_binding_table_offsets(); void setup_payload_gen4(); void setup_payload_gen6(); + void setup_vs_payload(); + void fixup_3src_null_dest(); void assign_curb_setup(); void calculate_urb_setup(); void assign_urb_setup(); + void assign_vs_urb_setup(); bool assign_regs(bool allow_spilling); void assign_regs_trivial(); void get_used_mrfs(bool *mrf_used); @@ -325,11 +210,11 @@ public: int choose_spill_reg(struct ra_graph *g); void spill_reg(int spill_reg); void split_virtual_grfs(); - void compact_virtual_grfs(); + bool compact_virtual_grfs(); void move_uniform_array_access_to_pull_constants(); void assign_constant_locations(); void demote_pull_constants(); - void invalidate_live_intervals(bool invalidate_cfg = true); + void invalidate_live_intervals(); void calculate_live_intervals(); void calculate_register_pressure(); bool opt_algebraic(); @@ -337,9 +222,9 @@ public: bool opt_cse_local(bblock_t *block); bool opt_copy_propagate(); bool try_copy_propagate(fs_inst *inst, int arg, acp_entry *entry); + bool try_constant_propagate(fs_inst *inst, acp_entry *entry); bool opt_copy_propagate_local(void *mem_ctx, bblock_t *block, exec_list *acp); - void opt_drop_redundant_mov_to_flags(); bool opt_register_renaming(); bool register_coalesce(); bool compute_to_mrf(); @@ -348,43 +233,70 @@ public: bool virtual_grf_interferes(int a, int b); void schedule_instructions(instruction_scheduler_mode mode); void insert_gen4_send_dependency_workarounds(); - void insert_gen4_pre_send_dependency_workarounds(fs_inst *inst); - void insert_gen4_post_send_dependency_workarounds(fs_inst *inst); + void insert_gen4_pre_send_dependency_workarounds(bblock_t *block, + fs_inst *inst); + void insert_gen4_post_send_dependency_workarounds(bblock_t *block, + fs_inst *inst); void vfail(const char *msg, va_list args); void fail(const char *msg, ...); void no16(const char *msg, ...); void lower_uniform_pull_constant_loads(); bool lower_load_payload(); - - void try_rep_send(); - - void push_force_uncompressed(); - void pop_force_uncompressed(); + bool opt_combine_constants(); void emit_dummy_fs(); - fs_reg *emit_fragcoord_interpolation(ir_variable *ir); + void emit_repclear_shader(); + fs_reg *emit_fragcoord_interpolation(bool pixel_center_integer, + bool origin_upper_left); fs_inst *emit_linterp(const fs_reg &attr, const fs_reg &interp, glsl_interp_qualifier interpolation_mode, bool is_centroid, bool is_sample); fs_reg *emit_frontfacing_interpolation(); fs_reg *emit_samplepos_setup(); - fs_reg *emit_sampleid_setup(ir_variable *ir); - fs_reg *emit_general_interpolation(ir_variable *ir); + fs_reg *emit_sampleid_setup(); + void emit_general_interpolation(fs_reg attr, const char *name, + const glsl_type *type, + glsl_interp_qualifier interpolation_mode, + int location, bool mod_centroid, + bool mod_sample); + fs_reg *emit_vs_system_value(int location); void emit_interpolation_setup_gen4(); void emit_interpolation_setup_gen6(); void compute_sample_position(fs_reg dst, fs_reg int_sample_pos); - fs_reg rescale_texcoord(ir_texture *ir, fs_reg coordinate, + fs_reg rescale_texcoord(fs_reg coordinate, int coord_components, bool is_rect, uint32_t sampler, int texunit); - fs_inst *emit_texture_gen4(ir_texture *ir, fs_reg dst, fs_reg coordinate, - fs_reg shadow_comp, fs_reg lod, fs_reg lod2, + fs_inst *emit_texture_gen4(ir_texture_opcode op, fs_reg dst, + fs_reg coordinate, int coord_components, + fs_reg shadow_comp, + fs_reg lod, fs_reg lod2, int grad_components, uint32_t sampler); - fs_inst *emit_texture_gen5(ir_texture *ir, fs_reg dst, fs_reg coordinate, - fs_reg shadow_comp, fs_reg lod, fs_reg lod2, - fs_reg sample_index, uint32_t sampler); - fs_inst *emit_texture_gen7(ir_texture *ir, fs_reg dst, fs_reg coordinate, - fs_reg shadow_comp, fs_reg lod, fs_reg lod2, - fs_reg sample_index, fs_reg mcs, fs_reg sampler); - fs_reg emit_mcs_fetch(ir_texture *ir, fs_reg coordinate, fs_reg sampler); + fs_inst *emit_texture_gen5(ir_texture_opcode op, fs_reg dst, + fs_reg coordinate, int coord_components, + fs_reg shadow_comp, + fs_reg lod, fs_reg lod2, int grad_components, + fs_reg sample_index, uint32_t sampler, + bool has_offset); + fs_inst *emit_texture_gen7(ir_texture_opcode op, fs_reg dst, + fs_reg coordinate, int coord_components, + fs_reg shadow_comp, + fs_reg lod, fs_reg lod2, int grad_components, + fs_reg sample_index, fs_reg mcs, fs_reg sampler, + fs_reg offset_value); + void emit_texture(ir_texture_opcode op, + const glsl_type *dest_type, + fs_reg coordinate, int components, + fs_reg shadow_c, + fs_reg lod, fs_reg dpdy, int grad_components, + fs_reg sample_index, + fs_reg offset, unsigned offset_components, + fs_reg mcs, + int gather_component, + bool is_cube_array, + bool is_rect, + uint32_t sampler, + fs_reg sampler_reg, + int texunit); + fs_reg emit_mcs_fetch(fs_reg coordinate, int components, fs_reg sampler); void emit_gen6_gather_wa(uint8_t wa, fs_reg dst); fs_reg fix_math_operand(fs_reg src); fs_inst *emit_math(enum opcode op, fs_reg dst, fs_reg src0); @@ -394,15 +306,20 @@ public: void emit_minmax(enum brw_conditional_mod conditionalmod, const fs_reg &dst, const fs_reg &src0, const fs_reg &src1); bool try_emit_saturate(ir_expression *ir); + bool try_emit_line(ir_expression *ir); bool try_emit_mad(ir_expression *ir); - void try_replace_with_sel(); + bool try_replace_with_sel(); + bool try_opt_frontfacing_ternary(ir_if *ir); bool opt_peephole_sel(); bool opt_peephole_predicated_break(); bool opt_saturate_propagation(); + bool opt_cmod_propagation(); void emit_bool_to_cond_code(ir_rvalue *condition); void emit_if_gen6(ir_if *ir); void emit_unspill(bblock_t *block, fs_inst *inst, fs_reg reg, uint32_t spill_offset, int count); + void emit_spill(bblock_t *block, fs_inst *inst, fs_reg reg, + uint32_t spill_offset, int count); void emit_fragment_program_code(); void setup_fp_regs(); @@ -427,9 +344,36 @@ public: const struct prog_instruction *fpi, fs_reg dst, fs_reg src0, fs_reg src1, fs_reg one); - void emit_color_write(int target, int index, int first_color_mrf); + void emit_nir_code(); + void nir_setup_inputs(nir_shader *shader); + void nir_setup_outputs(nir_shader *shader); + void nir_setup_uniforms(nir_shader *shader); + void nir_setup_uniform(nir_variable *var); + void nir_setup_builtin_uniform(nir_variable *var); + void nir_emit_system_values(nir_shader *shader); + void nir_emit_impl(nir_function_impl *impl); + void nir_emit_cf_list(exec_list *list); + void nir_emit_if(nir_if *if_stmt); + void nir_emit_loop(nir_loop *loop); + void nir_emit_block(nir_block *block); + void nir_emit_instr(nir_instr *instr); + void nir_emit_alu(nir_alu_instr *instr); + void nir_emit_intrinsic(nir_intrinsic_instr *instr); + void nir_emit_texture(nir_tex_instr *instr); + void nir_emit_jump(nir_jump_instr *instr); + fs_reg get_nir_src(nir_src src); + fs_reg get_nir_dest(nir_dest dest); + void emit_percomp(fs_inst *inst, unsigned wr_mask); + + bool optimize_frontfacing_ternary(nir_alu_instr *instr, + const fs_reg &result); + + int setup_color_payload(fs_reg *dst, fs_reg color, unsigned components); void emit_alpha_test(); + fs_inst *emit_single_fb_write(fs_reg color1, fs_reg color2, + fs_reg src0_alpha, unsigned components); void emit_fb_writes(); + void emit_urb_writes(); void emit_shader_time_begin(); void emit_shader_time_end(); @@ -469,16 +413,12 @@ public: void visit_atomic_counter_intrinsic(ir_call *ir); - struct gl_fragment_program *fp; - const struct brw_wm_prog_key *const key; - struct brw_wm_prog_data *prog_data; + const void *const key; + struct brw_stage_prog_data *prog_data; unsigned int sanity_param_count; int *param_size; - int *virtual_grf_sizes; - int virtual_grf_count; - int virtual_grf_array_size; int *virtual_grf_start; int *virtual_grf_end; brw::fs_live_variables *live_intervals; @@ -506,17 +446,24 @@ public: struct hash_table *variable_ht; fs_reg frag_depth; fs_reg sample_mask; - fs_reg outputs[BRW_MAX_DRAW_BUFFERS]; - unsigned output_components[BRW_MAX_DRAW_BUFFERS]; + fs_reg outputs[VARYING_SLOT_MAX]; + unsigned output_components[VARYING_SLOT_MAX]; fs_reg dual_src_output; bool do_dual_src; int first_non_payload_grf; /** Either BRW_MAX_GRF or GEN7_MRF_HACK_START */ - int max_grf; + unsigned max_grf; fs_reg *fp_temp_regs; fs_reg *fp_input_regs; + fs_reg *nir_locals; + fs_reg *nir_globals; + fs_reg nir_inputs; + fs_reg nir_outputs; + fs_reg nir_uniforms; + fs_reg *nir_system_values; + /** @{ debug annotation info */ const char *current_annotation; const void *base_ir; @@ -554,13 +501,12 @@ public: fs_reg delta_x[BRW_WM_BARYCENTRIC_INTERP_MODE_COUNT]; fs_reg delta_y[BRW_WM_BARYCENTRIC_INTERP_MODE_COUNT]; fs_reg shader_start_time; + fs_reg userplane[MAX_CLIP_PLANES]; - int grf_used; + unsigned grf_used; bool spilled_any_registers; const unsigned dispatch_width; /**< 8 or 16 */ - - int force_uncompressed_stack; }; /** @@ -573,27 +519,25 @@ class fs_generator public: fs_generator(struct brw_context *brw, void *mem_ctx, - const struct brw_wm_prog_key *key, - struct brw_wm_prog_data *prog_data, - struct gl_shader_program *prog, - struct gl_fragment_program *fp, + const void *key, + struct brw_stage_prog_data *prog_data, + struct gl_program *fp, bool runtime_check_aads_emit, - bool debug_flag); + const char *stage_abbrev); ~fs_generator(); - const unsigned *generate_assembly(const cfg_t *simd8_cfg, - const cfg_t *simd16_cfg, - unsigned *assembly_size); + void enable_debug(const char *shader_name); + int generate_code(const cfg_t *cfg, int dispatch_width); + const unsigned *get_assembly(unsigned int *assembly_size); private: - void generate_code(const cfg_t *cfg); void fire_fb_write(fs_inst *inst, - GLuint base_reg, + struct brw_reg payload, struct brw_reg implied_header, GLuint nr); - void generate_fb_write(fs_inst *inst); + void generate_fb_write(fs_inst *inst, struct brw_reg payload); + void generate_urb_write(fs_inst *inst, struct brw_reg payload); void generate_blorp_fb_write(fs_inst *inst); - void generate_rep_fb_write(fs_inst *inst); void generate_pixel_xy(struct brw_reg dst, bool is_x); void generate_linterp(fs_inst *inst, struct brw_reg dst, struct brw_reg *src); @@ -609,9 +553,9 @@ private: void generate_math_g45(fs_inst *inst, struct brw_reg dst, struct brw_reg src); - void generate_ddx(fs_inst *inst, struct brw_reg dst, struct brw_reg src, struct brw_reg quality); - void generate_ddy(fs_inst *inst, struct brw_reg dst, struct brw_reg src, - struct brw_reg quality, bool negate_value); + void generate_ddx(enum opcode op, struct brw_reg dst, struct brw_reg src); + void generate_ddy(enum opcode op, struct brw_reg dst, struct brw_reg src, + bool negate_value); void generate_scratch_write(fs_inst *inst, struct brw_reg src); void generate_scratch_read(fs_inst *inst, struct brw_reg dst); void generate_scratch_read_gen7(fs_inst *inst, struct brw_reg dst); @@ -666,11 +610,13 @@ private: void generate_untyped_atomic(fs_inst *inst, struct brw_reg dst, + struct brw_reg payload, struct brw_reg atomic_op, struct brw_reg surf_index); void generate_untyped_surface_read(fs_inst *inst, struct brw_reg dst, + struct brw_reg payload, struct brw_reg surf_index); bool patch_discard_jumps_to_fb_writes(); @@ -679,22 +625,20 @@ private: struct gl_context *ctx; struct brw_compile *p; - const struct brw_wm_prog_key *const key; - struct brw_wm_prog_data *prog_data; + const void * const key; + struct brw_stage_prog_data * const prog_data; - struct gl_shader_program *prog; - const struct gl_fragment_program *fp; + const struct gl_program *prog; unsigned dispatch_width; /**< 8 or 16 */ exec_list discard_halt_patches; bool runtime_check_aads_emit; - const bool debug_flag; + bool debug_flag; + const char *shader_name; + const char *stage_abbrev; void *mem_ctx; }; bool brw_do_channel_expressions(struct exec_list *instructions); bool brw_do_vector_splitting(struct exec_list *instructions); -bool brw_fs_precompile(struct gl_context *ctx, struct gl_shader_program *prog); - -struct brw_reg brw_reg_from_fs_reg(fs_reg *reg);