10e24387849b090cafc3b610f602223f8baa64f6
[mesa.git] / src / gallium / auxiliary / nir / tgsi_to_nir.c
1 /*
2 * Copyright © 2014-2015 Broadcom
3 * Copyright (C) 2014 Rob Clark <robclark@freedesktop.org>
4 *
5 * Permission is hereby granted, free of charge, to any person obtaining a
6 * copy of this software and associated documentation files (the "Software"),
7 * to deal in the Software without restriction, including without limitation
8 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
9 * and/or sell copies of the Software, and to permit persons to whom the
10 * Software is furnished to do so, subject to the following conditions:
11 *
12 * The above copyright notice and this permission notice (including the next
13 * paragraph) shall be included in all copies or substantial portions of the
14 * Software.
15 *
16 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
19 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
21 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
22 * IN THE SOFTWARE.
23 */
24
25 #include "util/ralloc.h"
26 #include "compiler/nir/nir.h"
27 #include "compiler/nir/nir_control_flow.h"
28 #include "compiler/nir/nir_builder.h"
29 #include "compiler/glsl/list.h"
30 #include "compiler/shader_enums.h"
31
32 #include "tgsi_to_nir.h"
33 #include "tgsi/tgsi_parse.h"
34 #include "tgsi/tgsi_dump.h"
35 #include "tgsi/tgsi_info.h"
36 #include "tgsi/tgsi_scan.h"
37 #include "tgsi/tgsi_from_mesa.h"
38
39 #define SWIZ(X, Y, Z, W) (unsigned[4]){ \
40 TGSI_SWIZZLE_##X, \
41 TGSI_SWIZZLE_##Y, \
42 TGSI_SWIZZLE_##Z, \
43 TGSI_SWIZZLE_##W, \
44 }
45
46 struct ttn_reg_info {
47 /** nir register containing this TGSI index. */
48 nir_register *reg;
49 nir_variable *var;
50 /** Offset (in vec4s) from the start of var for this TGSI index. */
51 int offset;
52 };
53
54 struct ttn_compile {
55 union tgsi_full_token *token;
56 nir_builder build;
57 struct tgsi_shader_info *scan;
58
59 struct ttn_reg_info *output_regs;
60 struct ttn_reg_info *temp_regs;
61 nir_ssa_def **imm_defs;
62
63 unsigned num_samp_types;
64 nir_alu_type *samp_types;
65
66 nir_register *addr_reg;
67
68 nir_variable **inputs;
69 nir_variable **outputs;
70
71 /**
72 * Stack of nir_cursors where instructions should be pushed as we pop
73 * back out of the control flow stack.
74 *
75 * For each IF/ELSE/ENDIF block, if_stack[if_stack_pos] has where the else
76 * instructions should be placed, and if_stack[if_stack_pos - 1] has where
77 * the next instructions outside of the if/then/else block go.
78 */
79 nir_cursor *if_stack;
80 unsigned if_stack_pos;
81
82 /**
83 * Stack of nir_cursors where instructions should be pushed as we pop
84 * back out of the control flow stack.
85 *
86 * loop_stack[loop_stack_pos - 1] contains the cf_node_list for the outside
87 * of the loop.
88 */
89 nir_cursor *loop_stack;
90 unsigned loop_stack_pos;
91
92 /* How many TGSI_FILE_IMMEDIATE vec4s have been parsed so far. */
93 unsigned next_imm;
94 };
95
96 #define ttn_swizzle(b, src, x, y, z, w) \
97 nir_swizzle(b, src, SWIZ(x, y, z, w), 4, false)
98 #define ttn_channel(b, src, swiz) \
99 nir_swizzle(b, src, SWIZ(swiz, swiz, swiz, swiz), 1, false)
100
101 static gl_varying_slot
102 tgsi_varying_semantic_to_slot(unsigned semantic, unsigned index)
103 {
104 switch (semantic) {
105 case TGSI_SEMANTIC_POSITION:
106 return VARYING_SLOT_POS;
107 case TGSI_SEMANTIC_COLOR:
108 if (index == 0)
109 return VARYING_SLOT_COL0;
110 else
111 return VARYING_SLOT_COL1;
112 case TGSI_SEMANTIC_BCOLOR:
113 if (index == 0)
114 return VARYING_SLOT_BFC0;
115 else
116 return VARYING_SLOT_BFC1;
117 case TGSI_SEMANTIC_FOG:
118 return VARYING_SLOT_FOGC;
119 case TGSI_SEMANTIC_PSIZE:
120 return VARYING_SLOT_PSIZ;
121 case TGSI_SEMANTIC_GENERIC:
122 return VARYING_SLOT_VAR0 + index;
123 case TGSI_SEMANTIC_FACE:
124 return VARYING_SLOT_FACE;
125 case TGSI_SEMANTIC_EDGEFLAG:
126 return VARYING_SLOT_EDGE;
127 case TGSI_SEMANTIC_PRIMID:
128 return VARYING_SLOT_PRIMITIVE_ID;
129 case TGSI_SEMANTIC_CLIPDIST:
130 if (index == 0)
131 return VARYING_SLOT_CLIP_DIST0;
132 else
133 return VARYING_SLOT_CLIP_DIST1;
134 case TGSI_SEMANTIC_CLIPVERTEX:
135 return VARYING_SLOT_CLIP_VERTEX;
136 case TGSI_SEMANTIC_TEXCOORD:
137 return VARYING_SLOT_TEX0 + index;
138 case TGSI_SEMANTIC_PCOORD:
139 return VARYING_SLOT_PNTC;
140 case TGSI_SEMANTIC_VIEWPORT_INDEX:
141 return VARYING_SLOT_VIEWPORT;
142 case TGSI_SEMANTIC_LAYER:
143 return VARYING_SLOT_LAYER;
144 default:
145 fprintf(stderr, "Bad TGSI semantic: %d/%d\n", semantic, index);
146 abort();
147 }
148 }
149
150 static nir_ssa_def *
151 ttn_src_for_dest(nir_builder *b, nir_alu_dest *dest)
152 {
153 nir_alu_src src;
154 memset(&src, 0, sizeof(src));
155
156 if (dest->dest.is_ssa)
157 src.src = nir_src_for_ssa(&dest->dest.ssa);
158 else {
159 assert(!dest->dest.reg.indirect);
160 src.src = nir_src_for_reg(dest->dest.reg.reg);
161 src.src.reg.base_offset = dest->dest.reg.base_offset;
162 }
163
164 for (int i = 0; i < 4; i++)
165 src.swizzle[i] = i;
166
167 return nir_fmov_alu(b, src, 4);
168 }
169
170 static void
171 ttn_emit_declaration(struct ttn_compile *c)
172 {
173 nir_builder *b = &c->build;
174 struct tgsi_full_declaration *decl = &c->token->FullDeclaration;
175 unsigned array_size = decl->Range.Last - decl->Range.First + 1;
176 unsigned file = decl->Declaration.File;
177 unsigned i;
178
179 if (file == TGSI_FILE_TEMPORARY) {
180 if (decl->Declaration.Array) {
181 /* for arrays, we create variables instead of registers: */
182 nir_variable *var = rzalloc(b->shader, nir_variable);
183
184 var->type = glsl_array_type(glsl_vec4_type(), array_size, 0);
185 var->data.mode = nir_var_shader_temp;
186 var->name = ralloc_asprintf(var, "arr_%d", decl->Array.ArrayID);
187
188 exec_list_push_tail(&b->shader->globals, &var->node);
189
190 for (i = 0; i < array_size; i++) {
191 /* point all the matching slots to the same var,
192 * with appropriate offset set, mostly just so
193 * we know what to do when tgsi does a non-indirect
194 * access
195 */
196 c->temp_regs[decl->Range.First + i].reg = NULL;
197 c->temp_regs[decl->Range.First + i].var = var;
198 c->temp_regs[decl->Range.First + i].offset = i;
199 }
200 } else {
201 for (i = 0; i < array_size; i++) {
202 nir_register *reg = nir_local_reg_create(b->impl);
203 reg->num_components = 4;
204 c->temp_regs[decl->Range.First + i].reg = reg;
205 c->temp_regs[decl->Range.First + i].var = NULL;
206 c->temp_regs[decl->Range.First + i].offset = 0;
207 }
208 }
209 } else if (file == TGSI_FILE_ADDRESS) {
210 c->addr_reg = nir_local_reg_create(b->impl);
211 c->addr_reg->num_components = 4;
212 } else if (file == TGSI_FILE_SYSTEM_VALUE) {
213 /* Nothing to record for system values. */
214 } else if (file == TGSI_FILE_SAMPLER) {
215 /* Nothing to record for samplers. */
216 } else if (file == TGSI_FILE_SAMPLER_VIEW) {
217 struct tgsi_declaration_sampler_view *sview = &decl->SamplerView;
218 nir_alu_type type;
219
220 assert((sview->ReturnTypeX == sview->ReturnTypeY) &&
221 (sview->ReturnTypeX == sview->ReturnTypeZ) &&
222 (sview->ReturnTypeX == sview->ReturnTypeW));
223
224 switch (sview->ReturnTypeX) {
225 case TGSI_RETURN_TYPE_SINT:
226 type = nir_type_int;
227 break;
228 case TGSI_RETURN_TYPE_UINT:
229 type = nir_type_uint;
230 break;
231 case TGSI_RETURN_TYPE_FLOAT:
232 default:
233 type = nir_type_float;
234 break;
235 }
236
237 for (i = 0; i < array_size; i++) {
238 c->samp_types[decl->Range.First + i] = type;
239 }
240 } else {
241 bool is_array = (array_size > 1);
242
243 assert(file == TGSI_FILE_INPUT ||
244 file == TGSI_FILE_OUTPUT ||
245 file == TGSI_FILE_CONSTANT);
246
247 /* nothing to do for UBOs: */
248 if ((file == TGSI_FILE_CONSTANT) && decl->Declaration.Dimension &&
249 decl->Dim.Index2D != 0) {
250 b->shader->info.num_ubos =
251 MAX2(b->shader->info.num_ubos, decl->Dim.Index2D);
252 return;
253 }
254
255 if ((file == TGSI_FILE_INPUT) || (file == TGSI_FILE_OUTPUT)) {
256 is_array = (is_array && decl->Declaration.Array &&
257 (decl->Array.ArrayID != 0));
258 }
259
260 for (i = 0; i < array_size; i++) {
261 unsigned idx = decl->Range.First + i;
262 nir_variable *var = rzalloc(b->shader, nir_variable);
263
264 var->data.driver_location = idx;
265
266 var->type = glsl_vec4_type();
267 if (is_array)
268 var->type = glsl_array_type(var->type, array_size, 0);
269
270 switch (file) {
271 case TGSI_FILE_INPUT:
272 var->data.read_only = true;
273 var->data.mode = nir_var_shader_in;
274 var->name = ralloc_asprintf(var, "in_%d", idx);
275
276 if (c->scan->processor == PIPE_SHADER_FRAGMENT) {
277 if (decl->Semantic.Name == TGSI_SEMANTIC_FACE) {
278 var->data.location = SYSTEM_VALUE_FRONT_FACE;
279 var->data.mode = nir_var_system_value;
280 } else {
281 var->data.location =
282 tgsi_varying_semantic_to_slot(decl->Semantic.Name,
283 decl->Semantic.Index);
284 }
285 } else {
286 assert(!decl->Declaration.Semantic);
287 var->data.location = VERT_ATTRIB_GENERIC0 + idx;
288 }
289 var->data.index = 0;
290
291 /* We definitely need to translate the interpolation field, because
292 * nir_print will decode it.
293 */
294 switch (decl->Interp.Interpolate) {
295 case TGSI_INTERPOLATE_CONSTANT:
296 var->data.interpolation = INTERP_MODE_FLAT;
297 break;
298 case TGSI_INTERPOLATE_LINEAR:
299 var->data.interpolation = INTERP_MODE_NOPERSPECTIVE;
300 break;
301 case TGSI_INTERPOLATE_PERSPECTIVE:
302 var->data.interpolation = INTERP_MODE_SMOOTH;
303 break;
304 }
305
306 exec_list_push_tail(&b->shader->inputs, &var->node);
307 c->inputs[idx] = var;
308
309 for (int i = 0; i < array_size; i++)
310 b->shader->info.inputs_read |= 1 << (var->data.location + i);
311
312 break;
313 case TGSI_FILE_OUTPUT: {
314 int semantic_name = decl->Semantic.Name;
315 int semantic_index = decl->Semantic.Index;
316 /* Since we can't load from outputs in the IR, we make temporaries
317 * for the outputs and emit stores to the real outputs at the end of
318 * the shader.
319 */
320 nir_register *reg = nir_local_reg_create(b->impl);
321 reg->num_components = 4;
322 if (is_array)
323 reg->num_array_elems = array_size;
324
325 var->data.mode = nir_var_shader_out;
326 var->name = ralloc_asprintf(var, "out_%d", idx);
327 var->data.index = 0;
328
329 if (c->scan->processor == PIPE_SHADER_FRAGMENT) {
330 switch (semantic_name) {
331 case TGSI_SEMANTIC_COLOR: {
332 /* TODO tgsi loses some information, so we cannot
333 * actually differentiate here between DSB and MRT
334 * at this point. But so far no drivers using tgsi-
335 * to-nir support dual source blend:
336 */
337 bool dual_src_blend = false;
338 if (dual_src_blend && (semantic_index == 1)) {
339 var->data.location = FRAG_RESULT_DATA0;
340 var->data.index = 1;
341 } else {
342 if (c->scan->properties[TGSI_PROPERTY_FS_COLOR0_WRITES_ALL_CBUFS])
343 var->data.location = FRAG_RESULT_COLOR;
344 else
345 var->data.location = FRAG_RESULT_DATA0 + semantic_index;
346 }
347 break;
348 }
349 case TGSI_SEMANTIC_POSITION:
350 var->data.location = FRAG_RESULT_DEPTH;
351 var->type = glsl_float_type();
352 break;
353 default:
354 fprintf(stderr, "Bad TGSI semantic: %d/%d\n",
355 decl->Semantic.Name, decl->Semantic.Index);
356 abort();
357 }
358 } else {
359 var->data.location =
360 tgsi_varying_semantic_to_slot(semantic_name, semantic_index);
361 }
362
363 if (is_array) {
364 unsigned j;
365 for (j = 0; j < array_size; j++) {
366 c->output_regs[idx + j].offset = i + j;
367 c->output_regs[idx + j].reg = reg;
368 }
369 } else {
370 c->output_regs[idx].offset = i;
371 c->output_regs[idx].reg = reg;
372 }
373
374 exec_list_push_tail(&b->shader->outputs, &var->node);
375 c->outputs[idx] = var;
376
377 for (int i = 0; i < array_size; i++)
378 b->shader->info.outputs_written |= 1ull << (var->data.location + i);
379 }
380 break;
381 case TGSI_FILE_CONSTANT:
382 var->data.mode = nir_var_uniform;
383 var->name = ralloc_asprintf(var, "uniform_%d", idx);
384
385 exec_list_push_tail(&b->shader->uniforms, &var->node);
386 break;
387 default:
388 unreachable("bad declaration file");
389 return;
390 }
391
392 if (is_array)
393 break;
394 }
395
396 }
397 }
398
399 static void
400 ttn_emit_immediate(struct ttn_compile *c)
401 {
402 nir_builder *b = &c->build;
403 struct tgsi_full_immediate *tgsi_imm = &c->token->FullImmediate;
404 nir_load_const_instr *load_const;
405 int i;
406
407 load_const = nir_load_const_instr_create(b->shader, 4, 32);
408 c->imm_defs[c->next_imm] = &load_const->def;
409 c->next_imm++;
410
411 for (i = 0; i < 4; i++)
412 load_const->value.u32[i] = tgsi_imm->u[i].Uint;
413
414 nir_builder_instr_insert(b, &load_const->instr);
415 }
416
417 static nir_ssa_def *
418 ttn_src_for_indirect(struct ttn_compile *c, struct tgsi_ind_register *indirect);
419
420 /* generate either a constant or indirect deref chain for accessing an
421 * array variable.
422 */
423 static nir_deref_instr *
424 ttn_array_deref(struct ttn_compile *c, nir_variable *var, unsigned offset,
425 struct tgsi_ind_register *indirect)
426 {
427 nir_deref_instr *deref = nir_build_deref_var(&c->build, var);
428 nir_ssa_def *index = nir_imm_int(&c->build, offset);
429 if (indirect)
430 index = nir_iadd(&c->build, index, ttn_src_for_indirect(c, indirect));
431 return nir_build_deref_array(&c->build, deref, index);
432 }
433
434 static nir_src
435 ttn_src_for_file_and_index(struct ttn_compile *c, unsigned file, unsigned index,
436 struct tgsi_ind_register *indirect,
437 struct tgsi_dimension *dim,
438 struct tgsi_ind_register *dimind)
439 {
440 nir_builder *b = &c->build;
441 nir_src src;
442
443 memset(&src, 0, sizeof(src));
444
445 switch (file) {
446 case TGSI_FILE_TEMPORARY:
447 if (c->temp_regs[index].var) {
448 unsigned offset = c->temp_regs[index].offset;
449 nir_variable *var = c->temp_regs[index].var;
450 nir_ssa_def *load = nir_load_deref(&c->build,
451 ttn_array_deref(c, var, offset, indirect));
452
453 src = nir_src_for_ssa(load);
454 } else {
455 assert(!indirect);
456 src.reg.reg = c->temp_regs[index].reg;
457 }
458 assert(!dim);
459 break;
460
461 case TGSI_FILE_ADDRESS:
462 src.reg.reg = c->addr_reg;
463 assert(!dim);
464 break;
465
466 case TGSI_FILE_IMMEDIATE:
467 src = nir_src_for_ssa(c->imm_defs[index]);
468 assert(!indirect);
469 assert(!dim);
470 break;
471
472 case TGSI_FILE_SYSTEM_VALUE: {
473 nir_intrinsic_instr *load;
474 nir_intrinsic_op op;
475 unsigned ncomp = 1;
476
477 assert(!indirect);
478 assert(!dim);
479
480 switch (c->scan->system_value_semantic_name[index]) {
481 case TGSI_SEMANTIC_VERTEXID_NOBASE:
482 op = nir_intrinsic_load_vertex_id_zero_base;
483 break;
484 case TGSI_SEMANTIC_VERTEXID:
485 op = nir_intrinsic_load_vertex_id;
486 break;
487 case TGSI_SEMANTIC_BASEVERTEX:
488 op = nir_intrinsic_load_base_vertex;
489 break;
490 case TGSI_SEMANTIC_INSTANCEID:
491 op = nir_intrinsic_load_instance_id;
492 break;
493 default:
494 unreachable("bad system value");
495 }
496
497 load = nir_intrinsic_instr_create(b->shader, op);
498 load->num_components = ncomp;
499
500 nir_ssa_dest_init(&load->instr, &load->dest, ncomp, 32, NULL);
501 nir_builder_instr_insert(b, &load->instr);
502
503 src = nir_src_for_ssa(&load->dest.ssa);
504
505 b->shader->info.system_values_read |=
506 (1 << nir_system_value_from_intrinsic(op));
507
508 break;
509 }
510
511 case TGSI_FILE_INPUT:
512 /* Special case: Turn the frontface varying into a load of the
513 * frontface intrinsic plus math, and appending the silly floats.
514 */
515 if (c->scan->processor == PIPE_SHADER_FRAGMENT &&
516 c->scan->input_semantic_name[index] == TGSI_SEMANTIC_FACE) {
517 nir_ssa_def *tgsi_frontface[4] = {
518 nir_bcsel(&c->build,
519 nir_load_front_face(&c->build, 1),
520 nir_imm_float(&c->build, 1.0),
521 nir_imm_float(&c->build, -1.0)),
522 nir_imm_float(&c->build, 0.0),
523 nir_imm_float(&c->build, 0.0),
524 nir_imm_float(&c->build, 1.0),
525 };
526
527 return nir_src_for_ssa(nir_vec(&c->build, tgsi_frontface, 4));
528 } else {
529 /* Indirection on input arrays isn't supported by TTN. */
530 assert(!dim);
531 nir_deref_instr *deref = nir_build_deref_var(&c->build,
532 c->inputs[index]);
533 return nir_src_for_ssa(nir_load_deref(&c->build, deref));
534 }
535 break;
536
537 case TGSI_FILE_CONSTANT: {
538 nir_intrinsic_instr *load;
539 nir_intrinsic_op op;
540 unsigned srcn = 0;
541
542 if (dim && (dim->Index > 0 || dim->Indirect)) {
543 op = nir_intrinsic_load_ubo;
544 } else {
545 op = nir_intrinsic_load_uniform;
546 }
547
548 load = nir_intrinsic_instr_create(b->shader, op);
549
550 load->num_components = 4;
551 if (dim && (dim->Index > 0 || dim->Indirect)) {
552 if (dimind) {
553 load->src[srcn] =
554 ttn_src_for_file_and_index(c, dimind->File, dimind->Index,
555 NULL, NULL, NULL);
556 } else {
557 /* UBOs start at index 1 in TGSI: */
558 load->src[srcn] =
559 nir_src_for_ssa(nir_imm_int(b, dim->Index - 1));
560 }
561 srcn++;
562 }
563
564 nir_ssa_def *offset;
565 if (op == nir_intrinsic_load_ubo) {
566 /* UBO loads don't have a base offset. */
567 offset = nir_imm_int(b, index);
568 if (indirect) {
569 offset = nir_iadd(b, offset, ttn_src_for_indirect(c, indirect));
570 }
571 /* UBO offsets are in bytes, but TGSI gives them to us in vec4's */
572 offset = nir_ishl(b, offset, nir_imm_int(b, 4));
573 } else {
574 nir_intrinsic_set_base(load, index);
575 if (indirect) {
576 offset = ttn_src_for_indirect(c, indirect);
577 } else {
578 offset = nir_imm_int(b, 0);
579 }
580 }
581 load->src[srcn++] = nir_src_for_ssa(offset);
582
583 nir_ssa_dest_init(&load->instr, &load->dest, 4, 32, NULL);
584 nir_builder_instr_insert(b, &load->instr);
585
586 src = nir_src_for_ssa(&load->dest.ssa);
587 break;
588 }
589
590 default:
591 unreachable("bad src file");
592 }
593
594
595 return src;
596 }
597
598 static nir_ssa_def *
599 ttn_src_for_indirect(struct ttn_compile *c, struct tgsi_ind_register *indirect)
600 {
601 nir_builder *b = &c->build;
602 nir_alu_src src;
603 memset(&src, 0, sizeof(src));
604 for (int i = 0; i < 4; i++)
605 src.swizzle[i] = indirect->Swizzle;
606 src.src = ttn_src_for_file_and_index(c,
607 indirect->File,
608 indirect->Index,
609 NULL, NULL, NULL);
610 return nir_imov_alu(b, src, 1);
611 }
612
613 static nir_alu_dest
614 ttn_get_dest(struct ttn_compile *c, struct tgsi_full_dst_register *tgsi_fdst)
615 {
616 struct tgsi_dst_register *tgsi_dst = &tgsi_fdst->Register;
617 nir_alu_dest dest;
618 unsigned index = tgsi_dst->Index;
619
620 memset(&dest, 0, sizeof(dest));
621
622 if (tgsi_dst->File == TGSI_FILE_TEMPORARY) {
623 if (c->temp_regs[index].var) {
624 nir_register *reg;
625
626 /* this works, because TGSI will give us a base offset
627 * (in case of indirect index) that points back into
628 * the array. Access can be direct or indirect, we
629 * don't really care. Just create a one-shot dst reg
630 * that will get store_var'd back into the array var
631 * at the end of ttn_emit_instruction()
632 */
633 reg = nir_local_reg_create(c->build.impl);
634 reg->num_components = 4;
635 dest.dest.reg.reg = reg;
636 dest.dest.reg.base_offset = 0;
637 } else {
638 assert(!tgsi_dst->Indirect);
639 dest.dest.reg.reg = c->temp_regs[index].reg;
640 dest.dest.reg.base_offset = c->temp_regs[index].offset;
641 }
642 } else if (tgsi_dst->File == TGSI_FILE_OUTPUT) {
643 dest.dest.reg.reg = c->output_regs[index].reg;
644 dest.dest.reg.base_offset = c->output_regs[index].offset;
645 } else if (tgsi_dst->File == TGSI_FILE_ADDRESS) {
646 assert(index == 0);
647 dest.dest.reg.reg = c->addr_reg;
648 }
649
650 dest.write_mask = tgsi_dst->WriteMask;
651 dest.saturate = false;
652
653 if (tgsi_dst->Indirect && (tgsi_dst->File != TGSI_FILE_TEMPORARY)) {
654 nir_src *indirect = ralloc(c->build.shader, nir_src);
655 *indirect = nir_src_for_ssa(ttn_src_for_indirect(c, &tgsi_fdst->Indirect));
656 dest.dest.reg.indirect = indirect;
657 }
658
659 return dest;
660 }
661
662 static nir_variable *
663 ttn_get_var(struct ttn_compile *c, struct tgsi_full_dst_register *tgsi_fdst)
664 {
665 struct tgsi_dst_register *tgsi_dst = &tgsi_fdst->Register;
666 unsigned index = tgsi_dst->Index;
667
668 if (tgsi_dst->File == TGSI_FILE_TEMPORARY) {
669 /* we should not have an indirect when there is no var! */
670 if (!c->temp_regs[index].var)
671 assert(!tgsi_dst->Indirect);
672 return c->temp_regs[index].var;
673 }
674
675 return NULL;
676 }
677
678 static nir_ssa_def *
679 ttn_get_src(struct ttn_compile *c, struct tgsi_full_src_register *tgsi_fsrc,
680 int src_idx)
681 {
682 nir_builder *b = &c->build;
683 struct tgsi_src_register *tgsi_src = &tgsi_fsrc->Register;
684 enum tgsi_opcode opcode = c->token->FullInstruction.Instruction.Opcode;
685 unsigned tgsi_src_type = tgsi_opcode_infer_src_type(opcode, src_idx);
686 bool src_is_float = !(tgsi_src_type == TGSI_TYPE_SIGNED ||
687 tgsi_src_type == TGSI_TYPE_UNSIGNED);
688 nir_alu_src src;
689
690 memset(&src, 0, sizeof(src));
691
692 if (tgsi_src->File == TGSI_FILE_NULL) {
693 return nir_imm_float(b, 0.0);
694 } else if (tgsi_src->File == TGSI_FILE_SAMPLER) {
695 /* Only the index of the sampler gets used in texturing, and it will
696 * handle looking that up on its own instead of using the nir_alu_src.
697 */
698 assert(!tgsi_src->Indirect);
699 return NULL;
700 } else {
701 struct tgsi_ind_register *ind = NULL;
702 struct tgsi_dimension *dim = NULL;
703 struct tgsi_ind_register *dimind = NULL;
704 if (tgsi_src->Indirect)
705 ind = &tgsi_fsrc->Indirect;
706 if (tgsi_src->Dimension) {
707 dim = &tgsi_fsrc->Dimension;
708 if (dim->Indirect)
709 dimind = &tgsi_fsrc->DimIndirect;
710 }
711 src.src = ttn_src_for_file_and_index(c,
712 tgsi_src->File,
713 tgsi_src->Index,
714 ind, dim, dimind);
715 }
716
717 src.swizzle[0] = tgsi_src->SwizzleX;
718 src.swizzle[1] = tgsi_src->SwizzleY;
719 src.swizzle[2] = tgsi_src->SwizzleZ;
720 src.swizzle[3] = tgsi_src->SwizzleW;
721
722 nir_ssa_def *def = nir_fmov_alu(b, src, 4);
723
724 if (tgsi_src->Absolute) {
725 if (src_is_float)
726 def = nir_fabs(b, def);
727 else
728 def = nir_iabs(b, def);
729 }
730
731 if (tgsi_src->Negate) {
732 if (src_is_float)
733 def = nir_fneg(b, def);
734 else
735 def = nir_ineg(b, def);
736 }
737
738 return def;
739 }
740
741 static void
742 ttn_alu(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
743 {
744 unsigned num_srcs = nir_op_infos[op].num_inputs;
745 nir_alu_instr *instr = nir_alu_instr_create(b->shader, op);
746 unsigned i;
747
748 for (i = 0; i < num_srcs; i++)
749 instr->src[i].src = nir_src_for_ssa(src[i]);
750
751 instr->dest = dest;
752 nir_builder_instr_insert(b, &instr->instr);
753 }
754
755 static void
756 ttn_move_dest_masked(nir_builder *b, nir_alu_dest dest,
757 nir_ssa_def *def, unsigned write_mask)
758 {
759 if (!(dest.write_mask & write_mask))
760 return;
761
762 nir_alu_instr *mov = nir_alu_instr_create(b->shader, nir_op_imov);
763 mov->dest = dest;
764 mov->dest.write_mask &= write_mask;
765 mov->src[0].src = nir_src_for_ssa(def);
766 for (unsigned i = def->num_components; i < 4; i++)
767 mov->src[0].swizzle[i] = def->num_components - 1;
768 nir_builder_instr_insert(b, &mov->instr);
769 }
770
771 static void
772 ttn_move_dest(nir_builder *b, nir_alu_dest dest, nir_ssa_def *def)
773 {
774 ttn_move_dest_masked(b, dest, def, TGSI_WRITEMASK_XYZW);
775 }
776
777 static void
778 ttn_arl(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
779 {
780 ttn_move_dest(b, dest, nir_f2i32(b, nir_ffloor(b, src[0])));
781 }
782
783 /* EXP - Approximate Exponential Base 2
784 * dst.x = 2^{\lfloor src.x\rfloor}
785 * dst.y = src.x - \lfloor src.x\rfloor
786 * dst.z = 2^{src.x}
787 * dst.w = 1.0
788 */
789 static void
790 ttn_exp(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
791 {
792 nir_ssa_def *srcx = ttn_channel(b, src[0], X);
793
794 ttn_move_dest_masked(b, dest, nir_fexp2(b, nir_ffloor(b, srcx)),
795 TGSI_WRITEMASK_X);
796 ttn_move_dest_masked(b, dest, nir_fsub(b, srcx, nir_ffloor(b, srcx)),
797 TGSI_WRITEMASK_Y);
798 ttn_move_dest_masked(b, dest, nir_fexp2(b, srcx), TGSI_WRITEMASK_Z);
799 ttn_move_dest_masked(b, dest, nir_imm_float(b, 1.0), TGSI_WRITEMASK_W);
800 }
801
802 /* LOG - Approximate Logarithm Base 2
803 * dst.x = \lfloor\log_2{|src.x|}\rfloor
804 * dst.y = \frac{|src.x|}{2^{\lfloor\log_2{|src.x|}\rfloor}}
805 * dst.z = \log_2{|src.x|}
806 * dst.w = 1.0
807 */
808 static void
809 ttn_log(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
810 {
811 nir_ssa_def *abs_srcx = nir_fabs(b, ttn_channel(b, src[0], X));
812 nir_ssa_def *log2 = nir_flog2(b, abs_srcx);
813
814 ttn_move_dest_masked(b, dest, nir_ffloor(b, log2), TGSI_WRITEMASK_X);
815 ttn_move_dest_masked(b, dest,
816 nir_fdiv(b, abs_srcx, nir_fexp2(b, nir_ffloor(b, log2))),
817 TGSI_WRITEMASK_Y);
818 ttn_move_dest_masked(b, dest, nir_flog2(b, abs_srcx), TGSI_WRITEMASK_Z);
819 ttn_move_dest_masked(b, dest, nir_imm_float(b, 1.0), TGSI_WRITEMASK_W);
820 }
821
822 /* DST - Distance Vector
823 * dst.x = 1.0
824 * dst.y = src0.y \times src1.y
825 * dst.z = src0.z
826 * dst.w = src1.w
827 */
828 static void
829 ttn_dst(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
830 {
831 ttn_move_dest_masked(b, dest, nir_imm_float(b, 1.0), TGSI_WRITEMASK_X);
832 ttn_move_dest_masked(b, dest, nir_fmul(b, src[0], src[1]), TGSI_WRITEMASK_Y);
833 ttn_move_dest_masked(b, dest, nir_fmov(b, src[0]), TGSI_WRITEMASK_Z);
834 ttn_move_dest_masked(b, dest, nir_fmov(b, src[1]), TGSI_WRITEMASK_W);
835 }
836
837 /* LIT - Light Coefficients
838 * dst.x = 1.0
839 * dst.y = max(src.x, 0.0)
840 * dst.z = (src.x > 0.0) ? max(src.y, 0.0)^{clamp(src.w, -128.0, 128.0))} : 0
841 * dst.w = 1.0
842 */
843 static void
844 ttn_lit(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
845 {
846 ttn_move_dest_masked(b, dest, nir_imm_float(b, 1.0), TGSI_WRITEMASK_XW);
847
848 ttn_move_dest_masked(b, dest, nir_fmax(b, ttn_channel(b, src[0], X),
849 nir_imm_float(b, 0.0)), TGSI_WRITEMASK_Y);
850
851 if (dest.write_mask & TGSI_WRITEMASK_Z) {
852 nir_ssa_def *src0_y = ttn_channel(b, src[0], Y);
853 nir_ssa_def *wclamp = nir_fmax(b, nir_fmin(b, ttn_channel(b, src[0], W),
854 nir_imm_float(b, 128.0)),
855 nir_imm_float(b, -128.0));
856 nir_ssa_def *pow = nir_fpow(b, nir_fmax(b, src0_y, nir_imm_float(b, 0.0)),
857 wclamp);
858
859 ttn_move_dest_masked(b, dest,
860 nir_bcsel(b,
861 nir_fge(b,
862 nir_imm_float(b, 0.0),
863 ttn_channel(b, src[0], X)),
864 nir_imm_float(b, 0.0),
865 pow),
866 TGSI_WRITEMASK_Z);
867 }
868 }
869
870 static void
871 ttn_sle(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
872 {
873 ttn_move_dest(b, dest, nir_sge(b, src[1], src[0]));
874 }
875
876 static void
877 ttn_sgt(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
878 {
879 ttn_move_dest(b, dest, nir_slt(b, src[1], src[0]));
880 }
881
882 static void
883 ttn_dp2(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
884 {
885 ttn_move_dest(b, dest, nir_fdot2(b, src[0], src[1]));
886 }
887
888 static void
889 ttn_dp3(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
890 {
891 ttn_move_dest(b, dest, nir_fdot3(b, src[0], src[1]));
892 }
893
894 static void
895 ttn_dp4(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
896 {
897 ttn_move_dest(b, dest, nir_fdot4(b, src[0], src[1]));
898 }
899
900 static void
901 ttn_umad(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
902 {
903 ttn_move_dest(b, dest, nir_iadd(b, nir_imul(b, src[0], src[1]), src[2]));
904 }
905
906 static void
907 ttn_arr(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
908 {
909 ttn_move_dest(b, dest, nir_ffloor(b, nir_fadd(b, src[0], nir_imm_float(b, 0.5))));
910 }
911
912 static void
913 ttn_cmp(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
914 {
915 ttn_move_dest(b, dest, nir_bcsel(b,
916 nir_flt(b, src[0], nir_imm_float(b, 0.0)),
917 src[1], src[2]));
918 }
919
920 static void
921 ttn_ucmp(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
922 {
923 ttn_move_dest(b, dest, nir_bcsel(b,
924 nir_ine(b, src[0], nir_imm_int(b, 0)),
925 src[1], src[2]));
926 }
927
928 static void
929 ttn_kill(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
930 {
931 nir_intrinsic_instr *discard =
932 nir_intrinsic_instr_create(b->shader, nir_intrinsic_discard);
933 nir_builder_instr_insert(b, &discard->instr);
934 b->shader->info.fs.uses_discard = true;
935 }
936
937 static void
938 ttn_kill_if(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
939 {
940 nir_ssa_def *cmp = nir_bany(b, nir_flt(b, src[0], nir_imm_float(b, 0.0)));
941 nir_intrinsic_instr *discard =
942 nir_intrinsic_instr_create(b->shader, nir_intrinsic_discard_if);
943 discard->src[0] = nir_src_for_ssa(cmp);
944 nir_builder_instr_insert(b, &discard->instr);
945 b->shader->info.fs.uses_discard = true;
946 }
947
948 static void
949 ttn_if(struct ttn_compile *c, nir_ssa_def *src, bool is_uint)
950 {
951 nir_builder *b = &c->build;
952
953 src = ttn_channel(b, src, X);
954
955 nir_if *if_stmt = nir_if_create(b->shader);
956 if (is_uint) {
957 if_stmt->condition = nir_src_for_ssa(nir_ine(b, src, nir_imm_int(b, 0)));
958 } else {
959 if_stmt->condition = nir_src_for_ssa(nir_fne(b, src, nir_imm_int(b, 0)));
960 }
961 nir_builder_cf_insert(b, &if_stmt->cf_node);
962
963 c->if_stack[c->if_stack_pos] = nir_after_cf_node(&if_stmt->cf_node);
964 c->if_stack_pos++;
965
966 b->cursor = nir_after_cf_list(&if_stmt->then_list);
967
968 c->if_stack[c->if_stack_pos] = nir_after_cf_list(&if_stmt->else_list);
969 c->if_stack_pos++;
970 }
971
972 static void
973 ttn_else(struct ttn_compile *c)
974 {
975 nir_builder *b = &c->build;
976
977 b->cursor = c->if_stack[c->if_stack_pos - 1];
978 }
979
980 static void
981 ttn_endif(struct ttn_compile *c)
982 {
983 nir_builder *b = &c->build;
984
985 c->if_stack_pos -= 2;
986 b->cursor = c->if_stack[c->if_stack_pos];
987 }
988
989 static void
990 ttn_bgnloop(struct ttn_compile *c)
991 {
992 nir_builder *b = &c->build;
993
994 nir_loop *loop = nir_loop_create(b->shader);
995 nir_builder_cf_insert(b, &loop->cf_node);
996
997 c->loop_stack[c->loop_stack_pos] = nir_after_cf_node(&loop->cf_node);
998 c->loop_stack_pos++;
999
1000 b->cursor = nir_after_cf_list(&loop->body);
1001 }
1002
1003 static void
1004 ttn_cont(nir_builder *b)
1005 {
1006 nir_jump_instr *instr = nir_jump_instr_create(b->shader, nir_jump_continue);
1007 nir_builder_instr_insert(b, &instr->instr);
1008 }
1009
1010 static void
1011 ttn_brk(nir_builder *b)
1012 {
1013 nir_jump_instr *instr = nir_jump_instr_create(b->shader, nir_jump_break);
1014 nir_builder_instr_insert(b, &instr->instr);
1015 }
1016
1017 static void
1018 ttn_endloop(struct ttn_compile *c)
1019 {
1020 nir_builder *b = &c->build;
1021
1022 c->loop_stack_pos--;
1023 b->cursor = c->loop_stack[c->loop_stack_pos];
1024 }
1025
1026 static void
1027 setup_texture_info(nir_tex_instr *instr, unsigned texture)
1028 {
1029 switch (texture) {
1030 case TGSI_TEXTURE_BUFFER:
1031 instr->sampler_dim = GLSL_SAMPLER_DIM_BUF;
1032 break;
1033 case TGSI_TEXTURE_1D:
1034 instr->sampler_dim = GLSL_SAMPLER_DIM_1D;
1035 break;
1036 case TGSI_TEXTURE_1D_ARRAY:
1037 instr->sampler_dim = GLSL_SAMPLER_DIM_1D;
1038 instr->is_array = true;
1039 break;
1040 case TGSI_TEXTURE_SHADOW1D:
1041 instr->sampler_dim = GLSL_SAMPLER_DIM_1D;
1042 instr->is_shadow = true;
1043 break;
1044 case TGSI_TEXTURE_SHADOW1D_ARRAY:
1045 instr->sampler_dim = GLSL_SAMPLER_DIM_1D;
1046 instr->is_shadow = true;
1047 instr->is_array = true;
1048 break;
1049 case TGSI_TEXTURE_2D:
1050 instr->sampler_dim = GLSL_SAMPLER_DIM_2D;
1051 break;
1052 case TGSI_TEXTURE_2D_ARRAY:
1053 instr->sampler_dim = GLSL_SAMPLER_DIM_2D;
1054 instr->is_array = true;
1055 break;
1056 case TGSI_TEXTURE_2D_MSAA:
1057 instr->sampler_dim = GLSL_SAMPLER_DIM_MS;
1058 break;
1059 case TGSI_TEXTURE_2D_ARRAY_MSAA:
1060 instr->sampler_dim = GLSL_SAMPLER_DIM_MS;
1061 instr->is_array = true;
1062 break;
1063 case TGSI_TEXTURE_SHADOW2D:
1064 instr->sampler_dim = GLSL_SAMPLER_DIM_2D;
1065 instr->is_shadow = true;
1066 break;
1067 case TGSI_TEXTURE_SHADOW2D_ARRAY:
1068 instr->sampler_dim = GLSL_SAMPLER_DIM_2D;
1069 instr->is_shadow = true;
1070 instr->is_array = true;
1071 break;
1072 case TGSI_TEXTURE_3D:
1073 instr->sampler_dim = GLSL_SAMPLER_DIM_3D;
1074 break;
1075 case TGSI_TEXTURE_CUBE:
1076 instr->sampler_dim = GLSL_SAMPLER_DIM_CUBE;
1077 break;
1078 case TGSI_TEXTURE_CUBE_ARRAY:
1079 instr->sampler_dim = GLSL_SAMPLER_DIM_CUBE;
1080 instr->is_array = true;
1081 break;
1082 case TGSI_TEXTURE_SHADOWCUBE:
1083 instr->sampler_dim = GLSL_SAMPLER_DIM_CUBE;
1084 instr->is_shadow = true;
1085 break;
1086 case TGSI_TEXTURE_SHADOWCUBE_ARRAY:
1087 instr->sampler_dim = GLSL_SAMPLER_DIM_CUBE;
1088 instr->is_shadow = true;
1089 instr->is_array = true;
1090 break;
1091 case TGSI_TEXTURE_RECT:
1092 instr->sampler_dim = GLSL_SAMPLER_DIM_RECT;
1093 break;
1094 case TGSI_TEXTURE_SHADOWRECT:
1095 instr->sampler_dim = GLSL_SAMPLER_DIM_RECT;
1096 instr->is_shadow = true;
1097 break;
1098 default:
1099 fprintf(stderr, "Unknown TGSI texture target %d\n", texture);
1100 abort();
1101 }
1102 }
1103
1104 static void
1105 ttn_tex(struct ttn_compile *c, nir_alu_dest dest, nir_ssa_def **src)
1106 {
1107 nir_builder *b = &c->build;
1108 struct tgsi_full_instruction *tgsi_inst = &c->token->FullInstruction;
1109 nir_tex_instr *instr;
1110 nir_texop op;
1111 unsigned num_srcs, samp = 1, sview, i;
1112
1113 switch (tgsi_inst->Instruction.Opcode) {
1114 case TGSI_OPCODE_TEX:
1115 op = nir_texop_tex;
1116 num_srcs = 1;
1117 break;
1118 case TGSI_OPCODE_TEX2:
1119 op = nir_texop_tex;
1120 num_srcs = 1;
1121 samp = 2;
1122 break;
1123 case TGSI_OPCODE_TXP:
1124 op = nir_texop_tex;
1125 num_srcs = 2;
1126 break;
1127 case TGSI_OPCODE_TXB:
1128 op = nir_texop_txb;
1129 num_srcs = 2;
1130 break;
1131 case TGSI_OPCODE_TXB2:
1132 op = nir_texop_txb;
1133 num_srcs = 2;
1134 samp = 2;
1135 break;
1136 case TGSI_OPCODE_TXL:
1137 op = nir_texop_txl;
1138 num_srcs = 2;
1139 break;
1140 case TGSI_OPCODE_TXL2:
1141 op = nir_texop_txl;
1142 num_srcs = 2;
1143 samp = 2;
1144 break;
1145 case TGSI_OPCODE_TXF:
1146 if (tgsi_inst->Texture.Texture == TGSI_TEXTURE_2D_MSAA ||
1147 tgsi_inst->Texture.Texture == TGSI_TEXTURE_2D_ARRAY_MSAA) {
1148 op = nir_texop_txf_ms;
1149 } else {
1150 op = nir_texop_txf;
1151 }
1152 num_srcs = 2;
1153 break;
1154 case TGSI_OPCODE_TXD:
1155 op = nir_texop_txd;
1156 num_srcs = 3;
1157 samp = 3;
1158 break;
1159 case TGSI_OPCODE_LODQ:
1160 op = nir_texop_lod;
1161 num_srcs = 1;
1162 break;
1163
1164 default:
1165 fprintf(stderr, "unknown TGSI tex op %d\n", tgsi_inst->Instruction.Opcode);
1166 abort();
1167 }
1168
1169 if (tgsi_inst->Texture.Texture == TGSI_TEXTURE_SHADOW1D ||
1170 tgsi_inst->Texture.Texture == TGSI_TEXTURE_SHADOW1D_ARRAY ||
1171 tgsi_inst->Texture.Texture == TGSI_TEXTURE_SHADOW2D ||
1172 tgsi_inst->Texture.Texture == TGSI_TEXTURE_SHADOW2D_ARRAY ||
1173 tgsi_inst->Texture.Texture == TGSI_TEXTURE_SHADOWRECT ||
1174 tgsi_inst->Texture.Texture == TGSI_TEXTURE_SHADOWCUBE ||
1175 tgsi_inst->Texture.Texture == TGSI_TEXTURE_SHADOWCUBE_ARRAY) {
1176 num_srcs++;
1177 }
1178
1179 num_srcs += tgsi_inst->Texture.NumOffsets;
1180
1181 instr = nir_tex_instr_create(b->shader, num_srcs);
1182 instr->op = op;
1183
1184 setup_texture_info(instr, tgsi_inst->Texture.Texture);
1185
1186 switch (instr->sampler_dim) {
1187 case GLSL_SAMPLER_DIM_1D:
1188 case GLSL_SAMPLER_DIM_BUF:
1189 instr->coord_components = 1;
1190 break;
1191 case GLSL_SAMPLER_DIM_2D:
1192 case GLSL_SAMPLER_DIM_RECT:
1193 case GLSL_SAMPLER_DIM_EXTERNAL:
1194 case GLSL_SAMPLER_DIM_MS:
1195 instr->coord_components = 2;
1196 break;
1197 case GLSL_SAMPLER_DIM_3D:
1198 case GLSL_SAMPLER_DIM_CUBE:
1199 instr->coord_components = 3;
1200 break;
1201 case GLSL_SAMPLER_DIM_SUBPASS:
1202 case GLSL_SAMPLER_DIM_SUBPASS_MS:
1203 unreachable("invalid sampler_dim");
1204 }
1205
1206 if (instr->is_array)
1207 instr->coord_components++;
1208
1209 assert(tgsi_inst->Src[samp].Register.File == TGSI_FILE_SAMPLER);
1210 instr->texture_index = tgsi_inst->Src[samp].Register.Index;
1211 instr->sampler_index = tgsi_inst->Src[samp].Register.Index;
1212
1213 /* TODO if we supported any opc's which take an explicit SVIEW
1214 * src, we would use that here instead. But for the "legacy"
1215 * texture opc's the SVIEW index is same as SAMP index:
1216 */
1217 sview = instr->texture_index;
1218
1219 if (op == nir_texop_lod) {
1220 instr->dest_type = nir_type_float;
1221 } else if (sview < c->num_samp_types) {
1222 instr->dest_type = c->samp_types[sview];
1223 } else {
1224 instr->dest_type = nir_type_float;
1225 }
1226
1227 unsigned src_number = 0;
1228
1229 instr->src[src_number].src =
1230 nir_src_for_ssa(nir_swizzle(b, src[0], SWIZ(X, Y, Z, W),
1231 instr->coord_components, false));
1232 instr->src[src_number].src_type = nir_tex_src_coord;
1233 src_number++;
1234
1235 if (tgsi_inst->Instruction.Opcode == TGSI_OPCODE_TXP) {
1236 instr->src[src_number].src = nir_src_for_ssa(ttn_channel(b, src[0], W));
1237 instr->src[src_number].src_type = nir_tex_src_projector;
1238 src_number++;
1239 }
1240
1241 if (tgsi_inst->Instruction.Opcode == TGSI_OPCODE_TXB) {
1242 instr->src[src_number].src = nir_src_for_ssa(ttn_channel(b, src[0], W));
1243 instr->src[src_number].src_type = nir_tex_src_bias;
1244 src_number++;
1245 }
1246
1247 if (tgsi_inst->Instruction.Opcode == TGSI_OPCODE_TXB2) {
1248 instr->src[src_number].src = nir_src_for_ssa(ttn_channel(b, src[1], X));
1249 instr->src[src_number].src_type = nir_tex_src_bias;
1250 src_number++;
1251 }
1252
1253 if (tgsi_inst->Instruction.Opcode == TGSI_OPCODE_TXL) {
1254 instr->src[src_number].src = nir_src_for_ssa(ttn_channel(b, src[0], W));
1255 instr->src[src_number].src_type = nir_tex_src_lod;
1256 src_number++;
1257 }
1258
1259 if (tgsi_inst->Instruction.Opcode == TGSI_OPCODE_TXL2) {
1260 instr->src[src_number].src = nir_src_for_ssa(ttn_channel(b, src[1], X));
1261 instr->src[src_number].src_type = nir_tex_src_lod;
1262 src_number++;
1263 }
1264
1265 if (tgsi_inst->Instruction.Opcode == TGSI_OPCODE_TXF) {
1266 instr->src[src_number].src = nir_src_for_ssa(ttn_channel(b, src[0], W));
1267 if (op == nir_texop_txf_ms)
1268 instr->src[src_number].src_type = nir_tex_src_ms_index;
1269 else
1270 instr->src[src_number].src_type = nir_tex_src_lod;
1271 src_number++;
1272 }
1273
1274 if (tgsi_inst->Instruction.Opcode == TGSI_OPCODE_TXD) {
1275 instr->src[src_number].src_type = nir_tex_src_ddx;
1276 instr->src[src_number].src =
1277 nir_src_for_ssa(nir_swizzle(b, src[1], SWIZ(X, Y, Z, W),
1278 nir_tex_instr_src_size(instr, src_number),
1279 false));
1280 src_number++;
1281 instr->src[src_number].src_type = nir_tex_src_ddy;
1282 instr->src[src_number].src =
1283 nir_src_for_ssa(nir_swizzle(b, src[2], SWIZ(X, Y, Z, W),
1284 nir_tex_instr_src_size(instr, src_number),
1285 false));
1286 src_number++;
1287 }
1288
1289 if (instr->is_shadow) {
1290 if (instr->coord_components == 4)
1291 instr->src[src_number].src = nir_src_for_ssa(ttn_channel(b, src[1], X));
1292 else if (instr->coord_components == 3)
1293 instr->src[src_number].src = nir_src_for_ssa(ttn_channel(b, src[0], W));
1294 else
1295 instr->src[src_number].src = nir_src_for_ssa(ttn_channel(b, src[0], Z));
1296
1297 instr->src[src_number].src_type = nir_tex_src_comparator;
1298 src_number++;
1299 }
1300
1301 for (i = 0; i < tgsi_inst->Texture.NumOffsets; i++) {
1302 struct tgsi_texture_offset *tex_offset = &tgsi_inst->TexOffsets[i];
1303 /* since TexOffset ins't using tgsi_full_src_register we get to
1304 * do some extra gymnastics:
1305 */
1306 nir_alu_src src;
1307
1308 memset(&src, 0, sizeof(src));
1309
1310 src.src = ttn_src_for_file_and_index(c,
1311 tex_offset->File,
1312 tex_offset->Index,
1313 NULL, NULL, NULL);
1314
1315 src.swizzle[0] = tex_offset->SwizzleX;
1316 src.swizzle[1] = tex_offset->SwizzleY;
1317 src.swizzle[2] = tex_offset->SwizzleZ;
1318 src.swizzle[3] = TGSI_SWIZZLE_W;
1319
1320 instr->src[src_number].src_type = nir_tex_src_offset;
1321 instr->src[src_number].src = nir_src_for_ssa(
1322 nir_fmov_alu(b, src, nir_tex_instr_src_size(instr, src_number)));
1323 src_number++;
1324 }
1325
1326 assert(src_number == num_srcs);
1327
1328 nir_ssa_dest_init(&instr->instr, &instr->dest,
1329 nir_tex_instr_dest_size(instr),
1330 32, NULL);
1331 nir_builder_instr_insert(b, &instr->instr);
1332
1333 /* Resolve the writemask on the texture op. */
1334 ttn_move_dest(b, dest, &instr->dest.ssa);
1335 }
1336
1337 /* TGSI_OPCODE_TXQ is actually two distinct operations:
1338 *
1339 * dst.x = texture\_width(unit, lod)
1340 * dst.y = texture\_height(unit, lod)
1341 * dst.z = texture\_depth(unit, lod)
1342 * dst.w = texture\_levels(unit)
1343 *
1344 * dst.xyz map to NIR txs opcode, and dst.w maps to query_levels
1345 */
1346 static void
1347 ttn_txq(struct ttn_compile *c, nir_alu_dest dest, nir_ssa_def **src)
1348 {
1349 nir_builder *b = &c->build;
1350 struct tgsi_full_instruction *tgsi_inst = &c->token->FullInstruction;
1351 nir_tex_instr *txs, *qlv;
1352
1353 txs = nir_tex_instr_create(b->shader, 1);
1354 txs->op = nir_texop_txs;
1355 setup_texture_info(txs, tgsi_inst->Texture.Texture);
1356
1357 qlv = nir_tex_instr_create(b->shader, 0);
1358 qlv->op = nir_texop_query_levels;
1359 setup_texture_info(qlv, tgsi_inst->Texture.Texture);
1360
1361 assert(tgsi_inst->Src[1].Register.File == TGSI_FILE_SAMPLER);
1362 txs->texture_index = tgsi_inst->Src[1].Register.Index;
1363 qlv->texture_index = tgsi_inst->Src[1].Register.Index;
1364
1365 /* only single src, the lod: */
1366 txs->src[0].src = nir_src_for_ssa(ttn_channel(b, src[0], X));
1367 txs->src[0].src_type = nir_tex_src_lod;
1368
1369 nir_ssa_dest_init(&txs->instr, &txs->dest,
1370 nir_tex_instr_dest_size(txs), 32, NULL);
1371 nir_builder_instr_insert(b, &txs->instr);
1372
1373 nir_ssa_dest_init(&qlv->instr, &qlv->dest, 1, 32, NULL);
1374 nir_builder_instr_insert(b, &qlv->instr);
1375
1376 ttn_move_dest_masked(b, dest, &txs->dest.ssa, TGSI_WRITEMASK_XYZ);
1377 ttn_move_dest_masked(b, dest, &qlv->dest.ssa, TGSI_WRITEMASK_W);
1378 }
1379
1380 static const nir_op op_trans[TGSI_OPCODE_LAST] = {
1381 [TGSI_OPCODE_ARL] = 0,
1382 [TGSI_OPCODE_MOV] = nir_op_fmov,
1383 [TGSI_OPCODE_LIT] = 0,
1384 [TGSI_OPCODE_RCP] = nir_op_frcp,
1385 [TGSI_OPCODE_RSQ] = nir_op_frsq,
1386 [TGSI_OPCODE_EXP] = 0,
1387 [TGSI_OPCODE_LOG] = 0,
1388 [TGSI_OPCODE_MUL] = nir_op_fmul,
1389 [TGSI_OPCODE_ADD] = nir_op_fadd,
1390 [TGSI_OPCODE_DP3] = 0,
1391 [TGSI_OPCODE_DP4] = 0,
1392 [TGSI_OPCODE_DST] = 0,
1393 [TGSI_OPCODE_MIN] = nir_op_fmin,
1394 [TGSI_OPCODE_MAX] = nir_op_fmax,
1395 [TGSI_OPCODE_SLT] = nir_op_slt,
1396 [TGSI_OPCODE_SGE] = nir_op_sge,
1397 [TGSI_OPCODE_MAD] = nir_op_ffma,
1398 [TGSI_OPCODE_LRP] = 0,
1399 [TGSI_OPCODE_SQRT] = nir_op_fsqrt,
1400 [TGSI_OPCODE_FRC] = nir_op_ffract,
1401 [TGSI_OPCODE_FLR] = nir_op_ffloor,
1402 [TGSI_OPCODE_ROUND] = nir_op_fround_even,
1403 [TGSI_OPCODE_EX2] = nir_op_fexp2,
1404 [TGSI_OPCODE_LG2] = nir_op_flog2,
1405 [TGSI_OPCODE_POW] = nir_op_fpow,
1406 [TGSI_OPCODE_COS] = nir_op_fcos,
1407 [TGSI_OPCODE_DDX] = nir_op_fddx,
1408 [TGSI_OPCODE_DDY] = nir_op_fddy,
1409 [TGSI_OPCODE_KILL] = 0,
1410 [TGSI_OPCODE_PK2H] = 0, /* XXX */
1411 [TGSI_OPCODE_PK2US] = 0, /* XXX */
1412 [TGSI_OPCODE_PK4B] = 0, /* XXX */
1413 [TGSI_OPCODE_PK4UB] = 0, /* XXX */
1414 [TGSI_OPCODE_SEQ] = nir_op_seq,
1415 [TGSI_OPCODE_SGT] = 0,
1416 [TGSI_OPCODE_SIN] = nir_op_fsin,
1417 [TGSI_OPCODE_SNE] = nir_op_sne,
1418 [TGSI_OPCODE_SLE] = 0,
1419 [TGSI_OPCODE_TEX] = 0,
1420 [TGSI_OPCODE_TXD] = 0,
1421 [TGSI_OPCODE_TXP] = 0,
1422 [TGSI_OPCODE_UP2H] = 0, /* XXX */
1423 [TGSI_OPCODE_UP2US] = 0, /* XXX */
1424 [TGSI_OPCODE_UP4B] = 0, /* XXX */
1425 [TGSI_OPCODE_UP4UB] = 0, /* XXX */
1426 [TGSI_OPCODE_ARR] = 0,
1427
1428 /* No function calls, yet. */
1429 [TGSI_OPCODE_CAL] = 0, /* XXX */
1430 [TGSI_OPCODE_RET] = 0, /* XXX */
1431
1432 [TGSI_OPCODE_SSG] = nir_op_fsign,
1433 [TGSI_OPCODE_CMP] = 0,
1434 [TGSI_OPCODE_TXB] = 0,
1435 [TGSI_OPCODE_DIV] = nir_op_fdiv,
1436 [TGSI_OPCODE_DP2] = 0,
1437 [TGSI_OPCODE_TXL] = 0,
1438
1439 [TGSI_OPCODE_BRK] = 0,
1440 [TGSI_OPCODE_IF] = 0,
1441 [TGSI_OPCODE_UIF] = 0,
1442 [TGSI_OPCODE_ELSE] = 0,
1443 [TGSI_OPCODE_ENDIF] = 0,
1444
1445 [TGSI_OPCODE_DDX_FINE] = nir_op_fddx_fine,
1446 [TGSI_OPCODE_DDY_FINE] = nir_op_fddy_fine,
1447
1448 [TGSI_OPCODE_CEIL] = nir_op_fceil,
1449 [TGSI_OPCODE_I2F] = nir_op_i2f32,
1450 [TGSI_OPCODE_NOT] = nir_op_inot,
1451 [TGSI_OPCODE_TRUNC] = nir_op_ftrunc,
1452 [TGSI_OPCODE_SHL] = nir_op_ishl,
1453 [TGSI_OPCODE_AND] = nir_op_iand,
1454 [TGSI_OPCODE_OR] = nir_op_ior,
1455 [TGSI_OPCODE_MOD] = nir_op_umod,
1456 [TGSI_OPCODE_XOR] = nir_op_ixor,
1457 [TGSI_OPCODE_TXF] = 0,
1458 [TGSI_OPCODE_TXQ] = 0,
1459
1460 [TGSI_OPCODE_CONT] = 0,
1461
1462 [TGSI_OPCODE_EMIT] = 0, /* XXX */
1463 [TGSI_OPCODE_ENDPRIM] = 0, /* XXX */
1464
1465 [TGSI_OPCODE_BGNLOOP] = 0,
1466 [TGSI_OPCODE_BGNSUB] = 0, /* XXX: no function calls */
1467 [TGSI_OPCODE_ENDLOOP] = 0,
1468 [TGSI_OPCODE_ENDSUB] = 0, /* XXX: no function calls */
1469
1470 [TGSI_OPCODE_NOP] = 0,
1471 [TGSI_OPCODE_FSEQ] = nir_op_feq32,
1472 [TGSI_OPCODE_FSGE] = nir_op_fge32,
1473 [TGSI_OPCODE_FSLT] = nir_op_flt32,
1474 [TGSI_OPCODE_FSNE] = nir_op_fne32,
1475
1476 [TGSI_OPCODE_KILL_IF] = 0,
1477
1478 [TGSI_OPCODE_END] = 0,
1479
1480 [TGSI_OPCODE_F2I] = nir_op_f2i32,
1481 [TGSI_OPCODE_IDIV] = nir_op_idiv,
1482 [TGSI_OPCODE_IMAX] = nir_op_imax,
1483 [TGSI_OPCODE_IMIN] = nir_op_imin,
1484 [TGSI_OPCODE_INEG] = nir_op_ineg,
1485 [TGSI_OPCODE_ISGE] = nir_op_ige32,
1486 [TGSI_OPCODE_ISHR] = nir_op_ishr,
1487 [TGSI_OPCODE_ISLT] = nir_op_ilt32,
1488 [TGSI_OPCODE_F2U] = nir_op_f2u32,
1489 [TGSI_OPCODE_U2F] = nir_op_u2f32,
1490 [TGSI_OPCODE_UADD] = nir_op_iadd,
1491 [TGSI_OPCODE_UDIV] = nir_op_udiv,
1492 [TGSI_OPCODE_UMAD] = 0,
1493 [TGSI_OPCODE_UMAX] = nir_op_umax,
1494 [TGSI_OPCODE_UMIN] = nir_op_umin,
1495 [TGSI_OPCODE_UMOD] = nir_op_umod,
1496 [TGSI_OPCODE_UMUL] = nir_op_imul,
1497 [TGSI_OPCODE_USEQ] = nir_op_ieq32,
1498 [TGSI_OPCODE_USGE] = nir_op_uge32,
1499 [TGSI_OPCODE_USHR] = nir_op_ushr,
1500 [TGSI_OPCODE_USLT] = nir_op_ult32,
1501 [TGSI_OPCODE_USNE] = nir_op_ine32,
1502
1503 [TGSI_OPCODE_SWITCH] = 0, /* not emitted by glsl_to_tgsi.cpp */
1504 [TGSI_OPCODE_CASE] = 0, /* not emitted by glsl_to_tgsi.cpp */
1505 [TGSI_OPCODE_DEFAULT] = 0, /* not emitted by glsl_to_tgsi.cpp */
1506 [TGSI_OPCODE_ENDSWITCH] = 0, /* not emitted by glsl_to_tgsi.cpp */
1507
1508 /* XXX: SAMPLE opcodes */
1509
1510 [TGSI_OPCODE_UARL] = nir_op_imov,
1511 [TGSI_OPCODE_UCMP] = 0,
1512 [TGSI_OPCODE_IABS] = nir_op_iabs,
1513 [TGSI_OPCODE_ISSG] = nir_op_isign,
1514
1515 /* XXX: atomics */
1516
1517 [TGSI_OPCODE_TEX2] = 0,
1518 [TGSI_OPCODE_TXB2] = 0,
1519 [TGSI_OPCODE_TXL2] = 0,
1520
1521 [TGSI_OPCODE_IMUL_HI] = nir_op_imul_high,
1522 [TGSI_OPCODE_UMUL_HI] = nir_op_umul_high,
1523
1524 [TGSI_OPCODE_TG4] = 0,
1525 [TGSI_OPCODE_LODQ] = 0,
1526
1527 [TGSI_OPCODE_IBFE] = nir_op_ibitfield_extract,
1528 [TGSI_OPCODE_UBFE] = nir_op_ubitfield_extract,
1529 [TGSI_OPCODE_BFI] = nir_op_bitfield_insert,
1530 [TGSI_OPCODE_BREV] = nir_op_bitfield_reverse,
1531 [TGSI_OPCODE_POPC] = nir_op_bit_count,
1532 [TGSI_OPCODE_LSB] = nir_op_find_lsb,
1533 [TGSI_OPCODE_IMSB] = nir_op_ifind_msb,
1534 [TGSI_OPCODE_UMSB] = nir_op_ufind_msb,
1535
1536 [TGSI_OPCODE_INTERP_CENTROID] = 0, /* XXX */
1537 [TGSI_OPCODE_INTERP_SAMPLE] = 0, /* XXX */
1538 [TGSI_OPCODE_INTERP_OFFSET] = 0, /* XXX */
1539 };
1540
1541 static void
1542 ttn_emit_instruction(struct ttn_compile *c)
1543 {
1544 nir_builder *b = &c->build;
1545 struct tgsi_full_instruction *tgsi_inst = &c->token->FullInstruction;
1546 unsigned i;
1547 unsigned tgsi_op = tgsi_inst->Instruction.Opcode;
1548 struct tgsi_full_dst_register *tgsi_dst = &tgsi_inst->Dst[0];
1549
1550 if (tgsi_op == TGSI_OPCODE_END)
1551 return;
1552
1553 nir_ssa_def *src[TGSI_FULL_MAX_SRC_REGISTERS];
1554 for (i = 0; i < tgsi_inst->Instruction.NumSrcRegs; i++) {
1555 src[i] = ttn_get_src(c, &tgsi_inst->Src[i], i);
1556 }
1557 nir_alu_dest dest = ttn_get_dest(c, tgsi_dst);
1558
1559 switch (tgsi_op) {
1560 case TGSI_OPCODE_RSQ:
1561 ttn_move_dest(b, dest, nir_frsq(b, ttn_channel(b, src[0], X)));
1562 break;
1563
1564 case TGSI_OPCODE_SQRT:
1565 ttn_move_dest(b, dest, nir_fsqrt(b, ttn_channel(b, src[0], X)));
1566 break;
1567
1568 case TGSI_OPCODE_RCP:
1569 ttn_move_dest(b, dest, nir_frcp(b, ttn_channel(b, src[0], X)));
1570 break;
1571
1572 case TGSI_OPCODE_EX2:
1573 ttn_move_dest(b, dest, nir_fexp2(b, ttn_channel(b, src[0], X)));
1574 break;
1575
1576 case TGSI_OPCODE_LG2:
1577 ttn_move_dest(b, dest, nir_flog2(b, ttn_channel(b, src[0], X)));
1578 break;
1579
1580 case TGSI_OPCODE_POW:
1581 ttn_move_dest(b, dest, nir_fpow(b,
1582 ttn_channel(b, src[0], X),
1583 ttn_channel(b, src[1], X)));
1584 break;
1585
1586 case TGSI_OPCODE_COS:
1587 ttn_move_dest(b, dest, nir_fcos(b, ttn_channel(b, src[0], X)));
1588 break;
1589
1590 case TGSI_OPCODE_SIN:
1591 ttn_move_dest(b, dest, nir_fsin(b, ttn_channel(b, src[0], X)));
1592 break;
1593
1594 case TGSI_OPCODE_ARL:
1595 ttn_arl(b, op_trans[tgsi_op], dest, src);
1596 break;
1597
1598 case TGSI_OPCODE_EXP:
1599 ttn_exp(b, op_trans[tgsi_op], dest, src);
1600 break;
1601
1602 case TGSI_OPCODE_LOG:
1603 ttn_log(b, op_trans[tgsi_op], dest, src);
1604 break;
1605
1606 case TGSI_OPCODE_DST:
1607 ttn_dst(b, op_trans[tgsi_op], dest, src);
1608 break;
1609
1610 case TGSI_OPCODE_LIT:
1611 ttn_lit(b, op_trans[tgsi_op], dest, src);
1612 break;
1613
1614 case TGSI_OPCODE_DP2:
1615 ttn_dp2(b, op_trans[tgsi_op], dest, src);
1616 break;
1617
1618 case TGSI_OPCODE_DP3:
1619 ttn_dp3(b, op_trans[tgsi_op], dest, src);
1620 break;
1621
1622 case TGSI_OPCODE_DP4:
1623 ttn_dp4(b, op_trans[tgsi_op], dest, src);
1624 break;
1625
1626 case TGSI_OPCODE_UMAD:
1627 ttn_umad(b, op_trans[tgsi_op], dest, src);
1628 break;
1629
1630 case TGSI_OPCODE_LRP:
1631 ttn_move_dest(b, dest, nir_flrp(b, src[2], src[1], src[0]));
1632 break;
1633
1634 case TGSI_OPCODE_KILL:
1635 ttn_kill(b, op_trans[tgsi_op], dest, src);
1636 break;
1637
1638 case TGSI_OPCODE_ARR:
1639 ttn_arr(b, op_trans[tgsi_op], dest, src);
1640 break;
1641
1642 case TGSI_OPCODE_CMP:
1643 ttn_cmp(b, op_trans[tgsi_op], dest, src);
1644 break;
1645
1646 case TGSI_OPCODE_UCMP:
1647 ttn_ucmp(b, op_trans[tgsi_op], dest, src);
1648 break;
1649
1650 case TGSI_OPCODE_SGT:
1651 ttn_sgt(b, op_trans[tgsi_op], dest, src);
1652 break;
1653
1654 case TGSI_OPCODE_SLE:
1655 ttn_sle(b, op_trans[tgsi_op], dest, src);
1656 break;
1657
1658 case TGSI_OPCODE_KILL_IF:
1659 ttn_kill_if(b, op_trans[tgsi_op], dest, src);
1660 break;
1661
1662 case TGSI_OPCODE_TEX:
1663 case TGSI_OPCODE_TXP:
1664 case TGSI_OPCODE_TXL:
1665 case TGSI_OPCODE_TXB:
1666 case TGSI_OPCODE_TXD:
1667 case TGSI_OPCODE_TEX2:
1668 case TGSI_OPCODE_TXL2:
1669 case TGSI_OPCODE_TXB2:
1670 case TGSI_OPCODE_TXF:
1671 case TGSI_OPCODE_TG4:
1672 case TGSI_OPCODE_LODQ:
1673 ttn_tex(c, dest, src);
1674 break;
1675
1676 case TGSI_OPCODE_TXQ:
1677 ttn_txq(c, dest, src);
1678 break;
1679
1680 case TGSI_OPCODE_NOP:
1681 break;
1682
1683 case TGSI_OPCODE_IF:
1684 ttn_if(c, src[0], false);
1685 break;
1686
1687 case TGSI_OPCODE_UIF:
1688 ttn_if(c, src[0], true);
1689 break;
1690
1691 case TGSI_OPCODE_ELSE:
1692 ttn_else(c);
1693 break;
1694
1695 case TGSI_OPCODE_ENDIF:
1696 ttn_endif(c);
1697 break;
1698
1699 case TGSI_OPCODE_BGNLOOP:
1700 ttn_bgnloop(c);
1701 break;
1702
1703 case TGSI_OPCODE_BRK:
1704 ttn_brk(b);
1705 break;
1706
1707 case TGSI_OPCODE_CONT:
1708 ttn_cont(b);
1709 break;
1710
1711 case TGSI_OPCODE_ENDLOOP:
1712 ttn_endloop(c);
1713 break;
1714
1715 default:
1716 if (op_trans[tgsi_op] != 0 || tgsi_op == TGSI_OPCODE_MOV) {
1717 ttn_alu(b, op_trans[tgsi_op], dest, src);
1718 } else {
1719 fprintf(stderr, "unknown TGSI opcode: %s\n",
1720 tgsi_get_opcode_name(tgsi_op));
1721 abort();
1722 }
1723 break;
1724 }
1725
1726 if (tgsi_inst->Instruction.Saturate) {
1727 assert(!dest.dest.is_ssa);
1728 ttn_move_dest(b, dest, nir_fsat(b, ttn_src_for_dest(b, &dest)));
1729 }
1730
1731 /* if the dst has a matching var, append store_var to move
1732 * output from reg to var
1733 */
1734 nir_variable *var = ttn_get_var(c, tgsi_dst);
1735 if (var) {
1736 unsigned index = tgsi_dst->Register.Index;
1737 unsigned offset = c->temp_regs[index].offset;
1738 struct tgsi_ind_register *indirect = tgsi_dst->Register.Indirect ?
1739 &tgsi_dst->Indirect : NULL;
1740 nir_src val = nir_src_for_reg(dest.dest.reg.reg);
1741 nir_store_deref(b, ttn_array_deref(c, var, offset, indirect),
1742 nir_ssa_for_src(b, val, 4), dest.write_mask);
1743 }
1744 }
1745
1746 /**
1747 * Puts a NIR intrinsic to store of each TGSI_FILE_OUTPUT value to the output
1748 * variables at the end of the shader.
1749 *
1750 * We don't generate these incrementally as the TGSI_FILE_OUTPUT values are
1751 * written, because there's no output load intrinsic, which means we couldn't
1752 * handle writemasks.
1753 */
1754 static void
1755 ttn_add_output_stores(struct ttn_compile *c)
1756 {
1757 nir_builder *b = &c->build;
1758
1759 for (int i = 0; i < c->build.shader->num_outputs; i++) {
1760 nir_variable *var = c->outputs[i];
1761 if (!var)
1762 continue;
1763
1764 nir_src src = nir_src_for_reg(c->output_regs[i].reg);
1765 src.reg.base_offset = c->output_regs[i].offset;
1766
1767 nir_ssa_def *store_value = nir_ssa_for_src(b, src, 4);
1768 if (c->build.shader->info.stage == MESA_SHADER_FRAGMENT &&
1769 var->data.location == FRAG_RESULT_DEPTH) {
1770 /* TGSI uses TGSI_SEMANTIC_POSITION.z for the depth output, while
1771 * NIR uses a single float FRAG_RESULT_DEPTH.
1772 */
1773 store_value = nir_channel(b, store_value, 2);
1774 }
1775
1776 nir_store_deref(b, nir_build_deref_var(b, var), store_value,
1777 (1 << store_value->num_components) - 1);
1778 }
1779 }
1780
1781 struct nir_shader *
1782 tgsi_to_nir(const void *tgsi_tokens,
1783 const nir_shader_compiler_options *options)
1784 {
1785 struct tgsi_parse_context parser;
1786 struct tgsi_shader_info scan;
1787 struct ttn_compile *c;
1788 struct nir_shader *s;
1789 int ret;
1790
1791 c = rzalloc(NULL, struct ttn_compile);
1792
1793 tgsi_scan_shader(tgsi_tokens, &scan);
1794 c->scan = &scan;
1795
1796 nir_builder_init_simple_shader(&c->build, NULL,
1797 tgsi_processor_to_shader_stage(scan.processor),
1798 options);
1799 s = c->build.shader;
1800
1801 s->num_inputs = scan.file_max[TGSI_FILE_INPUT] + 1;
1802 s->num_uniforms = scan.const_file_max[0] + 1;
1803 s->num_outputs = scan.file_max[TGSI_FILE_OUTPUT] + 1;
1804
1805 c->inputs = rzalloc_array(c, struct nir_variable *, s->num_inputs);
1806 c->outputs = rzalloc_array(c, struct nir_variable *, s->num_outputs);
1807
1808 c->output_regs = rzalloc_array(c, struct ttn_reg_info,
1809 scan.file_max[TGSI_FILE_OUTPUT] + 1);
1810 c->temp_regs = rzalloc_array(c, struct ttn_reg_info,
1811 scan.file_max[TGSI_FILE_TEMPORARY] + 1);
1812 c->imm_defs = rzalloc_array(c, nir_ssa_def *,
1813 scan.file_max[TGSI_FILE_IMMEDIATE] + 1);
1814
1815 c->num_samp_types = scan.file_max[TGSI_FILE_SAMPLER_VIEW] + 1;
1816 c->samp_types = rzalloc_array(c, nir_alu_type, c->num_samp_types);
1817
1818 c->if_stack = rzalloc_array(c, nir_cursor,
1819 (scan.opcode_count[TGSI_OPCODE_IF] +
1820 scan.opcode_count[TGSI_OPCODE_UIF]) * 2);
1821 c->loop_stack = rzalloc_array(c, nir_cursor,
1822 scan.opcode_count[TGSI_OPCODE_BGNLOOP]);
1823
1824 ret = tgsi_parse_init(&parser, tgsi_tokens);
1825 assert(ret == TGSI_PARSE_OK);
1826
1827 while (!tgsi_parse_end_of_tokens(&parser)) {
1828 tgsi_parse_token(&parser);
1829 c->token = &parser.FullToken;
1830
1831 switch (parser.FullToken.Token.Type) {
1832 case TGSI_TOKEN_TYPE_DECLARATION:
1833 ttn_emit_declaration(c);
1834 break;
1835
1836 case TGSI_TOKEN_TYPE_INSTRUCTION:
1837 ttn_emit_instruction(c);
1838 break;
1839
1840 case TGSI_TOKEN_TYPE_IMMEDIATE:
1841 ttn_emit_immediate(c);
1842 break;
1843 }
1844 }
1845
1846 tgsi_parse_free(&parser);
1847
1848 ttn_add_output_stores(c);
1849
1850 ralloc_free(c);
1851 return s;
1852 }