lp_bld_tgsi.h revision 5d10d757276a599a60a68b88b21087b5824a8df7
1/************************************************************************** 2 * 3 * Copyright 2011-2012 Advanced Micro Devices, Inc. 4 * Copyright 2009 VMware, Inc. 5 * All Rights Reserved. 6 * 7 * Permission is hereby granted, free of charge, to any person obtaining a 8 * copy of this software and associated documentation files (the 9 * "Software"), to deal in the Software without restriction, including 10 * without limitation the rights to use, copy, modify, merge, publish, 11 * distribute, sub license, and/or sell copies of the Software, and to 12 * permit persons to whom the Software is furnished to do so, subject to 13 * the following conditions: 14 * 15 * The above copyright notice and this permission notice (including the 16 * next paragraph) shall be included in all copies or substantial portions 17 * of the Software. 18 * 19 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS 20 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 21 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. 22 * IN NO EVENT SHALL VMWARE AND/OR ITS SUPPLIERS BE LIABLE FOR 23 * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, 24 * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE 25 * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 26 * 27 **************************************************************************/ 28 29/** 30 * @file 31 * TGSI to LLVM IR translation. 32 * 33 * @author Jose Fonseca <jfonseca@vmware.com> 34 * @author Tom Stellard <thomas.stellard@amd.com> 35 */ 36 37#ifndef LP_BLD_TGSI_H 38#define LP_BLD_TGSI_H 39 40#include "gallivm/lp_bld.h" 41#include "gallivm/lp_bld_tgsi_action.h" 42#include "gallivm/lp_bld_limits.h" 43#include "lp_bld_type.h" 44#include "pipe/p_compiler.h" 45#include "pipe/p_state.h" 46#include "tgsi/tgsi_exec.h" 47#include "tgsi/tgsi_scan.h" 48#include "tgsi/tgsi_info.h" 49 50#define LP_CHAN_ALL ~0 51 52#define LP_MAX_INSTRUCTIONS 256 53 54struct tgsi_full_declaration; 55struct tgsi_full_immediate; 56struct tgsi_full_instruction; 57struct tgsi_full_src_register; 58struct tgsi_opcode_info; 59struct tgsi_token; 60struct tgsi_shader_info; 61struct lp_build_mask_context; 62struct gallivm_state; 63 64 65enum lp_build_tex_modifier { 66 LP_BLD_TEX_MODIFIER_NONE = 0, 67 LP_BLD_TEX_MODIFIER_PROJECTED, 68 LP_BLD_TEX_MODIFIER_LOD_BIAS, 69 LP_BLD_TEX_MODIFIER_EXPLICIT_LOD, 70 LP_BLD_TEX_MODIFIER_EXPLICIT_DERIV 71}; 72 73 74/** 75 * Describe a channel of a register. 76 * 77 * The value can be a: 78 * - immediate value (i.e. derived from a IMM register) 79 * - CONST[n].x/y/z/w 80 * - IN[n].x/y/z/w 81 * - undetermined (when .file == TGSI_FILE_NULL) 82 * 83 * This is one of the analysis results, and is used to described 84 * the output color in terms of inputs. 85 */ 86struct lp_tgsi_channel_info 87{ 88 unsigned file:4; /* TGSI_FILE_* */ 89 unsigned swizzle:3; /* PIPE_SWIZZLE_x */ 90 union { 91 uint32_t index; 92 float value; /* for TGSI_FILE_IMMEDIATE */ 93 } u; 94}; 95 96 97/** 98 * Describe a texture sampler interpolator. 99 * 100 * The interpolation is described in terms of regular inputs. 101 */ 102struct lp_tgsi_texture_info 103{ 104 struct lp_tgsi_channel_info coord[4]; 105 unsigned target:8; /* TGSI_TEXTURE_* */ 106 unsigned unit:8; /* Sampler unit */ 107 unsigned modifier:8; /* LP_BLD_TEX_MODIFIER_* */ 108}; 109 110 111struct lp_tgsi_info 112{ 113 struct tgsi_shader_info base; 114 115 /* 116 * Whether any of the texture opcodes access a register file other than 117 * TGSI_FILE_INPUT. 118 * 119 * We could also handle TGSI_FILE_CONST/IMMEDIATE here, but there is little 120 * benefit. 121 */ 122 unsigned indirect_textures:1; 123 124 /* 125 * Whether any immediate values are outside the range of 0 and 1 126 */ 127 unsigned unclamped_immediates:1; 128 129 /* 130 * Texture opcode description. Aimed at detecting and described direct 131 * texture opcodes. 132 */ 133 unsigned num_texs; 134 struct lp_tgsi_texture_info tex[PIPE_MAX_SAMPLERS]; 135 136 /* 137 * Output description. Aimed at detecting and describing simple blit 138 * shaders. 139 */ 140 struct lp_tgsi_channel_info output[PIPE_MAX_SHADER_OUTPUTS][4]; 141 142 /* 143 * Shortcut pointers into the above (for fragment shaders). 144 */ 145 const struct lp_tgsi_channel_info *cbuf[PIPE_MAX_COLOR_BUFS]; 146}; 147 148/** 149 * Sampler code generation interface. 150 * 151 * Although texture sampling is a requirement for TGSI translation, it is 152 * a very different problem with several different approaches to it. This 153 * structure establishes an interface for texture sampling code generation, so 154 * that we can easily use different texture sampling strategies. 155 */ 156struct lp_build_sampler_soa 157{ 158 void 159 (*destroy)( struct lp_build_sampler_soa *sampler ); 160 161 void 162 (*emit_fetch_texel)( const struct lp_build_sampler_soa *sampler, 163 struct gallivm_state *gallivm, 164 struct lp_type type, 165 unsigned unit, 166 unsigned num_coords, 167 const LLVMValueRef *coords, 168 const LLVMValueRef *ddx, 169 const LLVMValueRef *ddy, 170 LLVMValueRef lod_bias, /* optional */ 171 LLVMValueRef explicit_lod, /* optional */ 172 LLVMValueRef *texel); 173 174 void 175 (*emit_size_query)( const struct lp_build_sampler_soa *sampler, 176 struct gallivm_state *gallivm, 177 unsigned unit, 178 LLVMValueRef explicit_lod, /* optional */ 179 LLVMValueRef *sizes_out); 180}; 181 182 183struct lp_build_sampler_aos 184{ 185 LLVMValueRef 186 (*emit_fetch_texel)( struct lp_build_sampler_aos *sampler, 187 struct lp_build_context *bld, 188 unsigned target, /* TGSI_TEXTURE_* */ 189 unsigned unit, 190 LLVMValueRef coords, 191 LLVMValueRef ddx, 192 LLVMValueRef ddy, 193 enum lp_build_tex_modifier modifier); 194}; 195 196 197void 198lp_build_tgsi_info(const struct tgsi_token *tokens, 199 struct lp_tgsi_info *info); 200 201 202void 203lp_build_tgsi_soa(struct gallivm_state *gallivm, 204 const struct tgsi_token *tokens, 205 struct lp_type type, 206 struct lp_build_mask_context *mask, 207 LLVMValueRef consts_ptr, 208 LLVMValueRef system_values_array, 209 const LLVMValueRef *pos, 210 const LLVMValueRef (*inputs)[4], 211 LLVMValueRef (*outputs)[4], 212 struct lp_build_sampler_soa *sampler, 213 const struct tgsi_shader_info *info); 214 215 216void 217lp_build_tgsi_aos(struct gallivm_state *gallivm, 218 const struct tgsi_token *tokens, 219 struct lp_type type, 220 const unsigned char swizzles[4], 221 LLVMValueRef consts_ptr, 222 const LLVMValueRef *inputs, 223 LLVMValueRef *outputs, 224 struct lp_build_sampler_aos *sampler, 225 const struct tgsi_shader_info *info); 226 227 228LLVMValueRef 229lp_build_system_values_array(struct gallivm_state *gallivm, 230 const struct tgsi_shader_info *info, 231 LLVMValueRef instance_id, 232 LLVMValueRef facing); 233 234 235struct lp_exec_mask { 236 struct lp_build_context *bld; 237 238 boolean has_mask; 239 240 LLVMTypeRef int_vec_type; 241 242 LLVMValueRef cond_stack[LP_MAX_TGSI_NESTING]; 243 int cond_stack_size; 244 LLVMValueRef cond_mask; 245 246 LLVMBasicBlockRef loop_block; 247 LLVMValueRef cont_mask; 248 LLVMValueRef break_mask; 249 LLVMValueRef break_var; 250 struct { 251 LLVMBasicBlockRef loop_block; 252 LLVMValueRef cont_mask; 253 LLVMValueRef break_mask; 254 LLVMValueRef break_var; 255 } loop_stack[LP_MAX_TGSI_NESTING]; 256 int loop_stack_size; 257 258 LLVMValueRef ret_mask; 259 struct { 260 int pc; 261 LLVMValueRef ret_mask; 262 } call_stack[LP_MAX_TGSI_NESTING]; 263 int call_stack_size; 264 265 LLVMValueRef exec_mask; 266 LLVMValueRef loop_limiter; 267}; 268 269struct lp_build_tgsi_inst_list 270{ 271 struct tgsi_full_instruction *instructions; 272 uint max_instructions; 273 uint num_instructions; 274}; 275 276unsigned lp_bld_tgsi_list_init(struct lp_build_tgsi_context * bld_base); 277 278 279unsigned lp_bld_tgsi_add_instruction( 280 struct lp_build_tgsi_context * bld_base, 281 struct tgsi_full_instruction *inst_to_add); 282 283 284struct lp_build_tgsi_context; 285 286 287typedef LLVMValueRef (*lp_build_emit_fetch_fn)(struct lp_build_tgsi_context *, 288 const struct tgsi_full_src_register *, 289 enum tgsi_opcode_type, 290 unsigned); 291 292struct lp_build_tgsi_context 293{ 294 struct lp_build_context base; 295 296 struct lp_build_context uint_bld; 297 struct lp_build_context int_bld; 298 299 /** This array stores functions that are used to transform TGSI opcodes to 300 * LLVM instructions. 301 */ 302 struct lp_build_tgsi_action op_actions[TGSI_OPCODE_LAST]; 303 304 /* TGSI_OPCODE_RSQ is defined as 1 / sqrt( abs(src0.x) ), rsq_action 305 * should compute 1 / sqrt (src0.x) */ 306 struct lp_build_tgsi_action rsq_action; 307 308 const struct tgsi_shader_info *info; 309 310 lp_build_emit_fetch_fn emit_fetch_funcs[TGSI_FILE_COUNT]; 311 312 LLVMValueRef (*emit_swizzle)(struct lp_build_tgsi_context *, 313 LLVMValueRef, unsigned, unsigned, unsigned, unsigned); 314 315 void (*emit_store)(struct lp_build_tgsi_context *, 316 const struct tgsi_full_instruction *, 317 const struct tgsi_opcode_info *, 318 LLVMValueRef dst[4]); 319 320 void (*emit_declaration)(struct lp_build_tgsi_context *, 321 const struct tgsi_full_declaration *decl); 322 323 void (*emit_immediate)(struct lp_build_tgsi_context *, 324 const struct tgsi_full_immediate *imm); 325 326 327 /* Allow the user to store data in this structure rather than passing it 328 * to every function. */ 329 void * userdata; 330 331 boolean soa; 332 333 int pc; 334 335 struct tgsi_full_instruction *instructions; 336 uint max_instructions; 337 uint num_instructions; 338 339 /** This function allows the user to insert some instructions at the 340 * beginning of the program. It is optional and does not need to be 341 * implemented. 342 */ 343 void (*emit_prologue)(struct lp_build_tgsi_context*); 344 345 /** This function allows the user to insert some instructions at the end of 346 * the program. This callback is intended to be used for emitting 347 * instructions to handle the export for the output registers, but it can 348 * be used for any purpose. Implementing this function is optiona, but 349 * recommended. 350 */ 351 void (*emit_epilogue)(struct lp_build_tgsi_context*); 352}; 353 354struct lp_build_tgsi_soa_context 355{ 356 struct lp_build_tgsi_context bld_base; 357 358 /* Builder for scalar elements of shader's data type (float) */ 359 struct lp_build_context elem_bld; 360 361 LLVMValueRef consts_ptr; 362 const LLVMValueRef *pos; 363 const LLVMValueRef (*inputs)[TGSI_NUM_CHANNELS]; 364 LLVMValueRef (*outputs)[TGSI_NUM_CHANNELS]; 365 366 const struct lp_build_sampler_soa *sampler; 367 368 LLVMValueRef immediates[LP_MAX_TGSI_IMMEDIATES][TGSI_NUM_CHANNELS]; 369 LLVMValueRef temps[LP_MAX_TGSI_TEMPS][TGSI_NUM_CHANNELS]; 370 LLVMValueRef addr[LP_MAX_TGSI_ADDRS][TGSI_NUM_CHANNELS]; 371 LLVMValueRef preds[LP_MAX_TGSI_PREDS][TGSI_NUM_CHANNELS]; 372 373 /* We allocate/use this array of temps if (1 << TGSI_FILE_TEMPORARY) is 374 * set in the indirect_files field. 375 * The temps[] array above is unused then. 376 */ 377 LLVMValueRef temps_array; 378 379 /* We allocate/use this array of output if (1 << TGSI_FILE_OUTPUT) is 380 * set in the indirect_files field. 381 * The outputs[] array above is unused then. 382 */ 383 LLVMValueRef outputs_array; 384 385 /* We allocate/use this array of inputs if (1 << TGSI_FILE_INPUT) is 386 * set in the indirect_files field. 387 * The inputs[] array above is unused then. 388 */ 389 LLVMValueRef inputs_array; 390 391 LLVMValueRef system_values_array; 392 393 /** bitmask indicating which register files are accessed indirectly */ 394 unsigned indirect_files; 395 396 struct lp_build_mask_context *mask; 397 struct lp_exec_mask exec_mask; 398 399 uint num_immediates; 400 401}; 402 403void 404lp_emit_declaration_soa( 405 struct lp_build_tgsi_context *bld, 406 const struct tgsi_full_declaration *decl); 407 408void lp_emit_immediate_soa( 409 struct lp_build_tgsi_context *bld_base, 410 const struct tgsi_full_immediate *imm); 411 412boolean 413lp_emit_instruction_soa( 414 struct lp_build_tgsi_soa_context *bld, 415 const struct tgsi_full_instruction *inst, 416 const struct tgsi_opcode_info *info); 417 418 419LLVMValueRef 420lp_get_temp_ptr_soa( 421 struct lp_build_tgsi_soa_context *bld, 422 unsigned index, 423 unsigned chan); 424 425LLVMValueRef 426lp_get_output_ptr( 427 struct lp_build_tgsi_soa_context *bld, 428 unsigned index, 429 unsigned chan); 430 431struct lp_build_tgsi_aos_context 432{ 433 struct lp_build_tgsi_context bld_base; 434 435 /* Builder for integer masks and indices */ 436 struct lp_build_context int_bld; 437 438 /* 439 * AoS swizzle used: 440 * - swizzles[0] = red index 441 * - swizzles[1] = green index 442 * - swizzles[2] = blue index 443 * - swizzles[3] = alpha index 444 */ 445 unsigned char swizzles[4]; 446 unsigned char inv_swizzles[4]; 447 448 LLVMValueRef consts_ptr; 449 const LLVMValueRef *inputs; 450 LLVMValueRef *outputs; 451 452 struct lp_build_sampler_aos *sampler; 453 454 LLVMValueRef immediates[LP_MAX_TGSI_IMMEDIATES]; 455 LLVMValueRef temps[LP_MAX_TGSI_TEMPS]; 456 LLVMValueRef addr[LP_MAX_TGSI_ADDRS]; 457 LLVMValueRef preds[LP_MAX_TGSI_PREDS]; 458 459 /* We allocate/use this array of temps if (1 << TGSI_FILE_TEMPORARY) is 460 * set in the indirect_files field. 461 * The temps[] array above is unused then. 462 */ 463 LLVMValueRef temps_array; 464 465 /** bitmask indicating which register files are accessed indirectly */ 466 unsigned indirect_files; 467 468}; 469 470static INLINE struct lp_build_tgsi_soa_context * 471lp_soa_context(struct lp_build_tgsi_context *bld_base) 472{ 473 return (struct lp_build_tgsi_soa_context *)bld_base; 474} 475 476static INLINE struct lp_build_tgsi_aos_context * 477lp_aos_context(struct lp_build_tgsi_context *bld_base) 478{ 479 return (struct lp_build_tgsi_aos_context *)bld_base; 480} 481 482void 483lp_emit_declaration_aos( 484 struct lp_build_tgsi_aos_context *bld, 485 const struct tgsi_full_declaration *decl); 486 487 488boolean 489lp_emit_instruction_aos( 490 struct lp_build_tgsi_aos_context *bld, 491 const struct tgsi_full_instruction *inst, 492 const struct tgsi_opcode_info *info, 493 int *pc); 494 495void 496lp_emit_store_aos( 497 struct lp_build_tgsi_aos_context *bld, 498 const struct tgsi_full_instruction *inst, 499 unsigned index, 500 LLVMValueRef value); 501 502void lp_build_fetch_args( 503 struct lp_build_tgsi_context * bld_base, 504 struct lp_build_emit_data * emit_data); 505 506LLVMValueRef 507lp_build_tgsi_inst_llvm_aos( 508 struct lp_build_tgsi_context * bld_base, 509 const struct tgsi_full_instruction *inst); 510 511void 512lp_build_tgsi_intrinsic( 513 const struct lp_build_tgsi_action * action, 514 struct lp_build_tgsi_context * bld_base, 515 struct lp_build_emit_data * emit_data); 516 517LLVMValueRef 518lp_build_emit_llvm( 519 struct lp_build_tgsi_context *bld_base, 520 unsigned tgsi_opcode, 521 struct lp_build_emit_data * emit_data); 522 523LLVMValueRef 524lp_build_emit_llvm_unary( 525 struct lp_build_tgsi_context *bld_base, 526 unsigned tgsi_opcode, 527 LLVMValueRef arg0); 528 529LLVMValueRef 530lp_build_emit_llvm_binary( 531 struct lp_build_tgsi_context *bld_base, 532 unsigned tgsi_opcode, 533 LLVMValueRef arg0, 534 LLVMValueRef arg1); 535 536LLVMValueRef 537lp_build_emit_llvm_ternary( 538 struct lp_build_tgsi_context *bld_base, 539 unsigned tgsi_opcode, 540 LLVMValueRef arg0, 541 LLVMValueRef arg1, 542 LLVMValueRef arg2); 543 544boolean 545lp_build_tgsi_inst_llvm( 546 struct lp_build_tgsi_context * bld_base, 547 const struct tgsi_full_instruction *inst); 548 549LLVMValueRef 550lp_build_emit_fetch( 551 struct lp_build_tgsi_context *bld_base, 552 const struct tgsi_full_instruction *inst, 553 unsigned src_op, 554 const unsigned chan_index); 555 556boolean 557lp_build_tgsi_llvm( 558 struct lp_build_tgsi_context * bld_base, 559 const struct tgsi_token *tokens); 560 561#endif /* LP_BLD_TGSI_H */ 562