• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 //
2 // Copyright 2002 The ANGLE Project Authors. All rights reserved.
3 // Use of this source code is governed by a BSD-style license that can be
4 // found in the LICENSE file.
5 //
6 
7 //
8 // Implement the top-level of interface to the compiler,
9 // as defined in ShaderLang.h
10 //
11 
12 #include "GLSLANG/ShaderLang.h"
13 
14 #include "compiler/translator/Compiler.h"
15 #include "compiler/translator/InitializeDll.h"
16 #include "compiler/translator/glslang_wrapper.h"
17 #include "compiler/translator/length_limits.h"
18 #ifdef ANGLE_ENABLE_HLSL
19 #    include "compiler/translator/TranslatorHLSL.h"
20 #endif  // ANGLE_ENABLE_HLSL
21 #include "angle_gl.h"
22 #include "compiler/translator/VariablePacker.h"
23 
24 namespace sh
25 {
26 
27 namespace
28 {
29 
30 bool isInitialized = false;
31 
32 // glslang can only be initialized/finalized once per process. Otherwise, the following EGL commands
33 // will call GlslangFinalize() without ever being able to GlslangInitialize() again, leading to
34 // crashes since GlslangFinalize() cleans up glslang for the entire process.
35 //   dpy1 = eglGetPlatformDisplay()   |
36 //   eglInitialize(dpy1)              | GlslangInitialize()
37 //   dpy2 = eglGetPlatformDisplay()   |
38 //   eglInitialize(dpy2)              | GlslangInitialize()
39 //   eglTerminate(dpy2)               | GlslangFinalize()
40 //   eglInitialize(dpy1)              | Display::isInitialized() == true, no GlslangInitialize()
41 int initializeGlslangRefCount = 0;
42 
43 //
44 // This is the platform independent interface between an OGL driver
45 // and the shading language compiler.
46 //
47 
48 template <typename VarT>
49 const std::vector<VarT> *GetVariableList(const TCompiler *compiler);
50 
51 template <>
GetVariableList(const TCompiler * compiler)52 const std::vector<InterfaceBlock> *GetVariableList(const TCompiler *compiler)
53 {
54     return &compiler->getInterfaceBlocks();
55 }
56 
GetCompilerFromHandle(ShHandle handle)57 TCompiler *GetCompilerFromHandle(ShHandle handle)
58 {
59     if (!handle)
60     {
61         return nullptr;
62     }
63 
64     TShHandleBase *base = static_cast<TShHandleBase *>(handle);
65     return base->getAsCompiler();
66 }
67 
68 template <typename VarT>
GetShaderVariables(const ShHandle handle)69 const std::vector<VarT> *GetShaderVariables(const ShHandle handle)
70 {
71     TCompiler *compiler = GetCompilerFromHandle(handle);
72     if (!compiler)
73     {
74         return nullptr;
75     }
76 
77     return GetVariableList<VarT>(compiler);
78 }
79 
80 #ifdef ANGLE_ENABLE_HLSL
GetTranslatorHLSLFromHandle(ShHandle handle)81 TranslatorHLSL *GetTranslatorHLSLFromHandle(ShHandle handle)
82 {
83     if (!handle)
84         return nullptr;
85     TShHandleBase *base = static_cast<TShHandleBase *>(handle);
86     return base->getAsTranslatorHLSL();
87 }
88 #endif  // ANGLE_ENABLE_HLSL
89 
GetGeometryShaderPrimitiveTypeEnum(sh::TLayoutPrimitiveType primitiveType)90 GLenum GetGeometryShaderPrimitiveTypeEnum(sh::TLayoutPrimitiveType primitiveType)
91 {
92     switch (primitiveType)
93     {
94         case EptPoints:
95             return GL_POINTS;
96         case EptLines:
97             return GL_LINES;
98         case EptLinesAdjacency:
99             return GL_LINES_ADJACENCY_EXT;
100         case EptTriangles:
101             return GL_TRIANGLES;
102         case EptTrianglesAdjacency:
103             return GL_TRIANGLES_ADJACENCY_EXT;
104 
105         case EptLineStrip:
106             return GL_LINE_STRIP;
107         case EptTriangleStrip:
108             return GL_TRIANGLE_STRIP;
109 
110         case EptUndefined:
111         default:
112             UNREACHABLE();
113             return GL_INVALID_VALUE;
114     }
115 }
116 
GetTessellationShaderTypeEnum(sh::TLayoutTessEvaluationType type)117 GLenum GetTessellationShaderTypeEnum(sh::TLayoutTessEvaluationType type)
118 {
119     switch (type)
120     {
121         case EtetTriangles:
122             return GL_TRIANGLES;
123         case EtetQuads:
124             return GL_QUADS;
125         case EtetIsolines:
126             return GL_ISOLINES;
127         case EtetEqualSpacing:
128             return GL_EQUAL;
129         case EtetFractionalEvenSpacing:
130             return GL_FRACTIONAL_EVEN;
131         case EtetFractionalOddSpacing:
132             return GL_FRACTIONAL_ODD;
133         case EtetCw:
134             return GL_CW;
135         case EtetCcw:
136             return GL_CCW;
137         case EtetPointMode:
138             return GL_TESS_GEN_POINT_MODE;
139 
140         case EtetUndefined:
141         default:
142             UNREACHABLE();
143             return GL_INVALID_VALUE;
144     }
145 }
146 
147 }  // anonymous namespace
148 
149 //
150 // Driver must call this first, once, before doing any other compiler operations.
151 // Subsequent calls to this function are no-op.
152 //
Initialize()153 bool Initialize()
154 {
155     if (!isInitialized)
156     {
157         isInitialized = InitProcess();
158     }
159     return isInitialized;
160 }
161 
162 //
163 // Cleanup symbol tables
164 //
Finalize()165 bool Finalize()
166 {
167     if (isInitialized)
168     {
169         DetachProcess();
170         isInitialized = false;
171     }
172     return true;
173 }
174 
175 //
176 // Initialize built-in resources with minimum expected values.
177 //
InitBuiltInResources(ShBuiltInResources * resources)178 void InitBuiltInResources(ShBuiltInResources *resources)
179 {
180     // Make comparable.
181     memset(resources, 0, sizeof(*resources));
182 
183     // Constants.
184     resources->MaxVertexAttribs             = 8;
185     resources->MaxVertexUniformVectors      = 128;
186     resources->MaxVaryingVectors            = 8;
187     resources->MaxVertexTextureImageUnits   = 0;
188     resources->MaxCombinedTextureImageUnits = 8;
189     resources->MaxTextureImageUnits         = 8;
190     resources->MaxFragmentUniformVectors    = 16;
191     resources->MaxDrawBuffers               = 1;
192 
193     // Extensions.
194     resources->OES_standard_derivatives                       = 0;
195     resources->OES_EGL_image_external                         = 0;
196     resources->OES_EGL_image_external_essl3                   = 0;
197     resources->NV_EGL_stream_consumer_external                = 0;
198     resources->ARB_texture_rectangle                          = 0;
199     resources->EXT_blend_func_extended                        = 0;
200     resources->EXT_draw_buffers                               = 0;
201     resources->EXT_frag_depth                                 = 0;
202     resources->EXT_shader_texture_lod                         = 0;
203     resources->EXT_shader_framebuffer_fetch                   = 0;
204     resources->EXT_shader_framebuffer_fetch_non_coherent      = 0;
205     resources->NV_shader_framebuffer_fetch                    = 0;
206     resources->ARM_shader_framebuffer_fetch                   = 0;
207     resources->OVR_multiview                                  = 0;
208     resources->OVR_multiview2                                 = 0;
209     resources->EXT_YUV_target                                 = 0;
210     resources->EXT_geometry_shader                            = 0;
211     resources->OES_geometry_shader                            = 0;
212     resources->EXT_gpu_shader5                                = 0;
213     resources->OES_shader_io_blocks                           = 0;
214     resources->EXT_shader_io_blocks                           = 0;
215     resources->EXT_shader_non_constant_global_initializers    = 0;
216     resources->NV_shader_noperspective_interpolation          = 0;
217     resources->OES_texture_storage_multisample_2d_array       = 0;
218     resources->OES_texture_3D                                 = 0;
219     resources->ANGLE_texture_multisample                      = 0;
220     resources->ANGLE_multi_draw                               = 0;
221     resources->ANGLE_base_vertex_base_instance                = 0;
222     resources->ANGLE_base_vertex_base_instance_shader_builtin = 0;
223     resources->WEBGL_video_texture                            = 0;
224     resources->APPLE_clip_distance                            = 0;
225     resources->OES_texture_cube_map_array                     = 0;
226     resources->EXT_texture_cube_map_array                     = 0;
227     resources->EXT_shadow_samplers                            = 0;
228     resources->OES_shader_multisample_interpolation           = 0;
229     resources->NV_draw_buffers                                = 0;
230     resources->OES_shader_image_atomic                        = 0;
231     resources->EXT_tessellation_shader                        = 0;
232     resources->OES_texture_buffer                             = 0;
233     resources->EXT_texture_buffer                             = 0;
234     resources->OES_sample_variables                           = 0;
235     resources->EXT_clip_cull_distance                         = 0;
236     resources->KHR_blend_equation_advanced                    = 0;
237 
238     resources->MaxClipDistances                = 8;
239     resources->MaxCullDistances                = 8;
240     resources->MaxCombinedClipAndCullDistances = 8;
241 
242     // Disable highp precision in fragment shader by default.
243     resources->FragmentPrecisionHigh = 0;
244 
245     // GLSL ES 3.0 constants.
246     resources->MaxVertexOutputVectors  = 16;
247     resources->MaxFragmentInputVectors = 15;
248     resources->MinProgramTexelOffset   = -8;
249     resources->MaxProgramTexelOffset   = 7;
250 
251     // Extensions constants.
252     resources->MaxDualSourceDrawBuffers = 0;
253 
254     resources->MaxViewsOVR = 4;
255 
256     // Disable name hashing by default.
257     resources->HashFunction = nullptr;
258 
259     resources->MaxExpressionComplexity = 256;
260     resources->MaxCallStackDepth       = 256;
261     resources->MaxFunctionParameters   = 1024;
262 
263     // ES 3.1 Revision 4, 7.2 Built-in Constants
264 
265     // ES 3.1, Revision 4, 8.13 Texture minification
266     // "The value of MIN_PROGRAM_TEXTURE_GATHER_OFFSET must be less than or equal to the value of
267     // MIN_PROGRAM_TEXEL_OFFSET. The value of MAX_PROGRAM_TEXTURE_GATHER_OFFSET must be greater than
268     // or equal to the value of MAX_PROGRAM_TEXEL_OFFSET"
269     resources->MinProgramTextureGatherOffset = -8;
270     resources->MaxProgramTextureGatherOffset = 7;
271 
272     resources->MaxImageUnits            = 4;
273     resources->MaxVertexImageUniforms   = 0;
274     resources->MaxFragmentImageUniforms = 0;
275     resources->MaxComputeImageUniforms  = 4;
276     resources->MaxCombinedImageUniforms = 4;
277 
278     resources->MaxUniformLocations = 1024;
279 
280     resources->MaxCombinedShaderOutputResources = 4;
281 
282     resources->MaxComputeWorkGroupCount[0] = 65535;
283     resources->MaxComputeWorkGroupCount[1] = 65535;
284     resources->MaxComputeWorkGroupCount[2] = 65535;
285     resources->MaxComputeWorkGroupSize[0]  = 128;
286     resources->MaxComputeWorkGroupSize[1]  = 128;
287     resources->MaxComputeWorkGroupSize[2]  = 64;
288     resources->MaxComputeUniformComponents = 512;
289     resources->MaxComputeTextureImageUnits = 16;
290 
291     resources->MaxComputeAtomicCounters       = 8;
292     resources->MaxComputeAtomicCounterBuffers = 1;
293 
294     resources->MaxVertexAtomicCounters   = 0;
295     resources->MaxFragmentAtomicCounters = 0;
296     resources->MaxCombinedAtomicCounters = 8;
297     resources->MaxAtomicCounterBindings  = 1;
298 
299     resources->MaxVertexAtomicCounterBuffers   = 0;
300     resources->MaxFragmentAtomicCounterBuffers = 0;
301     resources->MaxCombinedAtomicCounterBuffers = 1;
302     resources->MaxAtomicCounterBufferSize      = 32;
303 
304     resources->MaxUniformBufferBindings       = 32;
305     resources->MaxShaderStorageBufferBindings = 4;
306 
307     resources->MaxGeometryUniformComponents     = 1024;
308     resources->MaxGeometryUniformBlocks         = 12;
309     resources->MaxGeometryInputComponents       = 64;
310     resources->MaxGeometryOutputComponents      = 64;
311     resources->MaxGeometryOutputVertices        = 256;
312     resources->MaxGeometryTotalOutputComponents = 1024;
313     resources->MaxGeometryTextureImageUnits     = 16;
314     resources->MaxGeometryAtomicCounterBuffers  = 0;
315     resources->MaxGeometryAtomicCounters        = 0;
316     resources->MaxGeometryShaderStorageBlocks   = 0;
317     resources->MaxGeometryShaderInvocations     = 32;
318     resources->MaxGeometryImageUniforms         = 0;
319 
320     resources->MaxTessControlInputComponents       = 64;
321     resources->MaxTessControlOutputComponents      = 64;
322     resources->MaxTessControlTextureImageUnits     = 16;
323     resources->MaxTessControlUniformComponents     = 1024;
324     resources->MaxTessControlTotalOutputComponents = 2048;
325     resources->MaxTessControlImageUniforms         = 0;
326     resources->MaxTessControlAtomicCounters        = 0;
327     resources->MaxTessControlAtomicCounterBuffers  = 0;
328 
329     resources->MaxTessPatchComponents = 120;
330     resources->MaxPatchVertices       = 32;
331     resources->MaxTessGenLevel        = 64;
332 
333     resources->MaxTessEvaluationInputComponents      = 64;
334     resources->MaxTessEvaluationOutputComponents     = 64;
335     resources->MaxTessEvaluationTextureImageUnits    = 16;
336     resources->MaxTessEvaluationUniformComponents    = 1024;
337     resources->MaxTessEvaluationImageUniforms        = 0;
338     resources->MaxTessEvaluationAtomicCounters       = 0;
339     resources->MaxTessEvaluationAtomicCounterBuffers = 0;
340 
341     resources->SubPixelBits = 8;
342 
343     resources->MaxSamples = 4;
344 }
345 
346 //
347 // Driver calls these to create and destroy compiler objects.
348 //
ConstructCompiler(sh::GLenum type,ShShaderSpec spec,ShShaderOutput output,const ShBuiltInResources * resources)349 ShHandle ConstructCompiler(sh::GLenum type,
350                            ShShaderSpec spec,
351                            ShShaderOutput output,
352                            const ShBuiltInResources *resources)
353 {
354     TShHandleBase *base = static_cast<TShHandleBase *>(ConstructCompiler(type, spec, output));
355     if (base == nullptr)
356     {
357         return 0;
358     }
359 
360     TCompiler *compiler = base->getAsCompiler();
361     if (compiler == nullptr)
362     {
363         return 0;
364     }
365 
366     // Generate built-in symbol table.
367     if (!compiler->Init(*resources))
368     {
369         Destruct(base);
370         return 0;
371     }
372 
373     return base;
374 }
375 
Destruct(ShHandle handle)376 void Destruct(ShHandle handle)
377 {
378     if (handle == 0)
379         return;
380 
381     TShHandleBase *base = static_cast<TShHandleBase *>(handle);
382 
383     if (base->getAsCompiler())
384         DeleteCompiler(base->getAsCompiler());
385 }
386 
GetBuiltInResourcesString(const ShHandle handle)387 const std::string &GetBuiltInResourcesString(const ShHandle handle)
388 {
389     TCompiler *compiler = GetCompilerFromHandle(handle);
390     ASSERT(compiler);
391     return compiler->getBuiltInResourcesString();
392 }
393 
394 //
395 // Do an actual compile on the given strings.  The result is left
396 // in the given compile object.
397 //
398 // Return:  The return value of ShCompile is really boolean, indicating
399 // success or failure.
400 //
Compile(const ShHandle handle,const char * const shaderStrings[],size_t numStrings,ShCompileOptions compileOptions)401 bool Compile(const ShHandle handle,
402              const char *const shaderStrings[],
403              size_t numStrings,
404              ShCompileOptions compileOptions)
405 {
406     TCompiler *compiler = GetCompilerFromHandle(handle);
407     ASSERT(compiler);
408 
409     return compiler->compile(shaderStrings, numStrings, compileOptions);
410 }
411 
ClearResults(const ShHandle handle)412 void ClearResults(const ShHandle handle)
413 {
414     TCompiler *compiler = GetCompilerFromHandle(handle);
415     ASSERT(compiler);
416     compiler->clearResults();
417 }
418 
GetShaderVersion(const ShHandle handle)419 int GetShaderVersion(const ShHandle handle)
420 {
421     TCompiler *compiler = GetCompilerFromHandle(handle);
422     ASSERT(compiler);
423     return compiler->getShaderVersion();
424 }
425 
GetShaderOutputType(const ShHandle handle)426 ShShaderOutput GetShaderOutputType(const ShHandle handle)
427 {
428     TCompiler *compiler = GetCompilerFromHandle(handle);
429     ASSERT(compiler);
430     return compiler->getOutputType();
431 }
432 
433 //
434 // Return any compiler log of messages for the application.
435 //
GetInfoLog(const ShHandle handle)436 const std::string &GetInfoLog(const ShHandle handle)
437 {
438     TCompiler *compiler = GetCompilerFromHandle(handle);
439     ASSERT(compiler);
440 
441     TInfoSink &infoSink = compiler->getInfoSink();
442     return infoSink.info.str();
443 }
444 
445 //
446 // Return any object code.
447 //
GetObjectCode(const ShHandle handle)448 const std::string &GetObjectCode(const ShHandle handle)
449 {
450     TCompiler *compiler = GetCompilerFromHandle(handle);
451     ASSERT(compiler);
452 
453     TInfoSink &infoSink = compiler->getInfoSink();
454     return infoSink.obj.str();
455 }
456 
457 //
458 // Return any object binary code.
459 //
GetObjectBinaryBlob(const ShHandle handle)460 const BinaryBlob &GetObjectBinaryBlob(const ShHandle handle)
461 {
462     TCompiler *compiler = GetCompilerFromHandle(handle);
463     ASSERT(compiler);
464 
465     TInfoSink &infoSink = compiler->getInfoSink();
466     return infoSink.obj.getBinary();
467 }
468 
GetNameHashingMap(const ShHandle handle)469 const std::map<std::string, std::string> *GetNameHashingMap(const ShHandle handle)
470 {
471     TCompiler *compiler = GetCompilerFromHandle(handle);
472     ASSERT(compiler);
473     return &(compiler->getNameMap());
474 }
475 
GetUniforms(const ShHandle handle)476 const std::vector<ShaderVariable> *GetUniforms(const ShHandle handle)
477 {
478     TCompiler *compiler = GetCompilerFromHandle(handle);
479     if (!compiler)
480     {
481         return nullptr;
482     }
483     return &compiler->getUniforms();
484 }
485 
GetInputVaryings(const ShHandle handle)486 const std::vector<ShaderVariable> *GetInputVaryings(const ShHandle handle)
487 {
488     TCompiler *compiler = GetCompilerFromHandle(handle);
489     if (compiler == nullptr)
490     {
491         return nullptr;
492     }
493     return &compiler->getInputVaryings();
494 }
495 
GetOutputVaryings(const ShHandle handle)496 const std::vector<ShaderVariable> *GetOutputVaryings(const ShHandle handle)
497 {
498     TCompiler *compiler = GetCompilerFromHandle(handle);
499     if (compiler == nullptr)
500     {
501         return nullptr;
502     }
503     return &compiler->getOutputVaryings();
504 }
505 
GetVaryings(const ShHandle handle)506 const std::vector<ShaderVariable> *GetVaryings(const ShHandle handle)
507 {
508     TCompiler *compiler = GetCompilerFromHandle(handle);
509     if (compiler == nullptr)
510     {
511         return nullptr;
512     }
513 
514     switch (compiler->getShaderType())
515     {
516         case GL_VERTEX_SHADER:
517             return &compiler->getOutputVaryings();
518         case GL_FRAGMENT_SHADER:
519             return &compiler->getInputVaryings();
520         case GL_COMPUTE_SHADER:
521             ASSERT(compiler->getOutputVaryings().empty() && compiler->getInputVaryings().empty());
522             return &compiler->getOutputVaryings();
523         // Since geometry shaders have both input and output varyings, we shouldn't call GetVaryings
524         // on a geometry shader.
525         default:
526             return nullptr;
527     }
528 }
529 
GetAttributes(const ShHandle handle)530 const std::vector<ShaderVariable> *GetAttributes(const ShHandle handle)
531 {
532     TCompiler *compiler = GetCompilerFromHandle(handle);
533     if (!compiler)
534     {
535         return nullptr;
536     }
537     return &compiler->getAttributes();
538 }
539 
GetOutputVariables(const ShHandle handle)540 const std::vector<ShaderVariable> *GetOutputVariables(const ShHandle handle)
541 {
542     TCompiler *compiler = GetCompilerFromHandle(handle);
543     if (!compiler)
544     {
545         return nullptr;
546     }
547     return &compiler->getOutputVariables();
548 }
549 
GetInterfaceBlocks(const ShHandle handle)550 const std::vector<InterfaceBlock> *GetInterfaceBlocks(const ShHandle handle)
551 {
552     return GetShaderVariables<InterfaceBlock>(handle);
553 }
554 
GetUniformBlocks(const ShHandle handle)555 const std::vector<InterfaceBlock> *GetUniformBlocks(const ShHandle handle)
556 {
557     ASSERT(handle);
558     TShHandleBase *base = static_cast<TShHandleBase *>(handle);
559     TCompiler *compiler = base->getAsCompiler();
560     ASSERT(compiler);
561 
562     return &compiler->getUniformBlocks();
563 }
564 
GetShaderStorageBlocks(const ShHandle handle)565 const std::vector<InterfaceBlock> *GetShaderStorageBlocks(const ShHandle handle)
566 {
567     ASSERT(handle);
568     TShHandleBase *base = static_cast<TShHandleBase *>(handle);
569     TCompiler *compiler = base->getAsCompiler();
570     ASSERT(compiler);
571 
572     return &compiler->getShaderStorageBlocks();
573 }
574 
GetComputeShaderLocalGroupSize(const ShHandle handle)575 WorkGroupSize GetComputeShaderLocalGroupSize(const ShHandle handle)
576 {
577     ASSERT(handle);
578 
579     TShHandleBase *base = static_cast<TShHandleBase *>(handle);
580     TCompiler *compiler = base->getAsCompiler();
581     ASSERT(compiler);
582 
583     return compiler->getComputeShaderLocalSize();
584 }
585 
GetVertexShaderNumViews(const ShHandle handle)586 int GetVertexShaderNumViews(const ShHandle handle)
587 {
588     ASSERT(handle);
589     TShHandleBase *base = static_cast<TShHandleBase *>(handle);
590     TCompiler *compiler = base->getAsCompiler();
591     ASSERT(compiler);
592 
593     return compiler->getNumViews();
594 }
595 
HasEarlyFragmentTestsOptimization(const ShHandle handle)596 bool HasEarlyFragmentTestsOptimization(const ShHandle handle)
597 {
598     TCompiler *compiler = GetCompilerFromHandle(handle);
599     if (compiler == nullptr)
600     {
601         return false;
602     }
603     return compiler->isEarlyFragmentTestsOptimized();
604 }
605 
GetShaderSpecConstUsageBits(const ShHandle handle)606 uint32_t GetShaderSpecConstUsageBits(const ShHandle handle)
607 {
608     TCompiler *compiler = GetCompilerFromHandle(handle);
609     if (compiler == nullptr)
610     {
611         return 0;
612     }
613     return compiler->getSpecConstUsageBits().bits();
614 }
615 
CheckVariablesWithinPackingLimits(int maxVectors,const std::vector<ShaderVariable> & variables)616 bool CheckVariablesWithinPackingLimits(int maxVectors, const std::vector<ShaderVariable> &variables)
617 {
618     return CheckVariablesInPackingLimits(maxVectors, variables);
619 }
620 
GetShaderStorageBlockRegister(const ShHandle handle,const std::string & shaderStorageBlockName,unsigned int * indexOut)621 bool GetShaderStorageBlockRegister(const ShHandle handle,
622                                    const std::string &shaderStorageBlockName,
623                                    unsigned int *indexOut)
624 {
625 #ifdef ANGLE_ENABLE_HLSL
626     ASSERT(indexOut);
627 
628     TranslatorHLSL *translator = GetTranslatorHLSLFromHandle(handle);
629     ASSERT(translator);
630 
631     if (!translator->hasShaderStorageBlock(shaderStorageBlockName))
632     {
633         return false;
634     }
635 
636     *indexOut = translator->getShaderStorageBlockRegister(shaderStorageBlockName);
637     return true;
638 #else
639     return false;
640 #endif  // ANGLE_ENABLE_HLSL
641 }
642 
GetUniformBlockRegister(const ShHandle handle,const std::string & uniformBlockName,unsigned int * indexOut)643 bool GetUniformBlockRegister(const ShHandle handle,
644                              const std::string &uniformBlockName,
645                              unsigned int *indexOut)
646 {
647 #ifdef ANGLE_ENABLE_HLSL
648     ASSERT(indexOut);
649 
650     TranslatorHLSL *translator = GetTranslatorHLSLFromHandle(handle);
651     ASSERT(translator);
652 
653     if (!translator->hasUniformBlock(uniformBlockName))
654     {
655         return false;
656     }
657 
658     *indexOut = translator->getUniformBlockRegister(uniformBlockName);
659     return true;
660 #else
661     return false;
662 #endif  // ANGLE_ENABLE_HLSL
663 }
664 
ShouldUniformBlockUseStructuredBuffer(const ShHandle handle,const std::string & uniformBlockName)665 bool ShouldUniformBlockUseStructuredBuffer(const ShHandle handle,
666                                            const std::string &uniformBlockName)
667 {
668 #ifdef ANGLE_ENABLE_HLSL
669     TranslatorHLSL *translator = GetTranslatorHLSLFromHandle(handle);
670     ASSERT(translator);
671 
672     return translator->shouldUniformBlockUseStructuredBuffer(uniformBlockName);
673 #else
674     return false;
675 #endif  // ANGLE_ENABLE_HLSL
676 }
677 
GetUniformRegisterMap(const ShHandle handle)678 const std::map<std::string, unsigned int> *GetUniformRegisterMap(const ShHandle handle)
679 {
680 #ifdef ANGLE_ENABLE_HLSL
681     TranslatorHLSL *translator = GetTranslatorHLSLFromHandle(handle);
682     ASSERT(translator);
683 
684     return translator->getUniformRegisterMap();
685 #else
686     return nullptr;
687 #endif  // ANGLE_ENABLE_HLSL
688 }
689 
GetSlowCompilingUniformBlockSet(const ShHandle handle)690 const std::set<std::string> *GetSlowCompilingUniformBlockSet(const ShHandle handle)
691 {
692 #ifdef ANGLE_ENABLE_HLSL
693     TranslatorHLSL *translator = GetTranslatorHLSLFromHandle(handle);
694     ASSERT(translator);
695 
696     return translator->getSlowCompilingUniformBlockSet();
697 #else
698     return nullptr;
699 #endif  // ANGLE_ENABLE_HLSL
700 }
701 
GetReadonlyImage2DRegisterIndex(const ShHandle handle)702 unsigned int GetReadonlyImage2DRegisterIndex(const ShHandle handle)
703 {
704 #ifdef ANGLE_ENABLE_HLSL
705     TranslatorHLSL *translator = GetTranslatorHLSLFromHandle(handle);
706     ASSERT(translator);
707 
708     return translator->getReadonlyImage2DRegisterIndex();
709 #else
710     return 0;
711 #endif  // ANGLE_ENABLE_HLSL
712 }
713 
GetImage2DRegisterIndex(const ShHandle handle)714 unsigned int GetImage2DRegisterIndex(const ShHandle handle)
715 {
716 #ifdef ANGLE_ENABLE_HLSL
717     TranslatorHLSL *translator = GetTranslatorHLSLFromHandle(handle);
718     ASSERT(translator);
719 
720     return translator->getImage2DRegisterIndex();
721 #else
722     return 0;
723 #endif  // ANGLE_ENABLE_HLSL
724 }
725 
GetUsedImage2DFunctionNames(const ShHandle handle)726 const std::set<std::string> *GetUsedImage2DFunctionNames(const ShHandle handle)
727 {
728 #ifdef ANGLE_ENABLE_HLSL
729     TranslatorHLSL *translator = GetTranslatorHLSLFromHandle(handle);
730     ASSERT(translator);
731 
732     return translator->getUsedImage2DFunctionNames();
733 #else
734     return nullptr;
735 #endif  // ANGLE_ENABLE_HLSL
736 }
737 
HasValidGeometryShaderInputPrimitiveType(const ShHandle handle)738 bool HasValidGeometryShaderInputPrimitiveType(const ShHandle handle)
739 {
740     ASSERT(handle);
741 
742     TShHandleBase *base = static_cast<TShHandleBase *>(handle);
743     TCompiler *compiler = base->getAsCompiler();
744     ASSERT(compiler);
745 
746     return compiler->getGeometryShaderInputPrimitiveType() != EptUndefined;
747 }
748 
HasValidGeometryShaderOutputPrimitiveType(const ShHandle handle)749 bool HasValidGeometryShaderOutputPrimitiveType(const ShHandle handle)
750 {
751     ASSERT(handle);
752 
753     TShHandleBase *base = static_cast<TShHandleBase *>(handle);
754     TCompiler *compiler = base->getAsCompiler();
755     ASSERT(compiler);
756 
757     return compiler->getGeometryShaderOutputPrimitiveType() != EptUndefined;
758 }
759 
HasValidGeometryShaderMaxVertices(const ShHandle handle)760 bool HasValidGeometryShaderMaxVertices(const ShHandle handle)
761 {
762     ASSERT(handle);
763 
764     TShHandleBase *base = static_cast<TShHandleBase *>(handle);
765     TCompiler *compiler = base->getAsCompiler();
766     ASSERT(compiler);
767 
768     return compiler->getGeometryShaderMaxVertices() >= 0;
769 }
770 
HasValidTessGenMode(const ShHandle handle)771 bool HasValidTessGenMode(const ShHandle handle)
772 {
773     ASSERT(handle);
774 
775     TShHandleBase *base = static_cast<TShHandleBase *>(handle);
776     TCompiler *compiler = base->getAsCompiler();
777     ASSERT(compiler);
778 
779     return compiler->getTessEvaluationShaderInputPrimitiveType() != EtetUndefined;
780 }
781 
HasValidTessGenSpacing(const ShHandle handle)782 bool HasValidTessGenSpacing(const ShHandle handle)
783 {
784     ASSERT(handle);
785 
786     TShHandleBase *base = static_cast<TShHandleBase *>(handle);
787     TCompiler *compiler = base->getAsCompiler();
788     ASSERT(compiler);
789 
790     return compiler->getTessEvaluationShaderInputVertexSpacingType() != EtetUndefined;
791 }
792 
HasValidTessGenVertexOrder(const ShHandle handle)793 bool HasValidTessGenVertexOrder(const ShHandle handle)
794 {
795     ASSERT(handle);
796 
797     TShHandleBase *base = static_cast<TShHandleBase *>(handle);
798     TCompiler *compiler = base->getAsCompiler();
799     ASSERT(compiler);
800 
801     return compiler->getTessEvaluationShaderInputOrderingType() != EtetUndefined;
802 }
803 
HasValidTessGenPointMode(const ShHandle handle)804 bool HasValidTessGenPointMode(const ShHandle handle)
805 {
806     ASSERT(handle);
807 
808     TShHandleBase *base = static_cast<TShHandleBase *>(handle);
809     TCompiler *compiler = base->getAsCompiler();
810     ASSERT(compiler);
811 
812     return compiler->getTessEvaluationShaderInputPointType() != EtetUndefined;
813 }
814 
GetGeometryShaderInputPrimitiveType(const ShHandle handle)815 GLenum GetGeometryShaderInputPrimitiveType(const ShHandle handle)
816 {
817     ASSERT(handle);
818 
819     TShHandleBase *base = static_cast<TShHandleBase *>(handle);
820     TCompiler *compiler = base->getAsCompiler();
821     ASSERT(compiler);
822 
823     return GetGeometryShaderPrimitiveTypeEnum(compiler->getGeometryShaderInputPrimitiveType());
824 }
825 
GetGeometryShaderOutputPrimitiveType(const ShHandle handle)826 GLenum GetGeometryShaderOutputPrimitiveType(const ShHandle handle)
827 {
828     ASSERT(handle);
829 
830     TShHandleBase *base = static_cast<TShHandleBase *>(handle);
831     TCompiler *compiler = base->getAsCompiler();
832     ASSERT(compiler);
833 
834     return GetGeometryShaderPrimitiveTypeEnum(compiler->getGeometryShaderOutputPrimitiveType());
835 }
836 
GetGeometryShaderInvocations(const ShHandle handle)837 int GetGeometryShaderInvocations(const ShHandle handle)
838 {
839     ASSERT(handle);
840 
841     TShHandleBase *base = static_cast<TShHandleBase *>(handle);
842     TCompiler *compiler = base->getAsCompiler();
843     ASSERT(compiler);
844 
845     return compiler->getGeometryShaderInvocations();
846 }
847 
GetGeometryShaderMaxVertices(const ShHandle handle)848 int GetGeometryShaderMaxVertices(const ShHandle handle)
849 {
850     ASSERT(handle);
851 
852     TShHandleBase *base = static_cast<TShHandleBase *>(handle);
853     TCompiler *compiler = base->getAsCompiler();
854     ASSERT(compiler);
855 
856     int maxVertices = compiler->getGeometryShaderMaxVertices();
857     ASSERT(maxVertices >= 0);
858     return maxVertices;
859 }
860 
GetTessControlShaderVertices(const ShHandle handle)861 int GetTessControlShaderVertices(const ShHandle handle)
862 {
863     ASSERT(handle);
864 
865     TShHandleBase *base = static_cast<TShHandleBase *>(handle);
866     TCompiler *compiler = base->getAsCompiler();
867     ASSERT(compiler);
868 
869     int vertices = compiler->getTessControlShaderOutputVertices();
870     return vertices;
871 }
872 
GetTessGenMode(const ShHandle handle)873 GLenum GetTessGenMode(const ShHandle handle)
874 {
875     ASSERT(handle);
876 
877     TShHandleBase *base = static_cast<TShHandleBase *>(handle);
878     TCompiler *compiler = base->getAsCompiler();
879     ASSERT(compiler);
880 
881     return GetTessellationShaderTypeEnum(compiler->getTessEvaluationShaderInputPrimitiveType());
882 }
883 
GetTessGenSpacing(const ShHandle handle)884 GLenum GetTessGenSpacing(const ShHandle handle)
885 {
886     ASSERT(handle);
887 
888     TShHandleBase *base = static_cast<TShHandleBase *>(handle);
889     TCompiler *compiler = base->getAsCompiler();
890     ASSERT(compiler);
891 
892     return GetTessellationShaderTypeEnum(compiler->getTessEvaluationShaderInputVertexSpacingType());
893 }
894 
GetTessGenVertexOrder(const ShHandle handle)895 GLenum GetTessGenVertexOrder(const ShHandle handle)
896 {
897     ASSERT(handle);
898 
899     TShHandleBase *base = static_cast<TShHandleBase *>(handle);
900     TCompiler *compiler = base->getAsCompiler();
901     ASSERT(compiler);
902 
903     return GetTessellationShaderTypeEnum(compiler->getTessEvaluationShaderInputOrderingType());
904 }
905 
GetTessGenPointMode(const ShHandle handle)906 GLenum GetTessGenPointMode(const ShHandle handle)
907 {
908     ASSERT(handle);
909 
910     TShHandleBase *base = static_cast<TShHandleBase *>(handle);
911     TCompiler *compiler = base->getAsCompiler();
912     ASSERT(compiler);
913 
914     return GetTessellationShaderTypeEnum(compiler->getTessEvaluationShaderInputPointType());
915 }
916 
GetShaderSharedMemorySize(const ShHandle handle)917 unsigned int GetShaderSharedMemorySize(const ShHandle handle)
918 {
919     ASSERT(handle);
920 
921     TShHandleBase *base = static_cast<TShHandleBase *>(handle);
922     TCompiler *compiler = base->getAsCompiler();
923     ASSERT(compiler);
924 
925     unsigned int sharedMemorySize = compiler->getSharedMemorySize();
926     return sharedMemorySize;
927 }
928 
GetAdvancedBlendEquations(const ShHandle handle)929 uint32_t GetAdvancedBlendEquations(const ShHandle handle)
930 {
931     TCompiler *compiler = GetCompilerFromHandle(handle);
932     ASSERT(compiler);
933 
934     return compiler->getAdvancedBlendEquations().bits();
935 }
936 
InitializeGlslang()937 void InitializeGlslang()
938 {
939     if (initializeGlslangRefCount == 0)
940     {
941         GlslangInitialize();
942     }
943     ++initializeGlslangRefCount;
944     ASSERT(initializeGlslangRefCount < std::numeric_limits<int>::max());
945 }
946 
FinalizeGlslang()947 void FinalizeGlslang()
948 {
949     --initializeGlslangRefCount;
950     ASSERT(initializeGlslangRefCount >= 0);
951     if (initializeGlslangRefCount == 0)
952     {
953         GlslangFinalize();
954     }
955 }
956 
957 // Can't prefix with just _ because then we might introduce a double underscore, which is not safe
958 // in GLSL (ESSL 3.00.6 section 3.8: All identifiers containing a double underscore are reserved for
959 // use by the underlying implementation). u is short for user-defined.
960 const char kUserDefinedNamePrefix[] = "_u";
961 
962 namespace vk
963 {
964 // Interface block name containing the aggregate default uniforms
965 const char kDefaultUniformsNameVS[]  = "defaultUniformsVS";
966 const char kDefaultUniformsNameTCS[] = "defaultUniformsTCS";
967 const char kDefaultUniformsNameTES[] = "defaultUniformsTES";
968 const char kDefaultUniformsNameGS[]  = "defaultUniformsGS";
969 const char kDefaultUniformsNameFS[]  = "defaultUniformsFS";
970 const char kDefaultUniformsNameCS[]  = "defaultUniformsCS";
971 
972 // Interface block and variable names containing driver uniforms
973 const char kDriverUniformsBlockName[] = "ANGLEUniformBlock";
974 const char kDriverUniformsVarName[]   = "ANGLEUniforms";
975 
976 // Interface block array name used for atomic counter emulation
977 const char kAtomicCountersBlockName[] = "ANGLEAtomicCounters";
978 
979 const char kLineRasterEmulationPosition[] = "ANGLEPosition";
980 
981 const char kXfbEmulationGetOffsetsFunctionName[] = "ANGLEGetXfbOffsets";
982 const char kXfbEmulationCaptureFunctionName[]    = "ANGLECaptureXfb";
983 const char kXfbEmulationBufferBlockName[]        = "ANGLEXfbBuffer";
984 const char kXfbEmulationBufferName[]             = "ANGLEXfb";
985 const char kXfbEmulationBufferFieldName[]        = "xfbOut";
986 
987 const char kXfbExtensionPositionOutName[] = "ANGLEXfbPosition";
988 
989 // EXT_shader_framebuffer_fetch / EXT_shader_framebuffer_fetch_non_coherent
990 const char kInputAttachmentName[] = "ANGLEInputAttachment";
991 
992 }  // namespace vk
993 
BlockLayoutTypeToString(BlockLayoutType type)994 const char *BlockLayoutTypeToString(BlockLayoutType type)
995 {
996     switch (type)
997     {
998         case BlockLayoutType::BLOCKLAYOUT_STD140:
999             return "std140";
1000         case BlockLayoutType::BLOCKLAYOUT_STD430:
1001             return "std430";
1002         case BlockLayoutType::BLOCKLAYOUT_PACKED:
1003             return "packed";
1004         case BlockLayoutType::BLOCKLAYOUT_SHARED:
1005             return "shared";
1006         default:
1007             return "invalid";
1008     }
1009 }
1010 
BlockTypeToString(BlockType type)1011 const char *BlockTypeToString(BlockType type)
1012 {
1013     switch (type)
1014     {
1015         case BlockType::BLOCK_BUFFER:
1016             return "buffer";
1017         case BlockType::BLOCK_UNIFORM:
1018             return "uniform";
1019         default:
1020             return "invalid";
1021     }
1022 }
1023 
InterpolationTypeToString(InterpolationType type)1024 const char *InterpolationTypeToString(InterpolationType type)
1025 {
1026     switch (type)
1027     {
1028         case InterpolationType::INTERPOLATION_SMOOTH:
1029             return "smooth";
1030         case InterpolationType::INTERPOLATION_CENTROID:
1031             return "centroid";
1032         case InterpolationType::INTERPOLATION_SAMPLE:
1033             return "sample";
1034         case InterpolationType::INTERPOLATION_FLAT:
1035             return "flat";
1036         case InterpolationType::INTERPOLATION_NOPERSPECTIVE:
1037             return "noperspective";
1038         default:
1039             return "invalid";
1040     }
1041 }
1042 }  // namespace sh
1043