glsl: Remove unnecessary assignments to type
[mesa.git] / src / compiler / glsl / serialize.cpp
1 /*
2 * Copyright © 2014 Intel Corporation
3 *
4 * Permission is hereby granted, free of charge, to any person obtaining a
5 * copy of this software and associated documentation files (the "Software"),
6 * to deal in the Software without restriction, including without limitation
7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 * and/or sell copies of the Software, and to permit persons to whom the
9 * Software is furnished to do so, subject to the following conditions:
10 *
11 * The above copyright notice and this permission notice (including the next
12 * paragraph) shall be included in all copies or substantial portions of the
13 * Software.
14 *
15 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
18 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
20 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
21 * DEALINGS IN THE SOFTWARE.
22 */
23
24 /**
25 * \file serialize.cpp
26 *
27 * GLSL serialization
28 *
29 * Supports serializing and deserializing glsl programs using a blob.
30 */
31
32 #include "compiler/glsl_types.h"
33 #include "compiler/shader_info.h"
34 #include "ir_uniform.h"
35 #include "main/mtypes.h"
36 #include "string_to_uint_map.h"
37
38 extern "C" {
39 #include "main/shaderobj.h"
40 #include "program/program.h"
41 }
42
43 static void
44 write_subroutines(struct blob *metadata, struct gl_shader_program *prog)
45 {
46 for (unsigned i = 0; i < MESA_SHADER_STAGES; i++) {
47 struct gl_linked_shader *sh = prog->_LinkedShaders[i];
48 if (!sh)
49 continue;
50
51 struct gl_program *glprog = sh->Program;
52
53 blob_write_uint32(metadata, glprog->sh.NumSubroutineUniforms);
54 blob_write_uint32(metadata, glprog->sh.MaxSubroutineFunctionIndex);
55 blob_write_uint32(metadata, glprog->sh.NumSubroutineFunctions);
56 for (unsigned j = 0; j < glprog->sh.NumSubroutineFunctions; j++) {
57 int num_types = glprog->sh.SubroutineFunctions[j].num_compat_types;
58
59 blob_write_string(metadata, glprog->sh.SubroutineFunctions[j].name);
60 blob_write_uint32(metadata, glprog->sh.SubroutineFunctions[j].index);
61 blob_write_uint32(metadata, num_types);
62
63 for (int k = 0; k < num_types; k++) {
64 encode_type_to_blob(metadata,
65 glprog->sh.SubroutineFunctions[j].types[k]);
66 }
67 }
68 }
69 }
70
71 static void
72 read_subroutines(struct blob_reader *metadata, struct gl_shader_program *prog)
73 {
74 struct gl_subroutine_function *subs;
75
76 for (unsigned i = 0; i < MESA_SHADER_STAGES; i++) {
77 struct gl_linked_shader *sh = prog->_LinkedShaders[i];
78 if (!sh)
79 continue;
80
81 struct gl_program *glprog = sh->Program;
82
83 glprog->sh.NumSubroutineUniforms = blob_read_uint32(metadata);
84 glprog->sh.MaxSubroutineFunctionIndex = blob_read_uint32(metadata);
85 glprog->sh.NumSubroutineFunctions = blob_read_uint32(metadata);
86
87 subs = rzalloc_array(prog, struct gl_subroutine_function,
88 glprog->sh.NumSubroutineFunctions);
89 glprog->sh.SubroutineFunctions = subs;
90
91 for (unsigned j = 0; j < glprog->sh.NumSubroutineFunctions; j++) {
92 subs[j].name = ralloc_strdup(prog, blob_read_string (metadata));
93 subs[j].index = (int) blob_read_uint32(metadata);
94 subs[j].num_compat_types = (int) blob_read_uint32(metadata);
95
96 subs[j].types = rzalloc_array(prog, const struct glsl_type *,
97 subs[j].num_compat_types);
98 for (int k = 0; k < subs[j].num_compat_types; k++) {
99 subs[j].types[k] = decode_type_from_blob(metadata);
100 }
101 }
102 }
103 }
104
105 static void
106 write_buffer_block(struct blob *metadata, struct gl_uniform_block *b)
107 {
108 blob_write_string(metadata, b->Name);
109 blob_write_uint32(metadata, b->NumUniforms);
110 blob_write_uint32(metadata, b->Binding);
111 blob_write_uint32(metadata, b->UniformBufferSize);
112 blob_write_uint32(metadata, b->stageref);
113
114 for (unsigned j = 0; j < b->NumUniforms; j++) {
115 blob_write_string(metadata, b->Uniforms[j].Name);
116 blob_write_string(metadata, b->Uniforms[j].IndexName);
117 encode_type_to_blob(metadata, b->Uniforms[j].Type);
118 blob_write_uint32(metadata, b->Uniforms[j].Offset);
119 }
120 }
121
122 static void
123 write_buffer_blocks(struct blob *metadata, struct gl_shader_program *prog)
124 {
125 blob_write_uint32(metadata, prog->data->NumUniformBlocks);
126 blob_write_uint32(metadata, prog->data->NumShaderStorageBlocks);
127
128 for (unsigned i = 0; i < prog->data->NumUniformBlocks; i++) {
129 write_buffer_block(metadata, &prog->data->UniformBlocks[i]);
130 }
131
132 for (unsigned i = 0; i < prog->data->NumShaderStorageBlocks; i++) {
133 write_buffer_block(metadata, &prog->data->ShaderStorageBlocks[i]);
134 }
135
136 for (unsigned i = 0; i < MESA_SHADER_STAGES; i++) {
137 struct gl_linked_shader *sh = prog->_LinkedShaders[i];
138 if (!sh)
139 continue;
140
141 struct gl_program *glprog = sh->Program;
142
143 blob_write_uint32(metadata, glprog->info.num_ubos);
144 blob_write_uint32(metadata, glprog->info.num_ssbos);
145
146 for (unsigned j = 0; j < glprog->info.num_ubos; j++) {
147 uint32_t offset =
148 glprog->sh.UniformBlocks[j] - prog->data->UniformBlocks;
149 blob_write_uint32(metadata, offset);
150 }
151
152 for (unsigned j = 0; j < glprog->info.num_ssbos; j++) {
153 uint32_t offset = glprog->sh.ShaderStorageBlocks[j] -
154 prog->data->ShaderStorageBlocks;
155 blob_write_uint32(metadata, offset);
156 }
157 }
158 }
159
160 static void
161 read_buffer_block(struct blob_reader *metadata, struct gl_uniform_block *b,
162 struct gl_shader_program *prog)
163 {
164 b->Name = ralloc_strdup(prog->data, blob_read_string (metadata));
165 b->NumUniforms = blob_read_uint32(metadata);
166 b->Binding = blob_read_uint32(metadata);
167 b->UniformBufferSize = blob_read_uint32(metadata);
168 b->stageref = blob_read_uint32(metadata);
169
170 b->Uniforms =
171 rzalloc_array(prog->data, struct gl_uniform_buffer_variable,
172 b->NumUniforms);
173 for (unsigned j = 0; j < b->NumUniforms; j++) {
174 b->Uniforms[j].Name = ralloc_strdup(prog->data,
175 blob_read_string (metadata));
176
177 char *index_name = blob_read_string(metadata);
178 if (strcmp(b->Uniforms[j].Name, index_name) == 0) {
179 b->Uniforms[j].IndexName = b->Uniforms[j].Name;
180 } else {
181 b->Uniforms[j].IndexName = ralloc_strdup(prog->data, index_name);
182 }
183
184 b->Uniforms[j].Type = decode_type_from_blob(metadata);
185 b->Uniforms[j].Offset = blob_read_uint32(metadata);
186 }
187 }
188
189 static void
190 read_buffer_blocks(struct blob_reader *metadata,
191 struct gl_shader_program *prog)
192 {
193 prog->data->NumUniformBlocks = blob_read_uint32(metadata);
194 prog->data->NumShaderStorageBlocks = blob_read_uint32(metadata);
195
196 prog->data->UniformBlocks =
197 rzalloc_array(prog->data, struct gl_uniform_block,
198 prog->data->NumUniformBlocks);
199
200 prog->data->ShaderStorageBlocks =
201 rzalloc_array(prog->data, struct gl_uniform_block,
202 prog->data->NumShaderStorageBlocks);
203
204 for (unsigned i = 0; i < prog->data->NumUniformBlocks; i++) {
205 read_buffer_block(metadata, &prog->data->UniformBlocks[i], prog);
206 }
207
208 for (unsigned i = 0; i < prog->data->NumShaderStorageBlocks; i++) {
209 read_buffer_block(metadata, &prog->data->ShaderStorageBlocks[i], prog);
210 }
211
212 for (unsigned i = 0; i < MESA_SHADER_STAGES; i++) {
213 struct gl_linked_shader *sh = prog->_LinkedShaders[i];
214 if (!sh)
215 continue;
216
217 struct gl_program *glprog = sh->Program;
218
219 glprog->info.num_ubos = blob_read_uint32(metadata);
220 glprog->info.num_ssbos = blob_read_uint32(metadata);
221
222 glprog->sh.UniformBlocks =
223 rzalloc_array(glprog, gl_uniform_block *, glprog->info.num_ubos);
224 glprog->sh.ShaderStorageBlocks =
225 rzalloc_array(glprog, gl_uniform_block *, glprog->info.num_ssbos);
226
227 for (unsigned j = 0; j < glprog->info.num_ubos; j++) {
228 uint32_t offset = blob_read_uint32(metadata);
229 glprog->sh.UniformBlocks[j] = prog->data->UniformBlocks + offset;
230 }
231
232 for (unsigned j = 0; j < glprog->info.num_ssbos; j++) {
233 uint32_t offset = blob_read_uint32(metadata);
234 glprog->sh.ShaderStorageBlocks[j] =
235 prog->data->ShaderStorageBlocks + offset;
236 }
237 }
238 }
239
240 static void
241 write_atomic_buffers(struct blob *metadata, struct gl_shader_program *prog)
242 {
243 blob_write_uint32(metadata, prog->data->NumAtomicBuffers);
244
245 for (unsigned i = 0; i < MESA_SHADER_STAGES; i++) {
246 if (prog->_LinkedShaders[i]) {
247 struct gl_program *glprog = prog->_LinkedShaders[i]->Program;
248 blob_write_uint32(metadata, glprog->info.num_abos);
249 }
250 }
251
252 for (unsigned i = 0; i < prog->data->NumAtomicBuffers; i++) {
253 blob_write_uint32(metadata, prog->data->AtomicBuffers[i].Binding);
254 blob_write_uint32(metadata, prog->data->AtomicBuffers[i].MinimumSize);
255 blob_write_uint32(metadata, prog->data->AtomicBuffers[i].NumUniforms);
256
257 blob_write_bytes(metadata, prog->data->AtomicBuffers[i].StageReferences,
258 sizeof(prog->data->AtomicBuffers[i].StageReferences));
259
260 for (unsigned j = 0; j < prog->data->AtomicBuffers[i].NumUniforms; j++) {
261 blob_write_uint32(metadata, prog->data->AtomicBuffers[i].Uniforms[j]);
262 }
263 }
264 }
265
266 static void
267 read_atomic_buffers(struct blob_reader *metadata,
268 struct gl_shader_program *prog)
269 {
270 prog->data->NumAtomicBuffers = blob_read_uint32(metadata);
271 prog->data->AtomicBuffers =
272 rzalloc_array(prog, gl_active_atomic_buffer,
273 prog->data->NumAtomicBuffers);
274
275 struct gl_active_atomic_buffer **stage_buff_list[MESA_SHADER_STAGES];
276 for (unsigned i = 0; i < MESA_SHADER_STAGES; i++) {
277 if (prog->_LinkedShaders[i]) {
278 struct gl_program *glprog = prog->_LinkedShaders[i]->Program;
279
280 glprog->info.num_abos = blob_read_uint32(metadata);
281 glprog->sh.AtomicBuffers =
282 rzalloc_array(glprog, gl_active_atomic_buffer *,
283 glprog->info.num_abos);
284 stage_buff_list[i] = glprog->sh.AtomicBuffers;
285 }
286 }
287
288 for (unsigned i = 0; i < prog->data->NumAtomicBuffers; i++) {
289 prog->data->AtomicBuffers[i].Binding = blob_read_uint32(metadata);
290 prog->data->AtomicBuffers[i].MinimumSize = blob_read_uint32(metadata);
291 prog->data->AtomicBuffers[i].NumUniforms = blob_read_uint32(metadata);
292
293 blob_copy_bytes(metadata,
294 (uint8_t *) &prog->data->AtomicBuffers[i].StageReferences,
295 sizeof(prog->data->AtomicBuffers[i].StageReferences));
296
297 prog->data->AtomicBuffers[i].Uniforms = rzalloc_array(prog, unsigned,
298 prog->data->AtomicBuffers[i].NumUniforms);
299
300 for (unsigned j = 0; j < prog->data->AtomicBuffers[i].NumUniforms; j++) {
301 prog->data->AtomicBuffers[i].Uniforms[j] = blob_read_uint32(metadata);
302 }
303
304 for (unsigned j = 0; j < MESA_SHADER_STAGES; j++) {
305 if (prog->data->AtomicBuffers[i].StageReferences[j]) {
306 *stage_buff_list[j] = &prog->data->AtomicBuffers[i];
307 stage_buff_list[j]++;
308 }
309 }
310 }
311 }
312
313 static void
314 write_xfb(struct blob *metadata, struct gl_shader_program *shProg)
315 {
316 struct gl_program *prog = shProg->last_vert_prog;
317
318 if (!prog) {
319 blob_write_uint32(metadata, ~0u);
320 return;
321 }
322
323 struct gl_transform_feedback_info *ltf = prog->sh.LinkedTransformFeedback;
324
325 blob_write_uint32(metadata, prog->info.stage);
326
327 blob_write_uint32(metadata, ltf->NumOutputs);
328 blob_write_uint32(metadata, ltf->ActiveBuffers);
329 blob_write_uint32(metadata, ltf->NumVarying);
330
331 blob_write_bytes(metadata, ltf->Outputs,
332 sizeof(struct gl_transform_feedback_output) *
333 ltf->NumOutputs);
334
335 for (int i = 0; i < ltf->NumVarying; i++) {
336 blob_write_string(metadata, ltf->Varyings[i].Name);
337 blob_write_uint32(metadata, ltf->Varyings[i].Type);
338 blob_write_uint32(metadata, ltf->Varyings[i].BufferIndex);
339 blob_write_uint32(metadata, ltf->Varyings[i].Size);
340 blob_write_uint32(metadata, ltf->Varyings[i].Offset);
341 }
342
343 blob_write_bytes(metadata, ltf->Buffers,
344 sizeof(struct gl_transform_feedback_buffer) *
345 MAX_FEEDBACK_BUFFERS);
346 }
347
348 static void
349 read_xfb(struct blob_reader *metadata, struct gl_shader_program *shProg)
350 {
351 unsigned xfb_stage = blob_read_uint32(metadata);
352
353 if (xfb_stage == ~0u)
354 return;
355
356 struct gl_program *prog = shProg->_LinkedShaders[xfb_stage]->Program;
357 struct gl_transform_feedback_info *ltf =
358 rzalloc(prog, struct gl_transform_feedback_info);
359
360 prog->sh.LinkedTransformFeedback = ltf;
361 shProg->last_vert_prog = prog;
362
363 ltf->NumOutputs = blob_read_uint32(metadata);
364 ltf->ActiveBuffers = blob_read_uint32(metadata);
365 ltf->NumVarying = blob_read_uint32(metadata);
366
367 ltf->Outputs = rzalloc_array(prog, struct gl_transform_feedback_output,
368 ltf->NumOutputs);
369
370 blob_copy_bytes(metadata, (uint8_t *) ltf->Outputs,
371 sizeof(struct gl_transform_feedback_output) *
372 ltf->NumOutputs);
373
374 ltf->Varyings = rzalloc_array(prog,
375 struct gl_transform_feedback_varying_info,
376 ltf->NumVarying);
377
378 for (int i = 0; i < ltf->NumVarying; i++) {
379 ltf->Varyings[i].Name = ralloc_strdup(prog, blob_read_string(metadata));
380 ltf->Varyings[i].Type = blob_read_uint32(metadata);
381 ltf->Varyings[i].BufferIndex = blob_read_uint32(metadata);
382 ltf->Varyings[i].Size = blob_read_uint32(metadata);
383 ltf->Varyings[i].Offset = blob_read_uint32(metadata);
384 }
385
386 blob_copy_bytes(metadata, (uint8_t *) ltf->Buffers,
387 sizeof(struct gl_transform_feedback_buffer) *
388 MAX_FEEDBACK_BUFFERS);
389 }
390
391 static bool
392 has_uniform_storage(struct gl_shader_program *prog, unsigned idx)
393 {
394 if (!prog->data->UniformStorage[idx].builtin &&
395 !prog->data->UniformStorage[idx].is_shader_storage &&
396 prog->data->UniformStorage[idx].block_index == -1)
397 return true;
398
399 return false;
400 }
401
402 static void
403 write_uniforms(struct blob *metadata, struct gl_shader_program *prog)
404 {
405 blob_write_uint32(metadata, prog->SamplersValidated);
406 blob_write_uint32(metadata, prog->data->NumUniformStorage);
407 blob_write_uint32(metadata, prog->data->NumUniformDataSlots);
408
409 for (unsigned i = 0; i < prog->data->NumUniformStorage; i++) {
410 encode_type_to_blob(metadata, prog->data->UniformStorage[i].type);
411 blob_write_uint32(metadata, prog->data->UniformStorage[i].array_elements);
412 blob_write_string(metadata, prog->data->UniformStorage[i].name);
413 blob_write_uint32(metadata, prog->data->UniformStorage[i].builtin);
414 blob_write_uint32(metadata, prog->data->UniformStorage[i].remap_location);
415 blob_write_uint32(metadata, prog->data->UniformStorage[i].block_index);
416 blob_write_uint32(metadata, prog->data->UniformStorage[i].atomic_buffer_index);
417 blob_write_uint32(metadata, prog->data->UniformStorage[i].offset);
418 blob_write_uint32(metadata, prog->data->UniformStorage[i].array_stride);
419 blob_write_uint32(metadata, prog->data->UniformStorage[i].hidden);
420 blob_write_uint32(metadata, prog->data->UniformStorage[i].is_shader_storage);
421 blob_write_uint32(metadata, prog->data->UniformStorage[i].active_shader_mask);
422 blob_write_uint32(metadata, prog->data->UniformStorage[i].matrix_stride);
423 blob_write_uint32(metadata, prog->data->UniformStorage[i].row_major);
424 blob_write_uint32(metadata, prog->data->UniformStorage[i].is_bindless);
425 blob_write_uint32(metadata,
426 prog->data->UniformStorage[i].num_compatible_subroutines);
427 blob_write_uint32(metadata,
428 prog->data->UniformStorage[i].top_level_array_size);
429 blob_write_uint32(metadata,
430 prog->data->UniformStorage[i].top_level_array_stride);
431
432 if (has_uniform_storage(prog, i)) {
433 blob_write_uint32(metadata, prog->data->UniformStorage[i].storage -
434 prog->data->UniformDataSlots);
435 }
436
437 blob_write_bytes(metadata, prog->data->UniformStorage[i].opaque,
438 sizeof(prog->data->UniformStorage[i].opaque));
439 }
440
441 /* Here we cache all uniform values. We do this to retain values for
442 * uniforms with initialisers and also hidden uniforms that may be lowered
443 * constant arrays. We could possibly just store the values we need but for
444 * now we just store everything.
445 */
446 blob_write_uint32(metadata, prog->data->NumHiddenUniforms);
447 for (unsigned i = 0; i < prog->data->NumUniformStorage; i++) {
448 if (has_uniform_storage(prog, i)) {
449 unsigned vec_size =
450 prog->data->UniformStorage[i].type->component_slots() *
451 MAX2(prog->data->UniformStorage[i].array_elements, 1);
452 unsigned slot =
453 prog->data->UniformStorage[i].storage -
454 prog->data->UniformDataSlots;
455 blob_write_bytes(metadata, &prog->data->UniformDataDefaults[slot],
456 sizeof(union gl_constant_value) * vec_size);
457 }
458 }
459 }
460
461 static void
462 read_uniforms(struct blob_reader *metadata, struct gl_shader_program *prog)
463 {
464 struct gl_uniform_storage *uniforms;
465 union gl_constant_value *data;
466
467 prog->SamplersValidated = blob_read_uint32(metadata);
468 prog->data->NumUniformStorage = blob_read_uint32(metadata);
469 prog->data->NumUniformDataSlots = blob_read_uint32(metadata);
470
471 uniforms = rzalloc_array(prog->data, struct gl_uniform_storage,
472 prog->data->NumUniformStorage);
473 prog->data->UniformStorage = uniforms;
474
475 data = rzalloc_array(uniforms, union gl_constant_value,
476 prog->data->NumUniformDataSlots);
477 prog->data->UniformDataSlots = data;
478 prog->data->UniformDataDefaults =
479 rzalloc_array(uniforms, union gl_constant_value,
480 prog->data->NumUniformDataSlots);
481
482 prog->UniformHash = new string_to_uint_map;
483
484 for (unsigned i = 0; i < prog->data->NumUniformStorage; i++) {
485 uniforms[i].type = decode_type_from_blob(metadata);
486 uniforms[i].array_elements = blob_read_uint32(metadata);
487 uniforms[i].name = ralloc_strdup(prog, blob_read_string (metadata));
488 uniforms[i].builtin = blob_read_uint32(metadata);
489 uniforms[i].remap_location = blob_read_uint32(metadata);
490 uniforms[i].block_index = blob_read_uint32(metadata);
491 uniforms[i].atomic_buffer_index = blob_read_uint32(metadata);
492 uniforms[i].offset = blob_read_uint32(metadata);
493 uniforms[i].array_stride = blob_read_uint32(metadata);
494 uniforms[i].hidden = blob_read_uint32(metadata);
495 uniforms[i].is_shader_storage = blob_read_uint32(metadata);
496 uniforms[i].active_shader_mask = blob_read_uint32(metadata);
497 uniforms[i].matrix_stride = blob_read_uint32(metadata);
498 uniforms[i].row_major = blob_read_uint32(metadata);
499 uniforms[i].is_bindless = blob_read_uint32(metadata);
500 uniforms[i].num_compatible_subroutines = blob_read_uint32(metadata);
501 uniforms[i].top_level_array_size = blob_read_uint32(metadata);
502 uniforms[i].top_level_array_stride = blob_read_uint32(metadata);
503 prog->UniformHash->put(i, uniforms[i].name);
504
505 if (has_uniform_storage(prog, i)) {
506 uniforms[i].storage = data + blob_read_uint32(metadata);
507 }
508
509 memcpy(uniforms[i].opaque,
510 blob_read_bytes(metadata, sizeof(uniforms[i].opaque)),
511 sizeof(uniforms[i].opaque));
512 }
513
514 /* Restore uniform values. */
515 prog->data->NumHiddenUniforms = blob_read_uint32(metadata);
516 for (unsigned i = 0; i < prog->data->NumUniformStorage; i++) {
517 if (has_uniform_storage(prog, i)) {
518 unsigned vec_size =
519 prog->data->UniformStorage[i].type->component_slots() *
520 MAX2(prog->data->UniformStorage[i].array_elements, 1);
521 unsigned slot =
522 prog->data->UniformStorage[i].storage -
523 prog->data->UniformDataSlots;
524 blob_copy_bytes(metadata,
525 (uint8_t *) &prog->data->UniformDataSlots[slot],
526 sizeof(union gl_constant_value) * vec_size);
527
528 assert(vec_size + prog->data->UniformStorage[i].storage <=
529 data + prog->data->NumUniformDataSlots);
530 }
531 }
532
533 memcpy(prog->data->UniformDataDefaults, prog->data->UniformDataSlots,
534 sizeof(union gl_constant_value) * prog->data->NumUniformDataSlots);
535 }
536
537 enum uniform_remap_type
538 {
539 remap_type_inactive_explicit_location,
540 remap_type_null_ptr,
541 remap_type_uniform_offset
542 };
543
544 static void
545 write_uniform_remap_table_entry(struct blob *metadata,
546 gl_uniform_storage *uniform_storage,
547 gl_uniform_storage *entry)
548 {
549 if (entry == INACTIVE_UNIFORM_EXPLICIT_LOCATION) {
550 blob_write_uint32(metadata, remap_type_inactive_explicit_location);
551 } else if (entry == NULL) {
552 blob_write_uint32(metadata, remap_type_null_ptr);
553 } else {
554 blob_write_uint32(metadata, remap_type_uniform_offset);
555
556 uint32_t offset = entry - uniform_storage;
557 blob_write_uint32(metadata, offset);
558 }
559 }
560
561 static void
562 write_uniform_remap_tables(struct blob *metadata,
563 struct gl_shader_program *prog)
564 {
565 blob_write_uint32(metadata, prog->NumUniformRemapTable);
566
567 for (unsigned i = 0; i < prog->NumUniformRemapTable; i++) {
568 write_uniform_remap_table_entry(metadata, prog->data->UniformStorage,
569 prog->UniformRemapTable[i]);
570 }
571
572 for (unsigned i = 0; i < MESA_SHADER_STAGES; i++) {
573 struct gl_linked_shader *sh = prog->_LinkedShaders[i];
574 if (sh) {
575 struct gl_program *glprog = sh->Program;
576 blob_write_uint32(metadata, glprog->sh.NumSubroutineUniformRemapTable);
577
578 for (unsigned j = 0; j < glprog->sh.NumSubroutineUniformRemapTable; j++) {
579 write_uniform_remap_table_entry(metadata,
580 prog->data->UniformStorage,
581 glprog->sh.SubroutineUniformRemapTable[j]);
582 }
583 }
584 }
585 }
586
587 static void
588 read_uniform_remap_table_entry(struct blob_reader *metadata,
589 gl_uniform_storage *uniform_storage,
590 gl_uniform_storage **entry,
591 enum uniform_remap_type type)
592 {
593 if (type == remap_type_inactive_explicit_location) {
594 *entry = INACTIVE_UNIFORM_EXPLICIT_LOCATION;
595 } else if (type == remap_type_null_ptr) {
596 *entry = NULL;
597 } else {
598 uint32_t uni_offset = blob_read_uint32(metadata);
599 *entry = uniform_storage + uni_offset;
600 }
601 }
602
603 static void
604 read_uniform_remap_tables(struct blob_reader *metadata,
605 struct gl_shader_program *prog)
606 {
607 prog->NumUniformRemapTable = blob_read_uint32(metadata);
608
609 prog->UniformRemapTable = rzalloc_array(prog, struct gl_uniform_storage *,
610 prog->NumUniformRemapTable);
611
612 for (unsigned i = 0; i < prog->NumUniformRemapTable; i++) {
613 enum uniform_remap_type type =
614 (enum uniform_remap_type) blob_read_uint32(metadata);
615
616 read_uniform_remap_table_entry(metadata, prog->data->UniformStorage,
617 &prog->UniformRemapTable[i], type);
618 }
619
620 for (unsigned i = 0; i < MESA_SHADER_STAGES; i++) {
621 struct gl_linked_shader *sh = prog->_LinkedShaders[i];
622 if (sh) {
623 struct gl_program *glprog = sh->Program;
624 glprog->sh.NumSubroutineUniformRemapTable = blob_read_uint32(metadata);
625
626 glprog->sh.SubroutineUniformRemapTable =
627 rzalloc_array(glprog, struct gl_uniform_storage *,
628 glprog->sh.NumSubroutineUniformRemapTable);
629
630 for (unsigned j = 0; j < glprog->sh.NumSubroutineUniformRemapTable; j++) {
631 enum uniform_remap_type type =
632 (enum uniform_remap_type) blob_read_uint32(metadata);
633
634 read_uniform_remap_table_entry(metadata,
635 prog->data->UniformStorage,
636 &glprog->sh.SubroutineUniformRemapTable[j],
637 type);
638 }
639 }
640 }
641 }
642
643 struct whte_closure
644 {
645 struct blob *blob;
646 size_t num_entries;
647 };
648
649 static void
650 write_hash_table_entry(const char *key, unsigned value, void *closure)
651 {
652 struct whte_closure *whte = (struct whte_closure *) closure;
653
654 blob_write_string(whte->blob, key);
655 blob_write_uint32(whte->blob, value);
656
657 whte->num_entries++;
658 }
659
660 static void
661 write_hash_table(struct blob *metadata, struct string_to_uint_map *hash)
662 {
663 size_t offset;
664 struct whte_closure whte;
665
666 whte.blob = metadata;
667 whte.num_entries = 0;
668
669 offset = metadata->size;
670
671 /* Write a placeholder for the hashtable size. */
672 blob_write_uint32 (metadata, 0);
673
674 hash->iterate(write_hash_table_entry, &whte);
675
676 /* Overwrite with the computed number of entries written. */
677 blob_overwrite_uint32 (metadata, offset, whte.num_entries);
678 }
679
680 static void
681 read_hash_table(struct blob_reader *metadata, struct string_to_uint_map *hash)
682 {
683 size_t i, num_entries;
684 const char *key;
685 uint32_t value;
686
687 num_entries = blob_read_uint32 (metadata);
688
689 for (i = 0; i < num_entries; i++) {
690 key = blob_read_string(metadata);
691 value = blob_read_uint32(metadata);
692
693 hash->put(value, key);
694 }
695 }
696
697 static void
698 write_hash_tables(struct blob *metadata, struct gl_shader_program *prog)
699 {
700 write_hash_table(metadata, prog->AttributeBindings);
701 write_hash_table(metadata, prog->FragDataBindings);
702 write_hash_table(metadata, prog->FragDataIndexBindings);
703 }
704
705 static void
706 read_hash_tables(struct blob_reader *metadata, struct gl_shader_program *prog)
707 {
708 read_hash_table(metadata, prog->AttributeBindings);
709 read_hash_table(metadata, prog->FragDataBindings);
710 read_hash_table(metadata, prog->FragDataIndexBindings);
711 }
712
713 static void
714 write_shader_subroutine_index(struct blob *metadata,
715 struct gl_linked_shader *sh,
716 struct gl_program_resource *res)
717 {
718 assert(sh);
719
720 for (unsigned j = 0; j < sh->Program->sh.NumSubroutineFunctions; j++) {
721 if (strcmp(((gl_subroutine_function *)res->Data)->name,
722 sh->Program->sh.SubroutineFunctions[j].name) == 0) {
723 blob_write_uint32(metadata, j);
724 break;
725 }
726 }
727 }
728
729 static void
730 get_shader_var_and_pointer_sizes(size_t *s_var_size, size_t *s_var_ptrs,
731 const gl_shader_variable *var)
732 {
733 *s_var_size = sizeof(gl_shader_variable);
734 *s_var_ptrs =
735 sizeof(var->type) +
736 sizeof(var->interface_type) +
737 sizeof(var->outermost_struct_type) +
738 sizeof(var->name);
739 }
740
741 static void
742 write_program_resource_data(struct blob *metadata,
743 struct gl_shader_program *prog,
744 struct gl_program_resource *res)
745 {
746 struct gl_linked_shader *sh;
747
748 switch(res->Type) {
749 case GL_PROGRAM_INPUT:
750 case GL_PROGRAM_OUTPUT: {
751 const gl_shader_variable *var = (gl_shader_variable *)res->Data;
752
753 encode_type_to_blob(metadata, var->type);
754 encode_type_to_blob(metadata, var->interface_type);
755 encode_type_to_blob(metadata, var->outermost_struct_type);
756
757 blob_write_string(metadata, var->name);
758
759 size_t s_var_size, s_var_ptrs;
760 get_shader_var_and_pointer_sizes(&s_var_size, &s_var_ptrs, var);
761
762 /* Write gl_shader_variable skipping over the pointers */
763 blob_write_bytes(metadata, ((char *)var) + s_var_ptrs,
764 s_var_size - s_var_ptrs);
765 break;
766 }
767 case GL_UNIFORM_BLOCK:
768 for (unsigned i = 0; i < prog->data->NumUniformBlocks; i++) {
769 if (strcmp(((gl_uniform_block *)res->Data)->Name,
770 prog->data->UniformBlocks[i].Name) == 0) {
771 blob_write_uint32(metadata, i);
772 break;
773 }
774 }
775 break;
776 case GL_SHADER_STORAGE_BLOCK:
777 for (unsigned i = 0; i < prog->data->NumShaderStorageBlocks; i++) {
778 if (strcmp(((gl_uniform_block *)res->Data)->Name,
779 prog->data->ShaderStorageBlocks[i].Name) == 0) {
780 blob_write_uint32(metadata, i);
781 break;
782 }
783 }
784 break;
785 case GL_BUFFER_VARIABLE:
786 case GL_VERTEX_SUBROUTINE_UNIFORM:
787 case GL_GEOMETRY_SUBROUTINE_UNIFORM:
788 case GL_FRAGMENT_SUBROUTINE_UNIFORM:
789 case GL_COMPUTE_SUBROUTINE_UNIFORM:
790 case GL_TESS_CONTROL_SUBROUTINE_UNIFORM:
791 case GL_TESS_EVALUATION_SUBROUTINE_UNIFORM:
792 case GL_UNIFORM:
793 for (unsigned i = 0; i < prog->data->NumUniformStorage; i++) {
794 if (strcmp(((gl_uniform_storage *)res->Data)->name,
795 prog->data->UniformStorage[i].name) == 0) {
796 blob_write_uint32(metadata, i);
797 break;
798 }
799 }
800 break;
801 case GL_ATOMIC_COUNTER_BUFFER:
802 for (unsigned i = 0; i < prog->data->NumAtomicBuffers; i++) {
803 if (((gl_active_atomic_buffer *)res->Data)->Binding ==
804 prog->data->AtomicBuffers[i].Binding) {
805 blob_write_uint32(metadata, i);
806 break;
807 }
808 }
809 break;
810 case GL_TRANSFORM_FEEDBACK_BUFFER:
811 for (unsigned i = 0; i < MAX_FEEDBACK_BUFFERS; i++) {
812 if (((gl_transform_feedback_buffer *)res->Data)->Binding ==
813 prog->last_vert_prog->sh.LinkedTransformFeedback->Buffers[i].Binding) {
814 blob_write_uint32(metadata, i);
815 break;
816 }
817 }
818 break;
819 case GL_TRANSFORM_FEEDBACK_VARYING:
820 for (int i = 0; i < prog->last_vert_prog->sh.LinkedTransformFeedback->NumVarying; i++) {
821 if (strcmp(((gl_transform_feedback_varying_info *)res->Data)->Name,
822 prog->last_vert_prog->sh.LinkedTransformFeedback->Varyings[i].Name) == 0) {
823 blob_write_uint32(metadata, i);
824 break;
825 }
826 }
827 break;
828 case GL_VERTEX_SUBROUTINE:
829 case GL_TESS_CONTROL_SUBROUTINE:
830 case GL_TESS_EVALUATION_SUBROUTINE:
831 case GL_GEOMETRY_SUBROUTINE:
832 case GL_FRAGMENT_SUBROUTINE:
833 case GL_COMPUTE_SUBROUTINE:
834 sh =
835 prog->_LinkedShaders[_mesa_shader_stage_from_subroutine(res->Type)];
836 write_shader_subroutine_index(metadata, sh, res);
837 break;
838 default:
839 assert(!"Support for writing resource not yet implemented.");
840 }
841 }
842
843 static void
844 read_program_resource_data(struct blob_reader *metadata,
845 struct gl_shader_program *prog,
846 struct gl_program_resource *res)
847 {
848 struct gl_linked_shader *sh;
849
850 switch(res->Type) {
851 case GL_PROGRAM_INPUT:
852 case GL_PROGRAM_OUTPUT: {
853 gl_shader_variable *var = ralloc(prog, struct gl_shader_variable);
854
855 var->type = decode_type_from_blob(metadata);
856 var->interface_type = decode_type_from_blob(metadata);
857 var->outermost_struct_type = decode_type_from_blob(metadata);
858
859 var->name = ralloc_strdup(prog, blob_read_string(metadata));
860
861 size_t s_var_size, s_var_ptrs;
862 get_shader_var_and_pointer_sizes(&s_var_size, &s_var_ptrs, var);
863
864 blob_copy_bytes(metadata, ((uint8_t *) var) + s_var_ptrs,
865 s_var_size - s_var_ptrs);
866
867 res->Data = var;
868 break;
869 }
870 case GL_UNIFORM_BLOCK:
871 res->Data = &prog->data->UniformBlocks[blob_read_uint32(metadata)];
872 break;
873 case GL_SHADER_STORAGE_BLOCK:
874 res->Data = &prog->data->ShaderStorageBlocks[blob_read_uint32(metadata)];
875 break;
876 case GL_BUFFER_VARIABLE:
877 case GL_VERTEX_SUBROUTINE_UNIFORM:
878 case GL_GEOMETRY_SUBROUTINE_UNIFORM:
879 case GL_FRAGMENT_SUBROUTINE_UNIFORM:
880 case GL_COMPUTE_SUBROUTINE_UNIFORM:
881 case GL_TESS_CONTROL_SUBROUTINE_UNIFORM:
882 case GL_TESS_EVALUATION_SUBROUTINE_UNIFORM:
883 case GL_UNIFORM:
884 res->Data = &prog->data->UniformStorage[blob_read_uint32(metadata)];
885 break;
886 case GL_ATOMIC_COUNTER_BUFFER:
887 res->Data = &prog->data->AtomicBuffers[blob_read_uint32(metadata)];
888 break;
889 case GL_TRANSFORM_FEEDBACK_BUFFER:
890 res->Data = &prog->last_vert_prog->
891 sh.LinkedTransformFeedback->Buffers[blob_read_uint32(metadata)];
892 break;
893 case GL_TRANSFORM_FEEDBACK_VARYING:
894 res->Data = &prog->last_vert_prog->
895 sh.LinkedTransformFeedback->Varyings[blob_read_uint32(metadata)];
896 break;
897 case GL_VERTEX_SUBROUTINE:
898 case GL_TESS_CONTROL_SUBROUTINE:
899 case GL_TESS_EVALUATION_SUBROUTINE:
900 case GL_GEOMETRY_SUBROUTINE:
901 case GL_FRAGMENT_SUBROUTINE:
902 case GL_COMPUTE_SUBROUTINE:
903 sh =
904 prog->_LinkedShaders[_mesa_shader_stage_from_subroutine(res->Type)];
905 res->Data =
906 &sh->Program->sh.SubroutineFunctions[blob_read_uint32(metadata)];
907 break;
908 default:
909 assert(!"Support for reading resource not yet implemented.");
910 }
911 }
912
913 static void
914 write_program_resource_list(struct blob *metadata,
915 struct gl_shader_program *prog)
916 {
917 blob_write_uint32(metadata, prog->data->NumProgramResourceList);
918
919 for (unsigned i = 0; i < prog->data->NumProgramResourceList; i++) {
920 blob_write_uint32(metadata, prog->data->ProgramResourceList[i].Type);
921 write_program_resource_data(metadata, prog,
922 &prog->data->ProgramResourceList[i]);
923 blob_write_bytes(metadata,
924 &prog->data->ProgramResourceList[i].StageReferences,
925 sizeof(prog->data->ProgramResourceList[i].StageReferences));
926 }
927 }
928
929 static void
930 read_program_resource_list(struct blob_reader *metadata,
931 struct gl_shader_program *prog)
932 {
933 prog->data->NumProgramResourceList = blob_read_uint32(metadata);
934
935 prog->data->ProgramResourceList =
936 ralloc_array(prog->data, gl_program_resource,
937 prog->data->NumProgramResourceList);
938
939 for (unsigned i = 0; i < prog->data->NumProgramResourceList; i++) {
940 prog->data->ProgramResourceList[i].Type = blob_read_uint32(metadata);
941 read_program_resource_data(metadata, prog,
942 &prog->data->ProgramResourceList[i]);
943 blob_copy_bytes(metadata,
944 (uint8_t *) &prog->data->ProgramResourceList[i].StageReferences,
945 sizeof(prog->data->ProgramResourceList[i].StageReferences));
946 }
947 }
948
949 static void
950 write_shader_parameters(struct blob *metadata,
951 struct gl_program_parameter_list *params)
952 {
953 blob_write_uint32(metadata, params->NumParameters);
954 uint32_t i = 0;
955
956 while (i < params->NumParameters) {
957 struct gl_program_parameter *param = &params->Parameters[i];
958
959 blob_write_uint32(metadata, param->Type);
960 blob_write_string(metadata, param->Name);
961 blob_write_uint32(metadata, param->Size);
962 blob_write_uint32(metadata, param->DataType);
963 blob_write_bytes(metadata, param->StateIndexes,
964 sizeof(param->StateIndexes));
965
966 i++;
967 }
968
969 blob_write_bytes(metadata, params->ParameterValues,
970 sizeof(gl_constant_value) * 4 * params->NumParameters);
971
972 blob_write_uint32(metadata, params->StateFlags);
973 }
974
975 static void
976 read_shader_parameters(struct blob_reader *metadata,
977 struct gl_program_parameter_list *params)
978 {
979 gl_state_index state_indexes[STATE_LENGTH];
980 uint32_t i = 0;
981 uint32_t num_parameters = blob_read_uint32(metadata);
982
983 _mesa_reserve_parameter_storage(params, num_parameters);
984 while (i < num_parameters) {
985 gl_register_file type = (gl_register_file) blob_read_uint32(metadata);
986 const char *name = blob_read_string(metadata);
987 unsigned size = blob_read_uint32(metadata);
988 unsigned data_type = blob_read_uint32(metadata);
989 blob_copy_bytes(metadata, (uint8_t *) state_indexes,
990 sizeof(state_indexes));
991
992 _mesa_add_parameter(params, type, name, size, data_type,
993 NULL, state_indexes);
994
995 i++;
996 }
997
998 blob_copy_bytes(metadata, (uint8_t *) params->ParameterValues,
999 sizeof(gl_constant_value) * 4 * params->NumParameters);
1000
1001 params->StateFlags = blob_read_uint32(metadata);
1002 }
1003
1004 static void
1005 write_shader_metadata(struct blob *metadata, gl_linked_shader *shader)
1006 {
1007 assert(shader->Program);
1008 struct gl_program *glprog = shader->Program;
1009 unsigned i;
1010
1011 blob_write_bytes(metadata, glprog->TexturesUsed,
1012 sizeof(glprog->TexturesUsed));
1013 blob_write_uint64(metadata, glprog->SamplersUsed);
1014
1015 blob_write_bytes(metadata, glprog->SamplerUnits,
1016 sizeof(glprog->SamplerUnits));
1017 blob_write_bytes(metadata, glprog->sh.SamplerTargets,
1018 sizeof(glprog->sh.SamplerTargets));
1019 blob_write_uint32(metadata, glprog->ShadowSamplers);
1020
1021 blob_write_bytes(metadata, glprog->sh.ImageAccess,
1022 sizeof(glprog->sh.ImageAccess));
1023 blob_write_bytes(metadata, glprog->sh.ImageUnits,
1024 sizeof(glprog->sh.ImageUnits));
1025
1026 size_t ptr_size = sizeof(GLvoid *);
1027
1028 blob_write_uint32(metadata, glprog->sh.NumBindlessSamplers);
1029 blob_write_uint32(metadata, glprog->sh.HasBoundBindlessSampler);
1030 for (i = 0; i < glprog->sh.NumBindlessSamplers; i++) {
1031 blob_write_bytes(metadata, &glprog->sh.BindlessSamplers[i],
1032 sizeof(struct gl_bindless_sampler) - ptr_size);
1033 }
1034
1035 blob_write_uint32(metadata, glprog->sh.NumBindlessImages);
1036 blob_write_uint32(metadata, glprog->sh.HasBoundBindlessImage);
1037 for (i = 0; i < glprog->sh.NumBindlessImages; i++) {
1038 blob_write_bytes(metadata, &glprog->sh.BindlessImages[i],
1039 sizeof(struct gl_bindless_image) - ptr_size);
1040 }
1041
1042 blob_write_bytes(metadata, &glprog->sh.fs.BlendSupport,
1043 sizeof(glprog->sh.fs.BlendSupport));
1044
1045 write_shader_parameters(metadata, glprog->Parameters);
1046
1047 assert((glprog->driver_cache_blob == NULL) ==
1048 (glprog->driver_cache_blob_size == 0));
1049 blob_write_uint32(metadata, (uint32_t)glprog->driver_cache_blob_size);
1050 if (glprog->driver_cache_blob_size > 0) {
1051 blob_write_bytes(metadata, glprog->driver_cache_blob,
1052 glprog->driver_cache_blob_size);
1053 }
1054 }
1055
1056 static void
1057 read_shader_metadata(struct blob_reader *metadata,
1058 struct gl_program *glprog,
1059 gl_linked_shader *linked)
1060 {
1061 unsigned i;
1062
1063 blob_copy_bytes(metadata, (uint8_t *) glprog->TexturesUsed,
1064 sizeof(glprog->TexturesUsed));
1065 glprog->SamplersUsed = blob_read_uint64(metadata);
1066
1067 blob_copy_bytes(metadata, (uint8_t *) glprog->SamplerUnits,
1068 sizeof(glprog->SamplerUnits));
1069 blob_copy_bytes(metadata, (uint8_t *) glprog->sh.SamplerTargets,
1070 sizeof(glprog->sh.SamplerTargets));
1071 glprog->ShadowSamplers = blob_read_uint32(metadata);
1072
1073 blob_copy_bytes(metadata, (uint8_t *) glprog->sh.ImageAccess,
1074 sizeof(glprog->sh.ImageAccess));
1075 blob_copy_bytes(metadata, (uint8_t *) glprog->sh.ImageUnits,
1076 sizeof(glprog->sh.ImageUnits));
1077
1078 size_t ptr_size = sizeof(GLvoid *);
1079
1080 glprog->sh.NumBindlessSamplers = blob_read_uint32(metadata);
1081 glprog->sh.HasBoundBindlessSampler = blob_read_uint32(metadata);
1082 if (glprog->sh.NumBindlessSamplers > 0) {
1083 glprog->sh.BindlessSamplers =
1084 rzalloc_array(glprog, gl_bindless_sampler,
1085 glprog->sh.NumBindlessSamplers);
1086
1087 for (i = 0; i < glprog->sh.NumBindlessSamplers; i++) {
1088 blob_copy_bytes(metadata, (uint8_t *) &glprog->sh.BindlessSamplers[i],
1089 sizeof(struct gl_bindless_sampler) - ptr_size);
1090 }
1091 }
1092
1093 glprog->sh.NumBindlessImages = blob_read_uint32(metadata);
1094 glprog->sh.HasBoundBindlessImage = blob_read_uint32(metadata);
1095 if (glprog->sh.NumBindlessImages > 0) {
1096 glprog->sh.BindlessImages =
1097 rzalloc_array(glprog, gl_bindless_image,
1098 glprog->sh.NumBindlessImages);
1099
1100 for (i = 0; i < glprog->sh.NumBindlessImages; i++) {
1101 blob_copy_bytes(metadata, (uint8_t *) &glprog->sh.BindlessImages[i],
1102 sizeof(struct gl_bindless_image) - ptr_size);
1103 }
1104 }
1105
1106 blob_copy_bytes(metadata, (uint8_t *) &glprog->sh.fs.BlendSupport,
1107 sizeof(glprog->sh.fs.BlendSupport));
1108
1109 glprog->Parameters = _mesa_new_parameter_list();
1110 read_shader_parameters(metadata, glprog->Parameters);
1111
1112 glprog->driver_cache_blob_size = (size_t)blob_read_uint32(metadata);
1113 if (glprog->driver_cache_blob_size > 0) {
1114 glprog->driver_cache_blob =
1115 (uint8_t*)ralloc_size(glprog, glprog->driver_cache_blob_size);
1116 blob_copy_bytes(metadata, glprog->driver_cache_blob,
1117 glprog->driver_cache_blob_size);
1118 }
1119 }
1120
1121 static void
1122 get_shader_info_and_pointer_sizes(size_t *s_info_size, size_t *s_info_ptrs,
1123 shader_info *info)
1124 {
1125 *s_info_size = sizeof(shader_info);
1126 *s_info_ptrs = sizeof(info->name) + sizeof(info->label);
1127 }
1128
1129 static void
1130 create_linked_shader_and_program(struct gl_context *ctx,
1131 gl_shader_stage stage,
1132 struct gl_shader_program *prog,
1133 struct blob_reader *metadata)
1134 {
1135 struct gl_program *glprog;
1136
1137 struct gl_linked_shader *linked = rzalloc(NULL, struct gl_linked_shader);
1138 linked->Stage = stage;
1139
1140 glprog = ctx->Driver.NewProgram(ctx, _mesa_shader_stage_to_program(stage),
1141 prog->Name, false);
1142 glprog->info.stage = stage;
1143 linked->Program = glprog;
1144
1145 read_shader_metadata(metadata, glprog, linked);
1146
1147 glprog->info.name = ralloc_strdup(glprog, blob_read_string(metadata));
1148 glprog->info.label = ralloc_strdup(glprog, blob_read_string(metadata));
1149
1150 size_t s_info_size, s_info_ptrs;
1151 get_shader_info_and_pointer_sizes(&s_info_size, &s_info_ptrs,
1152 &glprog->info);
1153
1154 /* Restore shader info */
1155 blob_copy_bytes(metadata, ((uint8_t *) &glprog->info) + s_info_ptrs,
1156 s_info_size - s_info_ptrs);
1157
1158 _mesa_reference_shader_program_data(ctx, &glprog->sh.data, prog->data);
1159 _mesa_reference_program(ctx, &linked->Program, glprog);
1160 prog->_LinkedShaders[stage] = linked;
1161 }
1162
1163 extern "C" void
1164 serialize_glsl_program(struct blob *blob, struct gl_context *ctx,
1165 struct gl_shader_program *prog)
1166 {
1167 write_uniforms(blob, prog);
1168
1169 write_hash_tables(blob, prog);
1170
1171 blob_write_uint32(blob, prog->data->Version);
1172 blob_write_uint32(blob, prog->data->linked_stages);
1173
1174 for (unsigned i = 0; i < MESA_SHADER_STAGES; i++) {
1175 struct gl_linked_shader *sh = prog->_LinkedShaders[i];
1176 if (sh) {
1177 write_shader_metadata(blob, sh);
1178
1179 if (sh->Program->info.name)
1180 blob_write_string(blob, sh->Program->info.name);
1181 else
1182 blob_write_string(blob, "");
1183
1184 if (sh->Program->info.label)
1185 blob_write_string(blob, sh->Program->info.label);
1186 else
1187 blob_write_string(blob, "");
1188
1189 size_t s_info_size, s_info_ptrs;
1190 get_shader_info_and_pointer_sizes(&s_info_size, &s_info_ptrs,
1191 &sh->Program->info);
1192
1193 /* Store shader info */
1194 blob_write_bytes(blob,
1195 ((char *) &sh->Program->info) + s_info_ptrs,
1196 s_info_size - s_info_ptrs);
1197 }
1198 }
1199
1200 write_xfb(blob, prog);
1201
1202 write_uniform_remap_tables(blob, prog);
1203
1204 write_atomic_buffers(blob, prog);
1205
1206 write_buffer_blocks(blob, prog);
1207
1208 write_subroutines(blob, prog);
1209
1210 write_program_resource_list(blob, prog);
1211 }
1212
1213 extern "C" bool
1214 deserialize_glsl_program(struct blob_reader *blob, struct gl_context *ctx,
1215 struct gl_shader_program *prog)
1216 {
1217 /* Fixed function programs generated by Mesa can't be serialized. */
1218 if (prog->Name == 0)
1219 return false;
1220
1221 assert(prog->data->UniformStorage == NULL);
1222
1223 read_uniforms(blob, prog);
1224
1225 read_hash_tables(blob, prog);
1226
1227 prog->data->Version = blob_read_uint32(blob);
1228 prog->data->linked_stages = blob_read_uint32(blob);
1229
1230 unsigned mask = prog->data->linked_stages;
1231 while (mask) {
1232 const int j = u_bit_scan(&mask);
1233 create_linked_shader_and_program(ctx, (gl_shader_stage) j, prog,
1234 blob);
1235 }
1236
1237 read_xfb(blob, prog);
1238
1239 read_uniform_remap_tables(blob, prog);
1240
1241 read_atomic_buffers(blob, prog);
1242
1243 read_buffer_blocks(blob, prog);
1244
1245 read_subroutines(blob, prog);
1246
1247 read_program_resource_list(blob, prog);
1248
1249 return !blob->overrun;
1250 }