ilo: use an accessor for dev->gen
[mesa.git] / src / gallium / drivers / ilo / ilo_shader.c
1 /*
2 * Mesa 3-D graphics library
3 *
4 * Copyright (C) 2012-2013 LunarG, Inc.
5 *
6 * Permission is hereby granted, free of charge, to any person obtaining a
7 * copy of this software and associated documentation files (the "Software"),
8 * to deal in the Software without restriction, including without limitation
9 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
10 * and/or sell copies of the Software, and to permit persons to whom the
11 * Software is furnished to do so, subject to the following conditions:
12 *
13 * The above copyright notice and this permission notice shall be included
14 * in all copies or substantial portions of the 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
22 * DEALINGS IN THE SOFTWARE.
23 *
24 * Authors:
25 * Chia-I Wu <olv@lunarg.com>
26 */
27
28 #include "genhw/genhw.h" /* for SBE setup */
29 #include "tgsi/tgsi_parse.h"
30 #include "intel_winsys.h"
31
32 #include "shader/ilo_shader_internal.h"
33 #include "ilo_builder.h"
34 #include "ilo_state.h"
35 #include "ilo_shader.h"
36
37 struct ilo_shader_cache {
38 struct list_head shaders;
39 struct list_head changed;
40 };
41
42 /**
43 * Create a shader cache. A shader cache can manage shaders and upload them
44 * to a bo as a whole.
45 */
46 struct ilo_shader_cache *
47 ilo_shader_cache_create(void)
48 {
49 struct ilo_shader_cache *shc;
50
51 shc = CALLOC_STRUCT(ilo_shader_cache);
52 if (!shc)
53 return NULL;
54
55 list_inithead(&shc->shaders);
56 list_inithead(&shc->changed);
57
58 return shc;
59 }
60
61 /**
62 * Destroy a shader cache.
63 */
64 void
65 ilo_shader_cache_destroy(struct ilo_shader_cache *shc)
66 {
67 FREE(shc);
68 }
69
70 /**
71 * Add a shader to the cache.
72 */
73 void
74 ilo_shader_cache_add(struct ilo_shader_cache *shc,
75 struct ilo_shader_state *shader)
76 {
77 struct ilo_shader *sh;
78
79 shader->cache = shc;
80 LIST_FOR_EACH_ENTRY(sh, &shader->variants, list)
81 sh->uploaded = false;
82
83 list_add(&shader->list, &shc->changed);
84 }
85
86 /**
87 * Remove a shader from the cache.
88 */
89 void
90 ilo_shader_cache_remove(struct ilo_shader_cache *shc,
91 struct ilo_shader_state *shader)
92 {
93 list_del(&shader->list);
94 shader->cache = NULL;
95 }
96
97 /**
98 * Notify the cache that a managed shader has changed.
99 */
100 static void
101 ilo_shader_cache_notify_change(struct ilo_shader_cache *shc,
102 struct ilo_shader_state *shader)
103 {
104 if (shader->cache == shc) {
105 list_del(&shader->list);
106 list_add(&shader->list, &shc->changed);
107 }
108 }
109
110 /**
111 * Upload managed shaders to the bo. Only shaders that are changed or added
112 * after the last upload are uploaded.
113 */
114 void
115 ilo_shader_cache_upload(struct ilo_shader_cache *shc,
116 struct ilo_builder *builder)
117 {
118 struct ilo_shader_state *shader, *next;
119
120 LIST_FOR_EACH_ENTRY_SAFE(shader, next, &shc->changed, list) {
121 struct ilo_shader *sh;
122
123 LIST_FOR_EACH_ENTRY(sh, &shader->variants, list) {
124 if (sh->uploaded)
125 continue;
126
127 sh->cache_offset = ilo_builder_instruction_write(builder,
128 sh->kernel_size, sh->kernel);
129
130 sh->uploaded = true;
131 }
132
133 list_del(&shader->list);
134 list_add(&shader->list, &shc->shaders);
135 }
136 }
137
138 /**
139 * Invalidate all shaders so that they get uploaded in next
140 * ilo_shader_cache_upload().
141 */
142 void
143 ilo_shader_cache_invalidate(struct ilo_shader_cache *shc)
144 {
145 struct ilo_shader_state *shader, *next;
146
147 LIST_FOR_EACH_ENTRY_SAFE(shader, next, &shc->shaders, list) {
148 list_del(&shader->list);
149 list_add(&shader->list, &shc->changed);
150 }
151
152 LIST_FOR_EACH_ENTRY(shader, &shc->changed, list) {
153 struct ilo_shader *sh;
154
155 LIST_FOR_EACH_ENTRY(sh, &shader->variants, list)
156 sh->uploaded = false;
157 }
158 }
159
160 /**
161 * Initialize a shader variant.
162 */
163 void
164 ilo_shader_variant_init(struct ilo_shader_variant *variant,
165 const struct ilo_shader_info *info,
166 const struct ilo_context *ilo)
167 {
168 int num_views, i;
169
170 memset(variant, 0, sizeof(*variant));
171
172 switch (info->type) {
173 case PIPE_SHADER_VERTEX:
174 variant->u.vs.rasterizer_discard =
175 ilo->rasterizer->state.rasterizer_discard;
176 variant->u.vs.num_ucps =
177 util_last_bit(ilo->rasterizer->state.clip_plane_enable);
178 break;
179 case PIPE_SHADER_GEOMETRY:
180 variant->u.gs.rasterizer_discard =
181 ilo->rasterizer->state.rasterizer_discard;
182 variant->u.gs.num_inputs = ilo->vs->shader->out.count;
183 for (i = 0; i < ilo->vs->shader->out.count; i++) {
184 variant->u.gs.semantic_names[i] =
185 ilo->vs->shader->out.semantic_names[i];
186 variant->u.gs.semantic_indices[i] =
187 ilo->vs->shader->out.semantic_indices[i];
188 }
189 break;
190 case PIPE_SHADER_FRAGMENT:
191 variant->u.fs.flatshade =
192 (info->has_color_interp && ilo->rasterizer->state.flatshade);
193 variant->u.fs.fb_height = (info->has_pos) ?
194 ilo->fb.state.height : 1;
195 variant->u.fs.num_cbufs = ilo->fb.state.nr_cbufs;
196 break;
197 default:
198 assert(!"unknown shader type");
199 break;
200 }
201
202 /* use PCB unless constant buffer 0 is not in user buffer */
203 if ((ilo->cbuf[info->type].enabled_mask & 0x1) &&
204 !ilo->cbuf[info->type].cso[0].user_buffer)
205 variant->use_pcb = false;
206 else
207 variant->use_pcb = true;
208
209 num_views = ilo->view[info->type].count;
210 assert(info->num_samplers <= num_views);
211
212 variant->num_sampler_views = info->num_samplers;
213 for (i = 0; i < info->num_samplers; i++) {
214 const struct pipe_sampler_view *view = ilo->view[info->type].states[i];
215 const struct ilo_sampler_cso *sampler = ilo->sampler[info->type].cso[i];
216
217 if (view) {
218 variant->sampler_view_swizzles[i].r = view->swizzle_r;
219 variant->sampler_view_swizzles[i].g = view->swizzle_g;
220 variant->sampler_view_swizzles[i].b = view->swizzle_b;
221 variant->sampler_view_swizzles[i].a = view->swizzle_a;
222 }
223 else if (info->shadow_samplers & (1 << i)) {
224 variant->sampler_view_swizzles[i].r = PIPE_SWIZZLE_RED;
225 variant->sampler_view_swizzles[i].g = PIPE_SWIZZLE_RED;
226 variant->sampler_view_swizzles[i].b = PIPE_SWIZZLE_RED;
227 variant->sampler_view_swizzles[i].a = PIPE_SWIZZLE_ONE;
228 }
229 else {
230 variant->sampler_view_swizzles[i].r = PIPE_SWIZZLE_RED;
231 variant->sampler_view_swizzles[i].g = PIPE_SWIZZLE_GREEN;
232 variant->sampler_view_swizzles[i].b = PIPE_SWIZZLE_BLUE;
233 variant->sampler_view_swizzles[i].a = PIPE_SWIZZLE_ALPHA;
234 }
235
236 /*
237 * When non-nearest filter and PIPE_TEX_WRAP_CLAMP wrap mode is used,
238 * the HW wrap mode is set to GEN6_TEXCOORDMODE_CLAMP_BORDER, and we
239 * need to manually saturate the texture coordinates.
240 */
241 if (sampler) {
242 variant->saturate_tex_coords[0] |= sampler->saturate_s << i;
243 variant->saturate_tex_coords[1] |= sampler->saturate_t << i;
244 variant->saturate_tex_coords[2] |= sampler->saturate_r << i;
245 }
246 }
247 }
248
249 /**
250 * Guess the shader variant, knowing that the context may still change.
251 */
252 static void
253 ilo_shader_variant_guess(struct ilo_shader_variant *variant,
254 const struct ilo_shader_info *info,
255 const struct ilo_context *ilo)
256 {
257 int i;
258
259 memset(variant, 0, sizeof(*variant));
260
261 switch (info->type) {
262 case PIPE_SHADER_VERTEX:
263 break;
264 case PIPE_SHADER_GEOMETRY:
265 break;
266 case PIPE_SHADER_FRAGMENT:
267 variant->u.fs.flatshade = false;
268 variant->u.fs.fb_height = (info->has_pos) ?
269 ilo->fb.state.height : 1;
270 variant->u.fs.num_cbufs = 1;
271 break;
272 default:
273 assert(!"unknown shader type");
274 break;
275 }
276
277 variant->use_pcb = true;
278
279 variant->num_sampler_views = info->num_samplers;
280 for (i = 0; i < info->num_samplers; i++) {
281 if (info->shadow_samplers & (1 << i)) {
282 variant->sampler_view_swizzles[i].r = PIPE_SWIZZLE_RED;
283 variant->sampler_view_swizzles[i].g = PIPE_SWIZZLE_RED;
284 variant->sampler_view_swizzles[i].b = PIPE_SWIZZLE_RED;
285 variant->sampler_view_swizzles[i].a = PIPE_SWIZZLE_ONE;
286 }
287 else {
288 variant->sampler_view_swizzles[i].r = PIPE_SWIZZLE_RED;
289 variant->sampler_view_swizzles[i].g = PIPE_SWIZZLE_GREEN;
290 variant->sampler_view_swizzles[i].b = PIPE_SWIZZLE_BLUE;
291 variant->sampler_view_swizzles[i].a = PIPE_SWIZZLE_ALPHA;
292 }
293 }
294 }
295
296
297 /**
298 * Parse a TGSI instruction for the shader info.
299 */
300 static void
301 ilo_shader_info_parse_inst(struct ilo_shader_info *info,
302 const struct tgsi_full_instruction *inst)
303 {
304 int i;
305
306 /* look for edgeflag passthrough */
307 if (info->edgeflag_out >= 0 &&
308 inst->Instruction.Opcode == TGSI_OPCODE_MOV &&
309 inst->Dst[0].Register.File == TGSI_FILE_OUTPUT &&
310 inst->Dst[0].Register.Index == info->edgeflag_out) {
311
312 assert(inst->Src[0].Register.File == TGSI_FILE_INPUT);
313 info->edgeflag_in = inst->Src[0].Register.Index;
314 }
315
316 if (inst->Instruction.Texture) {
317 bool shadow;
318
319 switch (inst->Texture.Texture) {
320 case TGSI_TEXTURE_SHADOW1D:
321 case TGSI_TEXTURE_SHADOW2D:
322 case TGSI_TEXTURE_SHADOWRECT:
323 case TGSI_TEXTURE_SHADOW1D_ARRAY:
324 case TGSI_TEXTURE_SHADOW2D_ARRAY:
325 case TGSI_TEXTURE_SHADOWCUBE:
326 case TGSI_TEXTURE_SHADOWCUBE_ARRAY:
327 shadow = true;
328 break;
329 default:
330 shadow = false;
331 break;
332 }
333
334 for (i = 0; i < inst->Instruction.NumSrcRegs; i++) {
335 const struct tgsi_full_src_register *src = &inst->Src[i];
336
337 if (src->Register.File == TGSI_FILE_SAMPLER) {
338 const int idx = src->Register.Index;
339
340 if (idx >= info->num_samplers)
341 info->num_samplers = idx + 1;
342
343 if (shadow)
344 info->shadow_samplers |= 1 << idx;
345 }
346 }
347 }
348 }
349
350 /**
351 * Parse a TGSI property for the shader info.
352 */
353 static void
354 ilo_shader_info_parse_prop(struct ilo_shader_info *info,
355 const struct tgsi_full_property *prop)
356 {
357 switch (prop->Property.PropertyName) {
358 case TGSI_PROPERTY_FS_COLOR0_WRITES_ALL_CBUFS:
359 info->fs_color0_writes_all_cbufs = prop->u[0].Data;
360 break;
361 default:
362 break;
363 }
364 }
365
366 /**
367 * Parse a TGSI declaration for the shader info.
368 */
369 static void
370 ilo_shader_info_parse_decl(struct ilo_shader_info *info,
371 const struct tgsi_full_declaration *decl)
372 {
373 switch (decl->Declaration.File) {
374 case TGSI_FILE_INPUT:
375 if (decl->Declaration.Interpolate &&
376 decl->Interp.Interpolate == TGSI_INTERPOLATE_COLOR)
377 info->has_color_interp = true;
378 if (decl->Declaration.Semantic &&
379 decl->Semantic.Name == TGSI_SEMANTIC_POSITION)
380 info->has_pos = true;
381 break;
382 case TGSI_FILE_OUTPUT:
383 if (decl->Declaration.Semantic &&
384 decl->Semantic.Name == TGSI_SEMANTIC_EDGEFLAG)
385 info->edgeflag_out = decl->Range.First;
386 break;
387 case TGSI_FILE_SYSTEM_VALUE:
388 if (decl->Declaration.Semantic &&
389 decl->Semantic.Name == TGSI_SEMANTIC_INSTANCEID)
390 info->has_instanceid = true;
391 if (decl->Declaration.Semantic &&
392 decl->Semantic.Name == TGSI_SEMANTIC_VERTEXID)
393 info->has_vertexid = true;
394 break;
395 default:
396 break;
397 }
398 }
399
400 static void
401 ilo_shader_info_parse_tokens(struct ilo_shader_info *info)
402 {
403 struct tgsi_parse_context parse;
404
405 info->edgeflag_in = -1;
406 info->edgeflag_out = -1;
407
408 tgsi_parse_init(&parse, info->tokens);
409 while (!tgsi_parse_end_of_tokens(&parse)) {
410 const union tgsi_full_token *token;
411
412 tgsi_parse_token(&parse);
413 token = &parse.FullToken;
414
415 switch (token->Token.Type) {
416 case TGSI_TOKEN_TYPE_DECLARATION:
417 ilo_shader_info_parse_decl(info, &token->FullDeclaration);
418 break;
419 case TGSI_TOKEN_TYPE_INSTRUCTION:
420 ilo_shader_info_parse_inst(info, &token->FullInstruction);
421 break;
422 case TGSI_TOKEN_TYPE_PROPERTY:
423 ilo_shader_info_parse_prop(info, &token->FullProperty);
424 break;
425 default:
426 break;
427 }
428 }
429 tgsi_parse_free(&parse);
430 }
431
432 /**
433 * Create a shader state.
434 */
435 static struct ilo_shader_state *
436 ilo_shader_state_create(const struct ilo_context *ilo,
437 int type, const void *templ)
438 {
439 struct ilo_shader_state *state;
440 struct ilo_shader_variant variant;
441
442 state = CALLOC_STRUCT(ilo_shader_state);
443 if (!state)
444 return NULL;
445
446 state->info.dev = ilo->dev;
447 state->info.type = type;
448
449 if (type == PIPE_SHADER_COMPUTE) {
450 const struct pipe_compute_state *c =
451 (const struct pipe_compute_state *) templ;
452
453 state->info.tokens = tgsi_dup_tokens(c->prog);
454 state->info.compute.req_local_mem = c->req_local_mem;
455 state->info.compute.req_private_mem = c->req_private_mem;
456 state->info.compute.req_input_mem = c->req_input_mem;
457 }
458 else {
459 const struct pipe_shader_state *s =
460 (const struct pipe_shader_state *) templ;
461
462 state->info.tokens = tgsi_dup_tokens(s->tokens);
463 state->info.stream_output = s->stream_output;
464 }
465
466 list_inithead(&state->variants);
467
468 ilo_shader_info_parse_tokens(&state->info);
469
470 /* guess and compile now */
471 ilo_shader_variant_guess(&variant, &state->info, ilo);
472 if (!ilo_shader_state_use_variant(state, &variant)) {
473 ilo_shader_destroy(state);
474 return NULL;
475 }
476
477 return state;
478 }
479
480 /**
481 * Add a compiled shader to the shader state.
482 */
483 static void
484 ilo_shader_state_add_shader(struct ilo_shader_state *state,
485 struct ilo_shader *sh)
486 {
487 list_add(&sh->list, &state->variants);
488 state->num_variants++;
489 state->total_size += sh->kernel_size;
490
491 if (state->cache)
492 ilo_shader_cache_notify_change(state->cache, state);
493 }
494
495 /**
496 * Remove a compiled shader from the shader state.
497 */
498 static void
499 ilo_shader_state_remove_shader(struct ilo_shader_state *state,
500 struct ilo_shader *sh)
501 {
502 list_del(&sh->list);
503 state->num_variants--;
504 state->total_size -= sh->kernel_size;
505 }
506
507 /**
508 * Garbage collect shader variants in the shader state.
509 */
510 static void
511 ilo_shader_state_gc(struct ilo_shader_state *state)
512 {
513 /* activate when the variants take up more than 4KiB of space */
514 const int limit = 4 * 1024;
515 struct ilo_shader *sh, *next;
516
517 if (state->total_size < limit)
518 return;
519
520 /* remove from the tail as the most recently ones are at the head */
521 LIST_FOR_EACH_ENTRY_SAFE_REV(sh, next, &state->variants, list) {
522 ilo_shader_state_remove_shader(state, sh);
523 ilo_shader_destroy_kernel(sh);
524
525 if (state->total_size <= limit / 2)
526 break;
527 }
528 }
529
530 /**
531 * Search for a shader variant.
532 */
533 static struct ilo_shader *
534 ilo_shader_state_search_variant(struct ilo_shader_state *state,
535 const struct ilo_shader_variant *variant)
536 {
537 struct ilo_shader *sh = NULL, *tmp;
538
539 LIST_FOR_EACH_ENTRY(tmp, &state->variants, list) {
540 if (memcmp(&tmp->variant, variant, sizeof(*variant)) == 0) {
541 sh = tmp;
542 break;
543 }
544 }
545
546 return sh;
547 }
548
549 static void
550 copy_so_info(struct ilo_shader *sh,
551 const struct pipe_stream_output_info *so_info)
552 {
553 unsigned i, attr;
554
555 if (!so_info->num_outputs)
556 return;
557
558 sh->so_info = *so_info;
559
560 for (i = 0; i < so_info->num_outputs; i++) {
561 /* figure out which attribute is sourced */
562 for (attr = 0; attr < sh->out.count; attr++) {
563 const int reg_idx = sh->out.register_indices[attr];
564 if (reg_idx == so_info->output[i].register_index)
565 break;
566 }
567
568 if (attr < sh->out.count) {
569 sh->so_info.output[i].register_index = attr;
570 }
571 else {
572 assert(!"stream output an undefined register");
573 sh->so_info.output[i].register_index = 0;
574 }
575
576 /* PSIZE is at W channel */
577 if (sh->out.semantic_names[attr] == TGSI_SEMANTIC_PSIZE) {
578 assert(so_info->output[i].start_component == 0);
579 assert(so_info->output[i].num_components == 1);
580 sh->so_info.output[i].start_component = 3;
581 }
582 }
583 }
584
585 /**
586 * Add a shader variant to the shader state.
587 */
588 static struct ilo_shader *
589 ilo_shader_state_add_variant(struct ilo_shader_state *state,
590 const struct ilo_shader_variant *variant)
591 {
592 struct ilo_shader *sh;
593
594 switch (state->info.type) {
595 case PIPE_SHADER_VERTEX:
596 sh = ilo_shader_compile_vs(state, variant);
597 break;
598 case PIPE_SHADER_FRAGMENT:
599 sh = ilo_shader_compile_fs(state, variant);
600 break;
601 case PIPE_SHADER_GEOMETRY:
602 sh = ilo_shader_compile_gs(state, variant);
603 break;
604 case PIPE_SHADER_COMPUTE:
605 sh = ilo_shader_compile_cs(state, variant);
606 break;
607 default:
608 sh = NULL;
609 break;
610 }
611 if (!sh) {
612 assert(!"failed to compile shader");
613 return NULL;
614 }
615
616 sh->variant = *variant;
617
618 copy_so_info(sh, &state->info.stream_output);
619
620 ilo_shader_state_add_shader(state, sh);
621
622 return sh;
623 }
624
625 /**
626 * Update state->shader to point to a variant. If the variant does not exist,
627 * it will be added first.
628 */
629 bool
630 ilo_shader_state_use_variant(struct ilo_shader_state *state,
631 const struct ilo_shader_variant *variant)
632 {
633 struct ilo_shader *sh;
634 bool construct_cso = false;
635
636 sh = ilo_shader_state_search_variant(state, variant);
637 if (!sh) {
638 ilo_shader_state_gc(state);
639
640 sh = ilo_shader_state_add_variant(state, variant);
641 if (!sh)
642 return false;
643
644 construct_cso = true;
645 }
646
647 /* move to head */
648 if (state->variants.next != &sh->list) {
649 list_del(&sh->list);
650 list_add(&sh->list, &state->variants);
651 }
652
653 state->shader = sh;
654
655 if (construct_cso) {
656 switch (state->info.type) {
657 case PIPE_SHADER_VERTEX:
658 ilo_gpe_init_vs_cso(state->info.dev, state, &sh->cso);
659 break;
660 case PIPE_SHADER_GEOMETRY:
661 ilo_gpe_init_gs_cso(state->info.dev, state, &sh->cso);
662 break;
663 case PIPE_SHADER_FRAGMENT:
664 ilo_gpe_init_fs_cso(state->info.dev, state, &sh->cso);
665 break;
666 default:
667 break;
668 }
669 }
670
671 return true;
672 }
673
674 struct ilo_shader_state *
675 ilo_shader_create_vs(const struct ilo_dev_info *dev,
676 const struct pipe_shader_state *state,
677 const struct ilo_context *precompile)
678 {
679 struct ilo_shader_state *shader;
680
681 shader = ilo_shader_state_create(precompile, PIPE_SHADER_VERTEX, state);
682
683 /* states used in ilo_shader_variant_init() */
684 shader->info.non_orthogonal_states = ILO_DIRTY_VIEW_VS |
685 ILO_DIRTY_RASTERIZER |
686 ILO_DIRTY_CBUF;
687
688 return shader;
689 }
690
691 struct ilo_shader_state *
692 ilo_shader_create_gs(const struct ilo_dev_info *dev,
693 const struct pipe_shader_state *state,
694 const struct ilo_context *precompile)
695 {
696 struct ilo_shader_state *shader;
697
698 shader = ilo_shader_state_create(precompile, PIPE_SHADER_GEOMETRY, state);
699
700 /* states used in ilo_shader_variant_init() */
701 shader->info.non_orthogonal_states = ILO_DIRTY_VIEW_GS |
702 ILO_DIRTY_VS |
703 ILO_DIRTY_RASTERIZER |
704 ILO_DIRTY_CBUF;
705
706 return shader;
707 }
708
709 struct ilo_shader_state *
710 ilo_shader_create_fs(const struct ilo_dev_info *dev,
711 const struct pipe_shader_state *state,
712 const struct ilo_context *precompile)
713 {
714 struct ilo_shader_state *shader;
715
716 shader = ilo_shader_state_create(precompile, PIPE_SHADER_FRAGMENT, state);
717
718 /* states used in ilo_shader_variant_init() */
719 shader->info.non_orthogonal_states = ILO_DIRTY_VIEW_FS |
720 ILO_DIRTY_RASTERIZER |
721 ILO_DIRTY_FB |
722 ILO_DIRTY_CBUF;
723
724 return shader;
725 }
726
727 struct ilo_shader_state *
728 ilo_shader_create_cs(const struct ilo_dev_info *dev,
729 const struct pipe_compute_state *state,
730 const struct ilo_context *precompile)
731 {
732 struct ilo_shader_state *shader;
733
734 shader = ilo_shader_state_create(precompile, PIPE_SHADER_COMPUTE, state);
735
736 shader->info.non_orthogonal_states = 0;
737
738 return shader;
739 }
740
741 /**
742 * Destroy a shader state.
743 */
744 void
745 ilo_shader_destroy(struct ilo_shader_state *shader)
746 {
747 struct ilo_shader *sh, *next;
748
749 LIST_FOR_EACH_ENTRY_SAFE(sh, next, &shader->variants, list)
750 ilo_shader_destroy_kernel(sh);
751
752 FREE((struct tgsi_token *) shader->info.tokens);
753 FREE(shader);
754 }
755
756 /**
757 * Return the type (PIPE_SHADER_x) of the shader.
758 */
759 int
760 ilo_shader_get_type(const struct ilo_shader_state *shader)
761 {
762 return shader->info.type;
763 }
764
765 /**
766 * Select a kernel for the given context. This will compile a new kernel if
767 * none of the existing kernels work with the context.
768 *
769 * \param ilo the context
770 * \param dirty states of the context that are considered changed
771 * \return true if a different kernel is selected
772 */
773 bool
774 ilo_shader_select_kernel(struct ilo_shader_state *shader,
775 const struct ilo_context *ilo,
776 uint32_t dirty)
777 {
778 const struct ilo_shader * const cur = shader->shader;
779 struct ilo_shader_variant variant;
780
781 if (!(shader->info.non_orthogonal_states & dirty))
782 return false;
783
784 ilo_shader_variant_init(&variant, &shader->info, ilo);
785 ilo_shader_state_use_variant(shader, &variant);
786
787 return (shader->shader != cur);
788 }
789
790 static int
791 route_attr(const int *semantics, const int *indices, int len,
792 int semantic, int index)
793 {
794 int i;
795
796 for (i = 0; i < len; i++) {
797 if (semantics[i] == semantic && indices[i] == index)
798 return i;
799 }
800
801 /* failed to match for COLOR, try BCOLOR */
802 if (semantic == TGSI_SEMANTIC_COLOR) {
803 for (i = 0; i < len; i++) {
804 if (semantics[i] == TGSI_SEMANTIC_BCOLOR && indices[i] == index)
805 return i;
806 }
807 }
808
809 return -1;
810 }
811
812 /**
813 * Select a routing for the given source shader and rasterizer state.
814 *
815 * \return true if a different routing is selected
816 */
817 bool
818 ilo_shader_select_kernel_routing(struct ilo_shader_state *shader,
819 const struct ilo_shader_state *source,
820 const struct ilo_rasterizer_state *rasterizer)
821 {
822 const uint32_t sprite_coord_enable = rasterizer->state.sprite_coord_enable;
823 const bool light_twoside = rasterizer->state.light_twoside;
824 struct ilo_shader *kernel = shader->shader;
825 struct ilo_kernel_routing *routing = &kernel->routing;
826 const int *src_semantics, *src_indices;
827 int src_len, max_src_slot;
828 int dst_len, dst_slot;
829
830 /* we are constructing 3DSTATE_SBE here */
831 assert(ilo_dev_gen(shader->info.dev) >= ILO_GEN(6) &&
832 ilo_dev_gen(shader->info.dev) <= ILO_GEN(7.5));
833
834 assert(kernel);
835
836 if (source) {
837 assert(source->shader);
838 src_semantics = source->shader->out.semantic_names;
839 src_indices = source->shader->out.semantic_indices;
840 src_len = source->shader->out.count;
841 }
842 else {
843 src_semantics = kernel->in.semantic_names;
844 src_indices = kernel->in.semantic_indices;
845 src_len = kernel->in.count;
846 }
847
848 /* no change */
849 if (kernel->routing_initialized &&
850 routing->source_skip + routing->source_len <= src_len &&
851 kernel->routing_sprite_coord_enable == sprite_coord_enable &&
852 !memcmp(kernel->routing_src_semantics,
853 &src_semantics[routing->source_skip],
854 sizeof(kernel->routing_src_semantics[0]) * routing->source_len) &&
855 !memcmp(kernel->routing_src_indices,
856 &src_indices[routing->source_skip],
857 sizeof(kernel->routing_src_indices[0]) * routing->source_len))
858 return false;
859
860 if (source) {
861 /* skip PSIZE and POSITION (how about the optional CLIPDISTs?) */
862 assert(src_semantics[0] == TGSI_SEMANTIC_PSIZE);
863 assert(src_semantics[1] == TGSI_SEMANTIC_POSITION);
864 routing->source_skip = 2;
865
866 routing->source_len = src_len - routing->source_skip;
867 src_semantics += routing->source_skip;
868 src_indices += routing->source_skip;
869 }
870 else {
871 routing->source_skip = 0;
872 routing->source_len = src_len;
873 }
874
875 routing->const_interp_enable = kernel->in.const_interp_enable;
876 routing->point_sprite_enable = 0;
877 routing->swizzle_enable = false;
878
879 assert(kernel->in.count <= Elements(routing->swizzles));
880 dst_len = MIN2(kernel->in.count, Elements(routing->swizzles));
881 max_src_slot = -1;
882
883 for (dst_slot = 0; dst_slot < dst_len; dst_slot++) {
884 const int semantic = kernel->in.semantic_names[dst_slot];
885 const int index = kernel->in.semantic_indices[dst_slot];
886 int src_slot;
887
888 if (semantic == TGSI_SEMANTIC_GENERIC &&
889 (sprite_coord_enable & (1 << index)))
890 routing->point_sprite_enable |= 1 << dst_slot;
891
892 if (source) {
893 src_slot = route_attr(src_semantics, src_indices,
894 routing->source_len, semantic, index);
895
896 /*
897 * The source shader stage does not output this attribute. The value
898 * is supposed to be undefined, unless the attribute goes through
899 * point sprite replacement or the attribute is
900 * TGSI_SEMANTIC_POSITION. In all cases, we do not care which source
901 * attribute is picked.
902 *
903 * We should update the kernel code and omit the output of
904 * TGSI_SEMANTIC_POSITION here.
905 */
906 if (src_slot < 0)
907 src_slot = 0;
908 }
909 else {
910 src_slot = dst_slot;
911 }
912
913 routing->swizzles[dst_slot] = src_slot;
914
915 /* use the following slot for two-sided lighting */
916 if (semantic == TGSI_SEMANTIC_COLOR && light_twoside &&
917 src_slot + 1 < routing->source_len &&
918 src_semantics[src_slot + 1] == TGSI_SEMANTIC_BCOLOR &&
919 src_indices[src_slot + 1] == index) {
920 routing->swizzles[dst_slot] |= GEN7_SBE_ATTR_INPUTATTR_FACING;
921 src_slot++;
922 }
923
924 if (routing->swizzles[dst_slot] != dst_slot)
925 routing->swizzle_enable = true;
926
927 if (max_src_slot < src_slot)
928 max_src_slot = src_slot;
929 }
930
931 memset(&routing->swizzles[dst_slot], 0, sizeof(routing->swizzles) -
932 sizeof(routing->swizzles[0]) * dst_slot);
933
934 /*
935 * From the Sandy Bridge PRM, volume 2 part 1, page 248:
936 *
937 * "It is UNDEFINED to set this field (Vertex URB Entry Read Length) to
938 * 0 indicating no Vertex URB data to be read.
939 *
940 * This field should be set to the minimum length required to read the
941 * maximum source attribute. The maximum source attribute is indicated
942 * by the maximum value of the enabled Attribute # Source Attribute if
943 * Attribute Swizzle Enable is set, Number of Output Attributes-1 if
944 * enable is not set.
945 *
946 * read_length = ceiling((max_source_attr+1)/2)
947 *
948 * [errata] Corruption/Hang possible if length programmed larger than
949 * recommended"
950 */
951 routing->source_len = max_src_slot + 1;
952
953 /* remember the states of the source */
954 kernel->routing_initialized = true;
955 kernel->routing_sprite_coord_enable = sprite_coord_enable;
956 memcpy(kernel->routing_src_semantics, src_semantics,
957 sizeof(kernel->routing_src_semantics[0]) * routing->source_len);
958 memcpy(kernel->routing_src_indices, src_indices,
959 sizeof(kernel->routing_src_indices[0]) * routing->source_len);
960
961 return true;
962 }
963
964 /**
965 * Return the cache offset of the selected kernel. This must be called after
966 * ilo_shader_select_kernel() and ilo_shader_cache_upload().
967 */
968 uint32_t
969 ilo_shader_get_kernel_offset(const struct ilo_shader_state *shader)
970 {
971 const struct ilo_shader *kernel = shader->shader;
972
973 assert(kernel && kernel->uploaded);
974
975 return kernel->cache_offset;
976 }
977
978 /**
979 * Query a kernel parameter for the selected kernel.
980 */
981 int
982 ilo_shader_get_kernel_param(const struct ilo_shader_state *shader,
983 enum ilo_kernel_param param)
984 {
985 const struct ilo_shader *kernel = shader->shader;
986 int val;
987
988 assert(kernel);
989
990 switch (param) {
991 case ILO_KERNEL_INPUT_COUNT:
992 val = kernel->in.count;
993 break;
994 case ILO_KERNEL_OUTPUT_COUNT:
995 val = kernel->out.count;
996 break;
997 case ILO_KERNEL_URB_DATA_START_REG:
998 val = kernel->in.start_grf;
999 break;
1000 case ILO_KERNEL_SKIP_CBUF0_UPLOAD:
1001 val = kernel->skip_cbuf0_upload;
1002 break;
1003 case ILO_KERNEL_PCB_CBUF0_SIZE:
1004 val = kernel->pcb.cbuf0_size;
1005 break;
1006
1007 case ILO_KERNEL_VS_INPUT_INSTANCEID:
1008 val = shader->info.has_instanceid;
1009 break;
1010 case ILO_KERNEL_VS_INPUT_VERTEXID:
1011 val = shader->info.has_vertexid;
1012 break;
1013 case ILO_KERNEL_VS_INPUT_EDGEFLAG:
1014 if (shader->info.edgeflag_in >= 0) {
1015 /* we rely on the state tracker here */
1016 assert(shader->info.edgeflag_in == kernel->in.count - 1);
1017 val = true;
1018 }
1019 else {
1020 val = false;
1021 }
1022 break;
1023 case ILO_KERNEL_VS_PCB_UCP_SIZE:
1024 val = kernel->pcb.clip_state_size;
1025 break;
1026 case ILO_KERNEL_VS_GEN6_SO:
1027 val = kernel->stream_output;
1028 break;
1029 case ILO_KERNEL_VS_GEN6_SO_START_REG:
1030 val = kernel->gs_start_grf;
1031 break;
1032 case ILO_KERNEL_VS_GEN6_SO_POINT_OFFSET:
1033 val = kernel->gs_offsets[0];
1034 break;
1035 case ILO_KERNEL_VS_GEN6_SO_LINE_OFFSET:
1036 val = kernel->gs_offsets[1];
1037 break;
1038 case ILO_KERNEL_VS_GEN6_SO_TRI_OFFSET:
1039 val = kernel->gs_offsets[2];
1040 break;
1041
1042 case ILO_KERNEL_GS_DISCARD_ADJACENCY:
1043 val = kernel->in.discard_adj;
1044 break;
1045 case ILO_KERNEL_GS_GEN6_SVBI_POST_INC:
1046 val = kernel->svbi_post_inc;
1047 break;
1048
1049 case ILO_KERNEL_FS_INPUT_Z:
1050 case ILO_KERNEL_FS_INPUT_W:
1051 val = kernel->in.has_pos;
1052 break;
1053 case ILO_KERNEL_FS_OUTPUT_Z:
1054 val = kernel->out.has_pos;
1055 break;
1056 case ILO_KERNEL_FS_USE_KILL:
1057 val = kernel->has_kill;
1058 break;
1059 case ILO_KERNEL_FS_BARYCENTRIC_INTERPOLATIONS:
1060 val = kernel->in.barycentric_interpolation_mode;
1061 break;
1062 case ILO_KERNEL_FS_DISPATCH_16_OFFSET:
1063 val = 0;
1064 break;
1065
1066 default:
1067 assert(!"unknown kernel parameter");
1068 val = 0;
1069 break;
1070 }
1071
1072 return val;
1073 }
1074
1075 /**
1076 * Return the CSO of the selected kernel.
1077 */
1078 const struct ilo_shader_cso *
1079 ilo_shader_get_kernel_cso(const struct ilo_shader_state *shader)
1080 {
1081 const struct ilo_shader *kernel = shader->shader;
1082
1083 assert(kernel);
1084
1085 return &kernel->cso;
1086 }
1087
1088 /**
1089 * Return the SO info of the selected kernel.
1090 */
1091 const struct pipe_stream_output_info *
1092 ilo_shader_get_kernel_so_info(const struct ilo_shader_state *shader)
1093 {
1094 const struct ilo_shader *kernel = shader->shader;
1095
1096 assert(kernel);
1097
1098 return &kernel->so_info;
1099 }
1100
1101 /**
1102 * Return the routing info of the selected kernel.
1103 */
1104 const struct ilo_kernel_routing *
1105 ilo_shader_get_kernel_routing(const struct ilo_shader_state *shader)
1106 {
1107 const struct ilo_shader *kernel = shader->shader;
1108
1109 assert(kernel);
1110
1111 return &kernel->routing;
1112 }