1 /*
2 * Copyright © 2012 Rob Clark <[email protected]>
3 * SPDX-License-Identifier: MIT
4 */
5
6 #include <fcntl.h>
7 #include <stdint.h>
8 #include <stdio.h>
9 #include <stdlib.h>
10 #include <string.h>
11 #include <unistd.h>
12 #include <sys/stat.h>
13 #include <sys/types.h>
14
15 #include "disasm.h"
16 #include "io.h"
17 #include "redump.h"
18
19 #define ASCII_XOR 0xff
20 #include "util.h"
21
22 struct pgm_header {
23 uint32_t size;
24 uint32_t unknown1;
25 uint32_t unknown2;
26 uint32_t revision;
27 uint32_t unknown4;
28 uint32_t unknown5;
29 uint32_t unknown6;
30 uint32_t unknown7;
31 uint32_t unknown8;
32 uint32_t num_attribs;
33 uint32_t num_uniforms;
34 uint32_t num_samplers;
35 uint32_t num_varyings;
36 uint32_t num_uniformblocks;
37 };
38
39 struct vs_header {
40 uint32_t unknown1; /* seems to be # of sections up to and including shader */
41 uint32_t unknown2; /* seems to be low byte or so of SQ_PROGRAM_CNTL */
42 uint32_t unknown3;
43 uint32_t unknown4;
44 uint32_t unknown5;
45 uint32_t unknown6;
46 uint32_t unknown7;
47 uint32_t unknown8;
48 uint32_t unknown9; /* seems to be # of sections following shader */
49 };
50
51 struct fs_header {
52 uint32_t unknown1;
53 };
54 /*
55 // Covers a lot of type_info
56 // varying, attribute, uniform, sampler
57 type_info & 0xFF
58 if ((type_info >> 8) == 0x8b) // vector
59 0x50 = vec2
60 0x51 = vec3
61 0x52 = vec4
62 0x53 = ivec2
63 0x54 = ivec3
64 0x55 = ivec4
65 0x56 = bool // Why is this in vector?
66 0x57 = bvec2
67 0x58 = bvec3
68 0x59 = bvec4
69 0x5a = mat2
70 0x5b = mat3
71 0x5c = mat4
72 0x5a = mat2x2 // Same as mat2
73 0x65 = mat2x3
74 0x66 = mat2x4
75 0x67 = mat3x2
76 0x5b = mat3x3 // Same as mat3
77 0x68 = mat3x4
78 0x69 = mat4x2
79 0x6a = mat4x3
80 0x5c = mat4x4 // same as mat4
81 0x5e = sampler2D
82 0x5f = sampler3D
83 0x60 = samplerCube // XXX: Doesn't work
84 0x62 = sampler2DShadow
85 0xc6 = uvec2
86 0xc7 = uvec3
87 0xc8 = uvec4
88 else if ((type_info >> 8) == 0x8d) // GLES3 samplers
89 0xC1 = sampler2DArray
90 0xC4 = sampler2DArrayShadow
91 0xC5 = samplerCubeShadow
92 0xCA = isampler2D
93 0xCB = isampler3D
94 0xCC = isamplerCube
95 0xD2 = usampler2D
96 0xD3 = usampler3D
97 0xD4 = usamplerCube
98 0xD7 = isampler2DArray
99 0xD7 = usampler2DArray // Is the same as isampler2DArray?
100 else // 0x14 = single
101 0x04 = int
102 0x05 = uint
103 0x06 = float
104 */
105 struct attribute {
106 uint32_t type_info;
107 uint32_t reg; /* seems to be the register the fetch instruction loads to */
108 uint32_t const_idx; /* the CONST() indx value for sampler */
109 uint32_t unknown2;
110 uint32_t unknown3;
111 uint32_t unknown4;
112 uint32_t unknown5;
113 char name[];
114 };
115
116 struct uniform {
117 uint32_t type_info;
118 uint32_t unknown2;
119 uint32_t unknown3;
120 uint32_t unknown4;
121 uint32_t const_base; /* const base register (for uniforms that take more than
122 one const reg, ie. matrices) */
123 uint32_t unknown6;
124 uint32_t const_reg; /* the const register holding the value */
125 uint32_t unknown7;
126 uint32_t unknown8;
127 uint32_t unknown9;
128 union {
129 struct {
130 char name[1];
131 } v1;
132 struct {
133 uint32_t unknown10;
134 uint32_t unknown11;
135 uint32_t unknown12;
136 char name[];
137 } v2;
138 };
139 };
140
141 struct uniformblockmember {
142 uint32_t type_info;
143 uint32_t is_array;
144 uint32_t array_size; /* elements in the array */
145 uint32_t unknown2; /* Same as array_size */
146 uint32_t
147 unknown3; /* Seems to be a offset within UBO in vertex (by components) */
148 uint32_t unknown4;
149 uint32_t
150 unknown5; /* Seems to be a offset within UBO in fragment (by vec4) */
151 uint32_t unknown6;
152 uint32_t unknown7;
153 uint32_t unknown8;
154 uint32_t unknown9; /* UBO block index? */
155 uint32_t unknown10;
156 uint32_t unknown11;
157 uint32_t unknown12;
158 char name[];
159 };
160
161 struct uniformblock {
162 uint32_t type_info;
163 uint32_t unknown1;
164 uint32_t unknown2;
165 uint32_t unknown3;
166 uint32_t unknown4;
167 uint32_t num_members;
168 uint32_t num_members2;
169 uint32_t unknown5;
170 uint32_t unknown6;
171 uint32_t unknown7;
172 char name[];
173 };
174
175 struct sampler {
176 uint32_t type_info;
177 uint32_t is_array;
178 uint32_t array_size; /* elements in the array */
179 uint32_t unknown4; /* same as array_size */
180 uint32_t unknown5;
181 uint32_t unknown6;
182 uint32_t const_idx; /* the CONST() indx value for the sampler */
183 uint32_t unknown7;
184 char name[];
185 };
186
187 struct varying {
188 uint32_t type_info;
189 uint32_t unknown2;
190 uint32_t unknown3;
191 uint32_t reg; /* the register holding the value (on entry to the shader) */
192 char name[];
193 };
194
195 struct output {
196 uint32_t type_info;
197 uint32_t unknown2;
198 uint32_t unknown3;
199 uint32_t unknown4;
200 uint32_t unknown5;
201 uint32_t unknown6;
202 uint32_t unknown7;
203 uint32_t unknown8;
204 char name[];
205 };
206
207 struct constant {
208 uint32_t unknown1;
209 uint32_t unknown2;
210 uint32_t unknown3;
211 uint32_t const_idx;
212 float val[];
213 };
214
215 struct state {
216 char *buf;
217 int sz;
218 struct pgm_header *hdr;
219 struct attribute *attribs[32]; /* don't really know the upper limit.. */
220 struct uniform *uniforms[32];
221 struct sampler *samplers[32];
222 struct varying *varyings[32];
223 struct {
224 struct uniformblock *header;
225 struct uniformblockmember **members; /* GL ES 3.0 spec mandates minimum
226 16K support. a3xx supports 65K */
227 } uniformblocks[24]; /* Maximum a330 supports */
228 struct output *outputs[0]; /* I guess only one?? */
229 };
230
231 static const char *infile;
232 static int full_dump = 1;
233 static int dump_shaders = 0;
234 static int gpu_id;
235
236 static char *
find_sect_end(char * buf,int sz)237 find_sect_end(char *buf, int sz)
238 {
239 uint8_t *ptr = (uint8_t *)buf;
240 uint8_t *end = ptr + sz - 3;
241
242 while (ptr < end) {
243 uint32_t d = 0;
244
245 d |= ptr[0] << 0;
246 d |= ptr[1] << 8;
247 d |= ptr[2] << 16;
248 d |= ptr[3] << 24;
249
250 /* someone at QC likes baseball */
251 if (d == 0xba5eba11)
252 return (char *)ptr;
253
254 ptr++;
255 }
256 return NULL;
257 }
258
259 static void *
next_sect(struct state * state,int * sect_size)260 next_sect(struct state *state, int *sect_size)
261 {
262 char *end = find_sect_end(state->buf, state->sz);
263 void *sect;
264
265 if (!end)
266 return NULL;
267
268 *sect_size = end - state->buf;
269
270 /* copy the section to keep things nicely 32b aligned: */
271 sect = malloc(ALIGN(*sect_size, 4));
272 memcpy(sect, state->buf, *sect_size);
273
274 state->sz -= *sect_size + 4;
275 state->buf = end + 4;
276
277 return sect;
278 }
279
280 static int
valid_type(uint32_t type_info)281 valid_type(uint32_t type_info)
282 {
283 switch ((type_info >> 8) & 0xff) {
284 case 0x8b: /* vector */
285 case 0x8d: /* GLES3 samplers */
286 case 0x14: /* float */
287 return 1;
288 default:
289 return 0;
290 }
291 }
292
293 #if 0
294 static int valid_uniformblock(uint32_t type_info)
295 {
296 if (type_info == 0x128)
297 return 1;
298 return 0;
299 }
300 #endif
301
302 static void
dump_attribute(struct attribute * attrib)303 dump_attribute(struct attribute *attrib)
304 {
305 printf("\tR%d, CONST(%d): %s\n", attrib->reg, attrib->const_idx,
306 attrib->name);
307 }
308
309 static inline int
is_uniform_v2(struct uniform * uniform)310 is_uniform_v2(struct uniform *uniform)
311 {
312 /* TODO maybe this should be based on revision #? */
313 if (uniform->v2.unknown10 == 0)
314 return 1;
315 return 0;
316 }
317
318 static void
dump_uniform(struct uniform * uniform)319 dump_uniform(struct uniform *uniform)
320 {
321 char *name = is_uniform_v2(uniform) ? uniform->v2.name : uniform->v1.name;
322 if (uniform->const_reg == -1) {
323 printf("\tC%d+: %s\n", uniform->const_base, name);
324 } else {
325 printf("\tC%d: %s\n", uniform->const_reg, name);
326 }
327 }
328
329 static void
dump_sampler(struct sampler * sampler)330 dump_sampler(struct sampler *sampler)
331 {
332 printf("\tCONST(%d): %s\n", sampler->const_idx, sampler->name);
333 }
334
335 static void
dump_varying(struct varying * varying)336 dump_varying(struct varying *varying)
337 {
338 printf("\tR%d: %s\n", varying->reg, varying->name);
339 }
340
341 static void
dump_uniformblock(struct uniformblock * uniformblock)342 dump_uniformblock(struct uniformblock *uniformblock)
343 {
344 printf("\tUniform Block: %s(%d)\n", uniformblock->name,
345 uniformblock->num_members);
346 }
347
348 static void
dump_uniformblockmember(struct uniformblockmember * member)349 dump_uniformblockmember(struct uniformblockmember *member)
350 {
351 printf("Uniform Block member: %s\n", member->name);
352 }
353
354 static void
dump_output(struct output * output)355 dump_output(struct output *output)
356 {
357 printf("\tR?: %s\n", output->name);
358 }
359
360 static void
dump_constant(struct constant * constant)361 dump_constant(struct constant *constant)
362 {
363 printf("\tC%d: %f, %f, %f, %f\n", constant->const_idx, constant->val[0],
364 constant->val[1], constant->val[2], constant->val[3]);
365 }
366
367 /* dump attr/uniform/sampler/varying/const summary: */
368 static void
dump_short_summary(struct state * state,int nconsts,struct constant ** constants)369 dump_short_summary(struct state *state, int nconsts,
370 struct constant **constants)
371 {
372 int i;
373
374 /* dump attr/uniform/sampler/varying/const summary: */
375 for (i = 0; i < state->hdr->num_varyings; i++) {
376 dump_varying(state->varyings[i]);
377 }
378 for (i = 0; i < state->hdr->num_attribs; i++) {
379 dump_attribute(state->attribs[i]);
380 }
381 for (i = 0; i < state->hdr->num_uniforms; i++) {
382 dump_uniform(state->uniforms[i]);
383 }
384 for (i = 0; i < state->hdr->num_samplers; i++) {
385 dump_sampler(state->samplers[i]);
386 }
387 for (i = 0; i < nconsts - 1; i++) {
388 if (constants[i]->unknown2 == 0) {
389 dump_constant(constants[i]);
390 }
391 }
392 printf("\n");
393 }
394
395 static void
dump_raw_shader(uint32_t * dwords,uint32_t sizedwords,int n,char * ext)396 dump_raw_shader(uint32_t *dwords, uint32_t sizedwords, int n, char *ext)
397 {
398 static char filename[256];
399 int fd;
400
401 if (!dump_shaders)
402 return;
403
404 sprintf(filename, "%.*s-%d.%s", (int)strlen(infile) - 3, infile, n, ext);
405 fd = open(filename, O_WRONLY | O_TRUNC | O_CREAT, 0644);
406 if (fd != -1) {
407 write(fd, dwords, sizedwords * 4);
408 close(fd);
409 }
410 }
411
412 static void
dump_shaders_a2xx(struct state * state)413 dump_shaders_a2xx(struct state *state)
414 {
415 int i, sect_size;
416 uint8_t *ptr;
417
418 /* dump vertex shaders: */
419 for (i = 0; i < 3; i++) {
420 struct vs_header *vs_hdr = next_sect(state, §_size);
421 struct constant *constants[32];
422 int j, level = 0;
423
424 printf("\n");
425
426 if (full_dump) {
427 printf("#######################################################\n");
428 printf("######## VS%d HEADER: (size %d)\n", i, sect_size);
429 dump_hex((void *)vs_hdr, sect_size);
430 }
431
432 for (j = 0; j < (int)vs_hdr->unknown1 - 1; j++) {
433 constants[j] = next_sect(state, §_size);
434 if (full_dump) {
435 printf("######## VS%d CONST: (size=%d)\n", i, sect_size);
436 dump_constant(constants[j]);
437 dump_hex((char *)constants[j], sect_size);
438 }
439 }
440
441 ptr = next_sect(state, §_size);
442 printf("######## VS%d SHADER: (size=%d)\n", i, sect_size);
443 if (full_dump) {
444 dump_hex(ptr, sect_size);
445 level = 1;
446 } else {
447 dump_short_summary(state, vs_hdr->unknown1 - 1, constants);
448 }
449 disasm_a2xx((uint32_t *)(ptr + 32), (sect_size - 32) / 4, level + 1,
450 MESA_SHADER_VERTEX);
451 dump_raw_shader((uint32_t *)(ptr + 32), (sect_size - 32) / 4, i, "vo");
452 free(ptr);
453
454 for (j = 0; j < vs_hdr->unknown9; j++) {
455 ptr = next_sect(state, §_size);
456 if (full_dump) {
457 printf("######## VS%d CONST?: (size=%d)\n", i, sect_size);
458 dump_hex(ptr, sect_size);
459 }
460 free(ptr);
461 }
462
463 for (j = 0; j < vs_hdr->unknown1 - 1; j++) {
464 free(constants[j]);
465 }
466
467 free(vs_hdr);
468 }
469
470 /* dump fragment shaders: */
471 for (i = 0; i < 1; i++) {
472 struct fs_header *fs_hdr = next_sect(state, §_size);
473 struct constant *constants[32];
474 int j, level = 0;
475
476 printf("\n");
477
478 if (full_dump) {
479 printf("#######################################################\n");
480 printf("######## FS%d HEADER: (size %d)\n", i, sect_size);
481 dump_hex((void *)fs_hdr, sect_size);
482 }
483
484 for (j = 0; j < fs_hdr->unknown1 - 1; j++) {
485 constants[j] = next_sect(state, §_size);
486 if (full_dump) {
487 printf("######## FS%d CONST: (size=%d)\n", i, sect_size);
488 dump_constant(constants[j]);
489 dump_hex((char *)constants[j], sect_size);
490 }
491 }
492
493 ptr = next_sect(state, §_size);
494 printf("######## FS%d SHADER: (size=%d)\n", i, sect_size);
495 if (full_dump) {
496 dump_hex(ptr, sect_size);
497 level = 1;
498 } else {
499 dump_short_summary(state, fs_hdr->unknown1 - 1, constants);
500 }
501 disasm_a2xx((uint32_t *)(ptr + 32), (sect_size - 32) / 4, level + 1,
502 MESA_SHADER_FRAGMENT);
503 dump_raw_shader((uint32_t *)(ptr + 32), (sect_size - 32) / 4, i, "fo");
504 free(ptr);
505
506 for (j = 0; j < fs_hdr->unknown1 - 1; j++) {
507 free(constants[j]);
508 }
509
510 free(fs_hdr);
511 }
512 }
513
514 static void
dump_shaders_a3xx(struct state * state)515 dump_shaders_a3xx(struct state *state)
516 {
517 int i, j;
518
519 /* dump vertex shaders: */
520 for (i = 0; i < 2; i++) {
521 int instrs_size, hdr_size, sect_size, nconsts = 0, level = 0, compact = 0;
522 uint8_t *vs_hdr;
523 struct constant *constants[32];
524 uint8_t *instrs = NULL;
525
526 vs_hdr = next_sect(state, &hdr_size);
527 printf("hdr_size=%d\n", hdr_size);
528
529 /* seems like there are two cases, either:
530 * 1) 152 byte header,
531 * 2) zero or more 32 byte compiler const sections
532 * 3) followed by shader instructions
533 * or, if there are no compiler consts, this can be
534 * all smashed in one large section
535 */
536 int n;
537 if (state->hdr->revision >= 0xb)
538 n = 160;
539 else if (state->hdr->revision >= 7)
540 n = 156;
541 else
542 n = 152;
543 if (hdr_size > n) {
544 instrs = &vs_hdr[n];
545 instrs_size = hdr_size - n;
546 hdr_size = n;
547 compact = 1;
548 } else {
549 while (1) {
550 void *ptr = next_sect(state, §_size);
551
552 if ((sect_size != 32) && (sect_size != 44)) {
553 /* end of constants: */
554 instrs = ptr;
555 instrs_size = sect_size;
556 break;
557 }
558 dump_hex_ascii(ptr, sect_size, 0);
559 constants[nconsts++] = ptr;
560 }
561 }
562
563 printf("\n");
564
565 if (full_dump) {
566 printf("#######################################################\n");
567 printf("######## VS%d HEADER: (size %d)\n", i, hdr_size);
568 dump_hex((void *)vs_hdr, hdr_size);
569 for (j = 0; j < nconsts; j++) {
570 printf("######## VS%d CONST: (size=%d)\n", i,
571 (int)sizeof(constants[i]));
572 dump_constant(constants[j]);
573 dump_hex((char *)constants[j], sizeof(constants[j]));
574 }
575 }
576
577 printf("######## VS%d SHADER: (size=%d)\n", i, instrs_size);
578 if (full_dump) {
579 dump_hex(instrs, instrs_size);
580 level = 1;
581 } else {
582 dump_short_summary(state, nconsts, constants);
583 }
584
585 if (!compact) {
586 if (state->hdr->revision >= 7) {
587 instrs += ALIGN(instrs_size, 8) - instrs_size;
588 instrs_size = ALIGN(instrs_size, 8);
589 }
590 instrs += 32;
591 instrs_size -= 32;
592 }
593
594 disasm_a3xx((uint32_t *)instrs, instrs_size / 4, level + 1, stdout,
595 gpu_id);
596 dump_raw_shader((uint32_t *)instrs, instrs_size / 4, i, "vo3");
597 free(vs_hdr);
598 }
599
600 /* dump fragment shaders: */
601 for (i = 0; i < 1; i++) {
602 int instrs_size, hdr_size, sect_size, nconsts = 0, level = 0, compact = 0;
603 uint8_t *fs_hdr;
604 struct constant *constants[32];
605 uint8_t *instrs = NULL;
606
607 fs_hdr = next_sect(state, &hdr_size);
608
609 printf("hdr_size=%d\n", hdr_size);
610 /* two cases, similar to vertex shader, but magic # is 200
611 * (or 208 for newer?)..
612 */
613 int n;
614 if (state->hdr->revision >= 0xb)
615 n = 256;
616 else if (state->hdr->revision >= 8)
617 n = 208;
618 else if (state->hdr->revision == 7)
619 n = 204;
620 else
621 n = 200;
622
623 if (hdr_size > n) {
624 instrs = &fs_hdr[n];
625 instrs_size = hdr_size - n;
626 hdr_size = n;
627 compact = 1;
628 } else {
629 while (1) {
630 void *ptr = next_sect(state, §_size);
631
632 if ((sect_size != 32) && (sect_size != 44)) {
633 /* end of constants: */
634 instrs = ptr;
635 instrs_size = sect_size;
636 break;
637 }
638
639 dump_hex_ascii(ptr, sect_size, 0);
640 constants[nconsts++] = ptr;
641 }
642 }
643
644 printf("\n");
645
646 if (full_dump) {
647 printf("#######################################################\n");
648 printf("######## FS%d HEADER: (size %d)\n", i, hdr_size);
649 dump_hex((void *)fs_hdr, hdr_size);
650 for (j = 0; j < nconsts; j++) {
651 printf("######## FS%d CONST: (size=%d)\n", i,
652 (int)sizeof(constants[i]));
653 dump_constant(constants[j]);
654 dump_hex((char *)constants[j], sizeof(constants[j]));
655 }
656 }
657
658 printf("######## FS%d SHADER: (size=%d)\n", i, instrs_size);
659 if (full_dump) {
660 dump_hex(instrs, instrs_size);
661 level = 1;
662 } else {
663 dump_short_summary(state, nconsts, constants);
664 }
665
666 if (!compact) {
667 if (state->hdr->revision >= 7) {
668 instrs += 44;
669 instrs_size -= 44;
670 } else {
671 instrs += 32;
672 instrs_size -= 32;
673 }
674 }
675 disasm_a3xx((uint32_t *)instrs, instrs_size / 4, level + 1, stdout,
676 gpu_id);
677 dump_raw_shader((uint32_t *)instrs, instrs_size / 4, i, "fo3");
678 free(fs_hdr);
679 }
680 }
681
682 static void
dump_program(struct state * state)683 dump_program(struct state *state)
684 {
685 int i, sect_size;
686 uint8_t *ptr;
687
688 state->hdr = next_sect(state, §_size);
689
690 printf("######## HEADER: (size %d)\n", sect_size);
691 printf("\tsize: %d\n", state->hdr->size);
692 printf("\trevision: %d\n", state->hdr->revision);
693 printf("\tattributes: %d\n", state->hdr->num_attribs);
694 printf("\tuniforms: %d\n", state->hdr->num_uniforms);
695 printf("\tsamplers: %d\n", state->hdr->num_samplers);
696 printf("\tvaryings: %d\n", state->hdr->num_varyings);
697 printf("\tuniform blocks: %d\n", state->hdr->num_uniformblocks);
698 if (full_dump)
699 dump_hex((void *)state->hdr, sect_size);
700 printf("\n");
701
702 /* there seems to be two 0xba5eba11's at the end of the header, possibly
703 * with some other stuff between them:
704 */
705 ptr = next_sect(state, §_size);
706 if (full_dump) {
707 dump_hex_ascii(ptr, sect_size, 0);
708 }
709
710 for (i = 0; (i < state->hdr->num_attribs) && (state->sz > 0); i++) {
711 state->attribs[i] = next_sect(state, §_size);
712
713 /* hmm, for a3xx (or maybe just newer driver version), we have some
714 * extra sections that don't seem useful, so skip these:
715 */
716 while (!valid_type(state->attribs[i]->type_info)) {
717 dump_hex_ascii(state->attribs[i], sect_size, 0);
718 state->attribs[i] = next_sect(state, §_size);
719 }
720
721 clean_ascii(state->attribs[i]->name, sect_size - 28);
722 if (full_dump) {
723 printf("######## ATTRIBUTE: (size %d)\n", sect_size);
724 dump_attribute(state->attribs[i]);
725 dump_hex((char *)state->attribs[i], sect_size);
726 }
727 }
728
729 for (i = 0; (i < state->hdr->num_uniforms) && (state->sz > 0); i++) {
730 state->uniforms[i] = next_sect(state, §_size);
731
732 /* hmm, for a3xx (or maybe just newer driver version), we have some
733 * extra sections that don't seem useful, so skip these:
734 */
735 while (!valid_type(state->uniforms[i]->type_info)) {
736 dump_hex_ascii(state->uniforms[i], sect_size, 0);
737 state->uniforms[i] = next_sect(state, §_size);
738 }
739
740 if (is_uniform_v2(state->uniforms[i])) {
741 clean_ascii(state->uniforms[i]->v2.name, sect_size - 53);
742 } else {
743 clean_ascii(state->uniforms[i]->v1.name, sect_size - 41);
744 }
745
746 if (full_dump) {
747 printf("######## UNIFORM: (size %d)\n", sect_size);
748 dump_uniform(state->uniforms[i]);
749 dump_hex((char *)state->uniforms[i], sect_size);
750 }
751 }
752
753 for (i = 0; (i < state->hdr->num_samplers) && (state->sz > 0); i++) {
754 state->samplers[i] = next_sect(state, §_size);
755
756 /* hmm, for a3xx (or maybe just newer driver version), we have some
757 * extra sections that don't seem useful, so skip these:
758 */
759 while (!valid_type(state->samplers[i]->type_info)) {
760 dump_hex_ascii(state->samplers[i], sect_size, 0);
761 state->samplers[i] = next_sect(state, §_size);
762 }
763
764 clean_ascii(state->samplers[i]->name, sect_size - 33);
765 if (full_dump) {
766 printf("######## SAMPLER: (size %d)\n", sect_size);
767 dump_sampler(state->samplers[i]);
768 dump_hex((char *)state->samplers[i], sect_size);
769 }
770 }
771
772 // These sections show up after all of the other sampler sections
773 // Loops through them all since we don't deal with them
774 if (state->hdr->revision >= 7) {
775 for (i = 0; (i < state->hdr->num_samplers) && (state->sz > 0); i++) {
776 ptr = next_sect(state, §_size);
777 dump_hex_ascii(ptr, sect_size, 0);
778 }
779 }
780
781 for (i = 0; (i < state->hdr->num_varyings) && (state->sz > 0); i++) {
782 state->varyings[i] = next_sect(state, §_size);
783
784 /* hmm, for a3xx (or maybe just newer driver version), we have some
785 * extra sections that don't seem useful, so skip these:
786 */
787 while (!valid_type(state->varyings[i]->type_info)) {
788 dump_hex_ascii(state->varyings[i], sect_size, 0);
789 state->varyings[i] = next_sect(state, §_size);
790 }
791
792 clean_ascii(state->varyings[i]->name, sect_size - 16);
793 if (full_dump) {
794 printf("######## VARYING: (size %d)\n", sect_size);
795 dump_varying(state->varyings[i]);
796 dump_hex((char *)state->varyings[i], sect_size);
797 }
798 }
799
800 /* show up again for revision >= 14?? */
801 if (state->hdr->revision >= 14) {
802 for (i = 0; (i < state->hdr->num_varyings) && (state->sz > 0); i++) {
803 ptr = next_sect(state, §_size);
804 dump_hex_ascii(ptr, sect_size, 0);
805 }
806 }
807
808 /* not sure exactly which revision started this, but seems at least
809 * rev7 and rev8 implicitly include a new section for gl_FragColor:
810 */
811 if (state->hdr->revision >= 7) {
812 /* I guess only one? */
813 state->outputs[0] = next_sect(state, §_size);
814
815 clean_ascii(state->outputs[0]->name, sect_size - 32);
816 if (full_dump) {
817 printf("######## OUTPUT: (size %d)\n", sect_size);
818 dump_output(state->outputs[0]);
819 dump_hex((char *)state->outputs[0], sect_size);
820 }
821 }
822
823 for (i = 0; (i < state->hdr->num_uniformblocks) && (state->sz > 0); i++) {
824 state->uniformblocks[i].header = next_sect(state, §_size);
825
826 clean_ascii(state->uniformblocks[i].header->name, sect_size - 40);
827 if (full_dump) {
828 printf("######## UNIFORM BLOCK: (size %d)\n", sect_size);
829 dump_uniformblock(state->uniformblocks[i].header);
830 dump_hex((char *)state->uniformblocks[i].header, sect_size);
831 }
832
833 /*
834 * OpenGL ES 3.0 spec mandates a minimum amount of 16K members supported
835 * a330 supports a minimum of 65K
836 */
837 state->uniformblocks[i].members =
838 malloc(state->uniformblocks[i].header->num_members * sizeof(void *));
839
840 int member = 0;
841 for (member = 0; (member < state->uniformblocks[i].header->num_members) &&
842 (state->sz > 0);
843 member++) {
844 state->uniformblocks[i].members[member] = next_sect(state, §_size);
845
846 clean_ascii(state->uniformblocks[i].members[member]->name,
847 sect_size - 56);
848 if (full_dump) {
849 printf("######## UNIFORM BLOCK MEMBER: (size %d)\n", sect_size);
850 dump_uniformblockmember(state->uniformblocks[i].members[member]);
851 dump_hex((char *)state->uniformblocks[i].members[member],
852 sect_size);
853 }
854 }
855 /*
856 * Qualcomm saves the UBO members twice for each UBO
857 * Don't ask me why
858 */
859 for (member = 0; (member < state->uniformblocks[i].header->num_members) &&
860 (state->sz > 0);
861 member++) {
862 state->uniformblocks[i].members[member] = next_sect(state, §_size);
863
864 clean_ascii(state->uniformblocks[i].members[member]->name,
865 sect_size - 56);
866 if (full_dump) {
867 printf("######## UNIFORM BLOCK MEMBER2: (size %d)\n", sect_size);
868 dump_uniformblockmember(state->uniformblocks[i].members[member]);
869 dump_hex((char *)state->uniformblocks[i].members[member],
870 sect_size);
871 }
872 }
873 }
874
875 if (gpu_id >= 300) {
876 dump_shaders_a3xx(state);
877 } else {
878 dump_shaders_a2xx(state);
879 }
880
881 if (!full_dump)
882 return;
883
884 /* dump ascii version of shader program: */
885 ptr = next_sect(state, §_size);
886 printf("\n#######################################################\n");
887 printf("######## SHADER SRC: (size=%d)\n", sect_size);
888 dump_ascii(ptr, sect_size);
889 free(ptr);
890
891 /* dump remaining sections (there shouldn't be any): */
892 while (state->sz > 0) {
893 ptr = next_sect(state, §_size);
894 printf("######## section (size=%d)\n", sect_size);
895 printf("as hex:\n");
896 dump_hex(ptr, sect_size);
897 printf("as float:\n");
898 dump_float(ptr, sect_size);
899 printf("as ascii:\n");
900 dump_ascii(ptr, sect_size);
901 free(ptr);
902 }
903 /* cleanup the uniform buffer members we allocated */
904 if (state->hdr->num_uniformblocks > 0)
905 free(state->uniformblocks[i].members);
906 }
907
908 int
main(int argc,char ** argv)909 main(int argc, char **argv)
910 {
911 enum rd_sect_type type = RD_NONE;
912 enum debug_t debug = PRINT_RAW | PRINT_STATS;
913 void *buf = NULL;
914 int sz;
915 struct io *io;
916 int raw_program = 0;
917
918 /* lame argument parsing: */
919
920 while (1) {
921 if ((argc > 1) && !strcmp(argv[1], "--verbose")) {
922 debug |= PRINT_RAW | PRINT_VERBOSE;
923 argv++;
924 argc--;
925 continue;
926 }
927 if ((argc > 1) && !strcmp(argv[1], "--expand")) {
928 debug |= EXPAND_REPEAT;
929 argv++;
930 argc--;
931 continue;
932 }
933 if ((argc > 1) && !strcmp(argv[1], "--short")) {
934 /* only short dump, original shader, symbol table, and disassembly */
935 full_dump = 0;
936 argv++;
937 argc--;
938 continue;
939 }
940 if ((argc > 1) && !strcmp(argv[1], "--dump-shaders")) {
941 dump_shaders = 1;
942 argv++;
943 argc--;
944 continue;
945 }
946 if ((argc > 1) && !strcmp(argv[1], "--raw")) {
947 raw_program = 1;
948 argv++;
949 argc--;
950 continue;
951 }
952 if ((argc > 1) && !strcmp(argv[1], "--gpu300")) {
953 gpu_id = 320;
954 argv++;
955 argc--;
956 continue;
957 }
958 break;
959 }
960
961 if (argc != 2) {
962 fprintf(
963 stderr,
964 "usage: pgmdump [--verbose] [--short] [--dump-shaders] testlog.rd\n");
965 return -1;
966 }
967
968 disasm_a2xx_set_debug(debug);
969 disasm_a3xx_set_debug(debug);
970
971 infile = argv[1];
972
973 io = io_open(infile);
974 if (!io) {
975 fprintf(stderr, "could not open: %s\n", infile);
976 return -1;
977 }
978
979 if (raw_program) {
980 io_readn(io, &sz, 4);
981 free(buf);
982
983 /* note: allow hex dumps to go a bit past the end of the buffer..
984 * might see some garbage, but better than missing the last few bytes..
985 */
986 buf = calloc(1, sz + 3);
987 io_readn(io, buf + 4, sz);
988 (*(int *)buf) = sz;
989
990 struct state state = {
991 .buf = buf,
992 .sz = sz,
993 };
994 printf("############################################################\n");
995 printf("program:\n");
996 dump_program(&state);
997 printf("############################################################\n");
998 return 0;
999 }
1000
1001 /* figure out what sort of input we are dealing with: */
1002 if (!(check_extension(infile, ".rd") || check_extension(infile, ".rd.gz"))) {
1003 gl_shader_stage shader = ~0;
1004 int ret;
1005 if (check_extension(infile, ".vo")) {
1006 shader = MESA_SHADER_VERTEX;
1007 } else if (check_extension(infile, ".fo")) {
1008 shader = MESA_SHADER_FRAGMENT;
1009 } else if (check_extension(infile, ".vo3")) {
1010 } else if (check_extension(infile, ".fo3")) {
1011 } else if (check_extension(infile, ".co3")) {
1012 } else {
1013 fprintf(stderr, "invalid input file: %s\n", infile);
1014 return -1;
1015 }
1016 buf = calloc(1, 100 * 1024);
1017 ret = io_readn(io, buf, 100 * 1024);
1018 if (ret < 0) {
1019 fprintf(stderr, "error: %m");
1020 return -1;
1021 }
1022 if (shader != ~0) {
1023 return disasm_a2xx(buf, ret / 4, 0, shader);
1024 } else {
1025 /* disassembly does not depend on shader stage on a3xx+: */
1026 return disasm_a3xx(buf, ret / 4, 0, stdout, gpu_id);
1027 }
1028 }
1029
1030 while ((io_readn(io, &type, sizeof(type)) > 0) &&
1031 (io_readn(io, &sz, 4) > 0)) {
1032 free(buf);
1033
1034 /* note: allow hex dumps to go a bit past the end of the buffer..
1035 * might see some garbage, but better than missing the last few bytes..
1036 */
1037 buf = calloc(1, sz + 3);
1038 io_readn(io, buf, sz);
1039
1040 switch (type) {
1041 case RD_TEST:
1042 if (full_dump)
1043 printf("test: %s\n", (char *)buf);
1044 break;
1045 case RD_VERT_SHADER:
1046 printf("vertex shader:\n%s\n", (char *)buf);
1047 break;
1048 case RD_FRAG_SHADER:
1049 printf("fragment shader:\n%s\n", (char *)buf);
1050 break;
1051 case RD_PROGRAM: {
1052 struct state state = {
1053 .buf = buf,
1054 .sz = sz,
1055 };
1056 printf(
1057 "############################################################\n");
1058 printf("program:\n");
1059 dump_program(&state);
1060 printf(
1061 "############################################################\n");
1062 break;
1063 }
1064 case RD_GPU_ID:
1065 gpu_id = *((unsigned int *)buf);
1066 printf("gpu_id: %d\n", gpu_id);
1067 break;
1068 default:
1069 break;
1070 }
1071 }
1072
1073 io_close(io);
1074
1075 return 0;
1076 }
1077