blob: 39dd6ccd8b3bd306f587e7646eafa37cf188f191 [file] [log] [blame]
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001//
shannonwoods@chromium.org96e7ba12013-05-30 00:02:41 +00002// Copyright (c) 2002-2013 The ANGLE Project Authors. All rights reserved.
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00003// Use of this source code is governed by a BSD-style license that can be
4// found in the LICENSE file.
5//
Olli Etuaho0f684632017-07-13 12:42:15 +03006// Symbol table for parsing. The design principles and most of the functionality are documented in
7// the header file.
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00008//
9
apatrick@chromium.orge057c5d2012-01-26 19:18:24 +000010#if defined(_MSC_VER)
Jamie Madilld7b1ab52016-12-12 14:42:19 -050011#pragma warning(disable : 4718)
apatrick@chromium.orge057c5d2012-01-26 19:18:24 +000012#endif
13
Geoff Lang17732822013-08-29 13:46:49 -040014#include "compiler/translator/SymbolTable.h"
Olli Etuaho01d0ad02017-01-22 14:51:23 -080015
Olli Etuaho01d0ad02017-01-22 14:51:23 -080016#include "compiler/translator/IntermNode.h"
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +000017
apatrick@chromium.org8187fa82010-06-15 22:09:28 +000018#include <stdio.h>
kbr@chromium.org476541f2011-10-27 21:14:51 +000019#include <algorithm>
20
Jamie Madill45bcc782016-11-07 13:58:48 -050021namespace sh
22{
23
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +000024//
25// Symbol table levels are a map of pointers to symbols that have to be deleted.
26//
27TSymbolTableLevel::~TSymbolTableLevel()
28{
daniel@transgaming.com0578f812010-05-17 09:58:39 +000029 for (tLevel::iterator it = level.begin(); it != level.end(); ++it)
30 delete (*it).second;
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +000031}
32
Nicolas Capensadfffe42014-06-17 02:13:36 -040033bool TSymbolTableLevel::insert(TSymbol *symbol)
Jamie Madillbfa91f42014-06-05 15:45:18 -040034{
Jamie Madillbfa91f42014-06-05 15:45:18 -040035 // returning true means symbol was added to the table
Nicolas Capensadfffe42014-06-17 02:13:36 -040036 tInsertResult result = level.insert(tLevelPair(symbol->getMangledName(), symbol));
Jamie Madillbfa91f42014-06-05 15:45:18 -040037
38 return result.second;
39}
40
Olli Etuahob2983c92015-03-18 14:02:46 +020041bool TSymbolTableLevel::insertUnmangled(TFunction *function)
42{
Olli Etuahob2983c92015-03-18 14:02:46 +020043 // returning true means symbol was added to the table
Olli Etuahobed35d72017-12-20 16:36:26 +020044 tInsertResult result = level.insert(tLevelPair(function->name(), function));
Olli Etuahob2983c92015-03-18 14:02:46 +020045
46 return result.second;
47}
48
Jamie Madillbfa91f42014-06-05 15:45:18 -040049TSymbol *TSymbolTableLevel::find(const TString &name) const
50{
51 tLevel::const_iterator it = level.find(name);
52 if (it == level.end())
53 return 0;
54 else
55 return (*it).second;
56}
57
Olli Etuaho342b83d2018-01-10 13:24:01 +020058void TSymbolTableLevel::insertUnmangledBuiltInName(const char *name)
59{
60 mUnmangledBuiltInNames.insert(name);
61}
62
63bool TSymbolTableLevel::hasUnmangledBuiltIn(const char *name) const
64{
65 return mUnmangledBuiltInNames.count(name) > 0;
66}
67
Jamie Madilld7b1ab52016-12-12 14:42:19 -050068TSymbol *TSymbolTable::find(const TString &name,
69 int shaderVersion,
70 bool *builtIn,
71 bool *sameScope) const
shannonwoods@chromium.org96e7ba12013-05-30 00:02:41 +000072{
73 int level = currentLevel();
74 TSymbol *symbol;
75
76 do
77 {
Olli Etuaho977ee7e2017-07-21 11:38:27 +030078 if (level == GLSL_BUILTINS)
79 level--;
Martin Radeve93d24e2016-07-28 12:06:05 +030080 if (level == ESSL3_1_BUILTINS && shaderVersion != 310)
81 level--;
82 if (level == ESSL3_BUILTINS && shaderVersion < 300)
Zhenyao Mo9eedea02014-05-12 16:02:35 -070083 level--;
84 if (level == ESSL1_BUILTINS && shaderVersion != 100)
85 level--;
shannonwoods@chromium.org96e7ba12013-05-30 00:02:41 +000086
87 symbol = table[level]->find(name);
Jamie Madilld7b1ab52016-12-12 14:42:19 -050088 } while (symbol == 0 && --level >= 0);
shannonwoods@chromium.org96e7ba12013-05-30 00:02:41 +000089
90 if (builtIn)
91 *builtIn = (level <= LAST_BUILTIN_LEVEL);
92 if (sameScope)
93 *sameScope = (level == currentLevel());
94
95 return symbol;
96}
97
Zhenyao Mod7490962016-11-09 15:49:51 -080098TSymbol *TSymbolTable::findGlobal(const TString &name) const
99{
100 ASSERT(table.size() > GLOBAL_LEVEL);
101 return table[GLOBAL_LEVEL]->find(name);
102}
103
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500104TSymbol *TSymbolTable::findBuiltIn(const TString &name, int shaderVersion) const
shannonwoods@chromium.org96e7ba12013-05-30 00:02:41 +0000105{
Olli Etuaho977ee7e2017-07-21 11:38:27 +0300106 return findBuiltIn(name, shaderVersion, false);
107}
108
109TSymbol *TSymbolTable::findBuiltIn(const TString &name,
110 int shaderVersion,
111 bool includeGLSLBuiltins) const
112{
shannonwoods@chromium.org96e7ba12013-05-30 00:02:41 +0000113 for (int level = LAST_BUILTIN_LEVEL; level >= 0; level--)
114 {
Olli Etuaho977ee7e2017-07-21 11:38:27 +0300115 if (level == GLSL_BUILTINS && !includeGLSLBuiltins)
116 level--;
Martin Radeve93d24e2016-07-28 12:06:05 +0300117 if (level == ESSL3_1_BUILTINS && shaderVersion != 310)
118 level--;
119 if (level == ESSL3_BUILTINS && shaderVersion < 300)
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700120 level--;
121 if (level == ESSL1_BUILTINS && shaderVersion != 100)
122 level--;
shannonwoods@chromium.org96e7ba12013-05-30 00:02:41 +0000123
124 TSymbol *symbol = table[level]->find(name);
125
126 if (symbol)
127 return symbol;
128 }
129
Olli Etuaho977ee7e2017-07-21 11:38:27 +0300130 return nullptr;
shannonwoods@chromium.org96e7ba12013-05-30 00:02:41 +0000131}
Alok Priyadarshibc3f1ac2013-09-23 14:57:02 -0400132
133TSymbolTable::~TSymbolTable()
134{
135 while (table.size() > 0)
136 pop();
137}
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700138
Kai Ninomiya030017a2017-12-06 14:06:53 -0800139constexpr bool IsGenType(const TType *type)
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500140{
141 if (type)
142 {
143 TBasicType basicType = type->getBasicType();
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500144 return basicType == EbtGenType || basicType == EbtGenIType || basicType == EbtGenUType ||
145 basicType == EbtGenBType;
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500146 }
147
148 return false;
149}
150
Kai Ninomiya030017a2017-12-06 14:06:53 -0800151constexpr bool IsVecType(const TType *type)
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500152{
153 if (type)
154 {
155 TBasicType basicType = type->getBasicType();
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500156 return basicType == EbtVec || basicType == EbtIVec || basicType == EbtUVec ||
157 basicType == EbtBVec;
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500158 }
159
160 return false;
161}
162
Kai Ninomiya614dd0f2017-11-22 14:04:48 -0800163constexpr const TType *SpecificType(const TType *type, int size)
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500164{
165 ASSERT(size >= 1 && size <= 4);
166
167 if (!type)
168 {
169 return nullptr;
170 }
171
172 ASSERT(!IsVecType(type));
173
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500174 switch (type->getBasicType())
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500175 {
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500176 case EbtGenType:
Kai Ninomiya614dd0f2017-11-22 14:04:48 -0800177 return StaticType::GetForVec<EbtFloat>(type->getQualifier(),
178 static_cast<unsigned char>(size));
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500179 case EbtGenIType:
Kai Ninomiya614dd0f2017-11-22 14:04:48 -0800180 return StaticType::GetForVec<EbtInt>(type->getQualifier(),
181 static_cast<unsigned char>(size));
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500182 case EbtGenUType:
Kai Ninomiya614dd0f2017-11-22 14:04:48 -0800183 return StaticType::GetForVec<EbtUInt>(type->getQualifier(),
184 static_cast<unsigned char>(size));
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500185 case EbtGenBType:
Kai Ninomiya614dd0f2017-11-22 14:04:48 -0800186 return StaticType::GetForVec<EbtBool>(type->getQualifier(),
187 static_cast<unsigned char>(size));
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500188 default:
189 return type;
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500190 }
191}
192
Kai Ninomiya614dd0f2017-11-22 14:04:48 -0800193constexpr const TType *VectorType(const TType *type, int size)
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500194{
195 ASSERT(size >= 2 && size <= 4);
196
197 if (!type)
198 {
199 return nullptr;
200 }
201
202 ASSERT(!IsGenType(type));
203
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500204 switch (type->getBasicType())
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500205 {
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500206 case EbtVec:
Kai Ninomiya614dd0f2017-11-22 14:04:48 -0800207 return StaticType::GetForVecMat<EbtFloat>(static_cast<unsigned char>(size));
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500208 case EbtIVec:
Kai Ninomiya614dd0f2017-11-22 14:04:48 -0800209 return StaticType::GetForVecMat<EbtInt>(static_cast<unsigned char>(size));
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500210 case EbtUVec:
Kai Ninomiya614dd0f2017-11-22 14:04:48 -0800211 return StaticType::GetForVecMat<EbtUInt>(static_cast<unsigned char>(size));
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500212 case EbtBVec:
Kai Ninomiya614dd0f2017-11-22 14:04:48 -0800213 return StaticType::GetForVecMat<EbtBool>(static_cast<unsigned char>(size));
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500214 default:
215 return type;
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500216 }
217}
218
Olli Etuaho195be942017-12-04 23:40:14 +0200219bool TSymbolTable::declareVariable(TVariable *variable)
Olli Etuaho0f684632017-07-13 12:42:15 +0300220{
Olli Etuaho195be942017-12-04 23:40:14 +0200221 ASSERT(variable->symbolType() == SymbolType::UserDefined);
222 return insertVariable(currentLevel(), variable);
Olli Etuaho0f684632017-07-13 12:42:15 +0300223}
224
Olli Etuaho035419f2017-11-28 14:27:15 +0200225bool TSymbolTable::declareStructType(TStructure *str)
Olli Etuaho0f684632017-07-13 12:42:15 +0300226{
227 return insertStructType(currentLevel(), str);
228}
229
Olli Etuaho378c3a52017-12-04 11:32:13 +0200230bool TSymbolTable::declareInterfaceBlock(TInterfaceBlock *interfaceBlock)
Olli Etuaho0f684632017-07-13 12:42:15 +0300231{
Olli Etuaho378c3a52017-12-04 11:32:13 +0200232 return insert(currentLevel(), interfaceBlock);
Jiawei Shaod8105a02017-08-08 09:54:36 +0800233}
234
Olli Etuahob60d30f2018-01-16 12:31:06 +0200235TVariable *TSymbolTable::insertVariable(ESymbolLevel level, const char *name, const TType *type)
Olli Etuaho0f684632017-07-13 12:42:15 +0300236{
Olli Etuaho9d4d7f02017-12-07 17:11:41 +0100237 ASSERT(level <= LAST_BUILTIN_LEVEL);
Olli Etuahob60d30f2018-01-16 12:31:06 +0200238 ASSERT(type->isRealized());
Olli Etuaho9d4d7f02017-12-07 17:11:41 +0100239 return insertVariable(level, NewPoolTString(name), type, SymbolType::BuiltIn);
Olli Etuaho0f684632017-07-13 12:42:15 +0300240}
241
Olli Etuaho9d4d7f02017-12-07 17:11:41 +0100242TVariable *TSymbolTable::insertVariable(ESymbolLevel level,
243 const TString *name,
Olli Etuahob60d30f2018-01-16 12:31:06 +0200244 const TType *type,
Olli Etuaho9d4d7f02017-12-07 17:11:41 +0100245 SymbolType symbolType)
Olli Etuaho0f684632017-07-13 12:42:15 +0300246{
Olli Etuahob60d30f2018-01-16 12:31:06 +0200247 ASSERT(level > LAST_BUILTIN_LEVEL || type->isRealized());
Olli Etuaho9d4d7f02017-12-07 17:11:41 +0100248 TVariable *var = new TVariable(this, name, type, symbolType);
Olli Etuaho0f684632017-07-13 12:42:15 +0300249 if (insert(level, var))
250 {
Olli Etuaho0f684632017-07-13 12:42:15 +0300251 return var;
252 }
253 return nullptr;
254}
255
256TVariable *TSymbolTable::insertVariableExt(ESymbolLevel level,
Olli Etuaho2a1e8f92017-07-14 11:49:36 +0300257 TExtension ext,
Olli Etuaho0f684632017-07-13 12:42:15 +0300258 const char *name,
Olli Etuahob60d30f2018-01-16 12:31:06 +0200259 const TType *type)
Olli Etuaho0f684632017-07-13 12:42:15 +0300260{
Olli Etuahob60d30f2018-01-16 12:31:06 +0200261 ASSERT(level <= LAST_BUILTIN_LEVEL);
262 ASSERT(type->isRealized());
Olli Etuaho9d4d7f02017-12-07 17:11:41 +0100263 TVariable *var = new TVariable(this, NewPoolTString(name), type, SymbolType::BuiltIn, ext);
Olli Etuaho5d69db12017-11-24 16:51:15 +0200264 if (insert(level, var))
Olli Etuaho0f684632017-07-13 12:42:15 +0300265 {
Olli Etuaho0f684632017-07-13 12:42:15 +0300266 return var;
267 }
268 return nullptr;
269}
270
Olli Etuaho195be942017-12-04 23:40:14 +0200271bool TSymbolTable::insertVariable(ESymbolLevel level, TVariable *variable)
272{
273 ASSERT(variable);
Olli Etuahob60d30f2018-01-16 12:31:06 +0200274 ASSERT(level > LAST_BUILTIN_LEVEL || variable->getType().isRealized());
Olli Etuaho195be942017-12-04 23:40:14 +0200275 return insert(level, variable);
276}
277
Olli Etuaho035419f2017-11-28 14:27:15 +0200278bool TSymbolTable::insertStructType(ESymbolLevel level, TStructure *str)
Olli Etuaho0f684632017-07-13 12:42:15 +0300279{
Olli Etuaho035419f2017-11-28 14:27:15 +0200280 ASSERT(str);
Olli Etuaho378c3a52017-12-04 11:32:13 +0200281 return insert(level, str);
282}
283
284bool TSymbolTable::insertInterfaceBlock(ESymbolLevel level, TInterfaceBlock *interfaceBlock)
285{
286 ASSERT(interfaceBlock);
287 return insert(level, interfaceBlock);
Olli Etuaho0f684632017-07-13 12:42:15 +0300288}
289
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500290void TSymbolTable::insertBuiltIn(ESymbolLevel level,
291 TOperator op,
Olli Etuaho2a1e8f92017-07-14 11:49:36 +0300292 TExtension ext,
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500293 const TType *rvalue,
294 const char *name,
295 const TType *ptype1,
296 const TType *ptype2,
297 const TType *ptype3,
298 const TType *ptype4,
299 const TType *ptype5)
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700300{
301 if (ptype1->getBasicType() == EbtGSampler2D)
302 {
Martin Radevda6254b2016-12-14 17:00:36 +0200303 insertUnmangledBuiltInName(name, level);
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700304 bool gvec4 = (rvalue->getBasicType() == EbtGVec4);
Kai Ninomiya614dd0f2017-11-22 14:04:48 -0800305 insertBuiltIn(level, gvec4 ? StaticType::GetBasic<EbtFloat, 4>() : rvalue, name,
306 StaticType::GetBasic<EbtSampler2D>(), ptype2, ptype3, ptype4, ptype5);
307 insertBuiltIn(level, gvec4 ? StaticType::GetBasic<EbtInt, 4>() : rvalue, name,
308 StaticType::GetBasic<EbtISampler2D>(), ptype2, ptype3, ptype4, ptype5);
309 insertBuiltIn(level, gvec4 ? StaticType::GetBasic<EbtUInt, 4>() : rvalue, name,
310 StaticType::GetBasic<EbtUSampler2D>(), ptype2, ptype3, ptype4, ptype5);
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700311 }
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500312 else if (ptype1->getBasicType() == EbtGSampler3D)
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700313 {
Martin Radevda6254b2016-12-14 17:00:36 +0200314 insertUnmangledBuiltInName(name, level);
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700315 bool gvec4 = (rvalue->getBasicType() == EbtGVec4);
Kai Ninomiya614dd0f2017-11-22 14:04:48 -0800316 insertBuiltIn(level, gvec4 ? StaticType::GetBasic<EbtFloat, 4>() : rvalue, name,
317 StaticType::GetBasic<EbtSampler3D>(), ptype2, ptype3, ptype4, ptype5);
318 insertBuiltIn(level, gvec4 ? StaticType::GetBasic<EbtInt, 4>() : rvalue, name,
319 StaticType::GetBasic<EbtISampler3D>(), ptype2, ptype3, ptype4, ptype5);
320 insertBuiltIn(level, gvec4 ? StaticType::GetBasic<EbtUInt, 4>() : rvalue, name,
321 StaticType::GetBasic<EbtUSampler3D>(), ptype2, ptype3, ptype4, ptype5);
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700322 }
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500323 else if (ptype1->getBasicType() == EbtGSamplerCube)
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700324 {
Martin Radevda6254b2016-12-14 17:00:36 +0200325 insertUnmangledBuiltInName(name, level);
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700326 bool gvec4 = (rvalue->getBasicType() == EbtGVec4);
Kai Ninomiya614dd0f2017-11-22 14:04:48 -0800327 insertBuiltIn(level, gvec4 ? StaticType::GetBasic<EbtFloat, 4>() : rvalue, name,
328 StaticType::GetBasic<EbtSamplerCube>(), ptype2, ptype3, ptype4, ptype5);
329 insertBuiltIn(level, gvec4 ? StaticType::GetBasic<EbtInt, 4>() : rvalue, name,
330 StaticType::GetBasic<EbtISamplerCube>(), ptype2, ptype3, ptype4, ptype5);
331 insertBuiltIn(level, gvec4 ? StaticType::GetBasic<EbtUInt, 4>() : rvalue, name,
332 StaticType::GetBasic<EbtUSamplerCube>(), ptype2, ptype3, ptype4, ptype5);
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700333 }
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500334 else if (ptype1->getBasicType() == EbtGSampler2DArray)
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700335 {
Martin Radevda6254b2016-12-14 17:00:36 +0200336 insertUnmangledBuiltInName(name, level);
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700337 bool gvec4 = (rvalue->getBasicType() == EbtGVec4);
Kai Ninomiya614dd0f2017-11-22 14:04:48 -0800338 insertBuiltIn(level, gvec4 ? StaticType::GetBasic<EbtFloat, 4>() : rvalue, name,
339 StaticType::GetBasic<EbtSampler2DArray>(), ptype2, ptype3, ptype4,
340 ptype5);
341 insertBuiltIn(level, gvec4 ? StaticType::GetBasic<EbtInt, 4>() : rvalue, name,
342 StaticType::GetBasic<EbtISampler2DArray>(), ptype2, ptype3, ptype4,
343 ptype5);
344 insertBuiltIn(level, gvec4 ? StaticType::GetBasic<EbtUInt, 4>() : rvalue, name,
345 StaticType::GetBasic<EbtUSampler2DArray>(), ptype2, ptype3, ptype4,
346 ptype5);
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700347 }
JiangYizhou40219322016-12-09 09:50:51 +0800348 else if (ptype1->getBasicType() == EbtGSampler2DMS)
349 {
350 insertUnmangledBuiltInName(name, level);
351 bool gvec4 = (rvalue->getBasicType() == EbtGVec4);
Kai Ninomiya614dd0f2017-11-22 14:04:48 -0800352 insertBuiltIn(level, gvec4 ? StaticType::GetBasic<EbtFloat, 4>() : rvalue, name,
353 StaticType::GetBasic<EbtSampler2DMS>(), ptype2, ptype3, ptype4, ptype5);
354 insertBuiltIn(level, gvec4 ? StaticType::GetBasic<EbtInt, 4>() : rvalue, name,
355 StaticType::GetBasic<EbtISampler2DMS>(), ptype2, ptype3, ptype4, ptype5);
356 insertBuiltIn(level, gvec4 ? StaticType::GetBasic<EbtUInt, 4>() : rvalue, name,
357 StaticType::GetBasic<EbtUSampler2DMS>(), ptype2, ptype3, ptype4, ptype5);
JiangYizhou40219322016-12-09 09:50:51 +0800358 }
Martin Radev2cc85b32016-08-05 16:22:53 +0300359 else if (IsGImage(ptype1->getBasicType()))
360 {
Martin Radevda6254b2016-12-14 17:00:36 +0200361 insertUnmangledBuiltInName(name, level);
Martin Radev2cc85b32016-08-05 16:22:53 +0300362
Kai Ninomiya614dd0f2017-11-22 14:04:48 -0800363 const TType *floatType = StaticType::GetBasic<EbtFloat, 4>();
364 const TType *intType = StaticType::GetBasic<EbtInt, 4>();
365 const TType *unsignedType = StaticType::GetBasic<EbtUInt, 4>();
Martin Radev2cc85b32016-08-05 16:22:53 +0300366
Kai Ninomiya614dd0f2017-11-22 14:04:48 -0800367 const TType *floatImage = StaticType::GetForFloatImage(ptype1->getBasicType());
368 const TType *intImage = StaticType::GetForIntImage(ptype1->getBasicType());
369 const TType *unsignedImage = StaticType::GetForUintImage(ptype1->getBasicType());
Martin Radev2cc85b32016-08-05 16:22:53 +0300370
371 // GLSL ES 3.10, Revision 4, 8.12 Image Functions
372 if (rvalue->getBasicType() == EbtGVec4)
373 {
374 // imageLoad
375 insertBuiltIn(level, floatType, name, floatImage, ptype2, ptype3, ptype4, ptype5);
376 insertBuiltIn(level, intType, name, intImage, ptype2, ptype3, ptype4, ptype5);
377 insertBuiltIn(level, unsignedType, name, unsignedImage, ptype2, ptype3, ptype4, ptype5);
378 }
379 else if (rvalue->getBasicType() == EbtVoid)
380 {
381 // imageStore
382 insertBuiltIn(level, rvalue, name, floatImage, ptype2, floatType, ptype4, ptype5);
383 insertBuiltIn(level, rvalue, name, intImage, ptype2, intType, ptype4, ptype5);
384 insertBuiltIn(level, rvalue, name, unsignedImage, ptype2, unsignedType, ptype4, ptype5);
385 }
386 else
387 {
388 // imageSize
389 insertBuiltIn(level, rvalue, name, floatImage, ptype2, ptype3, ptype4, ptype5);
390 insertBuiltIn(level, rvalue, name, intImage, ptype2, ptype3, ptype4, ptype5);
391 insertBuiltIn(level, rvalue, name, unsignedImage, ptype2, ptype3, ptype4, ptype5);
392 }
393 }
Olli Etuaho9250cb22017-01-21 10:51:27 +0000394 else if (IsGenType(rvalue) || IsGenType(ptype1) || IsGenType(ptype2) || IsGenType(ptype3) ||
395 IsGenType(ptype4))
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500396 {
Olli Etuaho9250cb22017-01-21 10:51:27 +0000397 ASSERT(!ptype5);
Martin Radevda6254b2016-12-14 17:00:36 +0200398 insertUnmangledBuiltInName(name, level);
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500399 insertBuiltIn(level, op, ext, SpecificType(rvalue, 1), name, SpecificType(ptype1, 1),
Olli Etuaho9250cb22017-01-21 10:51:27 +0000400 SpecificType(ptype2, 1), SpecificType(ptype3, 1), SpecificType(ptype4, 1));
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500401 insertBuiltIn(level, op, ext, SpecificType(rvalue, 2), name, SpecificType(ptype1, 2),
Olli Etuaho9250cb22017-01-21 10:51:27 +0000402 SpecificType(ptype2, 2), SpecificType(ptype3, 2), SpecificType(ptype4, 2));
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500403 insertBuiltIn(level, op, ext, SpecificType(rvalue, 3), name, SpecificType(ptype1, 3),
Olli Etuaho9250cb22017-01-21 10:51:27 +0000404 SpecificType(ptype2, 3), SpecificType(ptype3, 3), SpecificType(ptype4, 3));
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500405 insertBuiltIn(level, op, ext, SpecificType(rvalue, 4), name, SpecificType(ptype1, 4),
Olli Etuaho9250cb22017-01-21 10:51:27 +0000406 SpecificType(ptype2, 4), SpecificType(ptype3, 4), SpecificType(ptype4, 4));
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500407 }
408 else if (IsVecType(rvalue) || IsVecType(ptype1) || IsVecType(ptype2) || IsVecType(ptype3))
409 {
410 ASSERT(!ptype4 && !ptype5);
Martin Radevda6254b2016-12-14 17:00:36 +0200411 insertUnmangledBuiltInName(name, level);
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500412 insertBuiltIn(level, op, ext, VectorType(rvalue, 2), name, VectorType(ptype1, 2),
413 VectorType(ptype2, 2), VectorType(ptype3, 2));
414 insertBuiltIn(level, op, ext, VectorType(rvalue, 3), name, VectorType(ptype1, 3),
415 VectorType(ptype2, 3), VectorType(ptype3, 3));
416 insertBuiltIn(level, op, ext, VectorType(rvalue, 4), name, VectorType(ptype1, 4),
417 VectorType(ptype2, 4), VectorType(ptype3, 4));
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500418 }
419 else
420 {
Olli Etuaho9d4d7f02017-12-07 17:11:41 +0100421 TFunction *function =
Olli Etuaho0c371002017-12-13 17:00:25 +0400422 new TFunction(this, NewPoolTString(name), rvalue, SymbolType::BuiltIn, false, op, ext);
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700423
Dmitry Skibaefa3d8e2015-06-22 14:52:10 -0700424 function->addParameter(TConstParameter(ptype1));
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700425
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500426 if (ptype2)
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700427 {
Dmitry Skibaefa3d8e2015-06-22 14:52:10 -0700428 function->addParameter(TConstParameter(ptype2));
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700429 }
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700430
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500431 if (ptype3)
432 {
Dmitry Skibaefa3d8e2015-06-22 14:52:10 -0700433 function->addParameter(TConstParameter(ptype3));
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500434 }
435
436 if (ptype4)
437 {
Dmitry Skibaefa3d8e2015-06-22 14:52:10 -0700438 function->addParameter(TConstParameter(ptype4));
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500439 }
440
441 if (ptype5)
442 {
Dmitry Skibaefa3d8e2015-06-22 14:52:10 -0700443 function->addParameter(TConstParameter(ptype5));
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500444 }
445
Martin Radevda6254b2016-12-14 17:00:36 +0200446 ASSERT(hasUnmangledBuiltInAtLevel(name, level));
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500447 insert(level, function);
448 }
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700449}
450
Olli Etuaho492cfab2017-01-20 21:18:29 +0000451void TSymbolTable::insertBuiltInOp(ESymbolLevel level,
452 TOperator op,
453 const TType *rvalue,
454 const TType *ptype1,
455 const TType *ptype2,
456 const TType *ptype3,
457 const TType *ptype4,
458 const TType *ptype5)
459{
460 const char *name = GetOperatorString(op);
461 ASSERT(strlen(name) > 0);
462 insertUnmangledBuiltInName(name, level);
Olli Etuaho2a1e8f92017-07-14 11:49:36 +0300463 insertBuiltIn(level, op, TExtension::UNDEFINED, rvalue, name, ptype1, ptype2, ptype3, ptype4,
464 ptype5);
Olli Etuaho492cfab2017-01-20 21:18:29 +0000465}
466
467void TSymbolTable::insertBuiltInOp(ESymbolLevel level,
468 TOperator op,
Olli Etuaho2a1e8f92017-07-14 11:49:36 +0300469 TExtension ext,
Olli Etuaho492cfab2017-01-20 21:18:29 +0000470 const TType *rvalue,
471 const TType *ptype1,
472 const TType *ptype2,
473 const TType *ptype3,
474 const TType *ptype4,
475 const TType *ptype5)
476{
477 const char *name = GetOperatorString(op);
478 insertUnmangledBuiltInName(name, level);
479 insertBuiltIn(level, op, ext, rvalue, name, ptype1, ptype2, ptype3, ptype4, ptype5);
480}
481
Martin Radevd7c5b0a2016-07-27 14:04:43 +0300482void TSymbolTable::insertBuiltInFunctionNoParameters(ESymbolLevel level,
483 TOperator op,
484 const TType *rvalue,
485 const char *name)
486{
487 insertUnmangledBuiltInName(name, level);
Olli Etuaho0c371002017-12-13 17:00:25 +0400488 insert(level,
489 new TFunction(this, NewPoolTString(name), rvalue, SymbolType::BuiltIn, false, op));
Martin Radevd7c5b0a2016-07-27 14:04:43 +0300490}
491
Jiawei Shaod27f5c82017-08-23 09:38:08 +0800492void TSymbolTable::insertBuiltInFunctionNoParametersExt(ESymbolLevel level,
Olli Etuaho2a1e8f92017-07-14 11:49:36 +0300493 TExtension ext,
Jiawei Shaod27f5c82017-08-23 09:38:08 +0800494 TOperator op,
495 const TType *rvalue,
496 const char *name)
497{
498 insertUnmangledBuiltInName(name, level);
Olli Etuaho0c371002017-12-13 17:00:25 +0400499 insert(level,
500 new TFunction(this, NewPoolTString(name), rvalue, SymbolType::BuiltIn, false, op, ext));
Jiawei Shaod27f5c82017-08-23 09:38:08 +0800501}
502
Zhenyao Moe740add2014-07-18 17:01:01 -0700503TPrecision TSymbolTable::getDefaultPrecision(TBasicType type) const
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700504{
505 if (!SupportsPrecision(type))
506 return EbpUndefined;
507
508 // unsigned integers use the same precision as signed
509 TBasicType baseType = (type == EbtUInt) ? EbtInt : type;
510
511 int level = static_cast<int>(precisionStack.size()) - 1;
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500512 assert(level >= 0); // Just to be safe. Should not happen.
Olli Etuaho183d7e22015-11-20 15:59:09 +0200513 // If we dont find anything we return this. Some types don't have predefined default precision.
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700514 TPrecision prec = EbpUndefined;
515 while (level >= 0)
516 {
517 PrecisionStackLevel::iterator it = precisionStack[level]->find(baseType);
518 if (it != precisionStack[level]->end())
519 {
520 prec = (*it).second;
521 break;
522 }
523 level--;
524 }
525 return prec;
526}
Jamie Madill45bcc782016-11-07 13:58:48 -0500527
Martin Radevda6254b2016-12-14 17:00:36 +0200528void TSymbolTable::insertUnmangledBuiltInName(const char *name, ESymbolLevel level)
529{
530 ASSERT(level >= 0 && level < static_cast<ESymbolLevel>(table.size()));
Olli Etuaho5d69db12017-11-24 16:51:15 +0200531 ASSERT(mUserDefinedUniqueIdsStart == -1);
Olli Etuaho342b83d2018-01-10 13:24:01 +0200532 table[level]->insertUnmangledBuiltInName(name);
Martin Radevda6254b2016-12-14 17:00:36 +0200533}
534
535bool TSymbolTable::hasUnmangledBuiltInAtLevel(const char *name, ESymbolLevel level)
536{
537 ASSERT(level >= 0 && level < static_cast<ESymbolLevel>(table.size()));
Olli Etuaho342b83d2018-01-10 13:24:01 +0200538 return table[level]->hasUnmangledBuiltIn(name);
Martin Radevda6254b2016-12-14 17:00:36 +0200539}
540
541bool TSymbolTable::hasUnmangledBuiltInForShaderVersion(const char *name, int shaderVersion)
542{
543 ASSERT(static_cast<ESymbolLevel>(table.size()) > LAST_BUILTIN_LEVEL);
544
545 for (int level = LAST_BUILTIN_LEVEL; level >= 0; --level)
546 {
547 if (level == ESSL3_1_BUILTINS && shaderVersion != 310)
548 {
549 --level;
550 }
551 if (level == ESSL3_BUILTINS && shaderVersion < 300)
552 {
553 --level;
554 }
555 if (level == ESSL1_BUILTINS && shaderVersion != 100)
556 {
557 --level;
558 }
559
560 if (table[level]->hasUnmangledBuiltIn(name))
561 {
562 return true;
563 }
564 }
565 return false;
566}
567
Olli Etuaho5d69db12017-11-24 16:51:15 +0200568void TSymbolTable::markBuiltInInitializationFinished()
569{
570 mUserDefinedUniqueIdsStart = mUniqueIdCounter;
571}
572
573void TSymbolTable::clearCompilationResults()
574{
575 mUniqueIdCounter = mUserDefinedUniqueIdsStart;
576
577 // User-defined scopes should have already been cleared when the compilation finished.
578 ASSERT(table.size() == LAST_BUILTIN_LEVEL + 1u);
579}
580
581int TSymbolTable::nextUniqueIdValue()
582{
583 ASSERT(mUniqueIdCounter < std::numeric_limits<int>::max());
584 return ++mUniqueIdCounter;
585}
586
Jamie Madill45bcc782016-11-07 13:58:48 -0500587} // namespace sh