Home | History | Annotate | Download | only in compiler
      1 /*
      2  Copyright (C) Intel Corp.  2006.  All Rights Reserved.
      3  Intel funded Tungsten Graphics to
      4  develop this 3D driver.
      5 
      6  Permission is hereby granted, free of charge, to any person obtaining
      7  a copy of this software and associated documentation files (the
      8  "Software"), to deal in the Software without restriction, including
      9  without limitation the rights to use, copy, modify, merge, publish,
     10  distribute, sublicense, and/or sell copies of the Software, and to
     11  permit persons to whom the Software is furnished to do so, subject to
     12  the following conditions:
     13 
     14  The above copyright notice and this permission notice (including the
     15  next paragraph) shall be included in all copies or substantial
     16  portions of the Software.
     17 
     18  THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
     19  EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
     20  MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
     21  IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE
     22  LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
     23  OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
     24  WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
     25 
     26  **********************************************************************/
     27  /*
     28   * Authors:
     29   *   Keith Whitwell <keithw (at) vmware.com>
     30   */
     31 
     32 
     33 #ifndef BRW_EU_H
     34 #define BRW_EU_H
     35 
     36 #include <stdbool.h>
     37 #include "brw_inst.h"
     38 #include "brw_eu_defines.h"
     39 #include "brw_reg.h"
     40 #include "brw_disasm_info.h"
     41 
     42 #ifdef __cplusplus
     43 extern "C" {
     44 #endif
     45 
     46 #define BRW_EU_MAX_INSN_STACK 5
     47 
     48 /* A helper for accessing the last instruction emitted.  This makes it easy
     49  * to set various bits on an instruction without having to create temporary
     50  * variable and assign the emitted instruction to those.
     51  */
     52 #define brw_last_inst (&p->store[p->nr_insn - 1])
     53 
     54 struct brw_codegen {
     55    brw_inst *store;
     56    int store_size;
     57    unsigned nr_insn;
     58    unsigned int next_insn_offset;
     59 
     60    void *mem_ctx;
     61 
     62    /* Allow clients to push/pop instruction state:
     63     */
     64    brw_inst stack[BRW_EU_MAX_INSN_STACK];
     65    bool compressed_stack[BRW_EU_MAX_INSN_STACK];
     66    brw_inst *current;
     67 
     68    /** Whether or not the user wants automatic exec sizes
     69     *
     70     * If true, codegen will try to automatically infer the exec size of an
     71     * instruction from the width of the destination register.  If false, it
     72     * will take whatever is set by brw_set_default_exec_size verbatim.
     73     *
     74     * This is set to true by default in brw_init_codegen.
     75     */
     76    bool automatic_exec_sizes;
     77 
     78    bool single_program_flow;
     79    const struct gen_device_info *devinfo;
     80 
     81    /* Control flow stacks:
     82     * - if_stack contains IF and ELSE instructions which must be patched
     83     *   (and popped) once the matching ENDIF instruction is encountered.
     84     *
     85     *   Just store the instruction pointer(an index).
     86     */
     87    int *if_stack;
     88    int if_stack_depth;
     89    int if_stack_array_size;
     90 
     91    /**
     92     * loop_stack contains the instruction pointers of the starts of loops which
     93     * must be patched (and popped) once the matching WHILE instruction is
     94     * encountered.
     95     */
     96    int *loop_stack;
     97    /**
     98     * pre-gen6, the BREAK and CONT instructions had to tell how many IF/ENDIF
     99     * blocks they were popping out of, to fix up the mask stack.  This tracks
    100     * the IF/ENDIF nesting in each current nested loop level.
    101     */
    102    int *if_depth_in_loop;
    103    int loop_stack_depth;
    104    int loop_stack_array_size;
    105 };
    106 
    107 void brw_pop_insn_state( struct brw_codegen *p );
    108 void brw_push_insn_state( struct brw_codegen *p );
    109 void brw_set_default_exec_size(struct brw_codegen *p, unsigned value);
    110 void brw_set_default_mask_control( struct brw_codegen *p, unsigned value );
    111 void brw_set_default_saturate( struct brw_codegen *p, bool enable );
    112 void brw_set_default_access_mode( struct brw_codegen *p, unsigned access_mode );
    113 void brw_inst_set_compression(const struct gen_device_info *devinfo,
    114                               brw_inst *inst, bool on);
    115 void brw_set_default_compression(struct brw_codegen *p, bool on);
    116 void brw_inst_set_group(const struct gen_device_info *devinfo,
    117                         brw_inst *inst, unsigned group);
    118 void brw_set_default_group(struct brw_codegen *p, unsigned group);
    119 void brw_set_default_compression_control(struct brw_codegen *p, enum brw_compression c);
    120 void brw_set_default_predicate_control( struct brw_codegen *p, unsigned pc );
    121 void brw_set_default_predicate_inverse(struct brw_codegen *p, bool predicate_inverse);
    122 void brw_set_default_flag_reg(struct brw_codegen *p, int reg, int subreg);
    123 void brw_set_default_acc_write_control(struct brw_codegen *p, unsigned value);
    124 
    125 void brw_init_codegen(const struct gen_device_info *, struct brw_codegen *p,
    126 		      void *mem_ctx);
    127 int brw_disassemble_inst(FILE *file, const struct gen_device_info *devinfo,
    128                          const struct brw_inst *inst, bool is_compacted);
    129 void brw_disassemble(const struct gen_device_info *devinfo,
    130                      const void *assembly, int start, int end, FILE *out);
    131 const unsigned *brw_get_program( struct brw_codegen *p, unsigned *sz );
    132 
    133 brw_inst *brw_next_insn(struct brw_codegen *p, unsigned opcode);
    134 void brw_set_dest(struct brw_codegen *p, brw_inst *insn, struct brw_reg dest);
    135 void brw_set_src0(struct brw_codegen *p, brw_inst *insn, struct brw_reg reg);
    136 
    137 void gen6_resolve_implied_move(struct brw_codegen *p,
    138 			       struct brw_reg *src,
    139 			       unsigned msg_reg_nr);
    140 
    141 /* Helpers for regular instructions:
    142  */
    143 #define ALU1(OP)				\
    144 brw_inst *brw_##OP(struct brw_codegen *p,	\
    145 	      struct brw_reg dest,		\
    146 	      struct brw_reg src0);
    147 
    148 #define ALU2(OP)				\
    149 brw_inst *brw_##OP(struct brw_codegen *p,	\
    150 	      struct brw_reg dest,		\
    151 	      struct brw_reg src0,		\
    152 	      struct brw_reg src1);
    153 
    154 #define ALU3(OP)				\
    155 brw_inst *brw_##OP(struct brw_codegen *p,	\
    156 	      struct brw_reg dest,		\
    157 	      struct brw_reg src0,		\
    158 	      struct brw_reg src1,		\
    159 	      struct brw_reg src2);
    160 
    161 #define ROUND(OP) \
    162 void brw_##OP(struct brw_codegen *p, struct brw_reg dest, struct brw_reg src0);
    163 
    164 ALU1(MOV)
    165 ALU2(SEL)
    166 ALU1(NOT)
    167 ALU2(AND)
    168 ALU2(OR)
    169 ALU2(XOR)
    170 ALU2(SHR)
    171 ALU2(SHL)
    172 ALU1(DIM)
    173 ALU2(ASR)
    174 ALU1(F32TO16)
    175 ALU1(F16TO32)
    176 ALU2(ADD)
    177 ALU2(AVG)
    178 ALU2(MUL)
    179 ALU1(FRC)
    180 ALU1(RNDD)
    181 ALU2(MAC)
    182 ALU2(MACH)
    183 ALU1(LZD)
    184 ALU2(DP4)
    185 ALU2(DPH)
    186 ALU2(DP3)
    187 ALU2(DP2)
    188 ALU2(LINE)
    189 ALU2(PLN)
    190 ALU3(MAD)
    191 ALU3(LRP)
    192 ALU1(BFREV)
    193 ALU3(BFE)
    194 ALU2(BFI1)
    195 ALU3(BFI2)
    196 ALU1(FBH)
    197 ALU1(FBL)
    198 ALU1(CBIT)
    199 ALU2(ADDC)
    200 ALU2(SUBB)
    201 ALU2(MAC)
    202 
    203 ROUND(RNDZ)
    204 ROUND(RNDE)
    205 
    206 #undef ALU1
    207 #undef ALU2
    208 #undef ALU3
    209 #undef ROUND
    210 
    211 
    212 /* Helpers for SEND instruction:
    213  */
    214 void brw_set_sampler_message(struct brw_codegen *p,
    215                              brw_inst *insn,
    216                              unsigned binding_table_index,
    217                              unsigned sampler,
    218                              unsigned msg_type,
    219                              unsigned response_length,
    220                              unsigned msg_length,
    221                              unsigned header_present,
    222                              unsigned simd_mode,
    223                              unsigned return_format);
    224 
    225 void brw_set_message_descriptor(struct brw_codegen *p,
    226                                 brw_inst *inst,
    227                                 enum brw_message_target sfid,
    228                                 unsigned msg_length,
    229                                 unsigned response_length,
    230                                 bool header_present,
    231                                 bool end_of_thread);
    232 
    233 void brw_set_dp_read_message(struct brw_codegen *p,
    234 			     brw_inst *insn,
    235 			     unsigned binding_table_index,
    236 			     unsigned msg_control,
    237 			     unsigned msg_type,
    238 			     unsigned target_cache,
    239 			     unsigned msg_length,
    240                              bool header_present,
    241 			     unsigned response_length);
    242 
    243 void brw_set_dp_write_message(struct brw_codegen *p,
    244 			      brw_inst *insn,
    245 			      unsigned binding_table_index,
    246 			      unsigned msg_control,
    247 			      unsigned msg_type,
    248                               unsigned target_cache,
    249 			      unsigned msg_length,
    250 			      bool header_present,
    251 			      unsigned last_render_target,
    252 			      unsigned response_length,
    253 			      unsigned end_of_thread,
    254 			      unsigned send_commit_msg);
    255 
    256 void brw_urb_WRITE(struct brw_codegen *p,
    257 		   struct brw_reg dest,
    258 		   unsigned msg_reg_nr,
    259 		   struct brw_reg src0,
    260                    enum brw_urb_write_flags flags,
    261 		   unsigned msg_length,
    262 		   unsigned response_length,
    263 		   unsigned offset,
    264 		   unsigned swizzle);
    265 
    266 /**
    267  * Send message to shared unit \p sfid with a possibly indirect descriptor \p
    268  * desc.  If \p desc is not an immediate it will be transparently loaded to an
    269  * address register using an OR instruction.  The returned instruction can be
    270  * passed as argument to the usual brw_set_*_message() functions in order to
    271  * specify any additional descriptor bits -- If \p desc is an immediate this
    272  * will be the SEND instruction itself, otherwise it will be the OR
    273  * instruction.
    274  */
    275 struct brw_inst *
    276 brw_send_indirect_message(struct brw_codegen *p,
    277                           unsigned sfid,
    278                           struct brw_reg dst,
    279                           struct brw_reg payload,
    280                           struct brw_reg desc);
    281 
    282 void brw_ff_sync(struct brw_codegen *p,
    283 		   struct brw_reg dest,
    284 		   unsigned msg_reg_nr,
    285 		   struct brw_reg src0,
    286 		   bool allocate,
    287 		   unsigned response_length,
    288 		   bool eot);
    289 
    290 void brw_svb_write(struct brw_codegen *p,
    291                    struct brw_reg dest,
    292                    unsigned msg_reg_nr,
    293                    struct brw_reg src0,
    294                    unsigned binding_table_index,
    295                    bool   send_commit_msg);
    296 
    297 void brw_fb_WRITE(struct brw_codegen *p,
    298 		   struct brw_reg payload,
    299 		   struct brw_reg implied_header,
    300 		   unsigned msg_control,
    301 		   unsigned binding_table_index,
    302 		   unsigned msg_length,
    303 		   unsigned response_length,
    304 		   bool eot,
    305 		   bool last_render_target,
    306 		   bool header_present);
    307 
    308 brw_inst *gen9_fb_READ(struct brw_codegen *p,
    309                        struct brw_reg dst,
    310                        struct brw_reg payload,
    311                        unsigned binding_table_index,
    312                        unsigned msg_length,
    313                        unsigned response_length,
    314                        bool per_sample);
    315 
    316 void brw_SAMPLE(struct brw_codegen *p,
    317 		struct brw_reg dest,
    318 		unsigned msg_reg_nr,
    319 		struct brw_reg src0,
    320 		unsigned binding_table_index,
    321 		unsigned sampler,
    322 		unsigned msg_type,
    323 		unsigned response_length,
    324 		unsigned msg_length,
    325 		unsigned header_present,
    326 		unsigned simd_mode,
    327 		unsigned return_format);
    328 
    329 void brw_adjust_sampler_state_pointer(struct brw_codegen *p,
    330                                       struct brw_reg header,
    331                                       struct brw_reg sampler_index);
    332 
    333 void gen4_math(struct brw_codegen *p,
    334 	       struct brw_reg dest,
    335 	       unsigned function,
    336 	       unsigned msg_reg_nr,
    337 	       struct brw_reg src,
    338 	       unsigned precision );
    339 
    340 void gen6_math(struct brw_codegen *p,
    341 	       struct brw_reg dest,
    342 	       unsigned function,
    343 	       struct brw_reg src0,
    344 	       struct brw_reg src1);
    345 
    346 void brw_oword_block_read(struct brw_codegen *p,
    347 			  struct brw_reg dest,
    348 			  struct brw_reg mrf,
    349 			  uint32_t offset,
    350 			  uint32_t bind_table_index);
    351 
    352 unsigned brw_scratch_surface_idx(const struct brw_codegen *p);
    353 
    354 void brw_oword_block_read_scratch(struct brw_codegen *p,
    355 				  struct brw_reg dest,
    356 				  struct brw_reg mrf,
    357 				  int num_regs,
    358 				  unsigned offset);
    359 
    360 void brw_oword_block_write_scratch(struct brw_codegen *p,
    361 				   struct brw_reg mrf,
    362 				   int num_regs,
    363 				   unsigned offset);
    364 
    365 void gen7_block_read_scratch(struct brw_codegen *p,
    366                              struct brw_reg dest,
    367                              int num_regs,
    368                              unsigned offset);
    369 
    370 void brw_shader_time_add(struct brw_codegen *p,
    371                          struct brw_reg payload,
    372                          uint32_t surf_index);
    373 
    374 /**
    375  * Return the generation-specific jump distance scaling factor.
    376  *
    377  * Given the number of instructions to jump, we need to scale by
    378  * some number to obtain the actual jump distance to program in an
    379  * instruction.
    380  */
    381 static inline unsigned
    382 brw_jump_scale(const struct gen_device_info *devinfo)
    383 {
    384    /* Broadwell measures jump targets in bytes. */
    385    if (devinfo->gen >= 8)
    386       return 16;
    387 
    388    /* Ironlake and later measure jump targets in 64-bit data chunks (in order
    389     * (to support compaction), so each 128-bit instruction requires 2 chunks.
    390     */
    391    if (devinfo->gen >= 5)
    392       return 2;
    393 
    394    /* Gen4 simply uses the number of 128-bit instructions. */
    395    return 1;
    396 }
    397 
    398 void brw_barrier(struct brw_codegen *p, struct brw_reg src);
    399 
    400 /* If/else/endif.  Works by manipulating the execution flags on each
    401  * channel.
    402  */
    403 brw_inst *brw_IF(struct brw_codegen *p, unsigned execute_size);
    404 brw_inst *gen6_IF(struct brw_codegen *p, enum brw_conditional_mod conditional,
    405                   struct brw_reg src0, struct brw_reg src1);
    406 
    407 void brw_ELSE(struct brw_codegen *p);
    408 void brw_ENDIF(struct brw_codegen *p);
    409 
    410 /* DO/WHILE loops:
    411  */
    412 brw_inst *brw_DO(struct brw_codegen *p, unsigned execute_size);
    413 
    414 brw_inst *brw_WHILE(struct brw_codegen *p);
    415 
    416 brw_inst *brw_BREAK(struct brw_codegen *p);
    417 brw_inst *brw_CONT(struct brw_codegen *p);
    418 brw_inst *gen6_HALT(struct brw_codegen *p);
    419 
    420 /* Forward jumps:
    421  */
    422 void brw_land_fwd_jump(struct brw_codegen *p, int jmp_insn_idx);
    423 
    424 brw_inst *brw_JMPI(struct brw_codegen *p, struct brw_reg index,
    425                    unsigned predicate_control);
    426 
    427 void brw_NOP(struct brw_codegen *p);
    428 
    429 void brw_WAIT(struct brw_codegen *p);
    430 
    431 /* Special case: there is never a destination, execution size will be
    432  * taken from src0:
    433  */
    434 void brw_CMP(struct brw_codegen *p,
    435 	     struct brw_reg dest,
    436 	     unsigned conditional,
    437 	     struct brw_reg src0,
    438 	     struct brw_reg src1);
    439 
    440 void
    441 brw_untyped_atomic(struct brw_codegen *p,
    442                    struct brw_reg dst,
    443                    struct brw_reg payload,
    444                    struct brw_reg surface,
    445                    unsigned atomic_op,
    446                    unsigned msg_length,
    447                    bool response_expected);
    448 
    449 void
    450 brw_untyped_surface_read(struct brw_codegen *p,
    451                          struct brw_reg dst,
    452                          struct brw_reg payload,
    453                          struct brw_reg surface,
    454                          unsigned msg_length,
    455                          unsigned num_channels);
    456 
    457 void
    458 brw_untyped_surface_write(struct brw_codegen *p,
    459                           struct brw_reg payload,
    460                           struct brw_reg surface,
    461                           unsigned msg_length,
    462                           unsigned num_channels);
    463 
    464 void
    465 brw_typed_atomic(struct brw_codegen *p,
    466                  struct brw_reg dst,
    467                  struct brw_reg payload,
    468                  struct brw_reg surface,
    469                  unsigned atomic_op,
    470                  unsigned msg_length,
    471                  bool response_expected);
    472 
    473 void
    474 brw_typed_surface_read(struct brw_codegen *p,
    475                        struct brw_reg dst,
    476                        struct brw_reg payload,
    477                        struct brw_reg surface,
    478                        unsigned msg_length,
    479                        unsigned num_channels);
    480 
    481 void
    482 brw_typed_surface_write(struct brw_codegen *p,
    483                         struct brw_reg payload,
    484                         struct brw_reg surface,
    485                         unsigned msg_length,
    486                         unsigned num_channels);
    487 
    488 void
    489 brw_byte_scattered_read(struct brw_codegen *p,
    490                         struct brw_reg dst,
    491                         struct brw_reg payload,
    492                         struct brw_reg surface,
    493                         unsigned msg_length,
    494                         unsigned bit_size);
    495 
    496 void
    497 brw_byte_scattered_write(struct brw_codegen *p,
    498                          struct brw_reg payload,
    499                          struct brw_reg surface,
    500                          unsigned msg_length,
    501                          unsigned bit_size);
    502 
    503 void
    504 brw_memory_fence(struct brw_codegen *p,
    505                  struct brw_reg dst);
    506 
    507 void
    508 brw_pixel_interpolator_query(struct brw_codegen *p,
    509                              struct brw_reg dest,
    510                              struct brw_reg mrf,
    511                              bool noperspective,
    512                              unsigned mode,
    513                              struct brw_reg data,
    514                              unsigned msg_length,
    515                              unsigned response_length);
    516 
    517 void
    518 brw_find_live_channel(struct brw_codegen *p,
    519                       struct brw_reg dst,
    520                       struct brw_reg mask);
    521 
    522 void
    523 brw_broadcast(struct brw_codegen *p,
    524               struct brw_reg dst,
    525               struct brw_reg src,
    526               struct brw_reg idx);
    527 
    528 void
    529 brw_rounding_mode(struct brw_codegen *p,
    530                   enum brw_rnd_mode mode);
    531 
    532 /***********************************************************************
    533  * brw_eu_util.c:
    534  */
    535 
    536 void brw_copy_indirect_to_indirect(struct brw_codegen *p,
    537 				   struct brw_indirect dst_ptr,
    538 				   struct brw_indirect src_ptr,
    539 				   unsigned count);
    540 
    541 void brw_copy_from_indirect(struct brw_codegen *p,
    542 			    struct brw_reg dst,
    543 			    struct brw_indirect ptr,
    544 			    unsigned count);
    545 
    546 void brw_copy4(struct brw_codegen *p,
    547 	       struct brw_reg dst,
    548 	       struct brw_reg src,
    549 	       unsigned count);
    550 
    551 void brw_copy8(struct brw_codegen *p,
    552 	       struct brw_reg dst,
    553 	       struct brw_reg src,
    554 	       unsigned count);
    555 
    556 void brw_math_invert( struct brw_codegen *p,
    557 		      struct brw_reg dst,
    558 		      struct brw_reg src);
    559 
    560 void brw_set_src1(struct brw_codegen *p, brw_inst *insn, struct brw_reg reg);
    561 
    562 void brw_set_uip_jip(struct brw_codegen *p, int start_offset);
    563 
    564 enum brw_conditional_mod brw_negate_cmod(uint32_t cmod);
    565 enum brw_conditional_mod brw_swap_cmod(uint32_t cmod);
    566 
    567 /* brw_eu_compact.c */
    568 void brw_init_compaction_tables(const struct gen_device_info *devinfo);
    569 void brw_compact_instructions(struct brw_codegen *p, int start_offset,
    570                               struct disasm_info *disasm);
    571 void brw_uncompact_instruction(const struct gen_device_info *devinfo,
    572                                brw_inst *dst, brw_compact_inst *src);
    573 bool brw_try_compact_instruction(const struct gen_device_info *devinfo,
    574                                  brw_compact_inst *dst, const brw_inst *src);
    575 
    576 void brw_debug_compact_uncompact(const struct gen_device_info *devinfo,
    577                                  brw_inst *orig, brw_inst *uncompacted);
    578 
    579 /* brw_eu_validate.c */
    580 bool brw_validate_instructions(const struct gen_device_info *devinfo,
    581                                const void *assembly, int start_offset, int end_offset,
    582                                struct disasm_info *disasm);
    583 
    584 static inline int
    585 next_offset(const struct gen_device_info *devinfo, void *store, int offset)
    586 {
    587    brw_inst *insn = (brw_inst *)((char *)store + offset);
    588 
    589    if (brw_inst_cmpt_control(devinfo, insn))
    590       return offset + 8;
    591    else
    592       return offset + 16;
    593 }
    594 
    595 struct opcode_desc {
    596    /* The union is an implementation detail used by brw_opcode_desc() to handle
    597     * opcodes that have been reused for different instructions across hardware
    598     * generations.
    599     *
    600     * The gens field acts as a tag. If it is non-zero, name points to a string
    601     * containing the instruction mnemonic. If it is zero, the table field is
    602     * valid and either points to a secondary opcode_desc table with 'size'
    603     * elements or is NULL and no such instruction exists for the opcode.
    604     */
    605    union {
    606       struct {
    607          char    *name;
    608          int      nsrc;
    609       };
    610       struct {
    611          const struct opcode_desc *table;
    612          unsigned size;
    613       };
    614    };
    615    int      ndst;
    616    int      gens;
    617 };
    618 
    619 const struct opcode_desc *
    620 brw_opcode_desc(const struct gen_device_info *devinfo, enum opcode opcode);
    621 
    622 static inline bool
    623 is_3src(const struct gen_device_info *devinfo, enum opcode opcode)
    624 {
    625    const struct opcode_desc *desc = brw_opcode_desc(devinfo, opcode);
    626    return desc && desc->nsrc == 3;
    627 }
    628 
    629 /** Maximum SEND message length */
    630 #define BRW_MAX_MSG_LENGTH 15
    631 
    632 /** First MRF register used by pull loads */
    633 #define FIRST_SPILL_MRF(gen) ((gen) == 6 ? 21 : 13)
    634 
    635 /** First MRF register used by spills */
    636 #define FIRST_PULL_LOAD_MRF(gen) ((gen) == 6 ? 16 : 13)
    637 
    638 #ifdef __cplusplus
    639 }
    640 #endif
    641 
    642 #endif
    643