Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
PojavLauncherTeam
GitHub Repository: PojavLauncherTeam/mesa
Path: blob/21.2-virgl/src/gallium/auxiliary/nir/tgsi_to_nir.c
4561 views
1
/*
2
* Copyright © 2014-2015 Broadcom
3
* Copyright (C) 2014 Rob Clark <[email protected]>
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/blob.h"
26
#include "util/disk_cache.h"
27
#include "util/u_memory.h"
28
#include "util/ralloc.h"
29
#include "pipe/p_screen.h"
30
31
#include "compiler/nir/nir.h"
32
#include "compiler/nir/nir_control_flow.h"
33
#include "compiler/nir/nir_builder.h"
34
#include "compiler/nir/nir_serialize.h"
35
#include "compiler/shader_enums.h"
36
37
#include "tgsi_to_nir.h"
38
#include "tgsi/tgsi_parse.h"
39
#include "tgsi/tgsi_dump.h"
40
#include "tgsi/tgsi_info.h"
41
#include "tgsi/tgsi_scan.h"
42
#include "tgsi/tgsi_from_mesa.h"
43
44
#define SWIZ(X, Y, Z, W) (unsigned[4]){ \
45
TGSI_SWIZZLE_##X, \
46
TGSI_SWIZZLE_##Y, \
47
TGSI_SWIZZLE_##Z, \
48
TGSI_SWIZZLE_##W, \
49
}
50
51
struct ttn_reg_info {
52
/** nir register containing this TGSI index. */
53
nir_register *reg;
54
nir_variable *var;
55
/** Offset (in vec4s) from the start of var for this TGSI index. */
56
int offset;
57
};
58
59
struct ttn_compile {
60
union tgsi_full_token *token;
61
nir_builder build;
62
struct tgsi_shader_info *scan;
63
64
struct ttn_reg_info *output_regs;
65
struct ttn_reg_info *temp_regs;
66
nir_ssa_def **imm_defs;
67
68
unsigned num_samp_types;
69
nir_alu_type *samp_types;
70
71
nir_register *addr_reg;
72
73
nir_variable **inputs;
74
nir_variable **outputs;
75
nir_variable *samplers[PIPE_MAX_SAMPLERS];
76
nir_variable *images[PIPE_MAX_SHADER_IMAGES];
77
nir_variable *ssbo[PIPE_MAX_SHADER_BUFFERS];
78
uint32_t ubo_sizes[PIPE_MAX_CONSTANT_BUFFERS];
79
80
unsigned num_samplers;
81
unsigned num_images;
82
unsigned num_msaa_images;
83
84
nir_variable *input_var_face;
85
nir_variable *input_var_position;
86
nir_variable *input_var_point;
87
88
/* How many TGSI_FILE_IMMEDIATE vec4s have been parsed so far. */
89
unsigned next_imm;
90
91
bool cap_face_is_sysval;
92
bool cap_position_is_sysval;
93
bool cap_point_is_sysval;
94
bool cap_samplers_as_deref;
95
};
96
97
#define ttn_swizzle(b, src, x, y, z, w) \
98
nir_swizzle(b, src, SWIZ(x, y, z, w), 4)
99
#define ttn_channel(b, src, swiz) \
100
nir_channel(b, src, TGSI_SWIZZLE_##swiz)
101
102
gl_varying_slot
103
tgsi_varying_semantic_to_slot(unsigned semantic, unsigned index)
104
{
105
switch (semantic) {
106
case TGSI_SEMANTIC_POSITION:
107
return VARYING_SLOT_POS;
108
case TGSI_SEMANTIC_COLOR:
109
if (index == 0)
110
return VARYING_SLOT_COL0;
111
else
112
return VARYING_SLOT_COL1;
113
case TGSI_SEMANTIC_BCOLOR:
114
if (index == 0)
115
return VARYING_SLOT_BFC0;
116
else
117
return VARYING_SLOT_BFC1;
118
case TGSI_SEMANTIC_FOG:
119
return VARYING_SLOT_FOGC;
120
case TGSI_SEMANTIC_PSIZE:
121
return VARYING_SLOT_PSIZ;
122
case TGSI_SEMANTIC_GENERIC:
123
assert(index < 32);
124
return VARYING_SLOT_VAR0 + index;
125
case TGSI_SEMANTIC_FACE:
126
return VARYING_SLOT_FACE;
127
case TGSI_SEMANTIC_EDGEFLAG:
128
return VARYING_SLOT_EDGE;
129
case TGSI_SEMANTIC_PRIMID:
130
return VARYING_SLOT_PRIMITIVE_ID;
131
case TGSI_SEMANTIC_CLIPDIST:
132
if (index == 0)
133
return VARYING_SLOT_CLIP_DIST0;
134
else
135
return VARYING_SLOT_CLIP_DIST1;
136
case TGSI_SEMANTIC_CLIPVERTEX:
137
return VARYING_SLOT_CLIP_VERTEX;
138
case TGSI_SEMANTIC_TEXCOORD:
139
assert(index < 8);
140
return VARYING_SLOT_TEX0 + index;
141
case TGSI_SEMANTIC_PCOORD:
142
return VARYING_SLOT_PNTC;
143
case TGSI_SEMANTIC_VIEWPORT_INDEX:
144
return VARYING_SLOT_VIEWPORT;
145
case TGSI_SEMANTIC_LAYER:
146
return VARYING_SLOT_LAYER;
147
case TGSI_SEMANTIC_TESSINNER:
148
return VARYING_SLOT_TESS_LEVEL_INNER;
149
case TGSI_SEMANTIC_TESSOUTER:
150
return VARYING_SLOT_TESS_LEVEL_OUTER;
151
default:
152
fprintf(stderr, "Bad TGSI semantic: %d/%d\n", semantic, index);
153
abort();
154
}
155
}
156
157
static enum gl_frag_depth_layout
158
ttn_get_depth_layout(unsigned tgsi_fs_depth_layout)
159
{
160
switch (tgsi_fs_depth_layout) {
161
case TGSI_FS_DEPTH_LAYOUT_NONE:
162
return FRAG_DEPTH_LAYOUT_NONE;
163
case TGSI_FS_DEPTH_LAYOUT_ANY:
164
return FRAG_DEPTH_LAYOUT_ANY;
165
case TGSI_FS_DEPTH_LAYOUT_GREATER:
166
return FRAG_DEPTH_LAYOUT_GREATER;
167
case TGSI_FS_DEPTH_LAYOUT_LESS:
168
return FRAG_DEPTH_LAYOUT_LESS;
169
case TGSI_FS_DEPTH_LAYOUT_UNCHANGED:
170
return FRAG_DEPTH_LAYOUT_UNCHANGED;
171
default:
172
unreachable("bad TGSI FS depth layout");
173
}
174
}
175
176
static nir_ssa_def *
177
ttn_src_for_dest(nir_builder *b, nir_alu_dest *dest)
178
{
179
nir_alu_src src;
180
memset(&src, 0, sizeof(src));
181
182
if (dest->dest.is_ssa)
183
src.src = nir_src_for_ssa(&dest->dest.ssa);
184
else {
185
assert(!dest->dest.reg.indirect);
186
src.src = nir_src_for_reg(dest->dest.reg.reg);
187
src.src.reg.base_offset = dest->dest.reg.base_offset;
188
}
189
190
for (int i = 0; i < 4; i++)
191
src.swizzle[i] = i;
192
193
return nir_mov_alu(b, src, 4);
194
}
195
196
static enum glsl_interp_mode
197
ttn_translate_interp_mode(unsigned tgsi_interp)
198
{
199
switch (tgsi_interp) {
200
case TGSI_INTERPOLATE_CONSTANT:
201
return INTERP_MODE_FLAT;
202
case TGSI_INTERPOLATE_LINEAR:
203
return INTERP_MODE_NOPERSPECTIVE;
204
case TGSI_INTERPOLATE_PERSPECTIVE:
205
return INTERP_MODE_SMOOTH;
206
case TGSI_INTERPOLATE_COLOR:
207
return INTERP_MODE_NONE;
208
default:
209
unreachable("bad TGSI interpolation mode");
210
}
211
}
212
213
static void
214
ttn_emit_declaration(struct ttn_compile *c)
215
{
216
nir_builder *b = &c->build;
217
struct tgsi_full_declaration *decl = &c->token->FullDeclaration;
218
unsigned array_size = decl->Range.Last - decl->Range.First + 1;
219
unsigned file = decl->Declaration.File;
220
unsigned i;
221
222
if (file == TGSI_FILE_TEMPORARY) {
223
if (decl->Declaration.Array) {
224
/* for arrays, we create variables instead of registers: */
225
nir_variable *var =
226
nir_variable_create(b->shader, nir_var_shader_temp,
227
glsl_array_type(glsl_vec4_type(), array_size, 0),
228
ralloc_asprintf(b->shader, "arr_%d",
229
decl->Array.ArrayID));
230
231
for (i = 0; i < array_size; i++) {
232
/* point all the matching slots to the same var,
233
* with appropriate offset set, mostly just so
234
* we know what to do when tgsi does a non-indirect
235
* access
236
*/
237
c->temp_regs[decl->Range.First + i].reg = NULL;
238
c->temp_regs[decl->Range.First + i].var = var;
239
c->temp_regs[decl->Range.First + i].offset = i;
240
}
241
} else {
242
for (i = 0; i < array_size; i++) {
243
nir_register *reg = nir_local_reg_create(b->impl);
244
reg->num_components = 4;
245
c->temp_regs[decl->Range.First + i].reg = reg;
246
c->temp_regs[decl->Range.First + i].var = NULL;
247
c->temp_regs[decl->Range.First + i].offset = 0;
248
}
249
}
250
} else if (file == TGSI_FILE_ADDRESS) {
251
c->addr_reg = nir_local_reg_create(b->impl);
252
c->addr_reg->num_components = 4;
253
} else if (file == TGSI_FILE_SYSTEM_VALUE) {
254
/* Nothing to record for system values. */
255
} else if (file == TGSI_FILE_BUFFER) {
256
/* Nothing to record for buffers. */
257
} else if (file == TGSI_FILE_IMAGE) {
258
/* Nothing to record for images. */
259
} else if (file == TGSI_FILE_SAMPLER) {
260
/* Nothing to record for samplers. */
261
} else if (file == TGSI_FILE_SAMPLER_VIEW) {
262
struct tgsi_declaration_sampler_view *sview = &decl->SamplerView;
263
nir_alu_type type;
264
265
assert((sview->ReturnTypeX == sview->ReturnTypeY) &&
266
(sview->ReturnTypeX == sview->ReturnTypeZ) &&
267
(sview->ReturnTypeX == sview->ReturnTypeW));
268
269
switch (sview->ReturnTypeX) {
270
case TGSI_RETURN_TYPE_SINT:
271
type = nir_type_int32;
272
break;
273
case TGSI_RETURN_TYPE_UINT:
274
type = nir_type_uint32;
275
break;
276
case TGSI_RETURN_TYPE_FLOAT:
277
default:
278
type = nir_type_float32;
279
break;
280
}
281
282
for (i = 0; i < array_size; i++) {
283
c->samp_types[decl->Range.First + i] = type;
284
}
285
} else {
286
bool is_array = (array_size > 1);
287
288
assert(file == TGSI_FILE_INPUT ||
289
file == TGSI_FILE_OUTPUT ||
290
file == TGSI_FILE_CONSTANT);
291
292
/* nothing to do for UBOs: */
293
if ((file == TGSI_FILE_CONSTANT) && decl->Declaration.Dimension &&
294
decl->Dim.Index2D != 0) {
295
b->shader->info.num_ubos =
296
MAX2(b->shader->info.num_ubos, decl->Dim.Index2D);
297
c->ubo_sizes[decl->Dim.Index2D] =
298
MAX2(c->ubo_sizes[decl->Dim.Index2D], decl->Range.Last * 16);
299
return;
300
}
301
302
if ((file == TGSI_FILE_INPUT) || (file == TGSI_FILE_OUTPUT)) {
303
is_array = (is_array && decl->Declaration.Array &&
304
(decl->Array.ArrayID != 0));
305
}
306
307
for (i = 0; i < array_size; i++) {
308
unsigned idx = decl->Range.First + i;
309
nir_variable *var = rzalloc(b->shader, nir_variable);
310
311
var->data.driver_location = idx;
312
313
var->type = glsl_vec4_type();
314
if (is_array)
315
var->type = glsl_array_type(var->type, array_size, 0);
316
317
switch (file) {
318
case TGSI_FILE_INPUT:
319
var->data.read_only = true;
320
var->data.mode = nir_var_shader_in;
321
var->name = ralloc_asprintf(var, "in_%d", idx);
322
323
if (c->scan->processor == PIPE_SHADER_FRAGMENT) {
324
if (decl->Semantic.Name == TGSI_SEMANTIC_FACE) {
325
var->type = glsl_bool_type();
326
if (c->cap_face_is_sysval) {
327
var->data.mode = nir_var_system_value;
328
var->data.location = SYSTEM_VALUE_FRONT_FACE;
329
} else {
330
var->data.location = VARYING_SLOT_FACE;
331
}
332
c->input_var_face = var;
333
} else if (decl->Semantic.Name == TGSI_SEMANTIC_POSITION) {
334
if (c->cap_position_is_sysval) {
335
var->data.mode = nir_var_system_value;
336
var->data.location = SYSTEM_VALUE_FRAG_COORD;
337
} else {
338
var->data.location = VARYING_SLOT_POS;
339
}
340
c->input_var_position = var;
341
} else if (decl->Semantic.Name == TGSI_SEMANTIC_PCOORD) {
342
if (c->cap_point_is_sysval) {
343
var->data.mode = nir_var_system_value;
344
var->data.location = SYSTEM_VALUE_POINT_COORD;
345
} else {
346
var->data.location = VARYING_SLOT_PNTC;
347
}
348
c->input_var_point = var;
349
} else {
350
var->data.location =
351
tgsi_varying_semantic_to_slot(decl->Semantic.Name,
352
decl->Semantic.Index);
353
}
354
} else {
355
assert(!decl->Declaration.Semantic);
356
var->data.location = VERT_ATTRIB_GENERIC0 + idx;
357
}
358
var->data.index = 0;
359
var->data.interpolation =
360
ttn_translate_interp_mode(decl->Interp.Interpolate);
361
362
c->inputs[idx] = var;
363
364
for (int i = 0; i < array_size; i++)
365
b->shader->info.inputs_read |= 1ull << (var->data.location + i);
366
367
break;
368
case TGSI_FILE_OUTPUT: {
369
int semantic_name = decl->Semantic.Name;
370
int semantic_index = decl->Semantic.Index;
371
/* Since we can't load from outputs in the IR, we make temporaries
372
* for the outputs and emit stores to the real outputs at the end of
373
* the shader.
374
*/
375
nir_register *reg = nir_local_reg_create(b->impl);
376
reg->num_components = 4;
377
if (is_array)
378
reg->num_array_elems = array_size;
379
380
var->data.mode = nir_var_shader_out;
381
var->name = ralloc_asprintf(var, "out_%d", idx);
382
var->data.index = 0;
383
var->data.interpolation =
384
ttn_translate_interp_mode(decl->Interp.Interpolate);
385
var->data.patch = semantic_name == TGSI_SEMANTIC_TESSINNER ||
386
semantic_name == TGSI_SEMANTIC_TESSOUTER ||
387
semantic_name == TGSI_SEMANTIC_PATCH;
388
389
if (c->scan->processor == PIPE_SHADER_FRAGMENT) {
390
switch (semantic_name) {
391
case TGSI_SEMANTIC_COLOR: {
392
/* TODO tgsi loses some information, so we cannot
393
* actually differentiate here between DSB and MRT
394
* at this point. But so far no drivers using tgsi-
395
* to-nir support dual source blend:
396
*/
397
bool dual_src_blend = false;
398
if (dual_src_blend && (semantic_index == 1)) {
399
var->data.location = FRAG_RESULT_DATA0;
400
var->data.index = 1;
401
} else {
402
if (c->scan->properties[TGSI_PROPERTY_FS_COLOR0_WRITES_ALL_CBUFS])
403
var->data.location = FRAG_RESULT_COLOR;
404
else
405
var->data.location = FRAG_RESULT_DATA0 + semantic_index;
406
}
407
break;
408
}
409
case TGSI_SEMANTIC_POSITION:
410
var->data.location = FRAG_RESULT_DEPTH;
411
var->type = glsl_float_type();
412
break;
413
case TGSI_SEMANTIC_STENCIL:
414
var->data.location = FRAG_RESULT_STENCIL;
415
var->type = glsl_int_type();
416
break;
417
case TGSI_SEMANTIC_SAMPLEMASK:
418
var->data.location = FRAG_RESULT_SAMPLE_MASK;
419
var->type = glsl_int_type();
420
break;
421
422
default:
423
fprintf(stderr, "Bad TGSI semantic: %d/%d\n",
424
decl->Semantic.Name, decl->Semantic.Index);
425
abort();
426
}
427
} else {
428
var->data.location =
429
tgsi_varying_semantic_to_slot(semantic_name, semantic_index);
430
if (var->data.location == VARYING_SLOT_FOGC ||
431
var->data.location == VARYING_SLOT_PSIZ) {
432
var->type = glsl_float_type();
433
}
434
}
435
436
if (is_array) {
437
unsigned j;
438
for (j = 0; j < array_size; j++) {
439
c->output_regs[idx + j].offset = i + j;
440
c->output_regs[idx + j].reg = reg;
441
}
442
} else {
443
c->output_regs[idx].offset = i;
444
c->output_regs[idx].reg = reg;
445
}
446
447
c->outputs[idx] = var;
448
449
for (int i = 0; i < array_size; i++)
450
b->shader->info.outputs_written |= 1ull << (var->data.location + i);
451
}
452
break;
453
case TGSI_FILE_CONSTANT:
454
var->data.mode = nir_var_uniform;
455
var->name = ralloc_asprintf(var, "uniform_%d", idx);
456
var->data.location = idx;
457
break;
458
default:
459
unreachable("bad declaration file");
460
return;
461
}
462
463
nir_shader_add_variable(b->shader, var);
464
465
if (is_array)
466
break;
467
}
468
469
}
470
}
471
472
static void
473
ttn_emit_immediate(struct ttn_compile *c)
474
{
475
nir_builder *b = &c->build;
476
struct tgsi_full_immediate *tgsi_imm = &c->token->FullImmediate;
477
nir_load_const_instr *load_const;
478
int i;
479
480
load_const = nir_load_const_instr_create(b->shader, 4, 32);
481
c->imm_defs[c->next_imm] = &load_const->def;
482
c->next_imm++;
483
484
for (i = 0; i < load_const->def.num_components; i++)
485
load_const->value[i].u32 = tgsi_imm->u[i].Uint;
486
487
nir_builder_instr_insert(b, &load_const->instr);
488
}
489
490
static nir_ssa_def *
491
ttn_src_for_indirect(struct ttn_compile *c, struct tgsi_ind_register *indirect);
492
493
/* generate either a constant or indirect deref chain for accessing an
494
* array variable.
495
*/
496
static nir_deref_instr *
497
ttn_array_deref(struct ttn_compile *c, nir_variable *var, unsigned offset,
498
struct tgsi_ind_register *indirect)
499
{
500
nir_deref_instr *deref = nir_build_deref_var(&c->build, var);
501
nir_ssa_def *index = nir_imm_int(&c->build, offset);
502
if (indirect)
503
index = nir_iadd(&c->build, index, ttn_src_for_indirect(c, indirect));
504
return nir_build_deref_array(&c->build, deref, index);
505
}
506
507
/* Special case: Turn the frontface varying into a load of the
508
* frontface variable, and create the vector as required by TGSI.
509
*/
510
static nir_ssa_def *
511
ttn_emulate_tgsi_front_face(struct ttn_compile *c)
512
{
513
nir_ssa_def *tgsi_frontface[4];
514
515
if (c->cap_face_is_sysval) {
516
/* When it's a system value, it should be an integer vector: (F, 0, 0, 1)
517
* F is 0xffffffff if front-facing, 0 if not.
518
*/
519
520
nir_ssa_def *frontface = nir_load_front_face(&c->build, 1);
521
522
tgsi_frontface[0] = nir_bcsel(&c->build,
523
frontface,
524
nir_imm_int(&c->build, 0xffffffff),
525
nir_imm_int(&c->build, 0));
526
tgsi_frontface[1] = nir_imm_int(&c->build, 0);
527
tgsi_frontface[2] = nir_imm_int(&c->build, 0);
528
tgsi_frontface[3] = nir_imm_int(&c->build, 1);
529
} else {
530
/* When it's an input, it should be a float vector: (F, 0.0, 0.0, 1.0)
531
* F is positive if front-facing, negative if not.
532
*/
533
534
assert(c->input_var_face);
535
nir_ssa_def *frontface = nir_load_var(&c->build, c->input_var_face);
536
537
tgsi_frontface[0] = nir_bcsel(&c->build,
538
frontface,
539
nir_imm_float(&c->build, 1.0),
540
nir_imm_float(&c->build, -1.0));
541
tgsi_frontface[1] = nir_imm_float(&c->build, 0.0);
542
tgsi_frontface[2] = nir_imm_float(&c->build, 0.0);
543
tgsi_frontface[3] = nir_imm_float(&c->build, 1.0);
544
}
545
546
return nir_vec(&c->build, tgsi_frontface, 4);
547
}
548
549
static nir_src
550
ttn_src_for_file_and_index(struct ttn_compile *c, unsigned file, unsigned index,
551
struct tgsi_ind_register *indirect,
552
struct tgsi_dimension *dim,
553
struct tgsi_ind_register *dimind,
554
bool src_is_float)
555
{
556
nir_builder *b = &c->build;
557
nir_src src;
558
559
memset(&src, 0, sizeof(src));
560
561
switch (file) {
562
case TGSI_FILE_TEMPORARY:
563
if (c->temp_regs[index].var) {
564
unsigned offset = c->temp_regs[index].offset;
565
nir_variable *var = c->temp_regs[index].var;
566
nir_ssa_def *load = nir_load_deref(&c->build,
567
ttn_array_deref(c, var, offset, indirect));
568
569
src = nir_src_for_ssa(load);
570
} else {
571
assert(!indirect);
572
src.reg.reg = c->temp_regs[index].reg;
573
}
574
assert(!dim);
575
break;
576
577
case TGSI_FILE_ADDRESS:
578
src.reg.reg = c->addr_reg;
579
assert(!dim);
580
break;
581
582
case TGSI_FILE_IMMEDIATE:
583
src = nir_src_for_ssa(c->imm_defs[index]);
584
assert(!indirect);
585
assert(!dim);
586
break;
587
588
case TGSI_FILE_SYSTEM_VALUE: {
589
nir_ssa_def *load;
590
591
assert(!indirect);
592
assert(!dim);
593
594
switch (c->scan->system_value_semantic_name[index]) {
595
case TGSI_SEMANTIC_VERTEXID_NOBASE:
596
load = nir_load_vertex_id_zero_base(b);
597
break;
598
case TGSI_SEMANTIC_VERTEXID:
599
load = nir_load_vertex_id(b);
600
break;
601
case TGSI_SEMANTIC_BASEVERTEX:
602
load = nir_load_base_vertex(b);
603
break;
604
case TGSI_SEMANTIC_INSTANCEID:
605
load = nir_load_instance_id(b);
606
break;
607
case TGSI_SEMANTIC_FACE:
608
assert(c->cap_face_is_sysval);
609
load = ttn_emulate_tgsi_front_face(c);
610
break;
611
case TGSI_SEMANTIC_POSITION:
612
assert(c->cap_position_is_sysval);
613
load = nir_load_frag_coord(b);
614
break;
615
case TGSI_SEMANTIC_PCOORD:
616
assert(c->cap_point_is_sysval);
617
load = nir_load_point_coord(b);
618
break;
619
case TGSI_SEMANTIC_THREAD_ID:
620
load = nir_load_local_invocation_id(b);
621
break;
622
case TGSI_SEMANTIC_BLOCK_ID:
623
load = nir_load_workgroup_id(b, 32);
624
break;
625
case TGSI_SEMANTIC_BLOCK_SIZE:
626
load = nir_load_workgroup_size(b);
627
break;
628
case TGSI_SEMANTIC_CS_USER_DATA_AMD:
629
load = nir_load_user_data_amd(b);
630
break;
631
case TGSI_SEMANTIC_TESS_DEFAULT_INNER_LEVEL:
632
load = nir_load_tess_level_inner_default(b);
633
break;
634
case TGSI_SEMANTIC_TESS_DEFAULT_OUTER_LEVEL:
635
load = nir_load_tess_level_outer_default(b);
636
break;
637
case TGSI_SEMANTIC_SAMPLEID:
638
load = nir_load_sample_id(b);
639
break;
640
default:
641
unreachable("bad system value");
642
}
643
644
if (load->num_components == 2)
645
load = nir_swizzle(b, load, SWIZ(X, Y, Y, Y), 4);
646
else if (load->num_components == 3)
647
load = nir_swizzle(b, load, SWIZ(X, Y, Z, Z), 4);
648
649
src = nir_src_for_ssa(load);
650
break;
651
}
652
653
case TGSI_FILE_INPUT:
654
if (c->scan->processor == PIPE_SHADER_FRAGMENT &&
655
c->scan->input_semantic_name[index] == TGSI_SEMANTIC_FACE) {
656
assert(!c->cap_face_is_sysval && c->input_var_face);
657
return nir_src_for_ssa(ttn_emulate_tgsi_front_face(c));
658
} else if (c->scan->processor == PIPE_SHADER_FRAGMENT &&
659
c->scan->input_semantic_name[index] == TGSI_SEMANTIC_POSITION) {
660
assert(!c->cap_position_is_sysval && c->input_var_position);
661
return nir_src_for_ssa(nir_load_var(&c->build, c->input_var_position));
662
} else if (c->scan->processor == PIPE_SHADER_FRAGMENT &&
663
c->scan->input_semantic_name[index] == TGSI_SEMANTIC_PCOORD) {
664
assert(!c->cap_point_is_sysval && c->input_var_point);
665
return nir_src_for_ssa(nir_load_var(&c->build, c->input_var_point));
666
} else {
667
/* Indirection on input arrays isn't supported by TTN. */
668
assert(!dim);
669
nir_deref_instr *deref = nir_build_deref_var(&c->build,
670
c->inputs[index]);
671
return nir_src_for_ssa(nir_load_deref(&c->build, deref));
672
}
673
break;
674
675
case TGSI_FILE_OUTPUT:
676
if (c->scan->processor == PIPE_SHADER_FRAGMENT) {
677
c->outputs[index]->data.fb_fetch_output = 1;
678
nir_deref_instr *deref = nir_build_deref_var(&c->build,
679
c->outputs[index]);
680
return nir_src_for_ssa(nir_load_deref(&c->build, deref));
681
}
682
unreachable("unsupported output read");
683
break;
684
685
case TGSI_FILE_CONSTANT: {
686
nir_intrinsic_instr *load;
687
nir_intrinsic_op op;
688
unsigned srcn = 0;
689
690
if (dim && (dim->Index > 0 || dim->Indirect)) {
691
op = nir_intrinsic_load_ubo;
692
} else {
693
op = nir_intrinsic_load_uniform;
694
}
695
696
load = nir_intrinsic_instr_create(b->shader, op);
697
if (op == nir_intrinsic_load_uniform) {
698
nir_intrinsic_set_dest_type(load, src_is_float ? nir_type_float :
699
nir_type_int);
700
}
701
702
load->num_components = 4;
703
if (dim && (dim->Index > 0 || dim->Indirect)) {
704
if (dimind) {
705
load->src[srcn] =
706
ttn_src_for_file_and_index(c, dimind->File, dimind->Index,
707
NULL, NULL, NULL, false);
708
} else {
709
/* UBOs start at index 1 in TGSI: */
710
load->src[srcn] =
711
nir_src_for_ssa(nir_imm_int(b, dim->Index - 1));
712
}
713
srcn++;
714
}
715
716
nir_ssa_def *offset;
717
if (op == nir_intrinsic_load_ubo) {
718
/* UBO loads don't have a base offset. */
719
offset = nir_imm_int(b, index);
720
if (indirect) {
721
offset = nir_iadd(b, offset, ttn_src_for_indirect(c, indirect));
722
}
723
/* UBO offsets are in bytes, but TGSI gives them to us in vec4's */
724
offset = nir_ishl(b, offset, nir_imm_int(b, 4));
725
nir_intrinsic_set_align(load, 16, 0);
726
727
/* Set a very conservative base/range of the access: 16 bytes if not
728
* indirect at all, offset to the end of the UBO if the offset is
729
* indirect, and totally unknown if the block number is indirect.
730
*/
731
uint32_t base = index * 16;
732
nir_intrinsic_set_range_base(load, base);
733
if (dimind)
734
nir_intrinsic_set_range(load, ~0);
735
else if (indirect)
736
nir_intrinsic_set_range(load, c->ubo_sizes[dim->Index] - base);
737
else
738
nir_intrinsic_set_range(load, base + 16);
739
} else {
740
nir_intrinsic_set_base(load, index);
741
if (indirect) {
742
offset = ttn_src_for_indirect(c, indirect);
743
nir_intrinsic_set_range(load, c->build.shader->num_uniforms * 16 - index);
744
} else {
745
offset = nir_imm_int(b, 0);
746
nir_intrinsic_set_range(load, 1);
747
}
748
}
749
load->src[srcn++] = nir_src_for_ssa(offset);
750
751
nir_ssa_dest_init(&load->instr, &load->dest, 4, 32, NULL);
752
nir_builder_instr_insert(b, &load->instr);
753
754
src = nir_src_for_ssa(&load->dest.ssa);
755
break;
756
}
757
758
default:
759
unreachable("bad src file");
760
}
761
762
763
return src;
764
}
765
766
static nir_ssa_def *
767
ttn_src_for_indirect(struct ttn_compile *c, struct tgsi_ind_register *indirect)
768
{
769
nir_builder *b = &c->build;
770
nir_alu_src src;
771
memset(&src, 0, sizeof(src));
772
for (int i = 0; i < 4; i++)
773
src.swizzle[i] = indirect->Swizzle;
774
src.src = ttn_src_for_file_and_index(c,
775
indirect->File,
776
indirect->Index,
777
NULL, NULL, NULL,
778
false);
779
return nir_mov_alu(b, src, 1);
780
}
781
782
static nir_alu_dest
783
ttn_get_dest(struct ttn_compile *c, struct tgsi_full_dst_register *tgsi_fdst)
784
{
785
struct tgsi_dst_register *tgsi_dst = &tgsi_fdst->Register;
786
nir_alu_dest dest;
787
unsigned index = tgsi_dst->Index;
788
789
memset(&dest, 0, sizeof(dest));
790
791
if (tgsi_dst->File == TGSI_FILE_TEMPORARY) {
792
if (c->temp_regs[index].var) {
793
nir_register *reg;
794
795
/* this works, because TGSI will give us a base offset
796
* (in case of indirect index) that points back into
797
* the array. Access can be direct or indirect, we
798
* don't really care. Just create a one-shot dst reg
799
* that will get store_var'd back into the array var
800
* at the end of ttn_emit_instruction()
801
*/
802
reg = nir_local_reg_create(c->build.impl);
803
reg->num_components = 4;
804
dest.dest.reg.reg = reg;
805
dest.dest.reg.base_offset = 0;
806
} else {
807
assert(!tgsi_dst->Indirect);
808
dest.dest.reg.reg = c->temp_regs[index].reg;
809
dest.dest.reg.base_offset = c->temp_regs[index].offset;
810
}
811
} else if (tgsi_dst->File == TGSI_FILE_OUTPUT) {
812
dest.dest.reg.reg = c->output_regs[index].reg;
813
dest.dest.reg.base_offset = c->output_regs[index].offset;
814
} else if (tgsi_dst->File == TGSI_FILE_ADDRESS) {
815
assert(index == 0);
816
dest.dest.reg.reg = c->addr_reg;
817
}
818
819
dest.write_mask = tgsi_dst->WriteMask;
820
dest.saturate = false;
821
822
if (tgsi_dst->Indirect && (tgsi_dst->File != TGSI_FILE_TEMPORARY)) {
823
nir_src *indirect = ralloc(c->build.shader, nir_src);
824
*indirect = nir_src_for_ssa(ttn_src_for_indirect(c, &tgsi_fdst->Indirect));
825
dest.dest.reg.indirect = indirect;
826
}
827
828
return dest;
829
}
830
831
static nir_variable *
832
ttn_get_var(struct ttn_compile *c, struct tgsi_full_dst_register *tgsi_fdst)
833
{
834
struct tgsi_dst_register *tgsi_dst = &tgsi_fdst->Register;
835
unsigned index = tgsi_dst->Index;
836
837
if (tgsi_dst->File == TGSI_FILE_TEMPORARY) {
838
/* we should not have an indirect when there is no var! */
839
if (!c->temp_regs[index].var)
840
assert(!tgsi_dst->Indirect);
841
return c->temp_regs[index].var;
842
}
843
844
return NULL;
845
}
846
847
static nir_ssa_def *
848
ttn_get_src(struct ttn_compile *c, struct tgsi_full_src_register *tgsi_fsrc,
849
int src_idx)
850
{
851
nir_builder *b = &c->build;
852
struct tgsi_src_register *tgsi_src = &tgsi_fsrc->Register;
853
enum tgsi_opcode opcode = c->token->FullInstruction.Instruction.Opcode;
854
unsigned tgsi_src_type = tgsi_opcode_infer_src_type(opcode, src_idx);
855
bool src_is_float = (tgsi_src_type == TGSI_TYPE_FLOAT ||
856
tgsi_src_type == TGSI_TYPE_DOUBLE ||
857
tgsi_src_type == TGSI_TYPE_UNTYPED);
858
nir_alu_src src;
859
860
memset(&src, 0, sizeof(src));
861
862
if (tgsi_src->File == TGSI_FILE_NULL) {
863
return nir_imm_float(b, 0.0);
864
} else if (tgsi_src->File == TGSI_FILE_SAMPLER ||
865
tgsi_src->File == TGSI_FILE_IMAGE ||
866
tgsi_src->File == TGSI_FILE_BUFFER) {
867
/* Only the index of the resource gets used in texturing, and it will
868
* handle looking that up on its own instead of using the nir_alu_src.
869
*/
870
assert(!tgsi_src->Indirect);
871
return NULL;
872
} else {
873
struct tgsi_ind_register *ind = NULL;
874
struct tgsi_dimension *dim = NULL;
875
struct tgsi_ind_register *dimind = NULL;
876
if (tgsi_src->Indirect)
877
ind = &tgsi_fsrc->Indirect;
878
if (tgsi_src->Dimension) {
879
dim = &tgsi_fsrc->Dimension;
880
if (dim->Indirect)
881
dimind = &tgsi_fsrc->DimIndirect;
882
}
883
src.src = ttn_src_for_file_and_index(c,
884
tgsi_src->File,
885
tgsi_src->Index,
886
ind, dim, dimind,
887
src_is_float);
888
}
889
890
src.swizzle[0] = tgsi_src->SwizzleX;
891
src.swizzle[1] = tgsi_src->SwizzleY;
892
src.swizzle[2] = tgsi_src->SwizzleZ;
893
src.swizzle[3] = tgsi_src->SwizzleW;
894
895
nir_ssa_def *def = nir_mov_alu(b, src, 4);
896
897
if (tgsi_type_is_64bit(tgsi_src_type))
898
def = nir_bitcast_vector(b, def, 64);
899
900
if (tgsi_src->Absolute) {
901
assert(src_is_float);
902
def = nir_fabs(b, def);
903
}
904
905
if (tgsi_src->Negate) {
906
if (src_is_float)
907
def = nir_fneg(b, def);
908
else
909
def = nir_ineg(b, def);
910
}
911
912
return def;
913
}
914
915
static void
916
ttn_move_dest_masked(nir_builder *b, nir_alu_dest dest,
917
nir_ssa_def *def, unsigned write_mask)
918
{
919
if (!(dest.write_mask & write_mask))
920
return;
921
922
nir_alu_instr *mov = nir_alu_instr_create(b->shader, nir_op_mov);
923
mov->dest = dest;
924
mov->dest.write_mask &= write_mask;
925
mov->src[0].src = nir_src_for_ssa(def);
926
for (unsigned i = def->num_components; i < 4; i++)
927
mov->src[0].swizzle[i] = def->num_components - 1;
928
nir_builder_instr_insert(b, &mov->instr);
929
}
930
931
static void
932
ttn_move_dest(nir_builder *b, nir_alu_dest dest, nir_ssa_def *def)
933
{
934
ttn_move_dest_masked(b, dest, def, TGSI_WRITEMASK_XYZW);
935
}
936
937
static void
938
ttn_alu(nir_builder *b, nir_op op, nir_alu_dest dest, unsigned dest_bitsize,
939
nir_ssa_def **src)
940
{
941
nir_ssa_def *def = nir_build_alu_src_arr(b, op, src);
942
if (def->bit_size == 1)
943
def = nir_ineg(b, nir_b2i(b, def, dest_bitsize));
944
assert(def->bit_size == dest_bitsize);
945
if (dest_bitsize == 64) {
946
if (def->num_components > 2) {
947
/* 32 -> 64 bit conversion ops are supposed to only convert the first
948
* two components, and we need to truncate here to avoid creating a
949
* vec8 after bitcasting the destination.
950
*/
951
def = nir_channels(b, def, 0x3);
952
}
953
def = nir_bitcast_vector(b, def, 32);
954
}
955
ttn_move_dest(b, dest, def);
956
}
957
958
static void
959
ttn_arl(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
960
{
961
ttn_move_dest(b, dest, nir_f2i32(b, nir_ffloor(b, src[0])));
962
}
963
964
/* EXP - Approximate Exponential Base 2
965
* dst.x = 2^{\lfloor src.x\rfloor}
966
* dst.y = src.x - \lfloor src.x\rfloor
967
* dst.z = 2^{src.x}
968
* dst.w = 1.0
969
*/
970
static void
971
ttn_exp(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
972
{
973
nir_ssa_def *srcx = ttn_channel(b, src[0], X);
974
975
ttn_move_dest_masked(b, dest, nir_fexp2(b, nir_ffloor(b, srcx)),
976
TGSI_WRITEMASK_X);
977
ttn_move_dest_masked(b, dest, nir_fsub(b, srcx, nir_ffloor(b, srcx)),
978
TGSI_WRITEMASK_Y);
979
ttn_move_dest_masked(b, dest, nir_fexp2(b, srcx), TGSI_WRITEMASK_Z);
980
ttn_move_dest_masked(b, dest, nir_imm_float(b, 1.0), TGSI_WRITEMASK_W);
981
}
982
983
/* LOG - Approximate Logarithm Base 2
984
* dst.x = \lfloor\log_2{|src.x|}\rfloor
985
* dst.y = \frac{|src.x|}{2^{\lfloor\log_2{|src.x|}\rfloor}}
986
* dst.z = \log_2{|src.x|}
987
* dst.w = 1.0
988
*/
989
static void
990
ttn_log(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
991
{
992
nir_ssa_def *abs_srcx = nir_fabs(b, ttn_channel(b, src[0], X));
993
nir_ssa_def *log2 = nir_flog2(b, abs_srcx);
994
995
ttn_move_dest_masked(b, dest, nir_ffloor(b, log2), TGSI_WRITEMASK_X);
996
ttn_move_dest_masked(b, dest,
997
nir_fdiv(b, abs_srcx, nir_fexp2(b, nir_ffloor(b, log2))),
998
TGSI_WRITEMASK_Y);
999
ttn_move_dest_masked(b, dest, nir_flog2(b, abs_srcx), TGSI_WRITEMASK_Z);
1000
ttn_move_dest_masked(b, dest, nir_imm_float(b, 1.0), TGSI_WRITEMASK_W);
1001
}
1002
1003
/* DST - Distance Vector
1004
* dst.x = 1.0
1005
* dst.y = src0.y \times src1.y
1006
* dst.z = src0.z
1007
* dst.w = src1.w
1008
*/
1009
static void
1010
ttn_dst(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
1011
{
1012
ttn_move_dest_masked(b, dest, nir_imm_float(b, 1.0), TGSI_WRITEMASK_X);
1013
ttn_move_dest_masked(b, dest, nir_fmul(b, src[0], src[1]), TGSI_WRITEMASK_Y);
1014
ttn_move_dest_masked(b, dest, nir_mov(b, src[0]), TGSI_WRITEMASK_Z);
1015
ttn_move_dest_masked(b, dest, nir_mov(b, src[1]), TGSI_WRITEMASK_W);
1016
}
1017
1018
/* LIT - Light Coefficients
1019
* dst.x = 1.0
1020
* dst.y = max(src.x, 0.0)
1021
* dst.z = (src.x > 0.0) ? max(src.y, 0.0)^{clamp(src.w, -128.0, 128.0))} : 0
1022
* dst.w = 1.0
1023
*/
1024
static void
1025
ttn_lit(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
1026
{
1027
ttn_move_dest_masked(b, dest, nir_imm_float(b, 1.0), TGSI_WRITEMASK_XW);
1028
1029
ttn_move_dest_masked(b, dest, nir_fmax(b, ttn_channel(b, src[0], X),
1030
nir_imm_float(b, 0.0)), TGSI_WRITEMASK_Y);
1031
1032
if (dest.write_mask & TGSI_WRITEMASK_Z) {
1033
nir_ssa_def *src0_y = ttn_channel(b, src[0], Y);
1034
nir_ssa_def *wclamp = nir_fmax(b, nir_fmin(b, ttn_channel(b, src[0], W),
1035
nir_imm_float(b, 128.0)),
1036
nir_imm_float(b, -128.0));
1037
nir_ssa_def *pow = nir_fpow(b, nir_fmax(b, src0_y, nir_imm_float(b, 0.0)),
1038
wclamp);
1039
1040
ttn_move_dest_masked(b, dest,
1041
nir_bcsel(b,
1042
nir_flt(b,
1043
ttn_channel(b, src[0], X),
1044
nir_imm_float(b, 0.0)),
1045
nir_imm_float(b, 0.0),
1046
pow),
1047
TGSI_WRITEMASK_Z);
1048
}
1049
}
1050
1051
static void
1052
ttn_sle(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
1053
{
1054
ttn_move_dest(b, dest, nir_sge(b, src[1], src[0]));
1055
}
1056
1057
static void
1058
ttn_sgt(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
1059
{
1060
ttn_move_dest(b, dest, nir_slt(b, src[1], src[0]));
1061
}
1062
1063
static void
1064
ttn_dp2(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
1065
{
1066
ttn_move_dest(b, dest, nir_fdot2(b, src[0], src[1]));
1067
}
1068
1069
static void
1070
ttn_dp3(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
1071
{
1072
ttn_move_dest(b, dest, nir_fdot3(b, src[0], src[1]));
1073
}
1074
1075
static void
1076
ttn_dp4(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
1077
{
1078
ttn_move_dest(b, dest, nir_fdot4(b, src[0], src[1]));
1079
}
1080
1081
static void
1082
ttn_umad(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
1083
{
1084
ttn_move_dest(b, dest, nir_iadd(b, nir_imul(b, src[0], src[1]), src[2]));
1085
}
1086
1087
static void
1088
ttn_arr(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
1089
{
1090
ttn_move_dest(b, dest, nir_f2i32(b, nir_fround_even(b, src[0])));
1091
}
1092
1093
static void
1094
ttn_cmp(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
1095
{
1096
ttn_move_dest(b, dest, nir_bcsel(b,
1097
nir_flt(b, src[0], nir_imm_float(b, 0.0)),
1098
src[1], src[2]));
1099
}
1100
1101
static void
1102
ttn_ucmp(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
1103
{
1104
ttn_move_dest(b, dest, nir_bcsel(b,
1105
nir_ine(b, src[0], nir_imm_int(b, 0)),
1106
src[1], src[2]));
1107
}
1108
1109
static void
1110
ttn_barrier(nir_builder *b)
1111
{
1112
nir_control_barrier(b);
1113
}
1114
1115
static void
1116
ttn_kill(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
1117
{
1118
nir_discard(b);
1119
b->shader->info.fs.uses_discard = true;
1120
}
1121
1122
static void
1123
ttn_kill_if(nir_builder *b, nir_op op, nir_alu_dest dest, nir_ssa_def **src)
1124
{
1125
/* flt must be exact, because NaN shouldn't discard. (apps rely on this) */
1126
b->exact = true;
1127
nir_ssa_def *cmp = nir_bany(b, nir_flt(b, src[0], nir_imm_float(b, 0.0)));
1128
b->exact = false;
1129
1130
nir_discard_if(b, cmp);
1131
b->shader->info.fs.uses_discard = true;
1132
}
1133
1134
static void
1135
get_texture_info(unsigned texture,
1136
enum glsl_sampler_dim *dim,
1137
bool *is_shadow,
1138
bool *is_array)
1139
{
1140
assert(is_array);
1141
*is_array = false;
1142
1143
if (is_shadow)
1144
*is_shadow = false;
1145
1146
switch (texture) {
1147
case TGSI_TEXTURE_BUFFER:
1148
*dim = GLSL_SAMPLER_DIM_BUF;
1149
break;
1150
case TGSI_TEXTURE_1D:
1151
*dim = GLSL_SAMPLER_DIM_1D;
1152
break;
1153
case TGSI_TEXTURE_1D_ARRAY:
1154
*dim = GLSL_SAMPLER_DIM_1D;
1155
*is_array = true;
1156
break;
1157
case TGSI_TEXTURE_SHADOW1D:
1158
*dim = GLSL_SAMPLER_DIM_1D;
1159
*is_shadow = true;
1160
break;
1161
case TGSI_TEXTURE_SHADOW1D_ARRAY:
1162
*dim = GLSL_SAMPLER_DIM_1D;
1163
*is_shadow = true;
1164
*is_array = true;
1165
break;
1166
case TGSI_TEXTURE_2D:
1167
*dim = GLSL_SAMPLER_DIM_2D;
1168
break;
1169
case TGSI_TEXTURE_2D_ARRAY:
1170
*dim = GLSL_SAMPLER_DIM_2D;
1171
*is_array = true;
1172
break;
1173
case TGSI_TEXTURE_2D_MSAA:
1174
*dim = GLSL_SAMPLER_DIM_MS;
1175
break;
1176
case TGSI_TEXTURE_2D_ARRAY_MSAA:
1177
*dim = GLSL_SAMPLER_DIM_MS;
1178
*is_array = true;
1179
break;
1180
case TGSI_TEXTURE_SHADOW2D:
1181
*dim = GLSL_SAMPLER_DIM_2D;
1182
*is_shadow = true;
1183
break;
1184
case TGSI_TEXTURE_SHADOW2D_ARRAY:
1185
*dim = GLSL_SAMPLER_DIM_2D;
1186
*is_shadow = true;
1187
*is_array = true;
1188
break;
1189
case TGSI_TEXTURE_3D:
1190
*dim = GLSL_SAMPLER_DIM_3D;
1191
break;
1192
case TGSI_TEXTURE_CUBE:
1193
*dim = GLSL_SAMPLER_DIM_CUBE;
1194
break;
1195
case TGSI_TEXTURE_CUBE_ARRAY:
1196
*dim = GLSL_SAMPLER_DIM_CUBE;
1197
*is_array = true;
1198
break;
1199
case TGSI_TEXTURE_SHADOWCUBE:
1200
*dim = GLSL_SAMPLER_DIM_CUBE;
1201
*is_shadow = true;
1202
break;
1203
case TGSI_TEXTURE_SHADOWCUBE_ARRAY:
1204
*dim = GLSL_SAMPLER_DIM_CUBE;
1205
*is_shadow = true;
1206
*is_array = true;
1207
break;
1208
case TGSI_TEXTURE_RECT:
1209
*dim = GLSL_SAMPLER_DIM_RECT;
1210
break;
1211
case TGSI_TEXTURE_SHADOWRECT:
1212
*dim = GLSL_SAMPLER_DIM_RECT;
1213
*is_shadow = true;
1214
break;
1215
default:
1216
fprintf(stderr, "Unknown TGSI texture target %d\n", texture);
1217
abort();
1218
}
1219
}
1220
1221
static enum glsl_base_type
1222
base_type_for_alu_type(nir_alu_type type)
1223
{
1224
type = nir_alu_type_get_base_type(type);
1225
1226
switch (type) {
1227
case nir_type_float:
1228
return GLSL_TYPE_FLOAT;
1229
case nir_type_int:
1230
return GLSL_TYPE_INT;
1231
case nir_type_uint:
1232
return GLSL_TYPE_UINT;
1233
default:
1234
unreachable("invalid type");
1235
}
1236
}
1237
1238
static nir_variable *
1239
get_sampler_var(struct ttn_compile *c, int binding,
1240
enum glsl_sampler_dim dim,
1241
bool is_shadow,
1242
bool is_array,
1243
enum glsl_base_type base_type,
1244
nir_texop op)
1245
{
1246
nir_variable *var = c->samplers[binding];
1247
if (!var) {
1248
const struct glsl_type *type =
1249
glsl_sampler_type(dim, is_shadow, is_array, base_type);
1250
var = nir_variable_create(c->build.shader, nir_var_uniform, type,
1251
"sampler");
1252
var->data.binding = binding;
1253
var->data.explicit_binding = true;
1254
1255
c->samplers[binding] = var;
1256
c->num_samplers = MAX2(c->num_samplers, binding + 1);
1257
1258
/* Record textures used */
1259
BITSET_SET(c->build.shader->info.textures_used, binding);
1260
if (op == nir_texop_txf ||
1261
op == nir_texop_txf_ms ||
1262
op == nir_texop_txf_ms_mcs)
1263
BITSET_SET(c->build.shader->info.textures_used_by_txf, binding);
1264
}
1265
1266
return var;
1267
}
1268
1269
static nir_variable *
1270
get_image_var(struct ttn_compile *c, int binding,
1271
enum glsl_sampler_dim dim,
1272
bool is_array,
1273
enum glsl_base_type base_type,
1274
enum gl_access_qualifier access,
1275
enum pipe_format format)
1276
{
1277
nir_variable *var = c->images[binding];
1278
1279
if (!var) {
1280
const struct glsl_type *type = glsl_image_type(dim, is_array, base_type);
1281
1282
var = nir_variable_create(c->build.shader, nir_var_uniform, type, "image");
1283
var->data.binding = binding;
1284
var->data.explicit_binding = true;
1285
var->data.access = access;
1286
var->data.image.format = format;
1287
1288
c->images[binding] = var;
1289
c->num_images = MAX2(c->num_images, binding + 1);
1290
if (dim == GLSL_SAMPLER_DIM_MS)
1291
c->num_msaa_images = c->num_images;
1292
}
1293
1294
return var;
1295
}
1296
1297
static void
1298
add_ssbo_var(struct ttn_compile *c, int binding)
1299
{
1300
nir_variable *var = c->ssbo[binding];
1301
1302
if (!var) {
1303
/* A length of 0 is used to denote unsized arrays */
1304
const struct glsl_type *type = glsl_array_type(glsl_uint_type(), 0, 0);
1305
1306
struct glsl_struct_field field = {
1307
.type = type,
1308
.name = "data",
1309
.location = -1,
1310
};
1311
1312
var = nir_variable_create(c->build.shader, nir_var_mem_ssbo, type, "ssbo");
1313
var->data.binding = binding;
1314
var->interface_type =
1315
glsl_interface_type(&field, 1, GLSL_INTERFACE_PACKING_STD430,
1316
false, "data");
1317
c->ssbo[binding] = var;
1318
}
1319
}
1320
1321
static void
1322
ttn_tex(struct ttn_compile *c, nir_alu_dest dest, nir_ssa_def **src)
1323
{
1324
nir_builder *b = &c->build;
1325
struct tgsi_full_instruction *tgsi_inst = &c->token->FullInstruction;
1326
nir_tex_instr *instr;
1327
nir_texop op;
1328
unsigned num_srcs, samp = 1, sview, i;
1329
1330
switch (tgsi_inst->Instruction.Opcode) {
1331
case TGSI_OPCODE_TEX:
1332
op = nir_texop_tex;
1333
num_srcs = 1;
1334
break;
1335
case TGSI_OPCODE_TEX2:
1336
op = nir_texop_tex;
1337
num_srcs = 1;
1338
samp = 2;
1339
break;
1340
case TGSI_OPCODE_TXP:
1341
op = nir_texop_tex;
1342
num_srcs = 2;
1343
break;
1344
case TGSI_OPCODE_TXB:
1345
op = nir_texop_txb;
1346
num_srcs = 2;
1347
break;
1348
case TGSI_OPCODE_TXB2:
1349
op = nir_texop_txb;
1350
num_srcs = 2;
1351
samp = 2;
1352
break;
1353
case TGSI_OPCODE_TXL:
1354
case TGSI_OPCODE_TEX_LZ:
1355
op = nir_texop_txl;
1356
num_srcs = 2;
1357
break;
1358
case TGSI_OPCODE_TXL2:
1359
op = nir_texop_txl;
1360
num_srcs = 2;
1361
samp = 2;
1362
break;
1363
case TGSI_OPCODE_TXF:
1364
case TGSI_OPCODE_TXF_LZ:
1365
if (tgsi_inst->Texture.Texture == TGSI_TEXTURE_2D_MSAA ||
1366
tgsi_inst->Texture.Texture == TGSI_TEXTURE_2D_ARRAY_MSAA) {
1367
op = nir_texop_txf_ms;
1368
} else {
1369
op = nir_texop_txf;
1370
}
1371
num_srcs = 2;
1372
break;
1373
case TGSI_OPCODE_TXD:
1374
op = nir_texop_txd;
1375
num_srcs = 3;
1376
samp = 3;
1377
break;
1378
case TGSI_OPCODE_LODQ:
1379
op = nir_texop_lod;
1380
num_srcs = 1;
1381
break;
1382
1383
default:
1384
fprintf(stderr, "unknown TGSI tex op %d\n", tgsi_inst->Instruction.Opcode);
1385
abort();
1386
}
1387
1388
if (tgsi_inst->Texture.Texture == TGSI_TEXTURE_SHADOW1D ||
1389
tgsi_inst->Texture.Texture == TGSI_TEXTURE_SHADOW1D_ARRAY ||
1390
tgsi_inst->Texture.Texture == TGSI_TEXTURE_SHADOW2D ||
1391
tgsi_inst->Texture.Texture == TGSI_TEXTURE_SHADOW2D_ARRAY ||
1392
tgsi_inst->Texture.Texture == TGSI_TEXTURE_SHADOWRECT ||
1393
tgsi_inst->Texture.Texture == TGSI_TEXTURE_SHADOWCUBE ||
1394
tgsi_inst->Texture.Texture == TGSI_TEXTURE_SHADOWCUBE_ARRAY) {
1395
num_srcs++;
1396
}
1397
1398
/* Deref sources */
1399
num_srcs += 2;
1400
1401
num_srcs += tgsi_inst->Texture.NumOffsets;
1402
1403
instr = nir_tex_instr_create(b->shader, num_srcs);
1404
instr->op = op;
1405
1406
get_texture_info(tgsi_inst->Texture.Texture,
1407
&instr->sampler_dim, &instr->is_shadow, &instr->is_array);
1408
1409
instr->coord_components =
1410
glsl_get_sampler_dim_coordinate_components(instr->sampler_dim);
1411
1412
if (instr->is_array)
1413
instr->coord_components++;
1414
1415
assert(tgsi_inst->Src[samp].Register.File == TGSI_FILE_SAMPLER);
1416
1417
/* TODO if we supported any opc's which take an explicit SVIEW
1418
* src, we would use that here instead. But for the "legacy"
1419
* texture opc's the SVIEW index is same as SAMP index:
1420
*/
1421
sview = tgsi_inst->Src[samp].Register.Index;
1422
1423
if (op == nir_texop_lod) {
1424
instr->dest_type = nir_type_float32;
1425
} else if (sview < c->num_samp_types) {
1426
instr->dest_type = c->samp_types[sview];
1427
} else {
1428
instr->dest_type = nir_type_float32;
1429
}
1430
1431
nir_variable *var =
1432
get_sampler_var(c, sview, instr->sampler_dim,
1433
instr->is_shadow,
1434
instr->is_array,
1435
base_type_for_alu_type(instr->dest_type),
1436
op);
1437
1438
nir_deref_instr *deref = nir_build_deref_var(b, var);
1439
1440
unsigned src_number = 0;
1441
1442
instr->src[src_number].src = nir_src_for_ssa(&deref->dest.ssa);
1443
instr->src[src_number].src_type = nir_tex_src_texture_deref;
1444
src_number++;
1445
instr->src[src_number].src = nir_src_for_ssa(&deref->dest.ssa);
1446
instr->src[src_number].src_type = nir_tex_src_sampler_deref;
1447
src_number++;
1448
1449
instr->src[src_number].src =
1450
nir_src_for_ssa(nir_swizzle(b, src[0], SWIZ(X, Y, Z, W),
1451
instr->coord_components));
1452
instr->src[src_number].src_type = nir_tex_src_coord;
1453
src_number++;
1454
1455
if (tgsi_inst->Instruction.Opcode == TGSI_OPCODE_TXP) {
1456
instr->src[src_number].src = nir_src_for_ssa(ttn_channel(b, src[0], W));
1457
instr->src[src_number].src_type = nir_tex_src_projector;
1458
src_number++;
1459
}
1460
1461
if (tgsi_inst->Instruction.Opcode == TGSI_OPCODE_TXB) {
1462
instr->src[src_number].src = nir_src_for_ssa(ttn_channel(b, src[0], W));
1463
instr->src[src_number].src_type = nir_tex_src_bias;
1464
src_number++;
1465
}
1466
1467
if (tgsi_inst->Instruction.Opcode == TGSI_OPCODE_TXB2) {
1468
instr->src[src_number].src = nir_src_for_ssa(ttn_channel(b, src[1], X));
1469
instr->src[src_number].src_type = nir_tex_src_bias;
1470
src_number++;
1471
}
1472
1473
if (tgsi_inst->Instruction.Opcode == TGSI_OPCODE_TXL ||
1474
tgsi_inst->Instruction.Opcode == TGSI_OPCODE_TEX_LZ) {
1475
if (tgsi_inst->Instruction.Opcode == TGSI_OPCODE_TEX_LZ)
1476
instr->src[src_number].src = nir_src_for_ssa(nir_imm_int(b, 0));
1477
else
1478
instr->src[src_number].src = nir_src_for_ssa(ttn_channel(b, src[0], W));
1479
instr->src[src_number].src_type = nir_tex_src_lod;
1480
src_number++;
1481
}
1482
1483
if (tgsi_inst->Instruction.Opcode == TGSI_OPCODE_TXL2) {
1484
instr->src[src_number].src = nir_src_for_ssa(ttn_channel(b, src[1], X));
1485
instr->src[src_number].src_type = nir_tex_src_lod;
1486
src_number++;
1487
}
1488
1489
if (tgsi_inst->Instruction.Opcode == TGSI_OPCODE_TXF ||
1490
tgsi_inst->Instruction.Opcode == TGSI_OPCODE_TXF_LZ) {
1491
if (op == nir_texop_txf_ms) {
1492
instr->src[src_number].src = nir_src_for_ssa(ttn_channel(b, src[0], W));
1493
instr->src[src_number].src_type = nir_tex_src_ms_index;
1494
} else {
1495
if (tgsi_inst->Instruction.Opcode == TGSI_OPCODE_TXF_LZ)
1496
instr->src[src_number].src = nir_src_for_ssa(nir_imm_int(b, 0));
1497
else
1498
instr->src[src_number].src = nir_src_for_ssa(ttn_channel(b, src[0], W));
1499
instr->src[src_number].src_type = nir_tex_src_lod;
1500
}
1501
src_number++;
1502
}
1503
1504
if (tgsi_inst->Instruction.Opcode == TGSI_OPCODE_TXD) {
1505
instr->src[src_number].src_type = nir_tex_src_ddx;
1506
instr->src[src_number].src =
1507
nir_src_for_ssa(nir_swizzle(b, src[1], SWIZ(X, Y, Z, W),
1508
nir_tex_instr_src_size(instr, src_number)));
1509
src_number++;
1510
instr->src[src_number].src_type = nir_tex_src_ddy;
1511
instr->src[src_number].src =
1512
nir_src_for_ssa(nir_swizzle(b, src[2], SWIZ(X, Y, Z, W),
1513
nir_tex_instr_src_size(instr, src_number)));
1514
src_number++;
1515
}
1516
1517
if (instr->is_shadow) {
1518
if (instr->coord_components == 4)
1519
instr->src[src_number].src = nir_src_for_ssa(ttn_channel(b, src[1], X));
1520
else if (instr->coord_components == 3)
1521
instr->src[src_number].src = nir_src_for_ssa(ttn_channel(b, src[0], W));
1522
else
1523
instr->src[src_number].src = nir_src_for_ssa(ttn_channel(b, src[0], Z));
1524
1525
instr->src[src_number].src_type = nir_tex_src_comparator;
1526
src_number++;
1527
}
1528
1529
for (i = 0; i < tgsi_inst->Texture.NumOffsets; i++) {
1530
struct tgsi_texture_offset *tex_offset = &tgsi_inst->TexOffsets[i];
1531
/* since TexOffset ins't using tgsi_full_src_register we get to
1532
* do some extra gymnastics:
1533
*/
1534
nir_alu_src src;
1535
1536
memset(&src, 0, sizeof(src));
1537
1538
src.src = ttn_src_for_file_and_index(c,
1539
tex_offset->File,
1540
tex_offset->Index,
1541
NULL, NULL, NULL,
1542
true);
1543
1544
src.swizzle[0] = tex_offset->SwizzleX;
1545
src.swizzle[1] = tex_offset->SwizzleY;
1546
src.swizzle[2] = tex_offset->SwizzleZ;
1547
src.swizzle[3] = TGSI_SWIZZLE_W;
1548
1549
instr->src[src_number].src_type = nir_tex_src_offset;
1550
instr->src[src_number].src = nir_src_for_ssa(
1551
nir_mov_alu(b, src, nir_tex_instr_src_size(instr, src_number)));
1552
src_number++;
1553
}
1554
1555
assert(src_number == num_srcs);
1556
assert(src_number == instr->num_srcs);
1557
1558
nir_ssa_dest_init(&instr->instr, &instr->dest,
1559
nir_tex_instr_dest_size(instr),
1560
32, NULL);
1561
nir_builder_instr_insert(b, &instr->instr);
1562
1563
/* Resolve the writemask on the texture op. */
1564
ttn_move_dest(b, dest, &instr->dest.ssa);
1565
}
1566
1567
/* TGSI_OPCODE_TXQ is actually two distinct operations:
1568
*
1569
* dst.x = texture\_width(unit, lod)
1570
* dst.y = texture\_height(unit, lod)
1571
* dst.z = texture\_depth(unit, lod)
1572
* dst.w = texture\_levels(unit)
1573
*
1574
* dst.xyz map to NIR txs opcode, and dst.w maps to query_levels
1575
*/
1576
static void
1577
ttn_txq(struct ttn_compile *c, nir_alu_dest dest, nir_ssa_def **src)
1578
{
1579
nir_builder *b = &c->build;
1580
struct tgsi_full_instruction *tgsi_inst = &c->token->FullInstruction;
1581
nir_tex_instr *txs, *qlv;
1582
1583
txs = nir_tex_instr_create(b->shader, 2);
1584
txs->op = nir_texop_txs;
1585
get_texture_info(tgsi_inst->Texture.Texture,
1586
&txs->sampler_dim, &txs->is_shadow, &txs->is_array);
1587
1588
qlv = nir_tex_instr_create(b->shader, 1);
1589
qlv->op = nir_texop_query_levels;
1590
get_texture_info(tgsi_inst->Texture.Texture,
1591
&qlv->sampler_dim, &qlv->is_shadow, &qlv->is_array);
1592
1593
assert(tgsi_inst->Src[1].Register.File == TGSI_FILE_SAMPLER);
1594
int tex_index = tgsi_inst->Src[1].Register.Index;
1595
1596
nir_variable *var =
1597
get_sampler_var(c, tex_index, txs->sampler_dim,
1598
txs->is_shadow,
1599
txs->is_array,
1600
base_type_for_alu_type(txs->dest_type),
1601
nir_texop_txs);
1602
1603
nir_deref_instr *deref = nir_build_deref_var(b, var);
1604
1605
txs->src[0].src = nir_src_for_ssa(&deref->dest.ssa);
1606
txs->src[0].src_type = nir_tex_src_texture_deref;
1607
1608
qlv->src[0].src = nir_src_for_ssa(&deref->dest.ssa);
1609
qlv->src[0].src_type = nir_tex_src_texture_deref;
1610
1611
/* lod: */
1612
txs->src[1].src = nir_src_for_ssa(ttn_channel(b, src[0], X));
1613
txs->src[1].src_type = nir_tex_src_lod;
1614
1615
nir_ssa_dest_init(&txs->instr, &txs->dest,
1616
nir_tex_instr_dest_size(txs), 32, NULL);
1617
nir_builder_instr_insert(b, &txs->instr);
1618
1619
nir_ssa_dest_init(&qlv->instr, &qlv->dest, 1, 32, NULL);
1620
nir_builder_instr_insert(b, &qlv->instr);
1621
1622
ttn_move_dest_masked(b, dest, &txs->dest.ssa, TGSI_WRITEMASK_XYZ);
1623
ttn_move_dest_masked(b, dest, &qlv->dest.ssa, TGSI_WRITEMASK_W);
1624
}
1625
1626
static enum glsl_base_type
1627
get_image_base_type(struct tgsi_full_instruction *tgsi_inst)
1628
{
1629
const struct util_format_description *desc =
1630
util_format_description(tgsi_inst->Memory.Format);
1631
1632
if (desc->channel[0].pure_integer) {
1633
if (desc->channel[0].type == UTIL_FORMAT_TYPE_SIGNED)
1634
return GLSL_TYPE_INT;
1635
else
1636
return GLSL_TYPE_UINT;
1637
}
1638
return GLSL_TYPE_FLOAT;
1639
}
1640
1641
static enum gl_access_qualifier
1642
get_mem_qualifier(struct tgsi_full_instruction *tgsi_inst)
1643
{
1644
enum gl_access_qualifier access = 0;
1645
1646
if (tgsi_inst->Memory.Qualifier & TGSI_MEMORY_COHERENT)
1647
access |= ACCESS_COHERENT;
1648
if (tgsi_inst->Memory.Qualifier & TGSI_MEMORY_RESTRICT)
1649
access |= ACCESS_RESTRICT;
1650
if (tgsi_inst->Memory.Qualifier & TGSI_MEMORY_VOLATILE)
1651
access |= ACCESS_VOLATILE;
1652
if (tgsi_inst->Memory.Qualifier & TGSI_MEMORY_STREAM_CACHE_POLICY)
1653
access |= ACCESS_STREAM_CACHE_POLICY;
1654
1655
return access;
1656
}
1657
1658
static void
1659
ttn_mem(struct ttn_compile *c, nir_alu_dest dest, nir_ssa_def **src)
1660
{
1661
nir_builder *b = &c->build;
1662
struct tgsi_full_instruction *tgsi_inst = &c->token->FullInstruction;
1663
nir_intrinsic_instr *instr = NULL;
1664
unsigned resource_index, addr_src_index, file;
1665
1666
switch (tgsi_inst->Instruction.Opcode) {
1667
case TGSI_OPCODE_LOAD:
1668
assert(!tgsi_inst->Src[0].Register.Indirect);
1669
resource_index = tgsi_inst->Src[0].Register.Index;
1670
file = tgsi_inst->Src[0].Register.File;
1671
addr_src_index = 1;
1672
break;
1673
case TGSI_OPCODE_STORE:
1674
assert(!tgsi_inst->Dst[0].Register.Indirect);
1675
resource_index = tgsi_inst->Dst[0].Register.Index;
1676
file = tgsi_inst->Dst[0].Register.File;
1677
addr_src_index = 0;
1678
break;
1679
default:
1680
unreachable("unexpected memory opcode");
1681
}
1682
1683
if (file == TGSI_FILE_BUFFER) {
1684
nir_intrinsic_op op;
1685
1686
switch (tgsi_inst->Instruction.Opcode) {
1687
case TGSI_OPCODE_LOAD:
1688
op = nir_intrinsic_load_ssbo;
1689
break;
1690
case TGSI_OPCODE_STORE:
1691
op = nir_intrinsic_store_ssbo;
1692
break;
1693
default:
1694
unreachable("unexpected buffer opcode");
1695
}
1696
1697
add_ssbo_var(c, resource_index);
1698
1699
instr = nir_intrinsic_instr_create(b->shader, op);
1700
instr->num_components = util_last_bit(tgsi_inst->Dst[0].Register.WriteMask);
1701
nir_intrinsic_set_access(instr, get_mem_qualifier(tgsi_inst));
1702
nir_intrinsic_set_align(instr, 4, 0);
1703
1704
unsigned i = 0;
1705
if (tgsi_inst->Instruction.Opcode == TGSI_OPCODE_STORE)
1706
instr->src[i++] = nir_src_for_ssa(nir_swizzle(b, src[1], SWIZ(X, Y, Z, W),
1707
instr->num_components));
1708
instr->src[i++] = nir_src_for_ssa(nir_imm_int(b, resource_index));
1709
instr->src[i++] = nir_src_for_ssa(ttn_channel(b, src[addr_src_index], X));
1710
1711
if (tgsi_inst->Instruction.Opcode == TGSI_OPCODE_STORE)
1712
nir_intrinsic_set_write_mask(instr, tgsi_inst->Dst[0].Register.WriteMask);
1713
1714
} else if (file == TGSI_FILE_IMAGE) {
1715
nir_intrinsic_op op;
1716
1717
switch (tgsi_inst->Instruction.Opcode) {
1718
case TGSI_OPCODE_LOAD:
1719
op = nir_intrinsic_image_deref_load;
1720
break;
1721
case TGSI_OPCODE_STORE:
1722
op = nir_intrinsic_image_deref_store;
1723
break;
1724
default:
1725
unreachable("unexpected file opcode");
1726
}
1727
1728
instr = nir_intrinsic_instr_create(b->shader, op);
1729
1730
/* Set the image variable dereference. */
1731
enum glsl_sampler_dim dim;
1732
bool is_array;
1733
get_texture_info(tgsi_inst->Memory.Texture, &dim, NULL, &is_array);
1734
1735
enum glsl_base_type base_type = get_image_base_type(tgsi_inst);
1736
enum gl_access_qualifier access = get_mem_qualifier(tgsi_inst);
1737
1738
nir_variable *image =
1739
get_image_var(c, resource_index,
1740
dim, is_array, base_type, access,
1741
tgsi_inst->Memory.Format);
1742
nir_deref_instr *image_deref = nir_build_deref_var(b, image);
1743
const struct glsl_type *type = image_deref->type;
1744
1745
nir_intrinsic_set_access(instr, image_deref->var->data.access);
1746
1747
instr->src[0] = nir_src_for_ssa(&image_deref->dest.ssa);
1748
instr->src[1] = nir_src_for_ssa(src[addr_src_index]);
1749
1750
/* Set the sample argument, which is undefined for single-sample images. */
1751
if (glsl_get_sampler_dim(type) == GLSL_SAMPLER_DIM_MS) {
1752
instr->src[2] = nir_src_for_ssa(ttn_channel(b, src[addr_src_index], W));
1753
} else {
1754
instr->src[2] = nir_src_for_ssa(nir_ssa_undef(b, 1, 32));
1755
}
1756
1757
if (tgsi_inst->Instruction.Opcode == TGSI_OPCODE_LOAD) {
1758
instr->src[3] = nir_src_for_ssa(nir_imm_int(b, 0)); /* LOD */
1759
}
1760
1761
unsigned num_components = util_last_bit(tgsi_inst->Dst[0].Register.WriteMask);
1762
1763
if (tgsi_inst->Instruction.Opcode == TGSI_OPCODE_STORE) {
1764
instr->src[3] = nir_src_for_ssa(nir_swizzle(b, src[1], SWIZ(X, Y, Z, W),
1765
num_components));
1766
instr->src[4] = nir_src_for_ssa(nir_imm_int(b, 0)); /* LOD */
1767
}
1768
1769
instr->num_components = num_components;
1770
} else {
1771
unreachable("unexpected file");
1772
}
1773
1774
1775
if (tgsi_inst->Instruction.Opcode == TGSI_OPCODE_LOAD) {
1776
nir_ssa_dest_init(&instr->instr, &instr->dest, instr->num_components,
1777
32, NULL);
1778
nir_builder_instr_insert(b, &instr->instr);
1779
ttn_move_dest(b, dest, &instr->dest.ssa);
1780
} else {
1781
nir_builder_instr_insert(b, &instr->instr);
1782
}
1783
}
1784
1785
static const nir_op op_trans[TGSI_OPCODE_LAST] = {
1786
[TGSI_OPCODE_ARL] = 0,
1787
[TGSI_OPCODE_MOV] = nir_op_mov,
1788
[TGSI_OPCODE_FBFETCH] = nir_op_mov,
1789
[TGSI_OPCODE_LIT] = 0,
1790
[TGSI_OPCODE_RCP] = nir_op_frcp,
1791
[TGSI_OPCODE_RSQ] = nir_op_frsq,
1792
[TGSI_OPCODE_EXP] = 0,
1793
[TGSI_OPCODE_LOG] = 0,
1794
[TGSI_OPCODE_MUL] = nir_op_fmul,
1795
[TGSI_OPCODE_ADD] = nir_op_fadd,
1796
[TGSI_OPCODE_DP3] = 0,
1797
[TGSI_OPCODE_DP4] = 0,
1798
[TGSI_OPCODE_DST] = 0,
1799
[TGSI_OPCODE_MIN] = nir_op_fmin,
1800
[TGSI_OPCODE_MAX] = nir_op_fmax,
1801
[TGSI_OPCODE_SLT] = nir_op_slt,
1802
[TGSI_OPCODE_SGE] = nir_op_sge,
1803
[TGSI_OPCODE_MAD] = nir_op_ffma,
1804
[TGSI_OPCODE_TEX_LZ] = 0,
1805
[TGSI_OPCODE_LRP] = 0,
1806
[TGSI_OPCODE_SQRT] = nir_op_fsqrt,
1807
[TGSI_OPCODE_FRC] = nir_op_ffract,
1808
[TGSI_OPCODE_TXF_LZ] = 0,
1809
[TGSI_OPCODE_FLR] = nir_op_ffloor,
1810
[TGSI_OPCODE_ROUND] = nir_op_fround_even,
1811
[TGSI_OPCODE_EX2] = nir_op_fexp2,
1812
[TGSI_OPCODE_LG2] = nir_op_flog2,
1813
[TGSI_OPCODE_POW] = nir_op_fpow,
1814
[TGSI_OPCODE_COS] = nir_op_fcos,
1815
[TGSI_OPCODE_DDX] = nir_op_fddx,
1816
[TGSI_OPCODE_DDY] = nir_op_fddy,
1817
[TGSI_OPCODE_KILL] = 0,
1818
[TGSI_OPCODE_PK2H] = 0, /* XXX */
1819
[TGSI_OPCODE_PK2US] = 0, /* XXX */
1820
[TGSI_OPCODE_PK4B] = 0, /* XXX */
1821
[TGSI_OPCODE_PK4UB] = 0, /* XXX */
1822
[TGSI_OPCODE_SEQ] = nir_op_seq,
1823
[TGSI_OPCODE_SGT] = 0,
1824
[TGSI_OPCODE_SIN] = nir_op_fsin,
1825
[TGSI_OPCODE_SNE] = nir_op_sne,
1826
[TGSI_OPCODE_SLE] = 0,
1827
[TGSI_OPCODE_TEX] = 0,
1828
[TGSI_OPCODE_TXD] = 0,
1829
[TGSI_OPCODE_TXP] = 0,
1830
[TGSI_OPCODE_UP2H] = 0, /* XXX */
1831
[TGSI_OPCODE_UP2US] = 0, /* XXX */
1832
[TGSI_OPCODE_UP4B] = 0, /* XXX */
1833
[TGSI_OPCODE_UP4UB] = 0, /* XXX */
1834
[TGSI_OPCODE_ARR] = 0,
1835
1836
/* No function calls, yet. */
1837
[TGSI_OPCODE_CAL] = 0, /* XXX */
1838
[TGSI_OPCODE_RET] = 0, /* XXX */
1839
1840
[TGSI_OPCODE_SSG] = nir_op_fsign,
1841
[TGSI_OPCODE_CMP] = 0,
1842
[TGSI_OPCODE_TXB] = 0,
1843
[TGSI_OPCODE_DIV] = nir_op_fdiv,
1844
[TGSI_OPCODE_DP2] = 0,
1845
[TGSI_OPCODE_TXL] = 0,
1846
1847
[TGSI_OPCODE_BRK] = 0,
1848
[TGSI_OPCODE_IF] = 0,
1849
[TGSI_OPCODE_UIF] = 0,
1850
[TGSI_OPCODE_ELSE] = 0,
1851
[TGSI_OPCODE_ENDIF] = 0,
1852
1853
[TGSI_OPCODE_DDX_FINE] = nir_op_fddx_fine,
1854
[TGSI_OPCODE_DDY_FINE] = nir_op_fddy_fine,
1855
1856
[TGSI_OPCODE_CEIL] = nir_op_fceil,
1857
[TGSI_OPCODE_I2F] = nir_op_i2f32,
1858
[TGSI_OPCODE_NOT] = nir_op_inot,
1859
[TGSI_OPCODE_TRUNC] = nir_op_ftrunc,
1860
[TGSI_OPCODE_SHL] = nir_op_ishl,
1861
[TGSI_OPCODE_AND] = nir_op_iand,
1862
[TGSI_OPCODE_OR] = nir_op_ior,
1863
[TGSI_OPCODE_MOD] = nir_op_umod,
1864
[TGSI_OPCODE_XOR] = nir_op_ixor,
1865
[TGSI_OPCODE_TXF] = 0,
1866
[TGSI_OPCODE_TXQ] = 0,
1867
1868
[TGSI_OPCODE_CONT] = 0,
1869
1870
[TGSI_OPCODE_EMIT] = 0, /* XXX */
1871
[TGSI_OPCODE_ENDPRIM] = 0, /* XXX */
1872
1873
[TGSI_OPCODE_BGNLOOP] = 0,
1874
[TGSI_OPCODE_BGNSUB] = 0, /* XXX: no function calls */
1875
[TGSI_OPCODE_ENDLOOP] = 0,
1876
[TGSI_OPCODE_ENDSUB] = 0, /* XXX: no function calls */
1877
1878
[TGSI_OPCODE_NOP] = 0,
1879
[TGSI_OPCODE_FSEQ] = nir_op_feq,
1880
[TGSI_OPCODE_FSGE] = nir_op_fge,
1881
[TGSI_OPCODE_FSLT] = nir_op_flt,
1882
[TGSI_OPCODE_FSNE] = nir_op_fneu,
1883
1884
[TGSI_OPCODE_KILL_IF] = 0,
1885
1886
[TGSI_OPCODE_END] = 0,
1887
1888
[TGSI_OPCODE_F2I] = nir_op_f2i32,
1889
[TGSI_OPCODE_IDIV] = nir_op_idiv,
1890
[TGSI_OPCODE_IMAX] = nir_op_imax,
1891
[TGSI_OPCODE_IMIN] = nir_op_imin,
1892
[TGSI_OPCODE_INEG] = nir_op_ineg,
1893
[TGSI_OPCODE_ISGE] = nir_op_ige,
1894
[TGSI_OPCODE_ISHR] = nir_op_ishr,
1895
[TGSI_OPCODE_ISLT] = nir_op_ilt,
1896
[TGSI_OPCODE_F2U] = nir_op_f2u32,
1897
[TGSI_OPCODE_U2F] = nir_op_u2f32,
1898
[TGSI_OPCODE_UADD] = nir_op_iadd,
1899
[TGSI_OPCODE_UDIV] = nir_op_udiv,
1900
[TGSI_OPCODE_UMAD] = 0,
1901
[TGSI_OPCODE_UMAX] = nir_op_umax,
1902
[TGSI_OPCODE_UMIN] = nir_op_umin,
1903
[TGSI_OPCODE_UMOD] = nir_op_umod,
1904
[TGSI_OPCODE_UMUL] = nir_op_imul,
1905
[TGSI_OPCODE_USEQ] = nir_op_ieq,
1906
[TGSI_OPCODE_USGE] = nir_op_uge,
1907
[TGSI_OPCODE_USHR] = nir_op_ushr,
1908
[TGSI_OPCODE_USLT] = nir_op_ult,
1909
[TGSI_OPCODE_USNE] = nir_op_ine,
1910
1911
[TGSI_OPCODE_SWITCH] = 0, /* not emitted by glsl_to_tgsi.cpp */
1912
[TGSI_OPCODE_CASE] = 0, /* not emitted by glsl_to_tgsi.cpp */
1913
[TGSI_OPCODE_DEFAULT] = 0, /* not emitted by glsl_to_tgsi.cpp */
1914
[TGSI_OPCODE_ENDSWITCH] = 0, /* not emitted by glsl_to_tgsi.cpp */
1915
1916
/* XXX: SAMPLE opcodes */
1917
1918
[TGSI_OPCODE_UARL] = nir_op_mov,
1919
[TGSI_OPCODE_UCMP] = 0,
1920
[TGSI_OPCODE_IABS] = nir_op_iabs,
1921
[TGSI_OPCODE_ISSG] = nir_op_isign,
1922
1923
[TGSI_OPCODE_LOAD] = 0,
1924
[TGSI_OPCODE_STORE] = 0,
1925
1926
/* XXX: atomics */
1927
1928
[TGSI_OPCODE_TEX2] = 0,
1929
[TGSI_OPCODE_TXB2] = 0,
1930
[TGSI_OPCODE_TXL2] = 0,
1931
1932
[TGSI_OPCODE_IMUL_HI] = nir_op_imul_high,
1933
[TGSI_OPCODE_UMUL_HI] = nir_op_umul_high,
1934
1935
[TGSI_OPCODE_TG4] = 0,
1936
[TGSI_OPCODE_LODQ] = 0,
1937
1938
[TGSI_OPCODE_IBFE] = nir_op_ibitfield_extract,
1939
[TGSI_OPCODE_UBFE] = nir_op_ubitfield_extract,
1940
[TGSI_OPCODE_BFI] = nir_op_bitfield_insert,
1941
[TGSI_OPCODE_BREV] = nir_op_bitfield_reverse,
1942
[TGSI_OPCODE_POPC] = nir_op_bit_count,
1943
[TGSI_OPCODE_LSB] = nir_op_find_lsb,
1944
[TGSI_OPCODE_IMSB] = nir_op_ifind_msb,
1945
[TGSI_OPCODE_UMSB] = nir_op_ufind_msb,
1946
1947
[TGSI_OPCODE_INTERP_CENTROID] = 0, /* XXX */
1948
[TGSI_OPCODE_INTERP_SAMPLE] = 0, /* XXX */
1949
[TGSI_OPCODE_INTERP_OFFSET] = 0, /* XXX */
1950
1951
[TGSI_OPCODE_F2D] = nir_op_f2f64,
1952
[TGSI_OPCODE_D2F] = nir_op_f2f32,
1953
[TGSI_OPCODE_DMUL] = nir_op_fmul,
1954
[TGSI_OPCODE_D2U] = nir_op_f2u32,
1955
[TGSI_OPCODE_U2D] = nir_op_u2f64,
1956
1957
[TGSI_OPCODE_U64ADD] = nir_op_iadd,
1958
[TGSI_OPCODE_U64MUL] = nir_op_imul,
1959
[TGSI_OPCODE_U64DIV] = nir_op_udiv,
1960
[TGSI_OPCODE_U64SNE] = nir_op_ine,
1961
[TGSI_OPCODE_I64NEG] = nir_op_ineg,
1962
[TGSI_OPCODE_I64ABS] = nir_op_iabs,
1963
};
1964
1965
static void
1966
ttn_emit_instruction(struct ttn_compile *c)
1967
{
1968
nir_builder *b = &c->build;
1969
struct tgsi_full_instruction *tgsi_inst = &c->token->FullInstruction;
1970
unsigned i;
1971
unsigned tgsi_op = tgsi_inst->Instruction.Opcode;
1972
struct tgsi_full_dst_register *tgsi_dst = &tgsi_inst->Dst[0];
1973
1974
if (tgsi_op == TGSI_OPCODE_END)
1975
return;
1976
1977
nir_ssa_def *src[TGSI_FULL_MAX_SRC_REGISTERS];
1978
for (i = 0; i < tgsi_inst->Instruction.NumSrcRegs; i++) {
1979
src[i] = ttn_get_src(c, &tgsi_inst->Src[i], i);
1980
}
1981
nir_alu_dest dest = ttn_get_dest(c, tgsi_dst);
1982
1983
unsigned tgsi_dst_type = tgsi_opcode_infer_dst_type(tgsi_op, 0);
1984
1985
/* The destination bitsize of the NIR opcode (not TGSI, where it's always
1986
* 32 bits). This needs to be passed into ttn_alu() because it can't be
1987
* inferred for comparison opcodes.
1988
*/
1989
unsigned dst_bitsize = tgsi_type_is_64bit(tgsi_dst_type) ? 64 : 32;
1990
1991
switch (tgsi_op) {
1992
case TGSI_OPCODE_RSQ:
1993
ttn_move_dest(b, dest, nir_frsq(b, ttn_channel(b, src[0], X)));
1994
break;
1995
1996
case TGSI_OPCODE_SQRT:
1997
ttn_move_dest(b, dest, nir_fsqrt(b, ttn_channel(b, src[0], X)));
1998
break;
1999
2000
case TGSI_OPCODE_RCP:
2001
ttn_move_dest(b, dest, nir_frcp(b, ttn_channel(b, src[0], X)));
2002
break;
2003
2004
case TGSI_OPCODE_EX2:
2005
ttn_move_dest(b, dest, nir_fexp2(b, ttn_channel(b, src[0], X)));
2006
break;
2007
2008
case TGSI_OPCODE_LG2:
2009
ttn_move_dest(b, dest, nir_flog2(b, ttn_channel(b, src[0], X)));
2010
break;
2011
2012
case TGSI_OPCODE_POW:
2013
ttn_move_dest(b, dest, nir_fpow(b,
2014
ttn_channel(b, src[0], X),
2015
ttn_channel(b, src[1], X)));
2016
break;
2017
2018
case TGSI_OPCODE_COS:
2019
ttn_move_dest(b, dest, nir_fcos(b, ttn_channel(b, src[0], X)));
2020
break;
2021
2022
case TGSI_OPCODE_SIN:
2023
ttn_move_dest(b, dest, nir_fsin(b, ttn_channel(b, src[0], X)));
2024
break;
2025
2026
case TGSI_OPCODE_ARL:
2027
ttn_arl(b, op_trans[tgsi_op], dest, src);
2028
break;
2029
2030
case TGSI_OPCODE_EXP:
2031
ttn_exp(b, op_trans[tgsi_op], dest, src);
2032
break;
2033
2034
case TGSI_OPCODE_LOG:
2035
ttn_log(b, op_trans[tgsi_op], dest, src);
2036
break;
2037
2038
case TGSI_OPCODE_DST:
2039
ttn_dst(b, op_trans[tgsi_op], dest, src);
2040
break;
2041
2042
case TGSI_OPCODE_LIT:
2043
ttn_lit(b, op_trans[tgsi_op], dest, src);
2044
break;
2045
2046
case TGSI_OPCODE_DP2:
2047
ttn_dp2(b, op_trans[tgsi_op], dest, src);
2048
break;
2049
2050
case TGSI_OPCODE_DP3:
2051
ttn_dp3(b, op_trans[tgsi_op], dest, src);
2052
break;
2053
2054
case TGSI_OPCODE_DP4:
2055
ttn_dp4(b, op_trans[tgsi_op], dest, src);
2056
break;
2057
2058
case TGSI_OPCODE_UMAD:
2059
ttn_umad(b, op_trans[tgsi_op], dest, src);
2060
break;
2061
2062
case TGSI_OPCODE_LRP:
2063
ttn_move_dest(b, dest, nir_flrp(b, src[2], src[1], src[0]));
2064
break;
2065
2066
case TGSI_OPCODE_KILL:
2067
ttn_kill(b, op_trans[tgsi_op], dest, src);
2068
break;
2069
2070
case TGSI_OPCODE_ARR:
2071
ttn_arr(b, op_trans[tgsi_op], dest, src);
2072
break;
2073
2074
case TGSI_OPCODE_CMP:
2075
ttn_cmp(b, op_trans[tgsi_op], dest, src);
2076
break;
2077
2078
case TGSI_OPCODE_UCMP:
2079
ttn_ucmp(b, op_trans[tgsi_op], dest, src);
2080
break;
2081
2082
case TGSI_OPCODE_SGT:
2083
ttn_sgt(b, op_trans[tgsi_op], dest, src);
2084
break;
2085
2086
case TGSI_OPCODE_SLE:
2087
ttn_sle(b, op_trans[tgsi_op], dest, src);
2088
break;
2089
2090
case TGSI_OPCODE_KILL_IF:
2091
ttn_kill_if(b, op_trans[tgsi_op], dest, src);
2092
break;
2093
2094
case TGSI_OPCODE_TEX:
2095
case TGSI_OPCODE_TEX_LZ:
2096
case TGSI_OPCODE_TXP:
2097
case TGSI_OPCODE_TXL:
2098
case TGSI_OPCODE_TXB:
2099
case TGSI_OPCODE_TXD:
2100
case TGSI_OPCODE_TEX2:
2101
case TGSI_OPCODE_TXL2:
2102
case TGSI_OPCODE_TXB2:
2103
case TGSI_OPCODE_TXF:
2104
case TGSI_OPCODE_TXF_LZ:
2105
case TGSI_OPCODE_TG4:
2106
case TGSI_OPCODE_LODQ:
2107
ttn_tex(c, dest, src);
2108
break;
2109
2110
case TGSI_OPCODE_TXQ:
2111
ttn_txq(c, dest, src);
2112
break;
2113
2114
case TGSI_OPCODE_LOAD:
2115
case TGSI_OPCODE_STORE:
2116
ttn_mem(c, dest, src);
2117
break;
2118
2119
case TGSI_OPCODE_NOP:
2120
break;
2121
2122
case TGSI_OPCODE_IF:
2123
nir_push_if(b, nir_fneu(b, nir_channel(b, src[0], 0), nir_imm_float(b, 0.0)));
2124
break;
2125
2126
case TGSI_OPCODE_UIF:
2127
nir_push_if(b, nir_ine(b, nir_channel(b, src[0], 0), nir_imm_int(b, 0)));
2128
break;
2129
2130
case TGSI_OPCODE_ELSE:
2131
nir_push_else(&c->build, NULL);
2132
break;
2133
2134
case TGSI_OPCODE_ENDIF:
2135
nir_pop_if(&c->build, NULL);
2136
break;
2137
2138
case TGSI_OPCODE_BGNLOOP:
2139
nir_push_loop(&c->build);
2140
break;
2141
2142
case TGSI_OPCODE_BRK:
2143
nir_jump(b, nir_jump_break);
2144
break;
2145
2146
case TGSI_OPCODE_CONT:
2147
nir_jump(b, nir_jump_continue);
2148
break;
2149
2150
case TGSI_OPCODE_ENDLOOP:
2151
nir_pop_loop(&c->build, NULL);
2152
break;
2153
2154
case TGSI_OPCODE_BARRIER:
2155
ttn_barrier(b);
2156
break;
2157
2158
default:
2159
if (op_trans[tgsi_op] != 0 || tgsi_op == TGSI_OPCODE_MOV) {
2160
ttn_alu(b, op_trans[tgsi_op], dest, dst_bitsize, src);
2161
} else {
2162
fprintf(stderr, "unknown TGSI opcode: %s\n",
2163
tgsi_get_opcode_name(tgsi_op));
2164
abort();
2165
}
2166
break;
2167
}
2168
2169
if (tgsi_inst->Instruction.Saturate) {
2170
assert(!dest.dest.is_ssa);
2171
ttn_move_dest(b, dest, nir_fsat(b, ttn_src_for_dest(b, &dest)));
2172
}
2173
2174
/* if the dst has a matching var, append store_var to move
2175
* output from reg to var
2176
*/
2177
nir_variable *var = ttn_get_var(c, tgsi_dst);
2178
if (var) {
2179
unsigned index = tgsi_dst->Register.Index;
2180
unsigned offset = c->temp_regs[index].offset;
2181
struct tgsi_ind_register *indirect = tgsi_dst->Register.Indirect ?
2182
&tgsi_dst->Indirect : NULL;
2183
nir_src val = nir_src_for_reg(dest.dest.reg.reg);
2184
nir_store_deref(b, ttn_array_deref(c, var, offset, indirect),
2185
nir_ssa_for_src(b, val, 4), dest.write_mask);
2186
}
2187
}
2188
2189
/**
2190
* Puts a NIR intrinsic to store of each TGSI_FILE_OUTPUT value to the output
2191
* variables at the end of the shader.
2192
*
2193
* We don't generate these incrementally as the TGSI_FILE_OUTPUT values are
2194
* written, because there's no output load intrinsic, which means we couldn't
2195
* handle writemasks.
2196
*/
2197
static void
2198
ttn_add_output_stores(struct ttn_compile *c)
2199
{
2200
nir_builder *b = &c->build;
2201
2202
for (int i = 0; i < c->build.shader->num_outputs; i++) {
2203
nir_variable *var = c->outputs[i];
2204
if (!var)
2205
continue;
2206
2207
nir_src src = nir_src_for_reg(c->output_regs[i].reg);
2208
src.reg.base_offset = c->output_regs[i].offset;
2209
2210
nir_ssa_def *store_value = nir_ssa_for_src(b, src, 4);
2211
if (c->build.shader->info.stage == MESA_SHADER_FRAGMENT) {
2212
/* TGSI uses TGSI_SEMANTIC_POSITION.z for the depth output
2213
* and TGSI_SEMANTIC_STENCIL.y for the stencil output,
2214
* while NIR uses a single-component output.
2215
*/
2216
if (var->data.location == FRAG_RESULT_DEPTH)
2217
store_value = nir_channel(b, store_value, 2);
2218
else if (var->data.location == FRAG_RESULT_STENCIL)
2219
store_value = nir_channel(b, store_value, 1);
2220
else if (var->data.location == FRAG_RESULT_SAMPLE_MASK)
2221
store_value = nir_channel(b, store_value, 0);
2222
} else {
2223
/* FOGC and PSIZ are scalar values */
2224
if (var->data.location == VARYING_SLOT_FOGC ||
2225
var->data.location == VARYING_SLOT_PSIZ) {
2226
store_value = nir_channel(b, store_value, 0);
2227
}
2228
}
2229
2230
nir_store_deref(b, nir_build_deref_var(b, var), store_value,
2231
(1 << store_value->num_components) - 1);
2232
}
2233
}
2234
2235
/**
2236
* Parses the given TGSI tokens.
2237
*/
2238
static void
2239
ttn_parse_tgsi(struct ttn_compile *c, const void *tgsi_tokens)
2240
{
2241
struct tgsi_parse_context parser;
2242
ASSERTED int ret;
2243
2244
ret = tgsi_parse_init(&parser, tgsi_tokens);
2245
assert(ret == TGSI_PARSE_OK);
2246
2247
while (!tgsi_parse_end_of_tokens(&parser)) {
2248
tgsi_parse_token(&parser);
2249
c->token = &parser.FullToken;
2250
2251
switch (parser.FullToken.Token.Type) {
2252
case TGSI_TOKEN_TYPE_DECLARATION:
2253
ttn_emit_declaration(c);
2254
break;
2255
2256
case TGSI_TOKEN_TYPE_INSTRUCTION:
2257
ttn_emit_instruction(c);
2258
break;
2259
2260
case TGSI_TOKEN_TYPE_IMMEDIATE:
2261
ttn_emit_immediate(c);
2262
break;
2263
}
2264
}
2265
2266
tgsi_parse_free(&parser);
2267
}
2268
2269
static void
2270
ttn_read_pipe_caps(struct ttn_compile *c,
2271
struct pipe_screen *screen)
2272
{
2273
c->cap_samplers_as_deref = screen->get_param(screen, PIPE_CAP_NIR_SAMPLERS_AS_DEREF);
2274
c->cap_face_is_sysval = screen->get_param(screen, PIPE_CAP_TGSI_FS_FACE_IS_INTEGER_SYSVAL);
2275
c->cap_position_is_sysval = screen->get_param(screen, PIPE_CAP_TGSI_FS_POSITION_IS_SYSVAL);
2276
c->cap_point_is_sysval = screen->get_param(screen, PIPE_CAP_TGSI_FS_POINT_IS_SYSVAL);
2277
}
2278
2279
/**
2280
* Initializes a TGSI-to-NIR compiler.
2281
*/
2282
static struct ttn_compile *
2283
ttn_compile_init(const void *tgsi_tokens,
2284
const nir_shader_compiler_options *options,
2285
struct pipe_screen *screen)
2286
{
2287
struct ttn_compile *c;
2288
struct nir_shader *s;
2289
struct tgsi_shader_info scan;
2290
2291
assert(options || screen);
2292
c = rzalloc(NULL, struct ttn_compile);
2293
2294
tgsi_scan_shader(tgsi_tokens, &scan);
2295
c->scan = &scan;
2296
2297
if (!options) {
2298
options =
2299
screen->get_compiler_options(screen, PIPE_SHADER_IR_NIR, scan.processor);
2300
}
2301
2302
c->build = nir_builder_init_simple_shader(tgsi_processor_to_shader_stage(scan.processor),
2303
options, "TTN");
2304
2305
s = c->build.shader;
2306
2307
if (screen) {
2308
ttn_read_pipe_caps(c, screen);
2309
} else {
2310
/* TTN used to be hard coded to always make FACE a sysval,
2311
* so it makes sense to preserve that behavior so users don't break. */
2312
c->cap_face_is_sysval = true;
2313
}
2314
2315
if (s->info.stage == MESA_SHADER_FRAGMENT)
2316
s->info.fs.untyped_color_outputs = true;
2317
2318
s->num_inputs = scan.file_max[TGSI_FILE_INPUT] + 1;
2319
s->num_uniforms = scan.const_file_max[0] + 1;
2320
s->num_outputs = scan.file_max[TGSI_FILE_OUTPUT] + 1;
2321
s->info.num_ssbos = util_last_bit(scan.shader_buffers_declared);
2322
s->info.num_ubos = util_last_bit(scan.const_buffers_declared >> 1);
2323
s->info.num_images = util_last_bit(scan.images_declared);
2324
s->info.num_textures = util_last_bit(scan.samplers_declared);
2325
2326
for (unsigned i = 0; i < TGSI_PROPERTY_COUNT; i++) {
2327
unsigned value = scan.properties[i];
2328
2329
switch (i) {
2330
case TGSI_PROPERTY_FS_COLOR0_WRITES_ALL_CBUFS:
2331
break; /* handled in ttn_emit_declaration */
2332
case TGSI_PROPERTY_FS_COORD_ORIGIN:
2333
if (s->info.stage == MESA_SHADER_FRAGMENT)
2334
s->info.fs.origin_upper_left = value == TGSI_FS_COORD_ORIGIN_UPPER_LEFT;
2335
break;
2336
case TGSI_PROPERTY_FS_COORD_PIXEL_CENTER:
2337
if (s->info.stage == MESA_SHADER_FRAGMENT)
2338
s->info.fs.pixel_center_integer = value == TGSI_FS_COORD_PIXEL_CENTER_INTEGER;
2339
break;
2340
case TGSI_PROPERTY_FS_DEPTH_LAYOUT:
2341
if (s->info.stage == MESA_SHADER_FRAGMENT)
2342
s->info.fs.depth_layout = ttn_get_depth_layout(value);
2343
break;
2344
case TGSI_PROPERTY_VS_WINDOW_SPACE_POSITION:
2345
if (s->info.stage == MESA_SHADER_VERTEX)
2346
s->info.vs.window_space_position = value;
2347
break;
2348
case TGSI_PROPERTY_NEXT_SHADER:
2349
s->info.next_stage = tgsi_processor_to_shader_stage(value);
2350
break;
2351
case TGSI_PROPERTY_VS_BLIT_SGPRS_AMD:
2352
if (s->info.stage == MESA_SHADER_VERTEX)
2353
s->info.vs.blit_sgprs_amd = value;
2354
break;
2355
case TGSI_PROPERTY_CS_FIXED_BLOCK_WIDTH:
2356
if (s->info.stage == MESA_SHADER_COMPUTE)
2357
s->info.workgroup_size[0] = value;
2358
break;
2359
case TGSI_PROPERTY_CS_FIXED_BLOCK_HEIGHT:
2360
if (s->info.stage == MESA_SHADER_COMPUTE)
2361
s->info.workgroup_size[1] = value;
2362
break;
2363
case TGSI_PROPERTY_CS_FIXED_BLOCK_DEPTH:
2364
if (s->info.stage == MESA_SHADER_COMPUTE)
2365
s->info.workgroup_size[2] = value;
2366
break;
2367
case TGSI_PROPERTY_CS_USER_DATA_COMPONENTS_AMD:
2368
if (s->info.stage == MESA_SHADER_COMPUTE)
2369
s->info.cs.user_data_components_amd = value;
2370
break;
2371
case TGSI_PROPERTY_NUM_CLIPDIST_ENABLED:
2372
s->info.clip_distance_array_size = value;
2373
break;
2374
default:
2375
if (value) {
2376
fprintf(stderr, "tgsi_to_nir: unhandled TGSI property %u = %u\n",
2377
i, value);
2378
unreachable("unhandled TGSI property");
2379
}
2380
}
2381
}
2382
2383
if (s->info.stage == MESA_SHADER_COMPUTE &&
2384
(!s->info.workgroup_size[0] ||
2385
!s->info.workgroup_size[1] ||
2386
!s->info.workgroup_size[2]))
2387
s->info.workgroup_size_variable = true;
2388
2389
c->inputs = rzalloc_array(c, struct nir_variable *, s->num_inputs);
2390
c->outputs = rzalloc_array(c, struct nir_variable *, s->num_outputs);
2391
2392
c->output_regs = rzalloc_array(c, struct ttn_reg_info,
2393
scan.file_max[TGSI_FILE_OUTPUT] + 1);
2394
c->temp_regs = rzalloc_array(c, struct ttn_reg_info,
2395
scan.file_max[TGSI_FILE_TEMPORARY] + 1);
2396
c->imm_defs = rzalloc_array(c, nir_ssa_def *,
2397
scan.file_max[TGSI_FILE_IMMEDIATE] + 1);
2398
2399
c->num_samp_types = scan.file_max[TGSI_FILE_SAMPLER_VIEW] + 1;
2400
c->samp_types = rzalloc_array(c, nir_alu_type, c->num_samp_types);
2401
2402
ttn_parse_tgsi(c, tgsi_tokens);
2403
ttn_add_output_stores(c);
2404
2405
nir_validate_shader(c->build.shader, "TTN: after parsing TGSI and creating the NIR shader");
2406
2407
return c;
2408
}
2409
2410
static void
2411
ttn_optimize_nir(nir_shader *nir)
2412
{
2413
bool progress;
2414
do {
2415
progress = false;
2416
2417
NIR_PASS_V(nir, nir_lower_vars_to_ssa);
2418
2419
if (nir->options->lower_to_scalar) {
2420
NIR_PASS_V(nir, nir_lower_alu_to_scalar, NULL, NULL);
2421
NIR_PASS_V(nir, nir_lower_phis_to_scalar, false);
2422
}
2423
2424
NIR_PASS_V(nir, nir_lower_alu);
2425
NIR_PASS_V(nir, nir_lower_pack);
2426
NIR_PASS(progress, nir, nir_copy_prop);
2427
NIR_PASS(progress, nir, nir_opt_remove_phis);
2428
NIR_PASS(progress, nir, nir_opt_dce);
2429
2430
if (nir_opt_trivial_continues(nir)) {
2431
progress = true;
2432
NIR_PASS(progress, nir, nir_copy_prop);
2433
NIR_PASS(progress, nir, nir_opt_dce);
2434
}
2435
2436
NIR_PASS(progress, nir, nir_opt_if, false);
2437
NIR_PASS(progress, nir, nir_opt_dead_cf);
2438
NIR_PASS(progress, nir, nir_opt_cse);
2439
NIR_PASS(progress, nir, nir_opt_peephole_select, 8, true, true);
2440
2441
NIR_PASS(progress, nir, nir_opt_algebraic);
2442
NIR_PASS(progress, nir, nir_opt_constant_folding);
2443
2444
NIR_PASS(progress, nir, nir_opt_undef);
2445
NIR_PASS(progress, nir, nir_opt_conditional_discard);
2446
2447
if (nir->options->max_unroll_iterations) {
2448
NIR_PASS(progress, nir, nir_opt_loop_unroll, (nir_variable_mode)0);
2449
}
2450
2451
} while (progress);
2452
2453
}
2454
2455
/**
2456
* Finalizes the NIR in a similar way as st_glsl_to_nir does.
2457
*
2458
* Drivers expect that these passes are already performed,
2459
* so we have to do it here too.
2460
*/
2461
static void
2462
ttn_finalize_nir(struct ttn_compile *c, struct pipe_screen *screen)
2463
{
2464
struct nir_shader *nir = c->build.shader;
2465
2466
NIR_PASS_V(nir, nir_lower_vars_to_ssa);
2467
NIR_PASS_V(nir, nir_lower_regs_to_ssa);
2468
2469
NIR_PASS_V(nir, nir_lower_global_vars_to_local);
2470
NIR_PASS_V(nir, nir_split_var_copies);
2471
NIR_PASS_V(nir, nir_lower_var_copies);
2472
NIR_PASS_V(nir, nir_lower_system_values);
2473
NIR_PASS_V(nir, nir_lower_compute_system_values, NULL);
2474
2475
if (!screen->get_param(screen, PIPE_CAP_TEXRECT)) {
2476
const struct nir_lower_tex_options opts = { .lower_rect = true, };
2477
NIR_PASS_V(nir, nir_lower_tex, &opts);
2478
}
2479
2480
if (nir->options->lower_uniforms_to_ubo)
2481
NIR_PASS_V(nir, nir_lower_uniforms_to_ubo, false, false);
2482
2483
if (!c->cap_samplers_as_deref)
2484
NIR_PASS_V(nir, nir_lower_samplers);
2485
2486
if (screen->finalize_nir) {
2487
screen->finalize_nir(screen, nir, true);
2488
} else {
2489
ttn_optimize_nir(nir);
2490
nir_shader_gather_info(nir, c->build.impl);
2491
}
2492
2493
nir->info.num_images = c->num_images;
2494
nir->info.num_textures = c->num_samplers;
2495
2496
nir_validate_shader(nir, "TTN: after all optimizations");
2497
}
2498
2499
static void save_nir_to_disk_cache(struct disk_cache *cache,
2500
uint8_t key[CACHE_KEY_SIZE],
2501
const nir_shader *s)
2502
{
2503
struct blob blob = {0};
2504
2505
blob_init(&blob);
2506
/* Because we cannot fully trust disk_cache_put
2507
* (EGL_ANDROID_blob_cache) we add the shader size,
2508
* which we'll check after disk_cache_get().
2509
*/
2510
if (blob_reserve_uint32(&blob) != 0) {
2511
blob_finish(&blob);
2512
return;
2513
}
2514
2515
nir_serialize(&blob, s, true);
2516
*(uint32_t *)blob.data = blob.size;
2517
2518
disk_cache_put(cache, key, blob.data, blob.size, NULL);
2519
blob_finish(&blob);
2520
}
2521
2522
static nir_shader *
2523
load_nir_from_disk_cache(struct disk_cache *cache,
2524
struct pipe_screen *screen,
2525
uint8_t key[CACHE_KEY_SIZE],
2526
unsigned processor)
2527
{
2528
const nir_shader_compiler_options *options =
2529
screen->get_compiler_options(screen, PIPE_SHADER_IR_NIR, processor);
2530
struct blob_reader blob_reader;
2531
size_t size;
2532
nir_shader *s;
2533
2534
uint32_t *buffer = (uint32_t *)disk_cache_get(cache, key, &size);
2535
if (!buffer)
2536
return NULL;
2537
2538
/* Match found. No need to check crc32 or other things.
2539
* disk_cache_get is supposed to do that for us.
2540
* However we do still check if the first element is indeed the size,
2541
* as we cannot fully trust disk_cache_get (EGL_ANDROID_blob_cache) */
2542
if (buffer[0] != size) {
2543
return NULL;
2544
}
2545
2546
size -= 4;
2547
blob_reader_init(&blob_reader, buffer + 1, size);
2548
s = nir_deserialize(NULL, options, &blob_reader);
2549
free(buffer); /* buffer was malloc-ed */
2550
return s;
2551
}
2552
2553
struct nir_shader *
2554
tgsi_to_nir(const void *tgsi_tokens,
2555
struct pipe_screen *screen,
2556
bool allow_disk_cache)
2557
{
2558
struct disk_cache *cache = NULL;
2559
struct ttn_compile *c;
2560
struct nir_shader *s = NULL;
2561
uint8_t key[CACHE_KEY_SIZE];
2562
unsigned processor;
2563
2564
if (allow_disk_cache)
2565
cache = screen->get_disk_shader_cache(screen);
2566
2567
/* Look first in the cache */
2568
if (cache) {
2569
disk_cache_compute_key(cache,
2570
tgsi_tokens,
2571
tgsi_num_tokens(tgsi_tokens) * sizeof(struct tgsi_token),
2572
key);
2573
processor = tgsi_get_processor_type(tgsi_tokens);
2574
s = load_nir_from_disk_cache(cache, screen, key, processor);
2575
}
2576
2577
if (s)
2578
return s;
2579
2580
/* Not in the cache */
2581
2582
c = ttn_compile_init(tgsi_tokens, NULL, screen);
2583
s = c->build.shader;
2584
ttn_finalize_nir(c, screen);
2585
ralloc_free(c);
2586
2587
if (cache)
2588
save_nir_to_disk_cache(cache, key, s);
2589
2590
return s;
2591
}
2592
2593
struct nir_shader *
2594
tgsi_to_nir_noscreen(const void *tgsi_tokens,
2595
const nir_shader_compiler_options *options)
2596
{
2597
struct ttn_compile *c;
2598
struct nir_shader *s;
2599
2600
c = ttn_compile_init(tgsi_tokens, options, NULL);
2601
s = c->build.shader;
2602
ralloc_free(c);
2603
2604
return s;
2605
}
2606
2607
2608