blob: a7f7e8f54151e40b18cb395bbf09fdc085807463 [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//
6
7//
8// Symbol table for parsing. Most functionaliy and main ideas
9// are documented in the header file.
10//
11
apatrick@chromium.orge057c5d2012-01-26 19:18:24 +000012#if defined(_MSC_VER)
Jamie Madilld7b1ab52016-12-12 14:42:19 -050013#pragma warning(disable : 4718)
apatrick@chromium.orge057c5d2012-01-26 19:18:24 +000014#endif
15
Geoff Lang17732822013-08-29 13:46:49 -040016#include "compiler/translator/SymbolTable.h"
Olli Etuaho01d0ad02017-01-22 14:51:23 -080017
Dmitry Skiba01971112015-07-10 14:54:00 -040018#include "compiler/translator/Cache.h"
Olli Etuaho01d0ad02017-01-22 14:51:23 -080019#include "compiler/translator/IntermNode.h"
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +000020
apatrick@chromium.org8187fa82010-06-15 22:09:28 +000021#include <stdio.h>
kbr@chromium.org476541f2011-10-27 21:14:51 +000022#include <algorithm>
23
Jamie Madill45bcc782016-11-07 13:58:48 -050024namespace sh
25{
26
Olli Etuahof2209f72017-04-01 12:45:55 +030027namespace
28{
29
30static const char kFunctionMangledNameSeparator = '(';
31
32} // anonymous namespace
33
Jamie Madillbfa91f42014-06-05 15:45:18 -040034int TSymbolTable::uniqueIdCounter = 0;
Nicolas Capensbd10cf52013-06-20 09:51:51 -040035
Olli Etuahofe486322017-03-21 09:30:54 +000036TSymbolUniqueId::TSymbolUniqueId() : mId(TSymbolTable::nextUniqueId())
37{
38}
39
40TSymbolUniqueId::TSymbolUniqueId(const TSymbol &symbol) : mId(symbol.getUniqueId())
41{
42}
43
44int TSymbolUniqueId::get() const
45{
46 return mId;
47}
48
Olli Etuaho476197f2016-10-11 13:59:08 +010049TSymbol::TSymbol(const TString *n) : uniqueId(TSymbolTable::nextUniqueId()), name(n)
50{
51}
52
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +000053//
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +000054// Functions have buried pointers to delete.
55//
56TFunction::~TFunction()
57{
Olli Etuaho476197f2016-10-11 13:59:08 +010058 clearParameters();
59}
60
61void TFunction::clearParameters()
62{
daniel@transgaming.com0578f812010-05-17 09:58:39 +000063 for (TParamList::iterator i = parameters.begin(); i != parameters.end(); ++i)
64 delete (*i).type;
Olli Etuaho476197f2016-10-11 13:59:08 +010065 parameters.clear();
66 mangledName = nullptr;
67}
68
69void TFunction::swapParameters(const TFunction &parametersSource)
70{
71 clearParameters();
72 for (auto parameter : parametersSource.parameters)
73 {
74 addParameter(parameter);
75 }
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +000076}
77
Dmitry Skiba58832202015-07-06 16:11:13 -070078const TString *TFunction::buildMangledName() const
79{
Olli Etuahof2209f72017-04-01 12:45:55 +030080 std::string newName = getName().c_str();
81 newName += kFunctionMangledNameSeparator;
Dmitry Skiba58832202015-07-06 16:11:13 -070082
83 for (const auto &p : parameters)
84 {
Cooper Partin149e6e62015-08-07 16:18:18 -070085 newName += p.type->getMangledName().c_str();
Dmitry Skiba58832202015-07-06 16:11:13 -070086 }
Cooper Partin149e6e62015-08-07 16:18:18 -070087 return NewPoolTString(newName.c_str());
Dmitry Skiba58832202015-07-06 16:11:13 -070088}
89
Olli Etuahof2209f72017-04-01 12:45:55 +030090const TString &TFunction::GetMangledNameFromCall(const TString &functionName,
91 const TIntermSequence &arguments)
Olli Etuahoaf6fc1b2017-01-26 17:45:35 -080092{
Olli Etuahof2209f72017-04-01 12:45:55 +030093 std::string newName = functionName.c_str();
94 newName += kFunctionMangledNameSeparator;
95
Olli Etuahoaf6fc1b2017-01-26 17:45:35 -080096 for (TIntermNode *argument : arguments)
97 {
98 newName += argument->getAsTyped()->getType().getMangledName().c_str();
99 }
100 return *NewPoolTString(newName.c_str());
101}
102
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000103//
104// Symbol table levels are a map of pointers to symbols that have to be deleted.
105//
106TSymbolTableLevel::~TSymbolTableLevel()
107{
daniel@transgaming.com0578f812010-05-17 09:58:39 +0000108 for (tLevel::iterator it = level.begin(); it != level.end(); ++it)
109 delete (*it).second;
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000110}
111
Nicolas Capensadfffe42014-06-17 02:13:36 -0400112bool TSymbolTableLevel::insert(TSymbol *symbol)
Jamie Madillbfa91f42014-06-05 15:45:18 -0400113{
Jamie Madillbfa91f42014-06-05 15:45:18 -0400114 // returning true means symbol was added to the table
Nicolas Capensadfffe42014-06-17 02:13:36 -0400115 tInsertResult result = level.insert(tLevelPair(symbol->getMangledName(), symbol));
Jamie Madillbfa91f42014-06-05 15:45:18 -0400116
117 return result.second;
118}
119
Olli Etuahob2983c92015-03-18 14:02:46 +0200120bool TSymbolTableLevel::insertUnmangled(TFunction *function)
121{
Olli Etuahob2983c92015-03-18 14:02:46 +0200122 // returning true means symbol was added to the table
123 tInsertResult result = level.insert(tLevelPair(function->getName(), function));
124
125 return result.second;
126}
127
Jamie Madillbfa91f42014-06-05 15:45:18 -0400128TSymbol *TSymbolTableLevel::find(const TString &name) const
129{
130 tLevel::const_iterator it = level.find(name);
131 if (it == level.end())
132 return 0;
133 else
134 return (*it).second;
135}
136
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500137TSymbol *TSymbolTable::find(const TString &name,
138 int shaderVersion,
139 bool *builtIn,
140 bool *sameScope) const
shannonwoods@chromium.org96e7ba12013-05-30 00:02:41 +0000141{
142 int level = currentLevel();
143 TSymbol *symbol;
144
145 do
146 {
Martin Radeve93d24e2016-07-28 12:06:05 +0300147 if (level == ESSL3_1_BUILTINS && shaderVersion != 310)
148 level--;
149 if (level == ESSL3_BUILTINS && shaderVersion < 300)
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700150 level--;
151 if (level == ESSL1_BUILTINS && shaderVersion != 100)
152 level--;
shannonwoods@chromium.org96e7ba12013-05-30 00:02:41 +0000153
154 symbol = table[level]->find(name);
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500155 } while (symbol == 0 && --level >= 0);
shannonwoods@chromium.org96e7ba12013-05-30 00:02:41 +0000156
157 if (builtIn)
158 *builtIn = (level <= LAST_BUILTIN_LEVEL);
159 if (sameScope)
160 *sameScope = (level == currentLevel());
161
162 return symbol;
163}
164
Zhenyao Mod7490962016-11-09 15:49:51 -0800165TSymbol *TSymbolTable::findGlobal(const TString &name) const
166{
167 ASSERT(table.size() > GLOBAL_LEVEL);
168 return table[GLOBAL_LEVEL]->find(name);
169}
170
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500171TSymbol *TSymbolTable::findBuiltIn(const TString &name, int shaderVersion) const
shannonwoods@chromium.org96e7ba12013-05-30 00:02:41 +0000172{
173 for (int level = LAST_BUILTIN_LEVEL; level >= 0; level--)
174 {
Martin Radeve93d24e2016-07-28 12:06:05 +0300175 if (level == ESSL3_1_BUILTINS && shaderVersion != 310)
176 level--;
177 if (level == ESSL3_BUILTINS && shaderVersion < 300)
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700178 level--;
179 if (level == ESSL1_BUILTINS && shaderVersion != 100)
180 level--;
shannonwoods@chromium.org96e7ba12013-05-30 00:02:41 +0000181
182 TSymbol *symbol = table[level]->find(name);
183
184 if (symbol)
185 return symbol;
186 }
187
188 return 0;
189}
Alok Priyadarshibc3f1ac2013-09-23 14:57:02 -0400190
191TSymbolTable::~TSymbolTable()
192{
193 while (table.size() > 0)
194 pop();
195}
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700196
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500197bool IsGenType(const TType *type)
198{
199 if (type)
200 {
201 TBasicType basicType = type->getBasicType();
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500202 return basicType == EbtGenType || basicType == EbtGenIType || basicType == EbtGenUType ||
203 basicType == EbtGenBType;
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500204 }
205
206 return false;
207}
208
209bool IsVecType(const TType *type)
210{
211 if (type)
212 {
213 TBasicType basicType = type->getBasicType();
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500214 return basicType == EbtVec || basicType == EbtIVec || basicType == EbtUVec ||
215 basicType == EbtBVec;
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500216 }
217
218 return false;
219}
220
Dmitry Skibaefa3d8e2015-06-22 14:52:10 -0700221const TType *SpecificType(const TType *type, int size)
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500222{
223 ASSERT(size >= 1 && size <= 4);
224
225 if (!type)
226 {
227 return nullptr;
228 }
229
230 ASSERT(!IsVecType(type));
231
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500232 switch (type->getBasicType())
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500233 {
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500234 case EbtGenType:
Olli Etuaho9250cb22017-01-21 10:51:27 +0000235 return TCache::getType(EbtFloat, type->getQualifier(),
236 static_cast<unsigned char>(size));
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500237 case EbtGenIType:
Olli Etuaho9250cb22017-01-21 10:51:27 +0000238 return TCache::getType(EbtInt, type->getQualifier(), static_cast<unsigned char>(size));
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500239 case EbtGenUType:
Olli Etuaho9250cb22017-01-21 10:51:27 +0000240 return TCache::getType(EbtUInt, type->getQualifier(), static_cast<unsigned char>(size));
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500241 case EbtGenBType:
Olli Etuaho9250cb22017-01-21 10:51:27 +0000242 return TCache::getType(EbtBool, type->getQualifier(), static_cast<unsigned char>(size));
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500243 default:
244 return type;
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500245 }
246}
247
Dmitry Skibaefa3d8e2015-06-22 14:52:10 -0700248const TType *VectorType(const TType *type, int size)
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500249{
250 ASSERT(size >= 2 && size <= 4);
251
252 if (!type)
253 {
254 return nullptr;
255 }
256
257 ASSERT(!IsGenType(type));
258
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500259 switch (type->getBasicType())
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500260 {
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500261 case EbtVec:
262 return TCache::getType(EbtFloat, static_cast<unsigned char>(size));
263 case EbtIVec:
264 return TCache::getType(EbtInt, static_cast<unsigned char>(size));
265 case EbtUVec:
266 return TCache::getType(EbtUInt, static_cast<unsigned char>(size));
267 case EbtBVec:
268 return TCache::getType(EbtBool, static_cast<unsigned char>(size));
269 default:
270 return type;
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500271 }
272}
273
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500274void TSymbolTable::insertBuiltIn(ESymbolLevel level,
275 TOperator op,
276 const char *ext,
277 const TType *rvalue,
278 const char *name,
279 const TType *ptype1,
280 const TType *ptype2,
281 const TType *ptype3,
282 const TType *ptype4,
283 const TType *ptype5)
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700284{
285 if (ptype1->getBasicType() == EbtGSampler2D)
286 {
Martin Radevda6254b2016-12-14 17:00:36 +0200287 insertUnmangledBuiltInName(name, level);
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700288 bool gvec4 = (rvalue->getBasicType() == EbtGVec4);
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500289 insertBuiltIn(level, gvec4 ? TCache::getType(EbtFloat, 4) : rvalue, name,
290 TCache::getType(EbtSampler2D), ptype2, ptype3, ptype4, ptype5);
291 insertBuiltIn(level, gvec4 ? TCache::getType(EbtInt, 4) : rvalue, name,
292 TCache::getType(EbtISampler2D), ptype2, ptype3, ptype4, ptype5);
293 insertBuiltIn(level, gvec4 ? TCache::getType(EbtUInt, 4) : rvalue, name,
294 TCache::getType(EbtUSampler2D), ptype2, ptype3, ptype4, ptype5);
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700295 }
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500296 else if (ptype1->getBasicType() == EbtGSampler3D)
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700297 {
Martin Radevda6254b2016-12-14 17:00:36 +0200298 insertUnmangledBuiltInName(name, level);
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700299 bool gvec4 = (rvalue->getBasicType() == EbtGVec4);
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500300 insertBuiltIn(level, gvec4 ? TCache::getType(EbtFloat, 4) : rvalue, name,
301 TCache::getType(EbtSampler3D), ptype2, ptype3, ptype4, ptype5);
302 insertBuiltIn(level, gvec4 ? TCache::getType(EbtInt, 4) : rvalue, name,
303 TCache::getType(EbtISampler3D), ptype2, ptype3, ptype4, ptype5);
304 insertBuiltIn(level, gvec4 ? TCache::getType(EbtUInt, 4) : rvalue, name,
305 TCache::getType(EbtUSampler3D), ptype2, ptype3, ptype4, ptype5);
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700306 }
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500307 else if (ptype1->getBasicType() == EbtGSamplerCube)
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700308 {
Martin Radevda6254b2016-12-14 17:00:36 +0200309 insertUnmangledBuiltInName(name, level);
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700310 bool gvec4 = (rvalue->getBasicType() == EbtGVec4);
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500311 insertBuiltIn(level, gvec4 ? TCache::getType(EbtFloat, 4) : rvalue, name,
312 TCache::getType(EbtSamplerCube), ptype2, ptype3, ptype4, ptype5);
313 insertBuiltIn(level, gvec4 ? TCache::getType(EbtInt, 4) : rvalue, name,
314 TCache::getType(EbtISamplerCube), ptype2, ptype3, ptype4, ptype5);
315 insertBuiltIn(level, gvec4 ? TCache::getType(EbtUInt, 4) : rvalue, name,
316 TCache::getType(EbtUSamplerCube), ptype2, ptype3, ptype4, ptype5);
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700317 }
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500318 else if (ptype1->getBasicType() == EbtGSampler2DArray)
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700319 {
Martin Radevda6254b2016-12-14 17:00:36 +0200320 insertUnmangledBuiltInName(name, level);
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700321 bool gvec4 = (rvalue->getBasicType() == EbtGVec4);
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500322 insertBuiltIn(level, gvec4 ? TCache::getType(EbtFloat, 4) : rvalue, name,
323 TCache::getType(EbtSampler2DArray), ptype2, ptype3, ptype4, ptype5);
324 insertBuiltIn(level, gvec4 ? TCache::getType(EbtInt, 4) : rvalue, name,
325 TCache::getType(EbtISampler2DArray), ptype2, ptype3, ptype4, ptype5);
326 insertBuiltIn(level, gvec4 ? TCache::getType(EbtUInt, 4) : rvalue, name,
327 TCache::getType(EbtUSampler2DArray), ptype2, ptype3, ptype4, ptype5);
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700328 }
JiangYizhou40219322016-12-09 09:50:51 +0800329 else if (ptype1->getBasicType() == EbtGSampler2DMS)
330 {
331 insertUnmangledBuiltInName(name, level);
332 bool gvec4 = (rvalue->getBasicType() == EbtGVec4);
333 insertBuiltIn(level, gvec4 ? TCache::getType(EbtFloat, 4) : rvalue, name,
334 TCache::getType(EbtSampler2DMS), ptype2, ptype3, ptype4, ptype5);
335 insertBuiltIn(level, gvec4 ? TCache::getType(EbtInt, 4) : rvalue, name,
336 TCache::getType(EbtISampler2DMS), ptype2, ptype3, ptype4, ptype5);
337 insertBuiltIn(level, gvec4 ? TCache::getType(EbtUInt, 4) : rvalue, name,
338 TCache::getType(EbtUSampler2DMS), ptype2, ptype3, ptype4, ptype5);
339 }
Martin Radev2cc85b32016-08-05 16:22:53 +0300340 else if (IsGImage(ptype1->getBasicType()))
341 {
Martin Radevda6254b2016-12-14 17:00:36 +0200342 insertUnmangledBuiltInName(name, level);
Martin Radev2cc85b32016-08-05 16:22:53 +0300343
344 const TType *floatType = TCache::getType(EbtFloat, 4);
345 const TType *intType = TCache::getType(EbtInt, 4);
346 const TType *unsignedType = TCache::getType(EbtUInt, 4);
347
348 const TType *floatImage =
349 TCache::getType(convertGImageToFloatImage(ptype1->getBasicType()));
350 const TType *intImage = TCache::getType(convertGImageToIntImage(ptype1->getBasicType()));
351 const TType *unsignedImage =
352 TCache::getType(convertGImageToUnsignedImage(ptype1->getBasicType()));
353
354 // GLSL ES 3.10, Revision 4, 8.12 Image Functions
355 if (rvalue->getBasicType() == EbtGVec4)
356 {
357 // imageLoad
358 insertBuiltIn(level, floatType, name, floatImage, ptype2, ptype3, ptype4, ptype5);
359 insertBuiltIn(level, intType, name, intImage, ptype2, ptype3, ptype4, ptype5);
360 insertBuiltIn(level, unsignedType, name, unsignedImage, ptype2, ptype3, ptype4, ptype5);
361 }
362 else if (rvalue->getBasicType() == EbtVoid)
363 {
364 // imageStore
365 insertBuiltIn(level, rvalue, name, floatImage, ptype2, floatType, ptype4, ptype5);
366 insertBuiltIn(level, rvalue, name, intImage, ptype2, intType, ptype4, ptype5);
367 insertBuiltIn(level, rvalue, name, unsignedImage, ptype2, unsignedType, ptype4, ptype5);
368 }
369 else
370 {
371 // imageSize
372 insertBuiltIn(level, rvalue, name, floatImage, ptype2, ptype3, ptype4, ptype5);
373 insertBuiltIn(level, rvalue, name, intImage, ptype2, ptype3, ptype4, ptype5);
374 insertBuiltIn(level, rvalue, name, unsignedImage, ptype2, ptype3, ptype4, ptype5);
375 }
376 }
Olli Etuaho9250cb22017-01-21 10:51:27 +0000377 else if (IsGenType(rvalue) || IsGenType(ptype1) || IsGenType(ptype2) || IsGenType(ptype3) ||
378 IsGenType(ptype4))
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500379 {
Olli Etuaho9250cb22017-01-21 10:51:27 +0000380 ASSERT(!ptype5);
Martin Radevda6254b2016-12-14 17:00:36 +0200381 insertUnmangledBuiltInName(name, level);
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500382 insertBuiltIn(level, op, ext, SpecificType(rvalue, 1), name, SpecificType(ptype1, 1),
Olli Etuaho9250cb22017-01-21 10:51:27 +0000383 SpecificType(ptype2, 1), SpecificType(ptype3, 1), SpecificType(ptype4, 1));
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500384 insertBuiltIn(level, op, ext, SpecificType(rvalue, 2), name, SpecificType(ptype1, 2),
Olli Etuaho9250cb22017-01-21 10:51:27 +0000385 SpecificType(ptype2, 2), SpecificType(ptype3, 2), SpecificType(ptype4, 2));
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500386 insertBuiltIn(level, op, ext, SpecificType(rvalue, 3), name, SpecificType(ptype1, 3),
Olli Etuaho9250cb22017-01-21 10:51:27 +0000387 SpecificType(ptype2, 3), SpecificType(ptype3, 3), SpecificType(ptype4, 3));
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500388 insertBuiltIn(level, op, ext, SpecificType(rvalue, 4), name, SpecificType(ptype1, 4),
Olli Etuaho9250cb22017-01-21 10:51:27 +0000389 SpecificType(ptype2, 4), SpecificType(ptype3, 4), SpecificType(ptype4, 4));
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500390 }
391 else if (IsVecType(rvalue) || IsVecType(ptype1) || IsVecType(ptype2) || IsVecType(ptype3))
392 {
393 ASSERT(!ptype4 && !ptype5);
Martin Radevda6254b2016-12-14 17:00:36 +0200394 insertUnmangledBuiltInName(name, level);
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500395 insertBuiltIn(level, op, ext, VectorType(rvalue, 2), name, VectorType(ptype1, 2),
396 VectorType(ptype2, 2), VectorType(ptype3, 2));
397 insertBuiltIn(level, op, ext, VectorType(rvalue, 3), name, VectorType(ptype1, 3),
398 VectorType(ptype2, 3), VectorType(ptype3, 3));
399 insertBuiltIn(level, op, ext, VectorType(rvalue, 4), name, VectorType(ptype1, 4),
400 VectorType(ptype2, 4), VectorType(ptype3, 4));
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500401 }
402 else
403 {
Dmitry Skiba7f17a502015-06-22 15:08:39 -0700404 TFunction *function = new TFunction(NewPoolTString(name), rvalue, op, ext);
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700405
Dmitry Skibaefa3d8e2015-06-22 14:52:10 -0700406 function->addParameter(TConstParameter(ptype1));
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700407
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500408 if (ptype2)
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700409 {
Dmitry Skibaefa3d8e2015-06-22 14:52:10 -0700410 function->addParameter(TConstParameter(ptype2));
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700411 }
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700412
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500413 if (ptype3)
414 {
Dmitry Skibaefa3d8e2015-06-22 14:52:10 -0700415 function->addParameter(TConstParameter(ptype3));
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500416 }
417
418 if (ptype4)
419 {
Dmitry Skibaefa3d8e2015-06-22 14:52:10 -0700420 function->addParameter(TConstParameter(ptype4));
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500421 }
422
423 if (ptype5)
424 {
Dmitry Skibaefa3d8e2015-06-22 14:52:10 -0700425 function->addParameter(TConstParameter(ptype5));
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500426 }
427
Martin Radevda6254b2016-12-14 17:00:36 +0200428 ASSERT(hasUnmangledBuiltInAtLevel(name, level));
Nicolas Capensf3cc4ae2015-02-23 13:51:25 -0500429 insert(level, function);
430 }
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700431}
432
Olli Etuaho492cfab2017-01-20 21:18:29 +0000433void TSymbolTable::insertBuiltInOp(ESymbolLevel level,
434 TOperator op,
435 const TType *rvalue,
436 const TType *ptype1,
437 const TType *ptype2,
438 const TType *ptype3,
439 const TType *ptype4,
440 const TType *ptype5)
441{
442 const char *name = GetOperatorString(op);
443 ASSERT(strlen(name) > 0);
444 insertUnmangledBuiltInName(name, level);
445 insertBuiltIn(level, op, "", rvalue, name, ptype1, ptype2, ptype3, ptype4, ptype5);
446}
447
448void TSymbolTable::insertBuiltInOp(ESymbolLevel level,
449 TOperator op,
450 const char *ext,
451 const TType *rvalue,
452 const TType *ptype1,
453 const TType *ptype2,
454 const TType *ptype3,
455 const TType *ptype4,
456 const TType *ptype5)
457{
458 const char *name = GetOperatorString(op);
459 insertUnmangledBuiltInName(name, level);
460 insertBuiltIn(level, op, ext, rvalue, name, ptype1, ptype2, ptype3, ptype4, ptype5);
461}
462
Martin Radevd7c5b0a2016-07-27 14:04:43 +0300463void TSymbolTable::insertBuiltInFunctionNoParameters(ESymbolLevel level,
464 TOperator op,
465 const TType *rvalue,
466 const char *name)
467{
468 insertUnmangledBuiltInName(name, level);
469 insert(level, new TFunction(NewPoolTString(name), rvalue, op));
470}
471
Zhenyao Moe740add2014-07-18 17:01:01 -0700472TPrecision TSymbolTable::getDefaultPrecision(TBasicType type) const
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700473{
474 if (!SupportsPrecision(type))
475 return EbpUndefined;
476
477 // unsigned integers use the same precision as signed
478 TBasicType baseType = (type == EbtUInt) ? EbtInt : type;
479
480 int level = static_cast<int>(precisionStack.size()) - 1;
Jamie Madilld7b1ab52016-12-12 14:42:19 -0500481 assert(level >= 0); // Just to be safe. Should not happen.
Olli Etuaho183d7e22015-11-20 15:59:09 +0200482 // If we dont find anything we return this. Some types don't have predefined default precision.
Zhenyao Mo9eedea02014-05-12 16:02:35 -0700483 TPrecision prec = EbpUndefined;
484 while (level >= 0)
485 {
486 PrecisionStackLevel::iterator it = precisionStack[level]->find(baseType);
487 if (it != precisionStack[level]->end())
488 {
489 prec = (*it).second;
490 break;
491 }
492 level--;
493 }
494 return prec;
495}
Jamie Madill45bcc782016-11-07 13:58:48 -0500496
Martin Radevda6254b2016-12-14 17:00:36 +0200497void TSymbolTable::insertUnmangledBuiltInName(const char *name, ESymbolLevel level)
498{
499 ASSERT(level >= 0 && level < static_cast<ESymbolLevel>(table.size()));
500 table[level]->insertUnmangledBuiltInName(std::string(name));
501}
502
503bool TSymbolTable::hasUnmangledBuiltInAtLevel(const char *name, ESymbolLevel level)
504{
505 ASSERT(level >= 0 && level < static_cast<ESymbolLevel>(table.size()));
506 return table[level]->hasUnmangledBuiltIn(std::string(name));
507}
508
509bool TSymbolTable::hasUnmangledBuiltInForShaderVersion(const char *name, int shaderVersion)
510{
511 ASSERT(static_cast<ESymbolLevel>(table.size()) > LAST_BUILTIN_LEVEL);
512
513 for (int level = LAST_BUILTIN_LEVEL; level >= 0; --level)
514 {
515 if (level == ESSL3_1_BUILTINS && shaderVersion != 310)
516 {
517 --level;
518 }
519 if (level == ESSL3_BUILTINS && shaderVersion < 300)
520 {
521 --level;
522 }
523 if (level == ESSL1_BUILTINS && shaderVersion != 100)
524 {
525 --level;
526 }
527
528 if (table[level]->hasUnmangledBuiltIn(name))
529 {
530 return true;
531 }
532 }
533 return false;
534}
535
Jamie Madill45bcc782016-11-07 13:58:48 -0500536} // namespace sh