Eliminate flex as the GLSL lexical analyzer, going from two nested lexical analyzers down to one, leaving just the preprocessor's lexical analysis. A new layer replaces it, to translate from the preprocessor's view of tokenization to glslang's view of tokenization.

Also:
 - change source locations from an int to TSourceLoc (shader number, line number) throughout
 - various improvements to the preprocessor


git-svn-id: https://cvs.khronos.org/svn/repos/ogl/trunk/ecosystem/public/sdk/tools/glslang@22277 e7fa87d3-cd2b-0410-9028-fcbf551c1848
This commit is contained in:
John Kessenich 2013-07-06 19:54:21 +00:00
parent 73ed17a87b
commit 5f1a0b7998
35 changed files with 2535 additions and 2515 deletions

View File

@ -125,5 +125,9 @@ int linenumber = __LINE__;
int filenumber = __FILE__; int filenumber = __FILE__;
int version = __VERSION__; int version = __VERSION__;
#define PI (3.14)
#define TWOPI (2.0 * PI)
float twoPi = TWOPI;
#define PASTE(a,b) a ## b #define PASTE(a,b) a ## b
float PASTE(tod, ay) = 17; float PASTE(tod, ay) = 17;

View File

@ -1,14 +1,20 @@
#version 300 es #version 300 es
// this file cont\ // this file cont\
ains no errors ains no errors other than the #error which are there to see if line numbering for errors is correct
#error e1
float f\ float f\
oo; // same as 'float foo;' oo; // same as 'float foo;'
#error e2
#define MAIN void main() \ #define MAIN void main() \
{ \ { \
gl_Position = vec4(foo); \ gl_Position = vec4(foo); \
} }
#error e3
MAIN MAIN

View File

@ -14,13 +14,13 @@ int OE = 0777777777777777777777; // ERROR
int HE = 0x1234567890ABCDEF0; // ERROR int HE = 0x1234567890ABCDEF0; // ERROR
// 1023 character fraction // 1023 character fraction
float F = 1.012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012; float F = 1.0123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890;
// 1024 character value // 1024 character value
float G = 1.0123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890; float G = 1.01234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678890;
// 1027 character fraction // 1025 character fraction
float E3 = 1.01234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234; float E3 = 1.012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012;
void main() void main()
{ {

View File

@ -150,7 +150,6 @@ xcopy /y $(IntDir)$(TargetName)$(TargetExt) Test</Command>
</ItemDefinitionGroup> </ItemDefinitionGroup>
<ItemGroup> <ItemGroup>
<ClCompile Include="glslang\MachineIndependent\Constant.cpp" /> <ClCompile Include="glslang\MachineIndependent\Constant.cpp" />
<ClCompile Include="glslang\MachineIndependent\gen_glslang.cpp" />
<ClCompile Include="glslang\MachineIndependent\glslang_tab.cpp" /> <ClCompile Include="glslang\MachineIndependent\glslang_tab.cpp" />
<ClCompile Include="glslang\MachineIndependent\InfoSink.cpp" /> <ClCompile Include="glslang\MachineIndependent\InfoSink.cpp" />
<ClCompile Include="glslang\MachineIndependent\Initialize.cpp" /> <ClCompile Include="glslang\MachineIndependent\Initialize.cpp" />
@ -192,7 +191,6 @@ xcopy /y $(IntDir)$(TargetName)$(TargetExt) Test</Command>
<ClInclude Include="glslang\MachineIndependent\RemoveTree.h" /> <ClInclude Include="glslang\MachineIndependent\RemoveTree.h" />
<ClInclude Include="glslang\MachineIndependent\localintermediate.h" /> <ClInclude Include="glslang\MachineIndependent\localintermediate.h" />
<ClInclude Include="glslang\MachineIndependent\preprocessor\atom.h" /> <ClInclude Include="glslang\MachineIndependent\preprocessor\atom.h" />
<ClInclude Include="glslang\MachineIndependent\preprocessor\compile.h" />
<ClInclude Include="glslang\MachineIndependent\preprocessor\cpp.h" /> <ClInclude Include="glslang\MachineIndependent\preprocessor\cpp.h" />
<ClInclude Include="glslang\MachineIndependent\preprocessor\memory.h" /> <ClInclude Include="glslang\MachineIndependent\preprocessor\memory.h" />
<ClInclude Include="glslang\MachineIndependent\preprocessor\parser.h" /> <ClInclude Include="glslang\MachineIndependent\preprocessor\parser.h" />
@ -206,6 +204,7 @@ xcopy /y $(IntDir)$(TargetName)$(TargetExt) Test</Command>
<ClInclude Include="glslang\Include\ConstantUnion.h" /> <ClInclude Include="glslang\Include\ConstantUnion.h" />
<ClInclude Include="glslang\Include\InfoSink.h" /> <ClInclude Include="glslang\Include\InfoSink.h" />
<ClInclude Include="glslang\MachineIndependent\Scan.h" /> <ClInclude Include="glslang\MachineIndependent\Scan.h" />
<ClInclude Include="glslang\MachineIndependent\ScanContext.h" />
<ClInclude Include="glslang\MachineIndependent\Versions.h" /> <ClInclude Include="glslang\MachineIndependent\Versions.h" />
<ClInclude Include="OGLCompilersDLL\InitializeDll.h" /> <ClInclude Include="OGLCompilersDLL\InitializeDll.h" />
<ClInclude Include="glslang\Include\InitializeGlobals.h" /> <ClInclude Include="glslang\Include\InitializeGlobals.h" />
@ -238,23 +237,6 @@ cd %(RootDir)%(Directory)
<Outputs Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">%(RootDir)%(Directory)%(Filename)_tab.cpp;%(Outputs)</Outputs> <Outputs Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">%(RootDir)%(Directory)%(Filename)_tab.cpp;%(Outputs)</Outputs>
</CustomBuild> </CustomBuild>
</ItemGroup> </ItemGroup>
<ItemGroup>
<CustomBuild Include="glslang\MachineIndependent\glslang.l">
<FileType>Document</FileType>
<Command Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">cd %(RootDir)%(Directory)
%(RootDir)%(Directory)..\..\tools\flex.exe glslang.l
</Command>
<Message Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">Executing flex on glslang.l</Message>
<Outputs Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">%(RootDir)%(Directory)gen_glslang.cpp</Outputs>
<AdditionalInputs Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">%(RootDir)%(Directory)glslang_tab.cpp.h</AdditionalInputs>
<Command Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">cd %(RootDir)%(Directory)
%(RootDir)%(Directory)..\..\tools\flex.exe glslang.l
</Command>
<Message Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">Executing flex on glslang.l</Message>
<Outputs Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">%(RootDir)%(Directory)gen_glslang.cpp</Outputs>
<AdditionalInputs Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">%(RootDir)%(Directory)glslang_tab.cpp.h</AdditionalInputs>
</CustomBuild>
</ItemGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" /> <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
<ImportGroup Label="ExtensionTargets"> <ImportGroup Label="ExtensionTargets">
</ImportGroup> </ImportGroup>

View File

@ -97,9 +97,6 @@
<ClCompile Include="glslang\OSDependent\Linux\ossource.cpp"> <ClCompile Include="glslang\OSDependent\Linux\ossource.cpp">
<Filter>OSDependent\Linux</Filter> <Filter>OSDependent\Linux</Filter>
</ClCompile> </ClCompile>
<ClCompile Include="glslang\MachineIndependent\gen_glslang.cpp">
<Filter>Machine Independent\Generated Source</Filter>
</ClCompile>
<ClCompile Include="glslang\MachineIndependent\glslang_tab.cpp"> <ClCompile Include="glslang\MachineIndependent\glslang_tab.cpp">
<Filter>Machine Independent\Generated Source</Filter> <Filter>Machine Independent\Generated Source</Filter>
</ClCompile> </ClCompile>
@ -135,9 +132,6 @@
<ClInclude Include="glslang\MachineIndependent\preprocessor\atom.h"> <ClInclude Include="glslang\MachineIndependent\preprocessor\atom.h">
<Filter>Machine Independent\CPP</Filter> <Filter>Machine Independent\CPP</Filter>
</ClInclude> </ClInclude>
<ClInclude Include="glslang\MachineIndependent\preprocessor\compile.h">
<Filter>Machine Independent\CPP</Filter>
</ClInclude>
<ClInclude Include="glslang\MachineIndependent\preprocessor\cpp.h"> <ClInclude Include="glslang\MachineIndependent\preprocessor\cpp.h">
<Filter>Machine Independent\CPP</Filter> <Filter>Machine Independent\CPP</Filter>
</ClInclude> </ClInclude>
@ -222,13 +216,13 @@
<ClInclude Include="glslang\MachineIndependent\Scan.h"> <ClInclude Include="glslang\MachineIndependent\Scan.h">
<Filter>Machine Independent</Filter> <Filter>Machine Independent</Filter>
</ClInclude> </ClInclude>
<ClInclude Include="glslang\MachineIndependent\ScanContext.h">
<Filter>Machine Independent</Filter>
</ClInclude>
</ItemGroup> </ItemGroup>
<ItemGroup> <ItemGroup>
<CustomBuild Include="glslang\MachineIndependent\glslang.y"> <CustomBuild Include="glslang\MachineIndependent\glslang.y">
<Filter>Machine Independent</Filter> <Filter>Machine Independent</Filter>
</CustomBuild> </CustomBuild>
<CustomBuild Include="glslang\MachineIndependent\glslang.l">
<Filter>Machine Independent</Filter>
</CustomBuild>
</ItemGroup> </ItemGroup>
</Project> </Project>

View File

@ -66,8 +66,6 @@
#include <stdio.h> #include <stdio.h>
#include <assert.h> #include <assert.h>
typedef int TSourceLoc;
#include "PoolAlloc.h" #include "PoolAlloc.h"
// //
@ -162,25 +160,10 @@ inline const TString String(const int i, const int base = 10)
return text; return text;
} }
const unsigned int SourceLocLineMask = 0xffff; struct TSourceLoc {
const unsigned int SourceLocStringShift = 16; int string;
int line;
__inline TPersistString FormatSourceLoc(const TSourceLoc loc) };
{
const int maxSize = 64;
char locText[maxSize];
int string = loc >> SourceLocStringShift;
int line = loc & SourceLocLineMask;
if (line)
snprintf(locText, maxSize, "%d:%d", string, line);
else
snprintf(locText, maxSize, "%d:? ", string);
return TPersistString(locText);
}
typedef TMap<TString, TString> TPragmaTable; typedef TMap<TString, TString> TPragmaTable;
typedef TMap<TString, TString>::tAllocator TPragmaTableAllocator; typedef TMap<TString, TString>::tAllocator TPragmaTableAllocator;

View File

@ -94,7 +94,10 @@ public:
} }
} }
void location(TSourceLoc loc) { void location(TSourceLoc loc) {
append(FormatSourceLoc(loc).c_str()); const int maxSize = 24;
char locText[maxSize];
snprintf(locText, maxSize, "%d:%d", loc.string, loc.line);
append(locText);
append(": "); append(": ");
} }
void message(TPrefixType message, const char* s) { void message(TPrefixType message, const char* s) {

View File

@ -142,11 +142,11 @@ struct TSampler {
// Need to have association of line numbers to types in a list for building structs. // Need to have association of line numbers to types in a list for building structs.
// //
class TType; class TType;
struct TTypeLine { struct TTypeLoc {
TType* type; TType* type;
int line; TSourceLoc loc;
}; };
typedef TVector<TTypeLine> TTypeList; typedef TVector<TTypeLoc> TTypeList;
inline TTypeList* NewPoolTTypeList() inline TTypeList* NewPoolTTypeList()
{ {
@ -347,9 +347,9 @@ public:
int matrixRows : 4; int matrixRows : 4;
TArraySizes arraySizes; TArraySizes arraySizes;
const TType* userDef; const TType* userDef;
int line; TSourceLoc loc;
void initType(int ln = 0) void initType(TSourceLoc l)
{ {
basicType = EbtVoid; basicType = EbtVoid;
vectorSize = 1; vectorSize = 1;
@ -357,7 +357,7 @@ public:
matrixCols = 0; matrixCols = 0;
arraySizes = 0; arraySizes = 0;
userDef = 0; userDef = 0;
line = ln; loc = l;
} }
void initQualifiers(bool global = false) void initQualifiers(bool global = false)
@ -367,9 +367,9 @@ public:
qualifier.storage = EvqGlobal; qualifier.storage = EvqGlobal;
} }
void init(int line = 0, bool global = false) void init(TSourceLoc loc, bool global = false)
{ {
initType(line); initType(loc);
sampler.clear(); sampler.clear();
initQualifiers(global); initQualifiers(global);
} }
@ -479,10 +479,10 @@ public:
// create the new structure here // create the new structure here
structure = NewPoolTTypeList(); structure = NewPoolTTypeList();
for (unsigned int i = 0; i < copyOf.structure->size(); ++i) { for (unsigned int i = 0; i < copyOf.structure->size(); ++i) {
TTypeLine typeLine; TTypeLoc typeLoc;
typeLine.line = (*copyOf.structure)[i].line; typeLoc.loc = (*copyOf.structure)[i].loc;
typeLine.type = (*copyOf.structure)[i].type->clone(remapper); typeLoc.type = (*copyOf.structure)[i].type->clone(remapper);
structure->push_back(typeLine); structure->push_back(typeLoc);
} }
} else { } else {
structure = iter->second; structure = iter->second;

View File

@ -320,9 +320,9 @@ class TIntermNode {
public: public:
POOL_ALLOCATOR_NEW_DELETE(GlobalPoolAllocator) POOL_ALLOCATOR_NEW_DELETE(GlobalPoolAllocator)
TIntermNode() : line(0) {} TIntermNode() { loc.line = 0; loc.string = 0; }
virtual TSourceLoc getLine() const { return line; } virtual TSourceLoc getLoc() const { return loc; }
virtual void setLine(TSourceLoc l) { line = l; } virtual void setLoc(TSourceLoc l) { loc = l; }
virtual void traverse(TIntermTraverser*) = 0; virtual void traverse(TIntermTraverser*) = 0;
virtual TIntermTyped* getAsTyped() { return 0; } virtual TIntermTyped* getAsTyped() { return 0; }
virtual TIntermConstantUnion* getAsConstantUnion() { return 0; } virtual TIntermConstantUnion* getAsConstantUnion() { return 0; }
@ -336,7 +336,7 @@ public:
virtual TIntermBranch* getAsBranchNode() { return 0; } virtual TIntermBranch* getAsBranchNode() { return 0; }
virtual ~TIntermNode() { } virtual ~TIntermNode() { }
protected: protected:
TSourceLoc line; TSourceLoc loc;
}; };
// //

View File

@ -195,7 +195,7 @@ TIntermTyped* TIntermConstantUnion::fold(TOperator op, TIntermTyped* constantNod
newConstArray[i].setUConst(unionArray[i].getUConst() / rightUnionArray[i].getUConst()); newConstArray[i].setUConst(unionArray[i].getUConst() / rightUnionArray[i].getUConst());
break; break;
default: default:
infoSink.info.message(EPrefixInternalError, "Constant folding cannot be done for \"/\"", getLine()); infoSink.info.message(EPrefixInternalError, "Constant folding cannot be done for \"/\"", getLoc());
return 0; return 0;
} }
} }
@ -352,13 +352,13 @@ TIntermTyped* TIntermConstantUnion::fold(TOperator op, TIntermTyped* constantNod
break; break;
default: default:
infoSink.info.message(EPrefixInternalError, "Invalid operator for constant folding", getLine()); infoSink.info.message(EPrefixInternalError, "Invalid operator for constant folding", getLoc());
return 0; return 0;
} }
TIntermConstantUnion *newNode = new TIntermConstantUnion(newConstArray, returnType); TIntermConstantUnion *newNode = new TIntermConstantUnion(newConstArray, returnType);
newNode->setLine(getLine()); newNode->setLoc(getLoc());
return newNode; return newNode;
} }
@ -416,7 +416,7 @@ TIntermTyped* TIntermConstantUnion::fold(TOperator op, const TType& returnType,
case EbtInt: newConstArray[i].setIConst(-unionArray[i].getIConst()); break; case EbtInt: newConstArray[i].setIConst(-unionArray[i].getIConst()); break;
case EbtUint: newConstArray[i].setUConst(static_cast<unsigned int>(-static_cast<int>(unionArray[i].getUConst()))); break; case EbtUint: newConstArray[i].setUConst(static_cast<unsigned int>(-static_cast<int>(unionArray[i].getUConst()))); break;
default: default:
infoSink.info.message(EPrefixInternalError, "Unary operation not folded into constant", getLine()); infoSink.info.message(EPrefixInternalError, "Unary operation not folded into constant", getLoc());
return 0; return 0;
} }
break; break;
@ -425,7 +425,7 @@ TIntermTyped* TIntermConstantUnion::fold(TOperator op, const TType& returnType,
switch (getType().getBasicType()) { switch (getType().getBasicType()) {
case EbtBool: newConstArray[i].setBConst(!unionArray[i].getBConst()); break; case EbtBool: newConstArray[i].setBConst(!unionArray[i].getBConst()); break;
default: default:
infoSink.info.message(EPrefixInternalError, "Unary operation not folded into constant", getLine()); infoSink.info.message(EPrefixInternalError, "Unary operation not folded into constant", getLoc());
return 0; return 0;
} }
break; break;
@ -570,14 +570,14 @@ TIntermTyped* TIntermConstantUnion::fold(TOperator op, const TType& returnType,
case EOpAll: case EOpAll:
default: default:
infoSink.info.message(EPrefixInternalError, "missing operator for unary constant folding", getLine()); infoSink.info.message(EPrefixInternalError, "missing operator for unary constant folding", getLoc());
return 0; return 0;
} }
} }
TIntermConstantUnion *newNode = new TIntermConstantUnion(newConstArray, returnType); TIntermConstantUnion *newNode = new TIntermConstantUnion(newConstArray, returnType);
newNode->getTypePointer()->getQualifier().storage = EvqConst; newNode->getTypePointer()->getQualifier().storage = EvqConst;
newNode->setLine(getLine()); newNode->setLoc(getLoc());
return newNode; return newNode;
} }
@ -667,7 +667,7 @@ TIntermTyped* TIntermediate::fold(TIntermAggregate* aggrNode)
case EOpReflect: case EOpReflect:
case EOpRefract: case EOpRefract:
case EOpOuterProduct: case EOpOuterProduct:
infoSink.info.message(EPrefixInternalError, "constant folding operation not implemented", aggrNode->getLine()); infoSink.info.message(EPrefixInternalError, "constant folding operation not implemented", aggrNode->getLoc());
return aggrNode; return aggrNode;
default: default:
@ -676,7 +676,7 @@ TIntermTyped* TIntermediate::fold(TIntermAggregate* aggrNode)
TIntermConstantUnion *newNode = new TIntermConstantUnion(newConstArray, aggrNode->getType()); TIntermConstantUnion *newNode = new TIntermConstantUnion(newConstArray, aggrNode->getType());
newNode->getTypePointer()->getQualifier().storage = EvqConst; newNode->getTypePointer()->getQualifier().storage = EvqConst;
newNode->setLine(aggrNode->getLine()); newNode->setLoc(aggrNode->getLoc());
return newNode; return newNode;
} }
@ -705,12 +705,12 @@ TIntermTyped* TIntermediate::foldConstructor(TIntermAggregate* aggrNode)
constUnion* unionArray = new constUnion[aggrNode->getType().getObjectSize()]; constUnion* unionArray = new constUnion[aggrNode->getType().getObjectSize()];
if (aggrNode->getSequence().size() == 1) if (aggrNode->getSequence().size() == 1)
returnVal = parseConstTree(aggrNode->getLine(), aggrNode, unionArray, aggrNode->getOp(), aggrNode->getType(), true); returnVal = parseConstTree(aggrNode->getLoc(), aggrNode, unionArray, aggrNode->getOp(), aggrNode->getType(), true);
else else
returnVal = parseConstTree(aggrNode->getLine(), aggrNode, unionArray, aggrNode->getOp(), aggrNode->getType()); returnVal = parseConstTree(aggrNode->getLoc(), aggrNode, unionArray, aggrNode->getOp(), aggrNode->getType());
if (returnVal) if (returnVal)
return aggrNode; return aggrNode;
return addConstantUnion(unionArray, aggrNode->getType(), aggrNode->getLine()); return addConstantUnion(unionArray, aggrNode->getType(), aggrNode->getLoc());
} }

View File

@ -70,7 +70,5 @@ protected:
void IdentifyBuiltIns(int version, EProfile profile, EShLanguage, TSymbolTable&); void IdentifyBuiltIns(int version, EProfile profile, EShLanguage, TSymbolTable&);
void IdentifyBuiltIns(int version, EProfile profile, EShLanguage, TSymbolTable&, const TBuiltInResource &resources); void IdentifyBuiltIns(int version, EProfile profile, EShLanguage, TSymbolTable&, const TBuiltInResource &resources);
extern "C" int InitPreprocessor(void);
extern "C" int FinalizePreprocessor(void);
#endif // _INITIALIZE_INCLUDED_ #endif // _INITIALIZE_INCLUDED_

View File

@ -56,10 +56,10 @@
// //
// Returns the added node. // Returns the added node.
// //
TIntermSymbol* TIntermediate::addSymbol(int id, const TString& name, const TType& type, TSourceLoc line) TIntermSymbol* TIntermediate::addSymbol(int id, const TString& name, const TType& type, TSourceLoc loc)
{ {
TIntermSymbol* node = new TIntermSymbol(id, name, type); TIntermSymbol* node = new TIntermSymbol(id, name, type);
node->setLine(line); node->setLoc(loc);
return node; return node;
} }
@ -69,7 +69,7 @@ TIntermSymbol* TIntermediate::addSymbol(int id, const TString& name, const TType
// //
// Returns the added node. // Returns the added node.
// //
TIntermTyped* TIntermediate::addBinaryMath(TOperator op, TIntermTyped* left, TIntermTyped* right, TSourceLoc line) TIntermTyped* TIntermediate::addBinaryMath(TOperator op, TIntermTyped* left, TIntermTyped* right, TSourceLoc loc)
{ {
// No operations work on blocks // No operations work on blocks
if (left->getType().getBasicType() == EbtBlock || right->getType().getBasicType() == EbtBlock) if (left->getType().getBasicType() == EbtBlock || right->getType().getBasicType() == EbtBlock)
@ -92,9 +92,9 @@ TIntermTyped* TIntermediate::addBinaryMath(TOperator op, TIntermTyped* left, TIn
// one and promote it to the right type. // one and promote it to the right type.
// //
TIntermBinary* node = new TIntermBinary(op); TIntermBinary* node = new TIntermBinary(op);
if (line == 0) if (loc.line == 0)
line = right->getLine(); loc = right->getLoc();
node->setLine(line); node->setLoc(loc);
node->setLeft(left); node->setLeft(left);
node->setRight(right); node->setRight(right);
@ -114,7 +114,7 @@ TIntermTyped* TIntermediate::addBinaryMath(TOperator op, TIntermTyped* left, TIn
if (folded) if (folded)
return folded; return folded;
else else
infoSink.info.message(EPrefixInternalError, "Constant folding failed", line); infoSink.info.message(EPrefixInternalError, "Constant folding failed", loc);
} }
return node; return node;
@ -125,7 +125,7 @@ TIntermTyped* TIntermediate::addBinaryMath(TOperator op, TIntermTyped* left, TIn
// //
// Returns the added node. // Returns the added node.
// //
TIntermTyped* TIntermediate::addAssign(TOperator op, TIntermTyped* left, TIntermTyped* right, TSourceLoc line) TIntermTyped* TIntermediate::addAssign(TOperator op, TIntermTyped* left, TIntermTyped* right, TSourceLoc loc)
{ {
// No block assignment // No block assignment
if (left->getType().getBasicType() == EbtBlock || right->getType().getBasicType() == EbtBlock) if (left->getType().getBasicType() == EbtBlock || right->getType().getBasicType() == EbtBlock)
@ -136,9 +136,9 @@ TIntermTyped* TIntermediate::addAssign(TOperator op, TIntermTyped* left, TInterm
// from right to left. // from right to left.
// //
TIntermBinary* node = new TIntermBinary(op); TIntermBinary* node = new TIntermBinary(op);
if (line == 0) if (loc.line == 0)
line = left->getLine(); loc = left->getLoc();
node->setLine(line); node->setLoc(loc);
TIntermTyped* child = addConversion(op, left->getType(), right); TIntermTyped* child = addConversion(op, left->getType(), right);
if (child == 0) if (child == 0)
@ -161,12 +161,12 @@ TIntermTyped* TIntermediate::addAssign(TOperator op, TIntermTyped* left, TInterm
// Returns the added node. // Returns the added node.
// The caller should set the type of the returned node. // The caller should set the type of the returned node.
// //
TIntermTyped* TIntermediate::addIndex(TOperator op, TIntermTyped* base, TIntermTyped* index, TSourceLoc line) TIntermTyped* TIntermediate::addIndex(TOperator op, TIntermTyped* base, TIntermTyped* index, TSourceLoc loc)
{ {
TIntermBinary* node = new TIntermBinary(op); TIntermBinary* node = new TIntermBinary(op);
if (line == 0) if (loc.line == 0)
line = index->getLine(); loc = index->getLoc();
node->setLine(line); node->setLoc(loc);
node->setLeft(base); node->setLeft(base);
node->setRight(index); node->setRight(index);
@ -180,7 +180,7 @@ TIntermTyped* TIntermediate::addIndex(TOperator op, TIntermTyped* base, TIntermT
// //
// Returns the added node. // Returns the added node.
// //
TIntermTyped* TIntermediate::addUnaryMath(TOperator op, TIntermNode* childNode, TSourceLoc line) TIntermTyped* TIntermediate::addUnaryMath(TOperator op, TIntermNode* childNode, TSourceLoc loc)
{ {
TIntermTyped* child = childNode->getAsTyped(); TIntermTyped* child = childNode->getAsTyped();
@ -188,7 +188,7 @@ TIntermTyped* TIntermediate::addUnaryMath(TOperator op, TIntermNode* childNode,
return 0; return 0;
if (child == 0) { if (child == 0) {
infoSink.info.message(EPrefixInternalError, "Bad type in AddUnaryMath", line); infoSink.info.message(EPrefixInternalError, "Bad type in AddUnaryMath", loc);
return 0; return 0;
} }
@ -248,9 +248,9 @@ TIntermTyped* TIntermediate::addUnaryMath(TOperator op, TIntermNode* childNode,
// Make a new node for the operator. // Make a new node for the operator.
// //
TIntermUnary* node = new TIntermUnary(op); TIntermUnary* node = new TIntermUnary(op);
if (line == 0) if (loc.line == 0)
line = child->getLine(); loc = child->getLoc();
node->setLine(line); node->setLoc(loc);
node->setOperand(child); node->setOperand(child);
if (! node->promote(infoSink)) if (! node->promote(infoSink))
@ -274,7 +274,7 @@ TIntermTyped* TIntermediate::addBuiltInFunctionCall(TOperator op, bool unary, TI
// //
TIntermTyped* child = childNode->getAsTyped(); TIntermTyped* child = childNode->getAsTyped();
if (child == 0) { if (child == 0) {
infoSink.info.message(EPrefixInternalError, "Bad type in AddUnaryMath", child->getLine()); infoSink.info.message(EPrefixInternalError, "Bad type in AddUnaryMath", child->getLoc());
return 0; return 0;
} }
@ -284,7 +284,7 @@ TIntermTyped* TIntermediate::addBuiltInFunctionCall(TOperator op, bool unary, TI
return child->getAsConstantUnion()->fold(op, returnType, infoSink); return child->getAsConstantUnion()->fold(op, returnType, infoSink);
TIntermUnary* node = new TIntermUnary(op); TIntermUnary* node = new TIntermUnary(op);
node->setLine(child->getLine()); node->setLoc(child->getLoc());
node->setOperand(child); node->setOperand(child);
node->setType(returnType); node->setType(returnType);
@ -299,7 +299,7 @@ TIntermTyped* TIntermediate::addBuiltInFunctionCall(TOperator op, bool unary, TI
return node; return node;
} else { } else {
// setAggregateOperater() calls fold() for constant folding // setAggregateOperater() calls fold() for constant folding
TIntermTyped* node = setAggregateOperator(childNode, op, returnType, childNode->getLine()); TIntermTyped* node = setAggregateOperator(childNode, op, returnType, childNode->getLoc());
TPrecisionQualifier correctPrecision = returnType.getQualifier().precision; TPrecisionQualifier correctPrecision = returnType.getQualifier().precision;
if (correctPrecision == EpqNone && profile == EEsProfile) { if (correctPrecision == EpqNone && profile == EEsProfile) {
@ -328,7 +328,7 @@ TIntermTyped* TIntermediate::addBuiltInFunctionCall(TOperator op, bool unary, TI
// Returns an aggregate node, which could be the one passed in if // Returns an aggregate node, which could be the one passed in if
// it was already an aggregate. // it was already an aggregate.
// //
TIntermTyped* TIntermediate::setAggregateOperator(TIntermNode* node, TOperator op, const TType& type, TSourceLoc line) TIntermTyped* TIntermediate::setAggregateOperator(TIntermNode* node, TOperator op, const TType& type, TSourceLoc loc)
{ {
TIntermAggregate* aggNode; TIntermAggregate* aggNode;
@ -343,8 +343,8 @@ TIntermTyped* TIntermediate::setAggregateOperator(TIntermNode* node, TOperator o
// //
aggNode = new TIntermAggregate(); aggNode = new TIntermAggregate();
aggNode->getSequence().push_back(node); aggNode->getSequence().push_back(node);
if (line == 0) if (loc.line == 0)
line = node->getLine(); loc = node->getLoc();
} }
} else } else
aggNode = new TIntermAggregate(); aggNode = new TIntermAggregate();
@ -353,8 +353,8 @@ TIntermTyped* TIntermediate::setAggregateOperator(TIntermNode* node, TOperator o
// Set the operator. // Set the operator.
// //
aggNode->setOperator(op); aggNode->setOperator(op);
if (line != 0) if (loc.line != 0)
aggNode->setLine(line); aggNode->setLoc(loc);
aggNode->setType(type); aggNode->setType(type);
@ -510,7 +510,7 @@ TIntermTyped* TIntermediate::addConversion(TOperator op, const TType& type, TInt
//case EbtBool: newOp = EOpConvBoolToDouble; break; //case EbtBool: newOp = EOpConvBoolToDouble; break;
//case EbtFloat: newOp = EOpConvFloatToDouble; break; //case EbtFloat: newOp = EOpConvFloatToDouble; break;
//default: //default:
infoSink.info.message(EPrefixInternalError, "Bad promotion node", node->getLine()); infoSink.info.message(EPrefixInternalError, "Bad promotion node", node->getLoc());
return 0; return 0;
//} //}
break; break;
@ -521,7 +521,7 @@ TIntermTyped* TIntermediate::addConversion(TOperator op, const TType& type, TInt
case EbtBool: newOp = EOpConvBoolToFloat; break; case EbtBool: newOp = EOpConvBoolToFloat; break;
case EbtDouble: newOp = EOpConvDoubleToFloat; break; case EbtDouble: newOp = EOpConvDoubleToFloat; break;
default: default:
infoSink.info.message(EPrefixInternalError, "Bad promotion node", node->getLine()); infoSink.info.message(EPrefixInternalError, "Bad promotion node", node->getLoc());
return 0; return 0;
} }
break; break;
@ -532,7 +532,7 @@ TIntermTyped* TIntermediate::addConversion(TOperator op, const TType& type, TInt
case EbtFloat: newOp = EOpConvFloatToBool; break; case EbtFloat: newOp = EOpConvFloatToBool; break;
case EbtDouble: newOp = EOpConvDoubleToBool; break; case EbtDouble: newOp = EOpConvDoubleToBool; break;
default: default:
infoSink.info.message(EPrefixInternalError, "Bad promotion node", node->getLine()); infoSink.info.message(EPrefixInternalError, "Bad promotion node", node->getLoc());
return 0; return 0;
} }
break; break;
@ -543,7 +543,7 @@ TIntermTyped* TIntermediate::addConversion(TOperator op, const TType& type, TInt
case EbtFloat: newOp = EOpConvFloatToInt; break; case EbtFloat: newOp = EOpConvFloatToInt; break;
case EbtDouble: newOp = EOpConvDoubleToInt; break; case EbtDouble: newOp = EOpConvDoubleToInt; break;
default: default:
infoSink.info.message(EPrefixInternalError, "Bad promotion node", node->getLine()); infoSink.info.message(EPrefixInternalError, "Bad promotion node", node->getLoc());
return 0; return 0;
} }
break; break;
@ -554,18 +554,18 @@ TIntermTyped* TIntermediate::addConversion(TOperator op, const TType& type, TInt
case EbtFloat: newOp = EOpConvFloatToUint; break; case EbtFloat: newOp = EOpConvFloatToUint; break;
case EbtDouble: newOp = EOpConvDoubleToUint; break; case EbtDouble: newOp = EOpConvDoubleToUint; break;
default: default:
infoSink.info.message(EPrefixInternalError, "Bad promotion node", node->getLine()); infoSink.info.message(EPrefixInternalError, "Bad promotion node", node->getLoc());
return 0; return 0;
} }
break; break;
default: default:
infoSink.info.message(EPrefixInternalError, "Bad promotion type", node->getLine()); infoSink.info.message(EPrefixInternalError, "Bad promotion type", node->getLoc());
return 0; return 0;
} }
TType type(promoteTo, EvqTemporary, node->getVectorSize(), node->getMatrixCols(), node->getMatrixRows()); TType type(promoteTo, EvqTemporary, node->getVectorSize(), node->getMatrixCols(), node->getMatrixRows());
newNode = new TIntermUnary(newOp, type); newNode = new TIntermUnary(newOp, type);
newNode->setLine(node->getLine()); newNode->setLoc(node->getLoc());
newNode->setOperand(node); newNode->setOperand(node);
return newNode; return newNode;
@ -628,7 +628,7 @@ bool TIntermediate::canImplicitlyPromote(TBasicType from, TBasicType to)
// Returns the resulting aggregate, unless 0 was passed in for // Returns the resulting aggregate, unless 0 was passed in for
// both existing nodes. // both existing nodes.
// //
TIntermAggregate* TIntermediate::growAggregate(TIntermNode* left, TIntermNode* right, TSourceLoc line) TIntermAggregate* TIntermediate::growAggregate(TIntermNode* left, TIntermNode* right)
{ {
if (left == 0 && right == 0) if (left == 0 && right == 0)
return 0; return 0;
@ -645,8 +645,13 @@ TIntermAggregate* TIntermediate::growAggregate(TIntermNode* left, TIntermNode* r
if (right) if (right)
aggNode->getSequence().push_back(right); aggNode->getSequence().push_back(right);
if (line != 0) return aggNode;
aggNode->setLine(line); }
TIntermAggregate* TIntermediate::growAggregate(TIntermNode* left, TIntermNode* right, TSourceLoc loc)
{
TIntermAggregate* aggNode = growAggregate(left, right);
aggNode->setLoc(loc);
return aggNode; return aggNode;
} }
@ -656,18 +661,26 @@ TIntermAggregate* TIntermediate::growAggregate(TIntermNode* left, TIntermNode* r
// //
// Returns an aggregate, unless 0 was passed in for the existing node. // Returns an aggregate, unless 0 was passed in for the existing node.
// //
TIntermAggregate* TIntermediate::makeAggregate(TIntermNode* node, TSourceLoc line) TIntermAggregate* TIntermediate::makeAggregate(TIntermNode* node)
{ {
if (node == 0) if (node == 0)
return 0; return 0;
TIntermAggregate* aggNode = new TIntermAggregate; TIntermAggregate* aggNode = new TIntermAggregate;
aggNode->getSequence().push_back(node); aggNode->getSequence().push_back(node);
aggNode->setLoc(node->getLoc());
if (line != 0) return aggNode;
aggNode->setLine(line); }
else
aggNode->setLine(node->getLine()); TIntermAggregate* TIntermediate::makeAggregate(TIntermNode* node, TSourceLoc loc)
{
if (node == 0)
return 0;
TIntermAggregate* aggNode = new TIntermAggregate;
aggNode->getSequence().push_back(node);
aggNode->setLoc(loc);
return aggNode; return aggNode;
} }
@ -679,7 +692,7 @@ TIntermAggregate* TIntermediate::makeAggregate(TIntermNode* node, TSourceLoc lin
// //
// Returns the selection node created. // Returns the selection node created.
// //
TIntermNode* TIntermediate::addSelection(TIntermTyped* cond, TIntermNodePair nodePair, TSourceLoc line) TIntermNode* TIntermediate::addSelection(TIntermTyped* cond, TIntermNodePair nodePair, TSourceLoc loc)
{ {
// //
// For compile time constant selections, prune the code and // For compile time constant selections, prune the code and
@ -694,20 +707,20 @@ TIntermNode* TIntermediate::addSelection(TIntermTyped* cond, TIntermNodePair nod
} }
TIntermSelection* node = new TIntermSelection(cond, nodePair.node1, nodePair.node2); TIntermSelection* node = new TIntermSelection(cond, nodePair.node1, nodePair.node2);
node->setLine(line); node->setLoc(loc);
return node; return node;
} }
TIntermTyped* TIntermediate::addComma(TIntermTyped* left, TIntermTyped* right, TSourceLoc line) TIntermTyped* TIntermediate::addComma(TIntermTyped* left, TIntermTyped* right, TSourceLoc loc)
{ {
if (left->getType().getQualifier().storage == EvqConst && if (left->getType().getQualifier().storage == EvqConst &&
right->getType().getQualifier().storage == EvqConst) { right->getType().getQualifier().storage == EvqConst) {
return right; return right;
} else { } else {
TIntermTyped *commaAggregate = growAggregate(left, right, line); TIntermTyped *commaAggregate = growAggregate(left, right, loc);
commaAggregate->getAsAggregate()->setOperator(EOpComma); commaAggregate->getAsAggregate()->setOperator(EOpComma);
commaAggregate->setType(right->getType()); commaAggregate->setType(right->getType());
commaAggregate->getTypePointer()->getQualifier().storage = EvqTemporary; commaAggregate->getTypePointer()->getQualifier().storage = EvqTemporary;
@ -717,10 +730,10 @@ TIntermTyped* TIntermediate::addComma(TIntermTyped* left, TIntermTyped* right, T
} }
} }
TIntermTyped* TIntermediate::addMethod(TIntermTyped* object, const TType& type, const TString* name, TSourceLoc line) TIntermTyped* TIntermediate::addMethod(TIntermTyped* object, const TType& type, const TString* name, TSourceLoc loc)
{ {
TIntermMethod* method = new TIntermMethod(object, type, *name); TIntermMethod* method = new TIntermMethod(object, type, *name);
method->setLine(line); method->setLoc(loc);
return method; return method;
} }
@ -732,7 +745,7 @@ TIntermTyped* TIntermediate::addMethod(TIntermTyped* object, const TType& type,
// //
// Returns the selection node created, or 0 if one could not be. // Returns the selection node created, or 0 if one could not be.
// //
TIntermTyped* TIntermediate::addSelection(TIntermTyped* cond, TIntermTyped* trueBlock, TIntermTyped* falseBlock, TSourceLoc line) TIntermTyped* TIntermediate::addSelection(TIntermTyped* cond, TIntermTyped* trueBlock, TIntermTyped* falseBlock, TSourceLoc loc)
{ {
// //
// Get compatible types. // Get compatible types.
@ -767,7 +780,7 @@ TIntermTyped* TIntermediate::addSelection(TIntermTyped* cond, TIntermTyped* true
// Make a selection node. // Make a selection node.
// //
TIntermSelection* node = new TIntermSelection(cond, trueBlock, falseBlock, trueBlock->getType()); TIntermSelection* node = new TIntermSelection(cond, trueBlock, falseBlock, trueBlock->getType());
node->setLine(line); node->setLoc(loc);
node->getQualifier().precision = std::max(trueBlock->getQualifier().precision, falseBlock->getQualifier().precision); node->getQualifier().precision = std::max(trueBlock->getQualifier().precision, falseBlock->getQualifier().precision);
return node; return node;
@ -779,20 +792,20 @@ TIntermTyped* TIntermediate::addSelection(TIntermTyped* cond, TIntermTyped* true
// Returns the constant union node created. // Returns the constant union node created.
// //
TIntermConstantUnion* TIntermediate::addConstantUnion(constUnion* unionArrayPointer, const TType& t, TSourceLoc line) TIntermConstantUnion* TIntermediate::addConstantUnion(constUnion* unionArrayPointer, const TType& t, TSourceLoc loc)
{ {
TIntermConstantUnion* node = new TIntermConstantUnion(unionArrayPointer, t); TIntermConstantUnion* node = new TIntermConstantUnion(unionArrayPointer, t);
node->setLine(line); node->setLoc(loc);
return node; return node;
} }
TIntermTyped* TIntermediate::addSwizzle(TVectorFields& fields, TSourceLoc line) TIntermTyped* TIntermediate::addSwizzle(TVectorFields& fields, TSourceLoc loc)
{ {
TIntermAggregate* node = new TIntermAggregate(EOpSequence); TIntermAggregate* node = new TIntermAggregate(EOpSequence);
node->setLine(line); node->setLoc(loc);
TIntermConstantUnion* constIntNode; TIntermConstantUnion* constIntNode;
TIntermSequence &sequenceVector = node->getSequence(); TIntermSequence &sequenceVector = node->getSequence();
constUnion* unionArray; constUnion* unionArray;
@ -800,7 +813,7 @@ TIntermTyped* TIntermediate::addSwizzle(TVectorFields& fields, TSourceLoc line)
for (int i = 0; i < fields.num; i++) { for (int i = 0; i < fields.num; i++) {
unionArray = new constUnion[1]; unionArray = new constUnion[1];
unionArray->setIConst(fields.offsets[i]); unionArray->setIConst(fields.offsets[i]);
constIntNode = addConstantUnion(unionArray, TType(EbtInt, EvqConst), line); constIntNode = addConstantUnion(unionArray, TType(EbtInt, EvqConst), loc);
sequenceVector.push_back(constIntNode); sequenceVector.push_back(constIntNode);
} }
@ -810,10 +823,10 @@ TIntermTyped* TIntermediate::addSwizzle(TVectorFields& fields, TSourceLoc line)
// //
// Create loop nodes. // Create loop nodes.
// //
TIntermNode* TIntermediate::addLoop(TIntermNode* body, TIntermTyped* test, TIntermTyped* terminal, bool testFirst, TSourceLoc line) TIntermNode* TIntermediate::addLoop(TIntermNode* body, TIntermTyped* test, TIntermTyped* terminal, bool testFirst, TSourceLoc loc)
{ {
TIntermNode* node = new TIntermLoop(body, test, terminal, testFirst); TIntermNode* node = new TIntermLoop(body, test, terminal, testFirst);
node->setLine(line); node->setLoc(loc);
return node; return node;
} }
@ -821,15 +834,15 @@ TIntermNode* TIntermediate::addLoop(TIntermNode* body, TIntermTyped* test, TInte
// //
// Add branches. // Add branches.
// //
TIntermBranch* TIntermediate::addBranch(TOperator branchOp, TSourceLoc line) TIntermBranch* TIntermediate::addBranch(TOperator branchOp, TSourceLoc loc)
{ {
return addBranch(branchOp, 0, line); return addBranch(branchOp, 0, loc);
} }
TIntermBranch* TIntermediate::addBranch(TOperator branchOp, TIntermTyped* expression, TSourceLoc line) TIntermBranch* TIntermediate::addBranch(TOperator branchOp, TIntermTyped* expression, TSourceLoc loc)
{ {
TIntermBranch* node = new TIntermBranch(branchOp, expression); TIntermBranch* node = new TIntermBranch(branchOp, expression);
node->setLine(line); node->setLoc(loc);
return node; return node;
} }
@ -886,7 +899,7 @@ void TIntermediate::addSymbolLinkageNodes(TIntermNode* root, TIntermAggregate*&
linkage->setOperator(EOpLinkerObjects); linkage->setOperator(EOpLinkerObjects);
// Add a child to the root node for the linker objects // Add a child to the root node for the linker objects
growAggregate(root, linkage, 0); growAggregate(root, linkage);
} }
} }
@ -900,7 +913,7 @@ void TIntermediate::addSymbolLinkageNode(TIntermAggregate*& linkage, TSymbolTabl
void TIntermediate::addSymbolLinkageNode(TIntermAggregate*& linkage, const TVariable& variable) void TIntermediate::addSymbolLinkageNode(TIntermAggregate*& linkage, const TVariable& variable)
{ {
TIntermSymbol* node = new TIntermSymbol(variable.getUniqueId(), variable.getName(), variable.getType()); TIntermSymbol* node = new TIntermSymbol(variable.getUniqueId(), variable.getName(), variable.getType());
linkage = growAggregate(linkage, node, 0); linkage = growAggregate(linkage, node);
} }
// //
@ -1218,7 +1231,7 @@ bool TIntermBinary::promote(TInfoSink& infoSink)
setType(TType(basicType, EvqTemporary, right->getVectorSize())); setType(TType(basicType, EvqTemporary, right->getVectorSize()));
} }
} else { } else {
infoSink.info.message(EPrefixInternalError, "Missing elses", getLine()); infoSink.info.message(EPrefixInternalError, "Missing elses", getLoc());
return false; return false;
} }
break; break;
@ -1250,7 +1263,7 @@ bool TIntermBinary::promote(TInfoSink& infoSink)
op = EOpVectorTimesScalarAssign; op = EOpVectorTimesScalarAssign;
} }
} else { } else {
infoSink.info.message(EPrefixInternalError, "Missing elses", getLine()); infoSink.info.message(EPrefixInternalError, "Missing elses", getLoc());
return false; return false;
} }
break; break;
@ -1381,7 +1394,7 @@ void TIntermTyped::propagatePrecision(TPrecisionQualifier newPrecision)
TIntermTyped* TIntermediate::promoteConstantUnion(TBasicType promoteTo, TIntermConstantUnion* node) TIntermTyped* TIntermediate::promoteConstantUnion(TBasicType promoteTo, TIntermConstantUnion* node)
{ {
if (node->getType().isArray()) if (node->getType().isArray())
infoSink.info.message(EPrefixInternalError, "Cannot promote array", node->getLine()); infoSink.info.message(EPrefixInternalError, "Cannot promote array", node->getLoc());
constUnion *rightUnionArray = node->getUnionArrayPointer(); constUnion *rightUnionArray = node->getUnionArrayPointer();
int size = node->getType().getObjectSize(); int size = node->getType().getObjectSize();
@ -1408,7 +1421,7 @@ TIntermTyped* TIntermediate::promoteConstantUnion(TBasicType promoteTo, TIntermC
leftUnionArray[i].setDConst(static_cast<double>(rightUnionArray[i].getBConst())); leftUnionArray[i].setDConst(static_cast<double>(rightUnionArray[i].getBConst()));
break; break;
default: default:
infoSink.info.message(EPrefixInternalError, "Cannot promote", node->getLine()); infoSink.info.message(EPrefixInternalError, "Cannot promote", node->getLoc());
return 0; return 0;
} }
break; break;
@ -1428,7 +1441,7 @@ TIntermTyped* TIntermediate::promoteConstantUnion(TBasicType promoteTo, TIntermC
leftUnionArray[i] = rightUnionArray[i]; leftUnionArray[i] = rightUnionArray[i];
break; break;
default: default:
infoSink.info.message(EPrefixInternalError, "Cannot promote", node->getLine()); infoSink.info.message(EPrefixInternalError, "Cannot promote", node->getLoc());
return 0; return 0;
} }
break; break;
@ -1448,7 +1461,7 @@ TIntermTyped* TIntermediate::promoteConstantUnion(TBasicType promoteTo, TIntermC
leftUnionArray[i].setIConst(static_cast<int>(rightUnionArray[i].getDConst())); leftUnionArray[i].setIConst(static_cast<int>(rightUnionArray[i].getDConst()));
break; break;
default: default:
infoSink.info.message(EPrefixInternalError, "Cannot promote", node->getLine()); infoSink.info.message(EPrefixInternalError, "Cannot promote", node->getLoc());
return 0; return 0;
} }
break; break;
@ -1468,7 +1481,7 @@ TIntermTyped* TIntermediate::promoteConstantUnion(TBasicType promoteTo, TIntermC
leftUnionArray[i].setUConst(static_cast<unsigned int>(rightUnionArray[i].getDConst())); leftUnionArray[i].setUConst(static_cast<unsigned int>(rightUnionArray[i].getDConst()));
break; break;
default: default:
infoSink.info.message(EPrefixInternalError, "Cannot promote", node->getLine()); infoSink.info.message(EPrefixInternalError, "Cannot promote", node->getLoc());
return 0; return 0;
} }
break; break;
@ -1488,12 +1501,12 @@ TIntermTyped* TIntermediate::promoteConstantUnion(TBasicType promoteTo, TIntermC
leftUnionArray[i].setBConst(rightUnionArray[i].getDConst() != 0.0); leftUnionArray[i].setBConst(rightUnionArray[i].getDConst() != 0.0);
break; break;
default: default:
infoSink.info.message(EPrefixInternalError, "Cannot promote", node->getLine()); infoSink.info.message(EPrefixInternalError, "Cannot promote", node->getLoc());
return 0; return 0;
} }
break; break;
default: default:
infoSink.info.message(EPrefixInternalError, "Incorrect data type found", node->getLine()); infoSink.info.message(EPrefixInternalError, "Incorrect data type found", node->getLoc());
return 0; return 0;
} }
} }
@ -1501,7 +1514,7 @@ TIntermTyped* TIntermediate::promoteConstantUnion(TBasicType promoteTo, TIntermC
const TType& t = node->getType(); const TType& t = node->getType();
return addConstantUnion(leftUnionArray, TType(promoteTo, t.getQualifier().storage, t.getVectorSize(), t.getMatrixCols(), t.getMatrixRows()), return addConstantUnion(leftUnionArray, TType(promoteTo, t.getQualifier().storage, t.getVectorSize(), t.getMatrixCols(), t.getMatrixRows()),
node->getLine()); node->getLoc());
} }
void TIntermAggregate::addToPragmaTable(const TPragmaTable& pTable) void TIntermAggregate::addToPragmaTable(const TPragmaTable& pTable)

File diff suppressed because it is too large Load Diff

View File

@ -55,7 +55,9 @@ struct TPragma {
TPragmaTable pragmaTable; TPragmaTable pragmaTable;
}; };
namespace glslang {
class TScanContext;
};
// //
// The following are extra variables needed during parsing, grouped together so // The following are extra variables needed during parsing, grouped together so
@ -64,6 +66,7 @@ struct TPragma {
struct TParseContext { struct TParseContext {
TParseContext(TSymbolTable&, TIntermediate&, bool parsingBuiltins, int version, EProfile, EShLanguage, TInfoSink&, TParseContext(TSymbolTable&, TIntermediate&, bool parsingBuiltins, int version, EProfile, EShLanguage, TInfoSink&,
bool forwardCompatible = false, EShMessages messages = EShMsgDefault); bool forwardCompatible = false, EShMessages messages = EShMsgDefault);
glslang::TScanContext *scanContext;
TIntermediate& intermediate; // to hold and build a parse tree TIntermediate& intermediate; // to hold and build a parse tree
TSymbolTable& symbolTable; // symbol table that goes with the current language, version, and profile TSymbolTable& symbolTable; // symbol table that goes with the current language, version, and profile
TInfoSink& infoSink; TInfoSink& infoSink;
@ -71,7 +74,6 @@ struct TParseContext {
TIntermNode* treeRoot; // root of parse tree being created TIntermNode* treeRoot; // root of parse tree being created
TIntermAggregate *linkage; // aggregate node of objects the linker may need, if not reference by the rest of the AST TIntermAggregate *linkage; // aggregate node of objects the linker may need, if not reference by the rest of the AST
int numErrors; // number of compile-time errors encountered int numErrors; // number of compile-time errors encountered
bool lexAfterType; // true if we've recognized a type, so can only be looking for an identifier
int loopNestingLevel; // 0 if outside all loops int loopNestingLevel; // 0 if outside all loops
int structNestingLevel; // 0 if outside blocks and structures int structNestingLevel; // 0 if outside blocks and structures
TList<TIntermSequence*> switchSequenceStack; // case, node, case, case, node, ...; ensure only one node between cases; stack of them for nesting TList<TIntermSequence*> switchSequenceStack; // case, node, case, case, node, ...; ensure only one node between cases; stack of them for nesting
@ -91,7 +93,7 @@ struct TParseContext {
static const int maxSamplerIndex = EsdNumDims * (EbtNumTypes * (2 * 2)); // see computeSamplerTypeIndex() static const int maxSamplerIndex = EsdNumDims * (EbtNumTypes * (2 * 2)); // see computeSamplerTypeIndex()
TPrecisionQualifier defaultSamplerPrecision[maxSamplerIndex]; TPrecisionQualifier defaultSamplerPrecision[maxSamplerIndex];
TString HashErrMsg; TString HashErrMsg;
bool AfterEOF; bool afterEOF;
const TString* blockName; const TString* blockName;
TQualifier globalUniformDefaults; TQualifier globalUniformDefaults;
TQualifier globalInputDefaults; TQualifier globalInputDefaults;
@ -100,93 +102,91 @@ struct TParseContext {
void initializeExtensionBehavior(); void initializeExtensionBehavior();
const char* getPreamble(); const char* getPreamble();
bool parseShaderStrings(char* strings[], int strLen[], int numStrings);
void C_DECL error(TSourceLoc, const char *szReason, const char *szToken, void C_DECL error(TSourceLoc, const char *szReason, const char *szToken,
const char *szExtraInfoFormat, ...); const char *szExtraInfoFormat, ...);
void C_DECL warn(TSourceLoc, const char *szReason, const char *szToken, void C_DECL warn(TSourceLoc, const char *szReason, const char *szToken,
const char *szExtraInfoFormat, ...); const char *szExtraInfoFormat, ...);
bool reservedErrorCheck(int line, const TString& identifier); bool reservedErrorCheck(TSourceLoc, const TString& identifier);
TIntermTyped* handleVariable(int line, TSymbol* symbol, TString* string); TIntermTyped* handleVariable(TSourceLoc, TSymbol* symbol, TString* string);
bool parseVectorFields(const TString&, int vecSize, TVectorFields&, int line); bool parseVectorFields(TSourceLoc, const TString&, int vecSize, TVectorFields&);
void assignError(int line, const char* op, TString left, TString right); void assignError(TSourceLoc, const char* op, TString left, TString right);
void unaryOpError(int line, const char* op, TString operand); void unaryOpError(TSourceLoc, const char* op, TString operand);
void binaryOpError(int line, const char* op, TString left, TString right); void binaryOpError(TSourceLoc, const char* op, TString left, TString right);
void variableCheck(TIntermTyped*& nodePtr); void variableCheck(TIntermTyped*& nodePtr);
bool lValueErrorCheck(int line, const char* op, TIntermTyped*); bool lValueErrorCheck(TSourceLoc, const char* op, TIntermTyped*);
void constCheck(TIntermTyped* node, const char* token); void constCheck(TIntermTyped* node, const char* token);
void integerCheck(TIntermTyped* node, const char* token); void integerCheck(TIntermTyped* node, const char* token);
void globalCheck(int line, bool global, const char* token); void globalCheck(TSourceLoc, bool global, const char* token);
bool constructorError(int line, TIntermNode*, TFunction&, TOperator, TType&); bool constructorError(TSourceLoc, TIntermNode*, TFunction&, TOperator, TType&);
void arraySizeCheck(int line, TIntermTyped* expr, int& size); void arraySizeCheck(TSourceLoc, TIntermTyped* expr, int& size);
bool arrayQualifierError(int line, const TPublicType&); bool arrayQualifierError(TSourceLoc, const TPublicType&);
void arraySizeRequiredCheck(int line, int& size); void arraySizeRequiredCheck(TSourceLoc, int& size);
void arrayDimError(int line); void arrayDimError(TSourceLoc);
void arrayDimCheck(int line, TArraySizes sizes1, TArraySizes sizes2); void arrayDimCheck(TSourceLoc, TArraySizes sizes1, TArraySizes sizes2);
void arrayDimCheck(int line, const TType*, TArraySizes); void arrayDimCheck(TSourceLoc, const TType*, TArraySizes);
void arrayCheck(int line, TString& identifier, const TPublicType&, TVariable*& variable); void arrayCheck(TSourceLoc, TString& identifier, const TPublicType&, TVariable*& variable);
bool insertBuiltInArrayAtGlobalLevel(); bool insertBuiltInArrayAtGlobalLevel();
bool voidErrorCheck(int, const TString&, const TPublicType&); bool voidErrorCheck(TSourceLoc, const TString&, const TPublicType&);
void boolCheck(int, const TIntermTyped*); void boolCheck(TSourceLoc, const TIntermTyped*);
void boolCheck(int, const TPublicType&); void boolCheck(TSourceLoc, const TPublicType&);
bool samplerErrorCheck(int line, const TPublicType& pType, const char* reason); bool samplerErrorCheck(TSourceLoc, const TPublicType& pType, const char* reason);
void globalQualifierFix(int line, TQualifier&, const TPublicType&); void globalQualifierFix(TSourceLoc, TQualifier&, const TPublicType&);
bool structQualifierErrorCheck(int line, const TPublicType& pType); bool structQualifierErrorCheck(TSourceLoc, const TPublicType& pType);
void mergeQualifiers(int line, TQualifier& dst, const TQualifier& src, bool force); void mergeQualifiers(TSourceLoc, TQualifier& dst, const TQualifier& src, bool force);
void setDefaultPrecision(int line, TPublicType&, TPrecisionQualifier); void setDefaultPrecision(TSourceLoc, TPublicType&, TPrecisionQualifier);
int computeSamplerTypeIndex(TSampler&); int computeSamplerTypeIndex(TSampler&);
TPrecisionQualifier getDefaultPrecision(TPublicType&); TPrecisionQualifier getDefaultPrecision(TPublicType&);
void precisionQualifierCheck(int line, TPublicType&); void precisionQualifierCheck(TSourceLoc, TPublicType&);
void parameterSamplerCheck(int line, TStorageQualifier qualifier, const TType& type); void parameterSamplerCheck(TSourceLoc, TStorageQualifier qualifier, const TType& type);
bool containsSampler(const TType& type); bool containsSampler(const TType& type);
void nonInitConstCheck(int line, TString& identifier, TPublicType& type); void nonInitConstCheck(TSourceLoc, TString& identifier, TPublicType& type);
void nonInitCheck(int line, TString& identifier, TPublicType& type); void nonInitCheck(TSourceLoc, TString& identifier, TPublicType& type);
void paramCheck(int line, TStorageQualifier qualifier, TType* type); void paramCheck(TSourceLoc, TStorageQualifier qualifier, TType* type);
void nestedBlockCheck(int line); void nestedBlockCheck(TSourceLoc);
void nestedStructCheck(int line); void nestedStructCheck(TSourceLoc);
void setLayoutQualifier(int line, TPublicType&, TString&); void setLayoutQualifier(TSourceLoc, TPublicType&, TString&);
void setLayoutQualifier(int line, TPublicType&, TString&, int); void setLayoutQualifier(TSourceLoc, TPublicType&, TString&, int);
void mergeLayoutQualifiers(int line, TQualifier& dest, const TQualifier& src); void mergeLayoutQualifiers(TSourceLoc, TQualifier& dest, const TQualifier& src);
const TFunction* findFunction(int line, TFunction* pfnCall, bool *builtIn = 0); const TFunction* findFunction(TSourceLoc, TFunction* pfnCall, bool *builtIn = 0);
bool executeInitializerError(TSourceLoc line, TString& identifier, TPublicType& pType, bool executeInitializerError(TSourceLoc, TString& identifier, TPublicType& pType,
TIntermTyped* initializer, TIntermNode*& intermNode, TVariable* variable = 0); TIntermTyped* initializer, TIntermNode*& intermNode, TVariable* variable = 0);
TIntermTyped* addConstructor(TIntermNode*, const TType&, TOperator, TFunction*, TSourceLoc); TIntermTyped* addConstructor(TIntermNode*, const TType&, TOperator, TFunction*, TSourceLoc);
TIntermTyped* constructStruct(TIntermNode*, const TType&, int, TSourceLoc); TIntermTyped* constructStruct(TIntermNode*, const TType&, int, TSourceLoc);
TIntermTyped* constructBuiltIn(const TType&, TOperator, TIntermNode*, TSourceLoc, bool subset); TIntermTyped* constructBuiltIn(const TType&, TOperator, TIntermNode*, TSourceLoc, bool subset);
void addBlock(int line, TTypeList& typeList, const TString* instanceName = 0, TArraySizes arraySizes = 0); void addBlock(TSourceLoc, TTypeList& typeList, const TString* instanceName = 0, TArraySizes arraySizes = 0);
void addQualifierToExisting(int line, TQualifier, const TString& identifier); void addQualifierToExisting(TSourceLoc, TQualifier, const TString& identifier);
void addQualifierToExisting(int line, TQualifier, TIdentifierList&); void addQualifierToExisting(TSourceLoc, TQualifier, TIdentifierList&);
void updateQualifierDefaults(TQualifier); void updateQualifierDefaults(TQualifier);
void updateQualifierDefaults(int line, TQualifier); void updateQualifierDefaults(TSourceLoc, TQualifier);
void updateTypedDefaults(int line, TQualifier, const TString* id); void updateTypedDefaults(TSourceLoc, TQualifier, const TString* id);
void wrapupSwitchSubsequence(TIntermAggregate* statements, TIntermNode* branchNode); void wrapupSwitchSubsequence(TIntermAggregate* statements, TIntermNode* branchNode);
TIntermNode* addSwitch(int line, TIntermTyped* expression, TIntermAggregate* body); TIntermNode* addSwitch(TSourceLoc, TIntermTyped* expression, TIntermAggregate* body);
TIntermTyped* addConstVectorNode(TVectorFields&, TIntermTyped*, TSourceLoc); TIntermTyped* addConstVectorNode(TVectorFields&, TIntermTyped*, TSourceLoc);
TIntermTyped* addConstMatrixNode(int , TIntermTyped*, TSourceLoc); TIntermTyped* addConstMatrixNode(int , TIntermTyped*, TSourceLoc);
TIntermTyped* addConstArrayNode(int index, TIntermTyped* node, TSourceLoc line); TIntermTyped* addConstArrayNode(int index, TIntermTyped* node, TSourceLoc);
TIntermTyped* addConstStruct(TString& , TIntermTyped*, TSourceLoc); TIntermTyped* addConstStruct(TString& , TIntermTyped*, TSourceLoc);
bool arraySetMaxSize(TIntermSymbol*, TType*, int, bool, TSourceLoc); bool arraySetMaxSize(TIntermSymbol*, TType*, int, bool, TSourceLoc);
void requireProfile(int line, EProfileMask profileMask, const char *featureDesc); void requireProfile(TSourceLoc, EProfileMask profileMask, const char *featureDesc);
void requireStage(int line, EShLanguageMask languageMask, const char *featureDesc); void requireStage(TSourceLoc, EShLanguageMask languageMask, const char *featureDesc);
void profileRequires(int line, EProfile callingProfile, int minVersion, int numExtensions, const char* extensions[], const char *featureDesc); void profileRequires(TSourceLoc, EProfile callingProfile, int minVersion, int numExtensions, const char* extensions[], const char *featureDesc);
void profileRequires(int line, EProfile callingProfile, int minVersion, const char* extension, const char *featureDesc); void profileRequires(TSourceLoc, EProfile callingProfile, int minVersion, const char* extension, const char *featureDesc);
void checkDeprecated(int line, EProfile callingProfile, int depVersion, const char *featureDesc); void checkDeprecated(TSourceLoc, EProfile callingProfile, int depVersion, const char *featureDesc);
void requireNotRemoved(int line, EProfile callingProfile, int removedVersion, const char *featureDesc); void requireNotRemoved(TSourceLoc, EProfile callingProfile, int removedVersion, const char *featureDesc);
void fullIntegerCheck(int line, const char* op); void fullIntegerCheck(TSourceLoc, const char* op);
void doubleCheck(int line, const char* op); void doubleCheck(TSourceLoc, const char* op);
}; };
int PaParseStrings(char* argv[], int strLen[], int argc, TParseContext&, const char* preamble);
int PaParseComment(int &lineno, TParseContext&);
void ResetFlex();
typedef TParseContext* TParseContextPointer; typedef TParseContext* TParseContextPointer;
TParseContextPointer& ThreadLocalParseContext(); TParseContextPointer& ThreadLocalParseContext();
// TODO: threading:
typedef struct TThreadParseContextRec typedef struct TThreadParseContextRec
{ {
TParseContext *lpGlobalParseContext; TParseContext *lpGlobalParseContext;

View File

@ -34,9 +34,24 @@
//POSSIBILITY OF SUCH DAMAGE. //POSSIBILITY OF SUCH DAMAGE.
// //
//
// GLSL scanning, leveraging the scanning done by the preprocessor.
//
#include <string.h> #include <string.h>
#include "Scan.h" #include "Scan.h"
#include "Include/Types.h"
#include "SymbolTable.h"
#include "glslang_tab.cpp.h"
#include "ParseHelper.h"
#include "ScanContext.h"
// preprocessor includes
extern "C" {
#include "preprocessor/parser.h"
#include "preprocessor/preprocess.h"
}
namespace glslang { namespace glslang {
@ -138,10 +153,14 @@ void ConsumeWhitespaceComment(TInputScanner& input, bool& foundNonSpaceTab)
} while (true); } while (true);
} }
// Returns true if there was non-white space (e.g., a comment, newline) before the #version; // Returns true if there was non-white space (e.g., a comment, newline) before the #version
// otherwise, returns true. // or no #version was found; otherwise, returns false. There is no error case, it always
// succeeds, but will leave version == 0 if no #version was found.
//
// N.B. does not attempt to leave input in any particular known state. The assumption
// is that scanning will start anew, following the rules for the chosen version/profile,
// and with a corresponding parsing context.
// //
// N.B. does not attempt to leave input in any particular known state
bool ScanVersion(TInputScanner& input, int& version, EProfile& profile) bool ScanVersion(TInputScanner& input, int& version, EProfile& profile)
{ {
// This function doesn't have to get all the semantics correct, // This function doesn't have to get all the semantics correct,
@ -214,3 +233,793 @@ bool ScanVersion(TInputScanner& input, int& version, EProfile& profile)
} }
}; // end glslang namespace }; // end glslang namespace
namespace glslang {
// This gets filled in by the preprocessor scanner.
class TPpToken{
public:
yystypepp lexer;
};
// Fill this in when doing glslang-level scanning, to hand back to the parser.
class TParserToken {
public:
explicit TParserToken(YYSTYPE& b) : sType(b) { }
YYSTYPE& sType;
};
}; // end namespace glslang
// This is the function the glslang parser (i.e., bison) calls to get its next token
int yylex(YYSTYPE* glslangTokenDesc, TParseContext& parseContext)
{
glslang::TParserToken token(*glslangTokenDesc);
return parseContext.scanContext->tokenize(token);
}
namespace {
// A single global usable by all threads, by all versions, by all languages.
// After a single process-level initialization, this is read only and thread safe
std::map<std::string, int>* KeywordMap = 0;
std::set<std::string>* ReservedSet = 0;
};
namespace glslang {
void TScanContext::fillInKeywordMap()
{
if (KeywordMap != 0) {
// this is really an error, as this should called only once per process
// but, the only risk is if two threads called simultaneously
return;
}
KeywordMap = new std::map<std::string, int>;
(*KeywordMap)["const"] = CONST;
(*KeywordMap)["uniform"] = UNIFORM;
(*KeywordMap)["in"] = IN;
(*KeywordMap)["out"] = OUT;
(*KeywordMap)["inout"] = INOUT;
(*KeywordMap)["struct"] = STRUCT;
(*KeywordMap)["break"] = BREAK;
(*KeywordMap)["continue"] = CONTINUE;
(*KeywordMap)["do"] = DO;
(*KeywordMap)["for"] = FOR;
(*KeywordMap)["while"] = WHILE;
(*KeywordMap)["switch"] = SWITCH;
(*KeywordMap)["case"] = CASE;
(*KeywordMap)["default"] = DEFAULT;
(*KeywordMap)["if"] = IF;
(*KeywordMap)["else"] = ELSE;
(*KeywordMap)["discard"] = DISCARD;
(*KeywordMap)["return"] = RETURN;
(*KeywordMap)["void"] = VOID;
(*KeywordMap)["bool"] = BOOL;
(*KeywordMap)["float"] = FLOAT;
(*KeywordMap)["int"] = INT;
(*KeywordMap)["bvec2"] = BVEC2;
(*KeywordMap)["bvec3"] = BVEC3;
(*KeywordMap)["bvec4"] = BVEC4;
(*KeywordMap)["vec2"] = VEC2;
(*KeywordMap)["vec3"] = VEC3;
(*KeywordMap)["vec4"] = VEC4;
(*KeywordMap)["ivec2"] = IVEC2;
(*KeywordMap)["ivec3"] = IVEC3;
(*KeywordMap)["ivec4"] = IVEC4;
(*KeywordMap)["mat2"] = MAT2;
(*KeywordMap)["mat3"] = MAT3;
(*KeywordMap)["mat4"] = MAT4;
(*KeywordMap)["sampler2D"] = SAMPLER2D;
(*KeywordMap)["samplerCube"] = SAMPLERCUBE;
(*KeywordMap)["true"] = BOOLCONSTANT;
(*KeywordMap)["false"] = BOOLCONSTANT;
(*KeywordMap)["attribute"] = ATTRIBUTE;
(*KeywordMap)["varying"] = VARYING;
(*KeywordMap)["buffer"] = BUFFER;
(*KeywordMap)["coherent"] = COHERENT;
(*KeywordMap)["restrict"] = RESTRICT;
(*KeywordMap)["readonly"] = READONLY;
(*KeywordMap)["writeonly"] = WRITEONLY;
(*KeywordMap)["atomic_uint"] = ATOMIC_UINT;
(*KeywordMap)["volatile"] = VOLATILE;
(*KeywordMap)["layout"] = LAYOUT;
(*KeywordMap)["shared"] = SHARED;
(*KeywordMap)["patch"] = PATCH;
(*KeywordMap)["sample"] = SAMPLE;
(*KeywordMap)["subroutine"] = SUBROUTINE;
(*KeywordMap)["highp"] = HIGH_PRECISION;
(*KeywordMap)["mediump"] = MEDIUM_PRECISION;
(*KeywordMap)["lowp"] = LOW_PRECISION;
(*KeywordMap)["precision"] = PRECISION;
(*KeywordMap)["mat2x2"] = MAT2X2;
(*KeywordMap)["mat2x3"] = MAT2X3;
(*KeywordMap)["mat2x4"] = MAT2X4;
(*KeywordMap)["mat3x2"] = MAT3X2;
(*KeywordMap)["mat3x3"] = MAT3X3;
(*KeywordMap)["mat3x4"] = MAT3X4;
(*KeywordMap)["mat4x2"] = MAT4X2;
(*KeywordMap)["mat4x3"] = MAT4X3;
(*KeywordMap)["mat4x4"] = MAT4X4;
(*KeywordMap)["dmat2"] = DMAT2;
(*KeywordMap)["dmat3"] = DMAT3;
(*KeywordMap)["dmat4"] = DMAT4;
(*KeywordMap)["dmat2x2"] = DMAT2X2;
(*KeywordMap)["dmat2x3"] = DMAT2X3;
(*KeywordMap)["dmat2x4"] = DMAT2X4;
(*KeywordMap)["dmat3x2"] = DMAT3X2;
(*KeywordMap)["dmat3x3"] = DMAT3X3;
(*KeywordMap)["dmat3x4"] = DMAT3X4;
(*KeywordMap)["dmat4x2"] = DMAT4X2;
(*KeywordMap)["dmat4x3"] = DMAT4X3;
(*KeywordMap)["dmat4x4"] = DMAT4X4;
(*KeywordMap)["image1D"] = IMAGE1D;
(*KeywordMap)["iimage1D"] = IIMAGE1D;
(*KeywordMap)["uimage1D"] = UIMAGE1D;
(*KeywordMap)["image2D"] = IMAGE2D;
(*KeywordMap)["iimage2D"] = IIMAGE2D;
(*KeywordMap)["uimage2D"] = UIMAGE2D;
(*KeywordMap)["image3D"] = IMAGE3D;
(*KeywordMap)["iimage3D"] = IIMAGE3D;
(*KeywordMap)["uimage3D"] = UIMAGE3D;
(*KeywordMap)["image2DRect"] = IMAGE2DRECT;
(*KeywordMap)["iimage2DRect"] = IIMAGE2DRECT;
(*KeywordMap)["uimage2DRect"] = UIMAGE2DRECT;
(*KeywordMap)["imageCube"] = IMAGECUBE;
(*KeywordMap)["iimageCube"] = IIMAGECUBE;
(*KeywordMap)["uimageCube"] = UIMAGECUBE;
(*KeywordMap)["imageBuffer"] = IMAGEBUFFER;
(*KeywordMap)["iimageBuffer"] = IIMAGEBUFFER;
(*KeywordMap)["uimageBuffer"] = UIMAGEBUFFER;
(*KeywordMap)["image1DArray"] = IMAGE1DARRAY;
(*KeywordMap)["iimage1DArray"] = IIMAGE1DARRAY;
(*KeywordMap)["uimage1DArray"] = UIMAGE1DARRAY;
(*KeywordMap)["image2DArray"] = IMAGE2DARRAY;
(*KeywordMap)["iimage2DArray"] = IIMAGE2DARRAY;
(*KeywordMap)["uimage2DArray"] = UIMAGE2DARRAY;
(*KeywordMap)["imageCubeArray"] = IMAGECUBEARRAY;
(*KeywordMap)["iimageCubeArray"] = IIMAGECUBEARRAY;
(*KeywordMap)["uimageCubeArray"] = UIMAGECUBEARRAY;
(*KeywordMap)["image2DMS"] = IMAGE2DMS;
(*KeywordMap)["iimage2DMS"] = IIMAGE2DMS;
(*KeywordMap)["uimage2DMS"] = UIMAGE2DMS;
(*KeywordMap)["image2DMSArray"] = IMAGE2DMSARRAY;
(*KeywordMap)["iimage2DMSArray"] = IIMAGE2DMSARRAY;
(*KeywordMap)["uimage2DMSArray"] = UIMAGE2DMSARRAY;
(*KeywordMap)["double"] = DOUBLE;
(*KeywordMap)["dvec2"] = DVEC2;
(*KeywordMap)["dvec3"] = DVEC3;
(*KeywordMap)["dvec4"] = DVEC4;
(*KeywordMap)["samplerCubeArray"] = SAMPLERCUBEARRAY;
(*KeywordMap)["samplerCubeArrayShadow"] = SAMPLERCUBEARRAYSHADOW;
(*KeywordMap)["isamplerCubeArray"] = ISAMPLERCUBEARRAY;
(*KeywordMap)["usamplerCubeArray"] = USAMPLERCUBEARRAY;
(*KeywordMap)["sampler1DArrayShadow"] = SAMPLER1DARRAYSHADOW;
(*KeywordMap)["isampler1DArray"] = ISAMPLER1DARRAY;
(*KeywordMap)["usampler1D"] = USAMPLER1D;
(*KeywordMap)["isampler1D"] = ISAMPLER1D;
(*KeywordMap)["usampler1DArray"] = USAMPLER1DARRAY;
(*KeywordMap)["samplerBuffer"] = SAMPLERBUFFER;
(*KeywordMap)["uint"] = UINT;
(*KeywordMap)["uvec2"] = UVEC2;
(*KeywordMap)["uvec3"] = UVEC3;
(*KeywordMap)["uvec4"] = UVEC4;
(*KeywordMap)["samplerCubeShadow"] = SAMPLERCUBESHADOW;
(*KeywordMap)["sampler2DArray"] = SAMPLER2DARRAY;
(*KeywordMap)["sampler2DArrayShadow"] = SAMPLER2DARRAYSHADOW;
(*KeywordMap)["isampler2D"] = ISAMPLER2D;
(*KeywordMap)["isampler3D"] = ISAMPLER3D;
(*KeywordMap)["isamplerCube"] = ISAMPLERCUBE;
(*KeywordMap)["isampler2DArray"] = ISAMPLER2DARRAY;
(*KeywordMap)["usampler2D"] = USAMPLER2D;
(*KeywordMap)["usampler3D"] = USAMPLER3D;
(*KeywordMap)["usamplerCube"] = USAMPLERCUBE;
(*KeywordMap)["usampler2DArray"] = USAMPLER2DARRAY;
(*KeywordMap)["isampler2DRect"] = ISAMPLER2DRECT;
(*KeywordMap)["usampler2DRect"] = USAMPLER2DRECT;
(*KeywordMap)["isamplerBuffer"] = ISAMPLERBUFFER;
(*KeywordMap)["usamplerBuffer"] = USAMPLERBUFFER;
(*KeywordMap)["sampler2DMS"] = SAMPLER2DMS;
(*KeywordMap)["isampler2DMS"] = ISAMPLER2DMS;
(*KeywordMap)["usampler2DMS"] = USAMPLER2DMS;
(*KeywordMap)["sampler2DMSArray"] = SAMPLER2DMSARRAY;
(*KeywordMap)["isampler2DMSArray"] = ISAMPLER2DMSARRAY;
(*KeywordMap)["usampler2DMSArray"] = USAMPLER2DMSARRAY;
(*KeywordMap)["sampler1D"] = SAMPLER1D;
(*KeywordMap)["sampler1DShadow"] = SAMPLER1DSHADOW;
(*KeywordMap)["sampler3D"] = SAMPLER3D;
(*KeywordMap)["sampler2DShadow"] = SAMPLER2DSHADOW;
(*KeywordMap)["sampler2DRect"] = SAMPLER2DRECT;
(*KeywordMap)["sampler2DRectShadow"] = SAMPLER2DRECTSHADOW;
(*KeywordMap)["sampler1DArray"] = SAMPLER1DARRAY;
(*KeywordMap)["noperspective"] = NOPERSPECTIVE;
(*KeywordMap)["smooth"] = SMOOTH;
(*KeywordMap)["flat"] = FLAT;
(*KeywordMap)["centroid"] = CENTROID;
(*KeywordMap)["precise"] = PRECISE;
(*KeywordMap)["invariant"] = INVARIANT;
(*KeywordMap)["packed"] = PACKED;
(*KeywordMap)["resource"] = RESOURCE;
(*KeywordMap)["superp"] = SUPERP;
ReservedSet = new std::set<std::string>;
ReservedSet->insert("common");
ReservedSet->insert("partition");
ReservedSet->insert("active");
ReservedSet->insert("asm");
ReservedSet->insert("class");
ReservedSet->insert("union");
ReservedSet->insert("enum");
ReservedSet->insert("typedef");
ReservedSet->insert("template");
ReservedSet->insert("this");
ReservedSet->insert("goto");
ReservedSet->insert("inline");
ReservedSet->insert("noinline");
ReservedSet->insert("public");
ReservedSet->insert("static");
ReservedSet->insert("extern");
ReservedSet->insert("external");
ReservedSet->insert("interface");
ReservedSet->insert("long");
ReservedSet->insert("short");
ReservedSet->insert("half");
ReservedSet->insert("fixed");
ReservedSet->insert("unsigned");
ReservedSet->insert("input");
ReservedSet->insert("output");
ReservedSet->insert("hvec2");
ReservedSet->insert("hvec3");
ReservedSet->insert("hvec4");
ReservedSet->insert("fvec2");
ReservedSet->insert("fvec3");
ReservedSet->insert("fvec4");
ReservedSet->insert("sampler3DRect");
ReservedSet->insert("filter");
ReservedSet->insert("sizeof");
ReservedSet->insert("cast");
ReservedSet->insert("namespace");
ReservedSet->insert("using");
}
int TScanContext::tokenize(TParserToken& token)
{
parserToken = &token;
TPpToken ppTokenStorage;
ppToken = &ppTokenStorage;
tokenText = PpTokenize(&ppToken->lexer);
loc.string = cpp->tokenLoc->file;
loc.line = cpp->tokenLoc->line;
parserToken->sType.lex.loc = loc;
switch (ppToken->lexer.ppToken) {
case ';': afterType = false; return SEMICOLON;
case ',': afterType = false; return COMMA;
case ':': return COLON;
case '=': afterType = false; return EQUAL;
case '(': afterType = false; return LEFT_PAREN;
case ')': afterType = false; return RIGHT_PAREN;
case '.': field = true; return DOT;
case '!': return BANG;
case '-': return DASH;
case '~': return TILDE;
case '+': return PLUS;
case '*': return STAR;
case '/': return SLASH;
case '%': return PERCENT;
case '<': return LEFT_ANGLE;
case '>': return RIGHT_ANGLE;
case '|': return VERTICAL_BAR;
case '^': return CARET;
case '&': return AMPERSAND;
case '?': return QUESTION;
case '[': return LEFT_BRACKET;
case ']': return RIGHT_BRACKET;
case '{': return LEFT_BRACE;
case '}': return RIGHT_BRACE;
case CPP_AND_OP: return AND_OP;
case CPP_SUB_ASSIGN: return SUB_ASSIGN;
case CPP_MOD_ASSIGN: return MOD_ASSIGN;
case CPP_ADD_ASSIGN: return ADD_ASSIGN;
case CPP_DIV_ASSIGN: return DIV_ASSIGN;
case CPP_MUL_ASSIGN: return MUL_ASSIGN;
case CPP_EQ_OP: return EQ_OP;
case CPP_XOR_OP: return XOR_OP;
case CPP_GE_OP: return GE_OP;
case CPP_RIGHT_OP: return RIGHT_OP;
case CPP_LE_OP: return LE_OP;
case CPP_LEFT_OP: return LEFT_OP;
case CPP_DEC_OP: return DEC_OP;
case CPP_NE_OP: return NE_OP;
case CPP_OR_OP: return OR_OP;
case CPP_INC_OP: return INC_OP;
case CPP_RIGHT_ASSIGN: return RIGHT_ASSIGN;
case CPP_LEFT_ASSIGN: return LEFT_ASSIGN;
case CPP_AND_ASSIGN: return AND_ASSIGN;
case CPP_OR_ASSIGN: return OR_ASSIGN;
case CPP_XOR_ASSIGN: return XOR_ASSIGN;
case CPP_INTCONSTANT: parserToken->sType.lex.i = ppToken->lexer.sc_int; return INTCONSTANT;
case CPP_UINTCONSTANT: parserToken->sType.lex.i = ppToken->lexer.sc_int; return UINTCONSTANT;
case CPP_FLOATCONSTANT: parserToken->sType.lex.d = ppToken->lexer.sc_dval; return FLOATCONSTANT;
case CPP_DOUBLECONSTANT: parserToken->sType.lex.d = ppToken->lexer.sc_dval; return DOUBLECONSTANT;
case CPP_IDENTIFIER: return tokenizeIdentifier();
case EOF: return 0;
default:
parseContext.infoSink.info.message(EPrefixInternalError, "Unknown PP token", loc);
return 0;
}
}
int TScanContext::tokenizeIdentifier()
{
if (ReservedSet->find(tokenText) != ReservedSet->end())
return reservedWord();
keyword = (*KeywordMap)[tokenText];
if (keyword == 0) {
// Should have an identifier of some sort
return identifierOrType();
}
field = false;
switch (keyword) {
case CONST:
case UNIFORM:
case IN:
case OUT:
case INOUT:
case STRUCT:
case BREAK:
case CONTINUE:
case DO:
case FOR:
case WHILE:
case IF:
case ELSE:
case DISCARD:
case RETURN:
case CASE:
return keyword;
case SWITCH:
case DEFAULT:
if (parseContext.profile == EEsProfile && parseContext.version < 300 ||
parseContext.profile != EEsProfile && parseContext.version < 130)
reservedWord();
return keyword;
case VOID:
case BOOL:
case FLOAT:
case INT:
case BVEC2:
case BVEC3:
case BVEC4:
case VEC2:
case VEC3:
case VEC4:
case IVEC2:
case IVEC3:
case IVEC4:
case MAT2:
case MAT3:
case MAT4:
case SAMPLER2D:
case SAMPLERCUBE:
afterType = true;
return keyword;
case BOOLCONSTANT:
if (strcmp("true", tokenText) == 0)
parserToken->sType.lex.b = true;
else
parserToken->sType.lex.b = false;
return keyword;
case ATTRIBUTE:
case VARYING:
if (parseContext.profile == EEsProfile && parseContext.version >= 300)
reservedWord();
return keyword;
case BUFFER:
if (parseContext.version < 430)
return identifierOrType();
return keyword;
case COHERENT:
case RESTRICT:
case READONLY:
case WRITEONLY:
case ATOMIC_UINT:
return es30ReservedFromGLSL(420);
case VOLATILE:
if (parseContext.profile == EEsProfile || parseContext.version < 420)
reservedWord();
return keyword;
case LAYOUT:
case SHARED:
if (parseContext.profile == EEsProfile && parseContext.version < 300 ||
parseContext.profile != EEsProfile && parseContext.version < 140)
return identifierOrType();
return keyword;
case PATCH:
case SAMPLE:
case SUBROUTINE:
return es30ReservedFromGLSL(400);
case HIGH_PRECISION:
case MEDIUM_PRECISION:
case LOW_PRECISION:
case PRECISION:
return precisionKeyword();
case MAT2X2:
case MAT2X3:
case MAT2X4:
case MAT3X2:
case MAT3X3:
case MAT3X4:
case MAT4X2:
case MAT4X3:
case MAT4X4:
return matNxM();
case DMAT2:
case DMAT3:
case DMAT4:
case DMAT2X2:
case DMAT2X3:
case DMAT2X4:
case DMAT3X2:
case DMAT3X3:
case DMAT3X4:
case DMAT4X2:
case DMAT4X3:
case DMAT4X4:
return dMat();
case IMAGE1D:
case IIMAGE1D:
case UIMAGE1D:
case IMAGE2D:
case IIMAGE2D:
case UIMAGE2D:
case IMAGE3D:
case IIMAGE3D:
case UIMAGE3D:
case IMAGE2DRECT:
case IIMAGE2DRECT:
case UIMAGE2DRECT:
case IMAGECUBE:
case IIMAGECUBE:
case UIMAGECUBE:
case IMAGEBUFFER:
case IIMAGEBUFFER:
case UIMAGEBUFFER:
case IMAGE1DARRAY:
case IIMAGE1DARRAY:
case UIMAGE1DARRAY:
case IMAGE2DARRAY:
case IIMAGE2DARRAY:
case UIMAGE2DARRAY:
return firstGenerationImage();
case IMAGECUBEARRAY:
case IIMAGECUBEARRAY:
case UIMAGECUBEARRAY:
case IMAGE2DMS:
case IIMAGE2DMS:
case UIMAGE2DMS:
case IMAGE2DMSARRAY:
case IIMAGE2DMSARRAY:
case UIMAGE2DMSARRAY:
return secondGenerationImage();
case DOUBLE:
case DVEC2:
case DVEC3:
case DVEC4:
case SAMPLERCUBEARRAY:
case SAMPLERCUBEARRAYSHADOW:
case ISAMPLERCUBEARRAY:
case USAMPLERCUBEARRAY:
afterType = true;
if (parseContext.profile == EEsProfile || parseContext.version < 400)
reservedWord();
return keyword;
case ISAMPLER1D:
case ISAMPLER1DARRAY:
case SAMPLER1DARRAYSHADOW:
case USAMPLER1D:
case USAMPLER1DARRAY:
case SAMPLERBUFFER:
afterType = true;
return es30ReservedFromGLSL(130);
case UINT:
case UVEC2:
case UVEC3:
case UVEC4:
case SAMPLERCUBESHADOW:
case SAMPLER2DARRAY:
case SAMPLER2DARRAYSHADOW:
case ISAMPLER2D:
case ISAMPLER3D:
case ISAMPLERCUBE:
case ISAMPLER2DARRAY:
case USAMPLER2D:
case USAMPLER3D:
case USAMPLERCUBE:
case USAMPLER2DARRAY:
afterType = true;
return nonreservedKeyword(300, 130);
case ISAMPLER2DRECT:
case USAMPLER2DRECT:
case ISAMPLERBUFFER:
case USAMPLERBUFFER:
afterType = true;
return es30ReservedFromGLSL(140);
case SAMPLER2DMS:
case ISAMPLER2DMS:
case USAMPLER2DMS:
case SAMPLER2DMSARRAY:
case ISAMPLER2DMSARRAY:
case USAMPLER2DMSARRAY:
afterType = true;
return es30ReservedFromGLSL(150);
case SAMPLER1D:
case SAMPLER1DSHADOW:
afterType = true;
if (parseContext.profile == EEsProfile)
reservedWord();
return keyword;
case SAMPLER3D:
case SAMPLER2DSHADOW:
afterType = true;
if (parseContext.profile == EEsProfile && parseContext.version < 300)
reservedWord();
return keyword;
case SAMPLER2DRECT:
case SAMPLER2DRECTSHADOW:
afterType = true;
if (parseContext.profile == EEsProfile ||
parseContext.profile != EEsProfile && parseContext.version < 140)
reservedWord();
return keyword;
case SAMPLER1DARRAY:
afterType = true;
if (parseContext.profile == EEsProfile && parseContext.version == 300)
reservedWord();
else if (parseContext.profile == EEsProfile && parseContext.version < 300 ||
parseContext.profile != EEsProfile && parseContext.version < 130)
return identifierOrType();
return keyword;
case NOPERSPECTIVE:
return es30ReservedFromGLSL(130);
case SMOOTH:
if (parseContext.profile == EEsProfile && parseContext.version < 300 ||
parseContext.profile != EEsProfile && parseContext.version < 130)
return identifierOrType();
return keyword;
case FLAT:
if (parseContext.profile == EEsProfile && parseContext.version < 300)
reservedWord();
else if (parseContext.profile != EEsProfile && parseContext.version < 130)
return identifierOrType();
return keyword;
case CENTROID:
if (parseContext.version < 120)
return identifierOrType();
return keyword;
case PRECISE:
if (parseContext.profile == EEsProfile ||
parseContext.profile != EEsProfile && parseContext.version < 400)
return identifierOrType();
return keyword;
case INVARIANT:
if (parseContext.profile != EEsProfile && parseContext.version < 120)
return identifierOrType();
return keyword;
case PACKED:
if (parseContext.profile == EEsProfile && parseContext.version < 300 ||
parseContext.profile != EEsProfile && parseContext.version < 330)
return reservedWord();
return identifierOrType();
case RESOURCE:
{
bool reserved = parseContext.profile == EEsProfile && parseContext.version >= 300 ||
parseContext.profile != EEsProfile && parseContext.version >= 420;
return identifierOrReserved(reserved);
}
case SUPERP:
{
bool reserved = parseContext.profile == EEsProfile || parseContext.version >= 130;
return identifierOrReserved(reserved);
}
default:
parseContext.infoSink.info.message(EPrefixInternalError, "Unknown glslang keyword", loc);
return 0;
}
}
int TScanContext::identifierOrType()
{
parserToken->sType.lex.string = NewPoolTString(tokenText);
if (field) {
field = false;
return FIELD_SELECTION;
}
parserToken->sType.lex.symbol = parseContext.symbolTable.find(*parserToken->sType.lex.string);
if (afterType == false && parserToken->sType.lex.symbol) {
if (TVariable* variable = parserToken->sType.lex.symbol->getAsVariable()) {
if (variable->isUserType()) {
afterType = true;
return TYPE_NAME;
}
}
}
return IDENTIFIER;
}
int TScanContext::reservedWord()
{
ThreadLocalParseContext()->error(loc, "Reserved word.", tokenText, "", "");
return 0;
}
int TScanContext::identifierOrReserved(bool reserved)
{
if (reserved) {
reservedWord();
return 0;
}
if (parseContext.forwardCompatible)
parseContext.warn(loc, "using future reserved keyword", tokenText, "");
return identifierOrType();
}
// For keywords that suddenly showed up on non-ES (not previously reserved)
// but then got reserved by ES 3.0.
int TScanContext::es30ReservedFromGLSL(int version)
{
if (parseContext.profile == EEsProfile && parseContext.version < 300 ||
parseContext.profile != EEsProfile && parseContext.version < version) {
if (parseContext.forwardCompatible)
parseContext.warn(loc, "future reserved word in ES 300 and keyword in GLSL", tokenText, "");
return identifierOrType();
} else if (parseContext.profile == EEsProfile && parseContext.version >= 300)
reservedWord();
return keyword;
}
// For a keyword that was never reserved, until it suddenly
// showed up, both in an es version and a non-ES version.
int TScanContext::nonreservedKeyword(int esVersion, int nonEsVersion)
{
if (parseContext.profile == EEsProfile && parseContext.version < esVersion ||
parseContext.profile != EEsProfile && parseContext.version < nonEsVersion) {
if (parseContext.forwardCompatible)
parseContext.warn(loc, "using future keyword", tokenText, "");
return identifierOrType();
}
return keyword;
}
int TScanContext::precisionKeyword()
{
if (parseContext.profile == EEsProfile || parseContext.version >= 130)
return keyword;
if (parseContext.forwardCompatible)
parseContext.warn(loc, "using ES precision qualifier keyword", tokenText, "");
return identifierOrType();
}
int TScanContext::matNxM()
{
afterType = true;
if (parseContext.version > 110)
return keyword;
if (parseContext.forwardCompatible)
parseContext.warn(loc, "using future non-square matrix type keyword", tokenText, "");
return identifierOrType();
}
int TScanContext::dMat()
{
afterType = true;
if (parseContext.profile == EEsProfile && parseContext.version >= 300) {
reservedWord();
return keyword;
}
if (parseContext.profile != EEsProfile && parseContext.version >= 400)
return keyword;
if (parseContext.forwardCompatible)
parseContext.warn(loc, "using future type keyword", tokenText, "");
return identifierOrType();
}
int TScanContext::firstGenerationImage()
{
afterType = true;
if (parseContext.profile != EEsProfile && parseContext.version >= 420)
return keyword;
if (parseContext.profile == EEsProfile && parseContext.version >= 300 ||
parseContext.profile != EEsProfile && parseContext.version >= 130) {
reservedWord();
return keyword;
}
if (parseContext.forwardCompatible)
parseContext.warn(loc, "using future type keyword", tokenText, "");
return identifierOrType();
}
int TScanContext::secondGenerationImage()
{
afterType = true;
if (parseContext.profile != EEsProfile && parseContext.version >= 420)
return keyword;
if (parseContext.forwardCompatible)
parseContext.warn(loc, "using future type keyword", tokenText, "");
return identifierOrType();
}
};

View File

@ -105,7 +105,7 @@ protected:
int currentChar; int currentChar;
}; };
// The location of these is still pending a grand design for going to a singular // TODO: The location of these is still pending a grand design for going to a singular
// scanner for version finding, preprocessing, and tokenizing: // scanner for version finding, preprocessing, and tokenizing:
void ConsumeWhiteSpace(TInputScanner& input, bool& foundNonSpaceTab); void ConsumeWhiteSpace(TInputScanner& input, bool& foundNonSpaceTab);
bool ConsumeComment(TInputScanner& input); bool ConsumeComment(TInputScanner& input);

View File

@ -0,0 +1,80 @@
//
//Copyright (C) 2013 LunarG, Inc.
//
//All rights reserved.
//
//Redistribution and use in source and binary forms, with or without
//modification, are permitted provided that the following conditions
//are met:
//
// Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following
// disclaimer in the documentation and/or other materials provided
// with the distribution.
//
// Neither the name of 3Dlabs Inc. Ltd. nor the names of its
// contributors may be used to endorse or promote products derived
// from this software without specific prior written permission.
//
//THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
//"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
//LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
//FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
//COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
//INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
//BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
//LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
//CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
//LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
//ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
//POSSIBILITY OF SUCH DAMAGE.
//
//
// This holds context specific to the GLSL scanner, which
// sits between the preprocessor scanner and parser.
//
#include "ParseHelper.h"
namespace glslang {
class TParserToken;
class TPpToken;
class TScanContext {
public:
explicit TScanContext(TParseContext& pc) : parseContext(pc), afterType(false), field(false) { }
virtual ~TScanContext() { }
static void fillInKeywordMap();
int tokenize(TParserToken&);
protected:
int tokenizeIdentifier();
int identifierOrType();
int reservedWord();
int identifierOrReserved(bool reserved);
int es30ReservedFromGLSL(int version);
int nonreservedKeyword(int esVersion, int nonEsVersion);
int precisionKeyword();
int matNxM();
int dMat();
int firstGenerationImage();
int secondGenerationImage();
TParseContext& parseContext;
bool afterType; // true if we've recognized a type, so can only be looking for an identifier
bool field; // true if we're on a field, right after a '.'
TSourceLoc loc;
TParserToken* parserToken;
TPpToken* ppToken;
const char* tokenText;
int keyword;
};
};

View File

@ -44,10 +44,15 @@
#include "SymbolTable.h" #include "SymbolTable.h"
#include "ParseHelper.h" #include "ParseHelper.h"
#include "Scan.h" #include "Scan.h"
#include "ScanContext.h"
#include "../Include/ShHandle.h" #include "../Include/ShHandle.h"
#include "InitializeDll.h" #include "InitializeDll.h"
extern "C" {
#include "preprocessor/preprocess.h"
}
#define SH_EXPORTING #define SH_EXPORTING
#include "../Public/ShaderLang.h" #include "../Public/ShaderLang.h"
#include "Initialize.h" #include "Initialize.h"
@ -99,8 +104,9 @@ bool InitializeSymbolTable(TBuiltInStrings* BuiltInStrings, int version, EProfil
symbolTable = &symbolTables[language]; symbolTable = &symbolTables[language];
TParseContext parseContext(*symbolTable, intermediate, true, version, profile, language, infoSink); TParseContext parseContext(*symbolTable, intermediate, true, version, profile, language, infoSink);
ThreadLocalParseContext() = &parseContext; ThreadLocalParseContext() = &parseContext;
glslang::TScanContext scanContext(parseContext);
parseContext.scanContext = &scanContext;
assert(symbolTable->isEmpty() || symbolTable->atSharedBuiltInLevel()); assert(symbolTable->isEmpty() || symbolTable->atSharedBuiltInLevel());
@ -123,8 +129,6 @@ bool InitializeSymbolTable(TBuiltInStrings* BuiltInStrings, int version, EProfil
return false; return false;
} }
ResetFlex();
for (TBuiltInStrings::iterator i = BuiltInStrings[parseContext.language].begin(); for (TBuiltInStrings::iterator i = BuiltInStrings[parseContext.language].begin();
i != BuiltInStrings[parseContext.language].end(); ++i) { i != BuiltInStrings[parseContext.language].end(); ++i) {
const char* builtInShaders[1]; const char* builtInShaders[1];
@ -132,7 +136,7 @@ bool InitializeSymbolTable(TBuiltInStrings* BuiltInStrings, int version, EProfil
builtInShaders[0] = (*i).c_str(); builtInShaders[0] = (*i).c_str();
builtInLengths[0] = (int) (*i).size(); builtInLengths[0] = (int) (*i).size();
if (PaParseStrings(const_cast<char**>(builtInShaders), builtInLengths, 1, parseContext, 0) != 0) { if (! parseContext.parseShaderStrings(const_cast<char**>(builtInShaders), builtInLengths, 1) != 0) {
infoSink.info.message(EPrefixInternalError, "Unable to parse built-ins"); infoSink.info.message(EPrefixInternalError, "Unable to parse built-ins");
printf("Unable to parse built-ins\n"); printf("Unable to parse built-ins\n");
@ -271,6 +275,8 @@ int ShInitialize()
PerProcessGPA = new TPoolAllocator(true); PerProcessGPA = new TPoolAllocator(true);
} }
glslang::TScanContext::fillInKeywordMap();
return true; return true;
} }
@ -411,19 +417,24 @@ int ShCompile(
AddContextSpecificSymbols(resources, compiler->infoSink, &symbolTable, version, profile, compiler->getLanguage()); AddContextSpecificSymbols(resources, compiler->infoSink, &symbolTable, version, profile, compiler->getLanguage());
TParseContext parseContext(symbolTable, intermediate, false, version, profile, compiler->getLanguage(), compiler->infoSink, forwardCompatible, messages); TParseContext parseContext(symbolTable, intermediate, false, version, profile, compiler->getLanguage(), compiler->infoSink, forwardCompatible, messages);
glslang::TScanContext scanContext(parseContext);
parseContext.scanContext = &scanContext;
TSourceLoc beginning;
beginning.line = 1;
beginning.string = 0;
if (! goodProfile) if (! goodProfile)
parseContext.error(1, "incorrect", "#version", ""); parseContext.error(beginning, "incorrect", "#version", "");
parseContext.initializeExtensionBehavior(); parseContext.initializeExtensionBehavior();
if (versionStatementMissing) if (versionStatementMissing)
parseContext.warn(1, "statement missing: use #version on first line of shader", "#version", ""); parseContext.warn(beginning, "statement missing: use #version on first line of shader", "#version", "");
else if (profile == EEsProfile && version >= 300 && versionNotFirst) else if (profile == EEsProfile && version >= 300 && versionNotFirst)
parseContext.error(1, "statement must appear first in ESSL shader; before comments or newlines", "#version", ""); parseContext.error(beginning, "statement must appear first in ESSL shader; before comments or newlines", "#version", "");
ThreadLocalParseContext() = &parseContext; ThreadLocalParseContext() = &parseContext;
ResetFlex();
InitPreprocessor(); InitPreprocessor();
// //
@ -440,8 +451,8 @@ int ShCompile(
if (parseContext.insertBuiltInArrayAtGlobalLevel()) if (parseContext.insertBuiltInArrayAtGlobalLevel())
success = false; success = false;
int ret = PaParseStrings(const_cast<char**>(shaderStrings), lengths, numStrings, parseContext, parseContext.getPreamble()); bool ret = parseContext.parseShaderStrings(const_cast<char**>(shaderStrings), lengths, numStrings);
if (ret) if (! ret)
success = false; success = false;
intermediate.addSymbolLinkageNodes(parseContext.treeRoot, parseContext.linkage, parseContext.language, symbolTable); intermediate.addSymbolLinkageNodes(parseContext.treeRoot, parseContext.linkage, parseContext.language, symbolTable);

View File

@ -64,10 +64,10 @@ const char* ProfileName[EProfileCount] = {
// which subset allows the feature. If the current profile is not present, // which subset allows the feature. If the current profile is not present,
// give an error message. // give an error message.
// //
void TParseContext::requireProfile(int line, EProfileMask profileMask, const char *featureDesc) void TParseContext::requireProfile(TSourceLoc loc, EProfileMask profileMask, const char *featureDesc)
{ {
if (((1 << profile) & profileMask) == 0) if (((1 << profile) & profileMask) == 0)
error(line, "not supported with this profile:", featureDesc, ProfileName[profile]); error(loc, "not supported with this profile:", featureDesc, ProfileName[profile]);
} }
// //
@ -75,10 +75,10 @@ void TParseContext::requireProfile(int line, EProfileMask profileMask, const cha
// which subset allows the feature. If the current stage is not present, // which subset allows the feature. If the current stage is not present,
// give an error message. // give an error message.
// //
void TParseContext::requireStage(int line, EShLanguageMask languageMask, const char *featureDesc) void TParseContext::requireStage(TSourceLoc loc, EShLanguageMask languageMask, const char *featureDesc)
{ {
if (((1 << language) & languageMask) == 0) if (((1 << language) & languageMask) == 0)
error(line, "not supported in this stage:", featureDesc, StageName[language]); error(loc, "not supported in this stage:", featureDesc, StageName[language]);
} }
// //
@ -88,7 +88,7 @@ void TParseContext::requireStage(int line, EShLanguageMask languageMask, const c
// //
// one that takes multiple extensions // one that takes multiple extensions
void TParseContext::profileRequires(int line, EProfile callingProfile, int minVersion, int numExtensions, const char* extensions[], const char *featureDesc) void TParseContext::profileRequires(TSourceLoc loc, EProfile callingProfile, int minVersion, int numExtensions, const char* extensions[], const char *featureDesc)
{ {
if (profile == callingProfile) { if (profile == callingProfile) {
bool okay = false; bool okay = false;
@ -98,7 +98,7 @@ void TParseContext::profileRequires(int line, EProfile callingProfile, int minVe
TBehavior behavior = extensionBehavior[extensions[i]]; TBehavior behavior = extensionBehavior[extensions[i]];
switch (behavior) { switch (behavior) {
case EBhWarn: case EBhWarn:
infoSink.info.message(EPrefixWarning, ("extension " + TString(extensions[i]) + " is being used for " + featureDesc).c_str(), line); infoSink.info.message(EPrefixWarning, ("extension " + TString(extensions[i]) + " is being used for " + featureDesc).c_str(), loc);
// fall through // fall through
case EBhRequire: case EBhRequire:
case EBhEnable: case EBhEnable:
@ -109,29 +109,29 @@ void TParseContext::profileRequires(int line, EProfile callingProfile, int minVe
} }
if (! okay) if (! okay)
error(line, "not supported for this version or the enabled extensions", featureDesc, ""); error(loc, "not supported for this version or the enabled extensions", featureDesc, "");
} }
} }
// one that takes a single extension // one that takes a single extension
void TParseContext::profileRequires(int line, EProfile callingProfile, int minVersion, const char* extension, const char *featureDesc) void TParseContext::profileRequires(TSourceLoc loc, EProfile callingProfile, int minVersion, const char* extension, const char *featureDesc)
{ {
profileRequires(line, callingProfile, minVersion, extension ? 1 : 0, &extension, featureDesc); profileRequires(loc, callingProfile, minVersion, extension ? 1 : 0, &extension, featureDesc);
} }
// //
// Within a profile, see if a feature is deprecated and error or warn based on whether // Within a profile, see if a feature is deprecated and error or warn based on whether
// a future compatibility context is being use. // a future compatibility context is being use.
// //
void TParseContext::checkDeprecated(int line, EProfile callingProfile, int depVersion, const char *featureDesc) void TParseContext::checkDeprecated(TSourceLoc loc, EProfile callingProfile, int depVersion, const char *featureDesc)
{ {
if (profile == callingProfile) { if (profile == callingProfile) {
if (version >= depVersion) { if (version >= depVersion) {
if (forwardCompatible) if (forwardCompatible)
error(line, "deprecated, may be removed in future release", featureDesc, ""); error(loc, "deprecated, may be removed in future release", featureDesc, "");
else if (! (messages & EShMsgSuppressWarnings)) else if (! (messages & EShMsgSuppressWarnings))
infoSink.info.message(EPrefixWarning, (TString(featureDesc) + " deprecated in version " + infoSink.info.message(EPrefixWarning, (TString(featureDesc) + " deprecated in version " +
String(depVersion) + "; may be removed in future release").c_str(), line); String(depVersion) + "; may be removed in future release").c_str(), loc);
} }
} }
} }
@ -140,27 +140,27 @@ void TParseContext::checkDeprecated(int line, EProfile callingProfile, int depVe
// Within a profile, see if a feature has now been removed and if so, give an error. // Within a profile, see if a feature has now been removed and if so, give an error.
// The version argument is the first version no longer having the feature. // The version argument is the first version no longer having the feature.
// //
void TParseContext::requireNotRemoved(int line, EProfile callingProfile, int removedVersion, const char *featureDesc) void TParseContext::requireNotRemoved(TSourceLoc loc, EProfile callingProfile, int removedVersion, const char *featureDesc)
{ {
if (profile == callingProfile) { if (profile == callingProfile) {
if (version >= removedVersion) { if (version >= removedVersion) {
const int maxSize = 60; const int maxSize = 60;
char buf[maxSize]; char buf[maxSize];
snprintf(buf, maxSize, "%s profile; removed in version %d", ProfileName[profile], removedVersion); snprintf(buf, maxSize, "%s profile; removed in version %d", ProfileName[profile], removedVersion);
error(line, "no longer supported in", featureDesc, buf); error(loc, "no longer supported in", featureDesc, buf);
} }
} }
} }
void TParseContext::fullIntegerCheck(int line, const char* op) void TParseContext::fullIntegerCheck(TSourceLoc loc, const char* op)
{ {
profileRequires(line, ENoProfile, 130, 0, op); profileRequires(loc, ENoProfile, 130, 0, op);
profileRequires(line, EEsProfile, 300, 0, op); profileRequires(loc, EEsProfile, 300, 0, op);
} }
void TParseContext::doubleCheck(int line, const char* op) void TParseContext::doubleCheck(TSourceLoc loc, const char* op)
{ {
requireProfile(line, (EProfileMask)(ECoreProfileMask | ECompatibilityProfileMask), op); requireProfile(loc, (EProfileMask)(ECoreProfileMask | ECompatibilityProfileMask), op);
profileRequires(line, ECoreProfile, 400, 0, op); profileRequires(loc, ECoreProfile, 400, 0, op);
profileRequires(line, ECompatibilityProfile, 400, 0, op); profileRequires(loc, ECompatibilityProfile, 400, 0, op);
} }

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@ -63,7 +63,11 @@ void OutputTreeText(TInfoSink& infoSink, TIntermNode* node, const int depth)
{ {
int i; int i;
infoSink.debug << FormatSourceLoc(node->getLine()); infoSink.debug << node->getLoc().string << ":";
if (node->getLoc().line)
infoSink.debug << node->getLoc().line;
else
infoSink.debug << "? ";
for (i = 0; i < depth; ++i) for (i = 0; i < depth; ++i)
infoSink.debug << " "; infoSink.debug << " ";
@ -445,7 +449,7 @@ void OutputConstantUnion(TIntermConstantUnion* node, TIntermTraverser* it)
} }
break; break;
default: default:
out.info.message(EPrefixInternalError, "Unknown constant", node->getLine()); out.info.message(EPrefixInternalError, "Unknown constant", node->getLoc());
break; break;
} }
} }

View File

@ -62,7 +62,9 @@ public:
TIntermTyped* addUnaryMath(TOperator, TIntermNode* child, TSourceLoc); TIntermTyped* addUnaryMath(TOperator, TIntermNode* child, TSourceLoc);
TIntermTyped* addBuiltInFunctionCall(TOperator, bool unary, TIntermNode*, const TType& returnType); TIntermTyped* addBuiltInFunctionCall(TOperator, bool unary, TIntermNode*, const TType& returnType);
bool canImplicitlyPromote(TBasicType from, TBasicType to); bool canImplicitlyPromote(TBasicType from, TBasicType to);
TIntermAggregate* growAggregate(TIntermNode* left, TIntermNode* right);
TIntermAggregate* growAggregate(TIntermNode* left, TIntermNode* right, TSourceLoc); TIntermAggregate* growAggregate(TIntermNode* left, TIntermNode* right, TSourceLoc);
TIntermAggregate* makeAggregate(TIntermNode* node);
TIntermAggregate* makeAggregate(TIntermNode* node, TSourceLoc); TIntermAggregate* makeAggregate(TIntermNode* node, TSourceLoc);
TIntermTyped* setAggregateOperator(TIntermNode*, TOperator, const TType& type, TSourceLoc); TIntermTyped* setAggregateOperator(TIntermNode*, TOperator, const TType& type, TSourceLoc);
bool areAllChildConst(TIntermAggregate* aggrNode); bool areAllChildConst(TIntermAggregate* aggrNode);

View File

@ -69,7 +69,7 @@ public:
void ParseSymbol(TIntermSymbol* node, TIntermTraverser* it) void ParseSymbol(TIntermSymbol* node, TIntermTraverser* it)
{ {
TConstTraverser* oit = static_cast<TConstTraverser*>(it); TConstTraverser* oit = static_cast<TConstTraverser*>(it);
oit->infoSink.info.message(EPrefixInternalError, "Symbol Node found in constant constructor", node->getLine()); oit->infoSink.info.message(EPrefixInternalError, "Symbol Node found in constant constructor", node->getLoc());
return; return;
} }
@ -84,13 +84,13 @@ bool ParseBinary(bool /* preVisit */, TIntermBinary* node, TIntermTraverser* it)
const int maxSize = GlslangMaxTypeLength + 50; const int maxSize = GlslangMaxTypeLength + 50;
char buf[maxSize]; char buf[maxSize];
snprintf(buf, maxSize, "'constructor' : assigning non-constant to %s", oit->type.getCompleteString().c_str()); snprintf(buf, maxSize, "'constructor' : assigning non-constant to %s", oit->type.getCompleteString().c_str());
oit->infoSink.info.message(EPrefixError, buf, node->getLine()); oit->infoSink.info.message(EPrefixError, buf, node->getLoc());
oit->error = true; oit->error = true;
return false; return false;
} }
oit->infoSink.info.message(EPrefixInternalError, "Binary Node found in constant constructor", node->getLine()); oit->infoSink.info.message(EPrefixInternalError, "Binary Node found in constant constructor", node->getLoc());
return false; return false;
} }
@ -102,7 +102,7 @@ bool ParseUnary(bool /* preVisit */, TIntermUnary* node, TIntermTraverser* it)
const int maxSize = GlslangMaxTypeLength + 50; const int maxSize = GlslangMaxTypeLength + 50;
char buf[maxSize]; char buf[maxSize];
snprintf(buf, maxSize, "'constructor' : assigning non-constant to '%s'", oit->type.getCompleteString().c_str()); snprintf(buf, maxSize, "'constructor' : assigning non-constant to '%s'", oit->type.getCompleteString().c_str());
oit->infoSink.info.message(EPrefixError, buf, node->getLine()); oit->infoSink.info.message(EPrefixError, buf, node->getLoc());
oit->error = true; oit->error = true;
return false; return false;
@ -116,7 +116,7 @@ bool ParseAggregate(bool /* preVisit */, TIntermAggregate* node, TIntermTraverse
const int maxSize = GlslangMaxTypeLength + 50; const int maxSize = GlslangMaxTypeLength + 50;
char buf[maxSize]; char buf[maxSize];
snprintf(buf, maxSize, "'constructor' : assigning non-constant to '%s'", oit->type.getCompleteString().c_str()); snprintf(buf, maxSize, "'constructor' : assigning non-constant to '%s'", oit->type.getCompleteString().c_str());
oit->infoSink.info.message(EPrefixError, buf, node->getLine()); oit->infoSink.info.message(EPrefixError, buf, node->getLoc());
oit->error = true; oit->error = true;
return false; return false;
@ -165,7 +165,7 @@ bool ParseAggregate(bool /* preVisit */, TIntermAggregate* node, TIntermTraverse
bool ParseSelection(bool /* preVisit */, TIntermSelection* node, TIntermTraverser* it) bool ParseSelection(bool /* preVisit */, TIntermSelection* node, TIntermTraverser* it)
{ {
TConstTraverser* oit = static_cast<TConstTraverser*>(it); TConstTraverser* oit = static_cast<TConstTraverser*>(it);
oit->infoSink.info.message(EPrefixInternalError, "Selection Node found in constant constructor", node->getLine()); oit->infoSink.info.message(EPrefixInternalError, "Selection Node found in constant constructor", node->getLoc());
oit->error = true; oit->error = true;
return false; return false;
} }
@ -235,7 +235,7 @@ void ParseConstantUnion(TIntermConstantUnion* node, TIntermTraverser* it)
bool ParseLoop(bool /* preVisit */, TIntermLoop* node, TIntermTraverser* it) bool ParseLoop(bool /* preVisit */, TIntermLoop* node, TIntermTraverser* it)
{ {
TConstTraverser* oit = static_cast<TConstTraverser*>(it); TConstTraverser* oit = static_cast<TConstTraverser*>(it);
oit->infoSink.info.message(EPrefixInternalError, "Loop Node found in constant constructor", node->getLine()); oit->infoSink.info.message(EPrefixInternalError, "Loop Node found in constant constructor", node->getLoc());
oit->error = true; oit->error = true;
return false; return false;
@ -244,7 +244,7 @@ bool ParseLoop(bool /* preVisit */, TIntermLoop* node, TIntermTraverser* it)
bool ParseBranch(bool /* previsit*/, TIntermBranch* node, TIntermTraverser* it) bool ParseBranch(bool /* previsit*/, TIntermBranch* node, TIntermTraverser* it)
{ {
TConstTraverser* oit = static_cast<TConstTraverser*>(it); TConstTraverser* oit = static_cast<TConstTraverser*>(it);
oit->infoSink.info.message(EPrefixInternalError, "Branch Node found in constant constructor", node->getLine()); oit->infoSink.info.message(EPrefixInternalError, "Branch Node found in constant constructor", node->getLoc());
oit->error = true; oit->error = true;
return false; return false;

View File

@ -107,29 +107,20 @@ static const struct {
{ CPP_ADD_ASSIGN, "+=" }, { CPP_ADD_ASSIGN, "+=" },
{ CPP_DIV_ASSIGN, "/=" }, { CPP_DIV_ASSIGN, "/=" },
{ CPP_MUL_ASSIGN, "*=" }, { CPP_MUL_ASSIGN, "*=" },
{ CPP_RIGHT_BRACKET, ":>" },
{ CPP_EQ_OP, "==" }, { CPP_EQ_OP, "==" },
{ CPP_XOR_OP, "^^" }, { CPP_XOR_OP, "^^" },
{ CPP_XOR_ASSIGN, "^=" }, { CPP_XOR_ASSIGN, "^=" },
{ CPP_FLOATCONSTANT, "<float-const>" },
{ CPP_GE_OP, ">=" }, { CPP_GE_OP, ">=" },
{ CPP_RIGHT_OP, ">>" }, { CPP_RIGHT_OP, ">>" },
{ CPP_RIGHT_ASSIGN, ">>=" }, { CPP_RIGHT_ASSIGN, ">>="},
{ CPP_IDENTIFIER, "<ident>" },
{ CPP_INTCONSTANT, "<int-const>" },
{ CPP_LE_OP, "<=" }, { CPP_LE_OP, "<=" },
{ CPP_LEFT_OP, "<<" }, { CPP_LEFT_OP, "<<" },
{ CPP_LEFT_ASSIGN, "<<=" }, { CPP_LEFT_ASSIGN, "<<="},
{ CPP_LEFT_BRACKET, "<:" },
{ CPP_LEFT_BRACE, "<%" },
{ CPP_DEC_OP, "--" }, { CPP_DEC_OP, "--" },
{ CPP_RIGHT_BRACE, "%>" },
{ CPP_NE_OP, "!=" }, { CPP_NE_OP, "!=" },
{ CPP_OR_OP, "||" }, { CPP_OR_OP, "||" },
{ CPP_OR_ASSIGN, "|=" }, { CPP_OR_ASSIGN, "|=" },
{ CPP_INC_OP, "++" }, { CPP_INC_OP, "++" },
{ CPP_STRCONSTANT, "<string-const>" },
{ CPP_TYPEIDENTIFIER, "<type-ident>" },
}; };
/////////////////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////////////////////
@ -672,7 +663,7 @@ int InitAtomTable(AtomTable *atable, int htsize)
// Initialize lower part of atom table to "<undefined>" atom: // Initialize lower part of atom table to "<undefined>" atom:
AddAtomFixed(atable, "<undefined>", 0); AddAtomFixed(atable, "<undefined>", 0);
for (ii = 0; ii < FIRST_USER_TOKEN_SY; ii++) for (ii = 0; ii < CPP_FIRST_USER_TOKEN_SY; ii++)
atable->amap[ii] = atable->amap[0]; atable->amap[ii] = atable->amap[0];
// Add single character tokens to the atom table: // Add single character tokens to the atom table:
@ -697,7 +688,7 @@ int InitAtomTable(AtomTable *atable, int htsize)
// Add error symbol if running in error mode: // Add error symbol if running in error mode:
if (cpp->options.ErrorMode) if (cpp->options.ErrorMode)
AddAtomFixed(atable, "error", ERROR_SY); AddAtomFixed(atable, "error", CPP_ERROR_SY);
AddAtom(atable, "<*** end fixed atoms ***>"); AddAtom(atable, "<*** end fixed atoms ***>");

View File

@ -1,132 +0,0 @@
//
//Copyright (C) 2002-2005 3Dlabs Inc. Ltd.
//All rights reserved.
//
//Redistribution and use in source and binary forms, with or without
//modification, are permitted provided that the following conditions
//are met:
//
// Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following
// disclaimer in the documentation and/or other materials provided
// with the distribution.
//
// Neither the name of 3Dlabs Inc. Ltd. nor the names of its
// contributors may be used to endorse or promote products derived
// from this software without specific prior written permission.
//
//THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
//"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
//LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
//FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
//COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
//INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
//BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
//LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
//CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
//LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
//ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
//POSSIBILITY OF SUCH DAMAGE.
//
/****************************************************************************\
Copyright (c) 2002, NVIDIA Corporation.
NVIDIA Corporation("NVIDIA") supplies this software to you in
consideration of your agreement to the following terms, and your use,
installation, modification or redistribution of this NVIDIA software
constitutes acceptance of these terms. If you do not agree with these
terms, please do not use, install, modify or redistribute this NVIDIA
software.
In consideration of your agreement to abide by the following terms, and
subject to these terms, NVIDIA grants you a personal, non-exclusive
license, under NVIDIA's copyrights in this original NVIDIA software (the
"NVIDIA Software"), to use, reproduce, modify and redistribute the
NVIDIA Software, with or without modifications, in source and/or binary
forms; provided that if you redistribute the NVIDIA Software, you must
retain the copyright notice of NVIDIA, this notice and the following
text and disclaimers in all such redistributions of the NVIDIA Software.
Neither the name, trademarks, service marks nor logos of NVIDIA
Corporation may be used to endorse or promote products derived from the
NVIDIA Software without specific prior written permission from NVIDIA.
Except as expressly stated in this notice, no other rights or licenses
express or implied, are granted by NVIDIA herein, including but not
limited to any patent rights that may be infringed by your derivative
works or by other works in which the NVIDIA Software may be
incorporated. No hardware is licensed hereunder.
THE NVIDIA SOFTWARE IS BEING PROVIDED ON AN "AS IS" BASIS, WITHOUT
WARRANTIES OR CONDITIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED,
INCLUDING WITHOUT LIMITATION, WARRANTIES OR CONDITIONS OF TITLE,
NON-INFRINGEMENT, MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, OR
ITS USE AND OPERATION EITHER ALONE OR IN COMBINATION WITH OTHER
PRODUCTS.
IN NO EVENT SHALL NVIDIA BE LIABLE FOR ANY SPECIAL, INDIRECT,
INCIDENTAL, EXEMPLARY, CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
TO, LOST PROFITS; PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) OR ARISING IN ANY WAY
OUT OF THE USE, REPRODUCTION, MODIFICATION AND/OR DISTRIBUTION OF THE
NVIDIA SOFTWARE, HOWEVER CAUSED AND WHETHER UNDER THEORY OF CONTRACT,
TORT (INCLUDING NEGLIGENCE), STRICT LIABILITY OR OTHERWISE, EVEN IF
NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
\****************************************************************************/
//
// compile.h
//
#if !defined(__COMPILE_H)
#define __COMPILE_H 1
int InitCPPStruct(void);
typedef struct Options_Rec{
const char *profileString;
int ErrorMode;
int Quiet;
// Debug The Compiler options:
int DumpAtomTable;
} Options;
struct CPPStruct_Rec {
// Public members
SourceLoc *pLastSourceLoc; // Set at the start of each statement by the tree walkers
Options options; // Compile options and parameters
// Private members
SourceLoc lastSourceLoc;
// Scanner data:
SourceLoc *tokenLoc; // Source location of most recent token seen by the scanner
int mostRecentToken; // Most recent token seen by the scanner
InputSrc *currentInput;
int previous_token;
int notAVersionToken; // used to make sure that #version is the first token seen in the file, if present
void *pC; // storing the parseContext of the compile object in cpp.
// Private members:
SourceLoc ltokenLoc;
int ifdepth; //current #if-#else-#endif nesting in the cpp.c file (pre-processor)
int elsedepth[64]; //Keep a track of #if depth..Max allowed is 64.
int elsetracker; //#if-#else and #endif constructs...Counter.
const char *ErrMsg;
int CompileError; //Indicate compile error when #error, #else,#elif mismatch.
//
// Globals used to communicate between PaParseStrings() and yy_input()and
// also across the files.(gen_glslang.cpp and scanner.c)
//
int PaWhichStr; // which string we're parsing
int* PaStrLen; // array of lengths of the PaArgv strings
int PaArgc; // count of strings in the array
char** PaArgv; // our array of strings to parse
unsigned int tokensBeforeEOF : 1;
};
#endif // !defined(__COMPILE_H)

View File

@ -630,7 +630,8 @@ static int CPPerror(yystypepp * yylvalpp)
const char *message; const char *message;
while (token != '\n') { while (token != '\n') {
if (token == CPP_FLOATCONSTANT || token == CPP_INTCONSTANT){ if (token == CPP_INTCONSTANT || token == CPP_UINTCONSTANT ||
token == CPP_FLOATCONSTANT || token == CPP_DOUBLECONSTANT) {
StoreStr(yylvalpp->symbol_name); StoreStr(yylvalpp->symbol_name);
}else if(token == CPP_IDENTIFIER || token == CPP_STRCONSTANT){ }else if(token == CPP_IDENTIFIER || token == CPP_STRCONSTANT){
StoreStr(GetStringOfAtom(atable, yylvalpp->sc_ident)); StoreStr(GetStringOfAtom(atable, yylvalpp->sc_ident));
@ -681,11 +682,9 @@ static int CPPpragma(yystypepp * yylvalpp)
strcpy(allTokens[tokenCount++], SrcStr); strcpy(allTokens[tokenCount++], SrcStr);
break; break;
case CPP_INTCONSTANT: case CPP_INTCONSTANT:
SrcStr = yylvalpp->symbol_name; case CPP_UINTCONSTANT:
allTokens[tokenCount] = (char*)malloc(strlen(SrcStr) + 1);
strcpy(allTokens[tokenCount++], SrcStr);
break;
case CPP_FLOATCONSTANT: case CPP_FLOATCONSTANT:
case CPP_DOUBLECONSTANT:
SrcStr = yylvalpp->symbol_name; SrcStr = yylvalpp->symbol_name;
allTokens[tokenCount] = (char*)malloc(strlen(SrcStr) + 1); allTokens[tokenCount] = (char*)malloc(strlen(SrcStr) + 1);
strcpy(allTokens[tokenCount++], SrcStr); strcpy(allTokens[tokenCount++], SrcStr);
@ -715,41 +714,35 @@ static int CPPpragma(yystypepp * yylvalpp)
return token; return token;
} // CPPpragma } // CPPpragma
// This is just for error checking: the version and profile are decided before preprocessing starts
static int CPPversion(yystypepp * yylvalpp) static int CPPversion(yystypepp * yylvalpp)
{ {
int token = cpp->currentInput->scan(cpp->currentInput, yylvalpp); int token = cpp->currentInput->scan(cpp->currentInput, yylvalpp);
if (cpp->notAVersionToken == 1) if (cpp->notAVersionToken == 1)
ShPpErrorToInfoLog("#version must occur before any other statement in the program"); ShPpErrorToInfoLog("#version must occur before any other statement in the program");
if(token=='\n'){ if (token == '\n'){
DecLineNumber(); DecLineNumber();
ShPpErrorToInfoLog("#version"); ShPpErrorToInfoLog("#version");
IncLineNumber(); IncLineNumber();
return token; return token;
} }
if (token != CPP_INTCONSTANT) if (token != CPP_INTCONSTANT)
ShPpErrorToInfoLog("#version"); ShPpErrorToInfoLog("#version");
yylvalpp->sc_int=atoi(yylvalpp->symbol_name); yylvalpp->sc_int = atoi(yylvalpp->symbol_name);
SetVersion(yylvalpp->sc_int);
token = cpp->currentInput->scan(cpp->currentInput, yylvalpp); token = cpp->currentInput->scan(cpp->currentInput, yylvalpp);
if (token == '\n') { if (token == '\n')
SetProfile(ENoProfile);
return token; return token;
}
else { else {
if (yylvalpp->sc_ident == coreAtom) if (yylvalpp->sc_ident != coreAtom &&
SetProfile(ECoreProfile); yylvalpp->sc_ident != compatibilityAtom &&
else if (yylvalpp->sc_ident == compatibilityAtom) yylvalpp->sc_ident != esAtom)
SetProfile(ECompatibilityProfile);
else if (yylvalpp->sc_ident == esAtom)
SetProfile(EEsProfile);
else
ShPpErrorToInfoLog("#version profile name"); ShPpErrorToInfoLog("#version profile name");
token = cpp->currentInput->scan(cpp->currentInput, yylvalpp); token = cpp->currentInput->scan(cpp->currentInput, yylvalpp);
@ -1025,7 +1018,7 @@ int MacroExpand(int atom, yystypepp* yylvalpp, int expandUndef)
} }
if (atom == __VERSION__Atom) { if (atom == __VERSION__Atom) {
yylvalpp->sc_int = GetVersion(cpp->pC); yylvalpp->sc_int = GetShaderVersion(cpp->pC);
sprintf(yylvalpp->symbol_name, "%d", yylvalpp->sc_int); sprintf(yylvalpp->symbol_name, "%d", yylvalpp->sc_int);
UngetToken(CPP_INTCONSTANT, yylvalpp); UngetToken(CPP_INTCONSTANT, yylvalpp);

View File

@ -116,8 +116,7 @@ int GetLineNumber(void); // Get the current String Number.
int GetStringNumber(void); // Get the current String Number. int GetStringNumber(void); // Get the current String Number.
const char* GetStrfromTStr(void); // Convert TString to String. const char* GetStrfromTStr(void); // Convert TString to String.
void SetVersion(int); void SetVersion(int);
void SetProfile(EProfile); int GetShaderVersion(void*);
int GetVersion(void*);
void updateExtensionBehavior(const char* extName, const char* behavior); void updateExtensionBehavior(const char* extName, const char* behavior);
int FreeCPP(void); int FreeCPP(void);

View File

@ -86,10 +86,8 @@ NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
CPPStruct *cpp = NULL; CPPStruct *cpp = NULL;
static int refCount = 0; static int refCount = 0;
int InitPreprocessor(void);
int ResetPreprocessor(void); int ResetPreprocessor(void);
int FreeCPPStruct(void); int FreeCPPStruct(void);
int FinalizePreprocessor(void);
/* /*
* InitCPPStruct() - Initilaize the CPP structure. * InitCPPStruct() - Initilaize the CPP structure.

View File

@ -75,20 +75,9 @@ TORT (INCLUDING NEGLIGENCE), STRICT LIABILITY OR OTHERWISE, EVEN IF
NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
\****************************************************************************/ \****************************************************************************/
#ifndef BISON_PARSER_H #ifndef PARSER_H
# define BISON_PARSER_H # define PARSER_H
#ifndef yystypepp
typedef struct {
int sc_int;
float sc_fval;
double sc_dval;
int sc_ident;
char symbol_name[MAX_SYMBOL_NAME_LEN+1];
} yystypepp;
# define YYSTYPE_IS_TRIVIAL 1
#endif
# define CPP_AND_OP 257 # define CPP_AND_OP 257
# define CPP_SUB_ASSIGN 259 # define CPP_SUB_ASSIGN 259
# define CPP_MOD_ASSIGN 260 # define CPP_MOD_ASSIGN 260
@ -97,7 +86,7 @@ typedef struct {
# define CPP_MUL_ASSIGN 263 # define CPP_MUL_ASSIGN 263
# define CPP_EQ_OP 264 # define CPP_EQ_OP 264
# define CPP_XOR_OP 265 # define CPP_XOR_OP 265
# define ERROR_SY 266 # define CPP_ERROR_SY 266
# define CPP_FLOATCONSTANT 267 # define CPP_FLOATCONSTANT 267
# define CPP_GE_OP 268 # define CPP_GE_OP 268
# define CPP_RIGHT_OP 269 # define CPP_RIGHT_OP 269
@ -111,9 +100,6 @@ typedef struct {
# define CPP_INC_OP 277 # define CPP_INC_OP 277
# define CPP_STRCONSTANT 278 # define CPP_STRCONSTANT 278
# define CPP_TYPEIDENTIFIER 279 # define CPP_TYPEIDENTIFIER 279
# define FIRST_USER_TOKEN_SY 289
# define CPP_RIGHT_ASSIGN 280 # define CPP_RIGHT_ASSIGN 280
# define CPP_LEFT_ASSIGN 281 # define CPP_LEFT_ASSIGN 281
# define CPP_AND_ASSIGN 282 # define CPP_AND_ASSIGN 282
@ -123,5 +109,8 @@ typedef struct {
# define CPP_RIGHT_BRACKET 286 # define CPP_RIGHT_BRACKET 286
# define CPP_LEFT_BRACE 287 # define CPP_LEFT_BRACE 287
# define CPP_RIGHT_BRACE 288 # define CPP_RIGHT_BRACE 288
# define CPP_UINTCONSTANT 289
# define CPP_DOUBLECONSTANT 290
# define CPP_FIRST_USER_TOKEN_SY 291
#endif /* not BISON_PARSER_H */ #endif /* not PARSER_H */

View File

@ -75,10 +75,84 @@ TORT (INCLUDING NEGLIGENCE), STRICT LIABILITY OR OTHERWISE, EVEN IF
NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
\****************************************************************************/ \****************************************************************************/
#include "slglobals.h" #ifndef PREPROCESS_H
#define PREPROCESS_H
typedef struct SourceLoc_Rec {
int file;
int line;
} SourceLoc;
typedef struct Options_Rec {
const char *profileString;
int ErrorMode;
int Quiet;
// Debug The Compiler options:
int DumpAtomTable;
} Options;
#define MAX_TOKEN_LENGTH 1024
typedef struct {
int ppToken;
int sc_int;
double sc_dval;
int sc_ident;
char symbol_name[MAX_TOKEN_LENGTH+1];
} yystypepp;
typedef struct InputSrc {
struct InputSrc *prev;
int (*scan)(struct InputSrc *, yystypepp *);
int (*getch)(struct InputSrc *, yystypepp *);
void (*ungetch)(struct InputSrc *, int, yystypepp *);
int name; /* atom */
int line;
} InputSrc;
typedef struct CPPStruct {
// Public members
SourceLoc *pLastSourceLoc; // Set at the start of each statement by the tree walkers
Options options; // Compile options and parameters
// Private members
SourceLoc lastSourceLoc;
// Scanner data:
SourceLoc *tokenLoc; // Source location of most recent token seen by the scanner
int mostRecentToken; // Most recent token seen by the scanner
InputSrc *currentInput;
int previous_token;
int notAVersionToken; // used to make sure that #version is the first token seen in the file, if present
void *pC; // storing the parseContext of the compile object in cpp.
// Private members:
SourceLoc ltokenLoc;
int ifdepth; //current #if-#else-#endif nesting in the cpp.c file (pre-processor)
int elsedepth[64]; //Keep a track of #if depth..Max allowed is 64.
int elsetracker; //#if-#else and #endif constructs...Counter.
const char *ErrMsg;
int CompileError; //Indicate compile error when #error, #else,#elif mismatch.
//
// Globals used to communicate between parseStrings() and yy_input()and
// also across the files.(gen_glslang.cpp and scanner.c)
//
int PaWhichStr; // which string we're parsing
int* PaStrLen; // array of lengths of the PaArgv strings
int PaArgc; // count of strings in the array
char** PaArgv; // our array of strings to parse
unsigned int tokensBeforeEOF : 1;
} CPPStruct;
extern CPPStruct *cpp; extern CPPStruct *cpp;
int InitCPPStruct(void);
int InitScanner(CPPStruct *cpp); int InitPreprocessor(void);
int InitAtomTable(AtomTable *atable, int htsize); int FinalizePreprocessor(void);
int ScanFromString(char *s); int ScanFromString(char *s);
char* GetStringOfAtom(AtomTable *atable, int atom); const char* PpTokenize(yystypepp*);
#endif

View File

@ -222,7 +222,7 @@ int ScanFromString(char *s)
cpp->currentInput = &in->base; cpp->currentInput = &in->base;
return 1; return 1;
} // ScanFromString; }
/////////////////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////////////////////
@ -239,6 +239,7 @@ static int lFloatConst(char *str, int len, int ch, yystypepp * yylvalpp)
{ {
int HasDecimal, declen, exp, ExpSign; int HasDecimal, declen, exp, ExpSign;
int str_len; int str_len;
int isDouble = 0;
HasDecimal = 0; HasDecimal = 0;
declen = 0; declen = 0;
@ -250,7 +251,7 @@ static int lFloatConst(char *str, int len, int ch, yystypepp * yylvalpp)
HasDecimal = 1; HasDecimal = 1;
ch = cpp->currentInput->getch(cpp->currentInput, yylvalpp); ch = cpp->currentInput->getch(cpp->currentInput, yylvalpp);
while (ch >= '0' && ch <= '9') { while (ch >= '0' && ch <= '9') {
if (len < MAX_SYMBOL_NAME_LEN) { if (len < MAX_TOKEN_LENGTH) {
declen++; declen++;
if (len > 0 || ch != '0') { if (len > 0 || ch != '0') {
str[len] = ch; str[len] = ch;
@ -267,7 +268,7 @@ static int lFloatConst(char *str, int len, int ch, yystypepp * yylvalpp)
// Exponent: // Exponent:
if (ch == 'e' || ch == 'E') { if (ch == 'e' || ch == 'E') {
if (len >= MAX_SYMBOL_NAME_LEN) { if (len >= MAX_TOKEN_LENGTH) {
ShPpErrorToInfoLog("floating-point literal too long"); ShPpErrorToInfoLog("floating-point literal too long");
len = 1,str_len=1; len = 1,str_len=1;
} else { } else {
@ -284,7 +285,7 @@ static int lFloatConst(char *str, int len, int ch, yystypepp * yylvalpp)
} }
if (ch >= '0' && ch <= '9') { if (ch >= '0' && ch <= '9') {
while (ch >= '0' && ch <= '9') { while (ch >= '0' && ch <= '9') {
if (len < MAX_SYMBOL_NAME_LEN) { if (len < MAX_TOKEN_LENGTH) {
exp = exp*10 + ch - '0'; exp = exp*10 + ch - '0';
str[len++]=ch; str[len++]=ch;
ch = cpp->currentInput->getch(cpp->currentInput, yylvalpp); ch = cpp->currentInput->getch(cpp->currentInput, yylvalpp);
@ -301,7 +302,6 @@ static int lFloatConst(char *str, int len, int ch, yystypepp * yylvalpp)
} }
if (len == 0) { if (len == 0) {
yylvalpp->sc_fval = 0.0f;
yylvalpp->sc_dval = 0.0; yylvalpp->sc_dval = 0.0;
strcpy(str, "0.0"); strcpy(str, "0.0");
} else { } else {
@ -311,16 +311,17 @@ static int lFloatConst(char *str, int len, int ch, yystypepp * yylvalpp)
cpp->currentInput->ungetch(cpp->currentInput, ch2, yylvalpp); cpp->currentInput->ungetch(cpp->currentInput, ch2, yylvalpp);
cpp->currentInput->ungetch(cpp->currentInput, ch, yylvalpp); cpp->currentInput->ungetch(cpp->currentInput, ch, yylvalpp);
} else { } else {
if (len < MAX_SYMBOL_NAME_LEN) { if (len < MAX_TOKEN_LENGTH) {
str[len++] = ch; str[len++] = ch;
str[len++] = ch2; str[len++] = ch2;
isDouble = 1;
} else { } else {
ShPpErrorToInfoLog("floating-point literal too long"); ShPpErrorToInfoLog("floating-point literal too long");
len = 1,str_len=1; len = 1,str_len=1;
} }
} }
} else if (ch == 'f' || ch == 'F') { } else if (ch == 'f' || ch == 'F') {
if (len < MAX_SYMBOL_NAME_LEN) if (len < MAX_TOKEN_LENGTH)
str[len++] = ch; str[len++] = ch;
else { else {
ShPpErrorToInfoLog("floating-point literal too long"); ShPpErrorToInfoLog("floating-point literal too long");
@ -332,12 +333,14 @@ static int lFloatConst(char *str, int len, int ch, yystypepp * yylvalpp)
str[len]='\0'; str[len]='\0';
yylvalpp->sc_dval = strtod(str, 0); yylvalpp->sc_dval = strtod(str, 0);
yylvalpp->sc_fval = (float)yylvalpp->sc_dval;
} }
// Suffix: // Suffix:
strcpy(yylvalpp->symbol_name, str); strcpy(yylvalpp->symbol_name, str);
return CPP_FLOATCONSTANT; if (isDouble)
return CPP_DOUBLECONSTANT;
else
return CPP_FLOATCONSTANT;
} // lFloatConst } // lFloatConst
/////////////////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////////////////////
@ -346,8 +349,7 @@ static int lFloatConst(char *str, int len, int ch, yystypepp * yylvalpp)
static int byte_scan(InputSrc *in, yystypepp * yylvalpp) static int byte_scan(InputSrc *in, yystypepp * yylvalpp)
{ {
char symbol_name[MAX_SYMBOL_NAME_LEN + 1]; char tokenText[MAX_TOKEN_LENGTH + 1];
char string_val[MAX_STRING_LEN + 1];
int AlreadyComplained = 0; int AlreadyComplained = 0;
int len, ch, ii; int len, ch, ii;
unsigned ival = 0; unsigned ival = 0;
@ -368,7 +370,7 @@ static int byte_scan(InputSrc *in, yystypepp * yylvalpp)
default: default:
return ch; // Single character token return ch; // Single character token
case EOF: case EOF:
return -1; return EOF;
case 'A': case 'B': case 'C': case 'D': case 'E': case 'A': case 'B': case 'C': case 'D': case 'E':
case 'F': case 'G': case 'H': case 'I': case 'J': case 'F': case 'G': case 'H': case 'I': case 'J':
case 'K': case 'L': case 'M': case 'N': case 'O': case 'K': case 'L': case 'M': case 'N': case 'O':
@ -393,30 +395,32 @@ static int byte_scan(InputSrc *in, yystypepp * yylvalpp)
ch = nextch; ch = nextch;
} else } else
ShPpErrorToInfoLog("can only escape newlines"); ShPpErrorToInfoLog("can only escape newlines");
} else if (len < MAX_SYMBOL_NAME_LEN) { } else if (len < MAX_TOKEN_LENGTH) {
symbol_name[len] = ch; tokenText[len++] = ch;
len++;
ch = cpp->currentInput->getch(cpp->currentInput, yylvalpp); ch = cpp->currentInput->getch(cpp->currentInput, yylvalpp);
} else { } else {
ShPpErrorToInfoLog("name too long"); if (! AlreadyComplained) {
break; ShPpErrorToInfoLog("name too long");
AlreadyComplained = 1;
}
ch = cpp->currentInput->getch(cpp->currentInput, yylvalpp);
} }
} while ((ch >= 'a' && ch <= 'z') || } while ((ch >= 'a' && ch <= 'z') ||
(ch >= 'A' && ch <= 'Z') || (ch >= 'A' && ch <= 'Z') ||
(ch >= '0' && ch <= '9') || (ch >= '0' && ch <= '9') ||
ch == '_' || ch == '_' ||
ch == '\\'); ch == '\\');
if (len > MAX_SYMBOL_NAME_LEN)
len = MAX_SYMBOL_NAME_LEN; tokenText[len] = '\0';
symbol_name[len] = '\0';
cpp->currentInput->ungetch(cpp->currentInput, ch, yylvalpp); cpp->currentInput->ungetch(cpp->currentInput, ch, yylvalpp);
yylvalpp->sc_ident = LookUpAddString(atable, symbol_name); yylvalpp->sc_ident = LookUpAddString(atable, tokenText);
return CPP_IDENTIFIER; return CPP_IDENTIFIER;
break;
case '0': case '0':
yylvalpp->symbol_name[len++] = ch; yylvalpp->symbol_name[len++] = ch;
ch = cpp->currentInput->getch(cpp->currentInput, yylvalpp); ch = cpp->currentInput->getch(cpp->currentInput, yylvalpp);
if (ch == 'x' || ch == 'X') { if (ch == 'x' || ch == 'X') {
int uint = 0;
yylvalpp->symbol_name[len++] = ch; yylvalpp->symbol_name[len++] = ch;
ch = cpp->currentInput->getch(cpp->currentInput, yylvalpp); ch = cpp->currentInput->getch(cpp->currentInput, yylvalpp);
if ((ch >= '0' && ch <= '9') || if ((ch >= '0' && ch <= '9') ||
@ -425,10 +429,8 @@ static int byte_scan(InputSrc *in, yystypepp * yylvalpp)
{ {
ival = 0; ival = 0;
do { do {
if (len >= MAX_SYMBOL_NAME_LEN)
break;
yylvalpp->symbol_name[len++] = ch;
if (ival <= 0x0fffffff) { if (ival <= 0x0fffffff) {
yylvalpp->symbol_name[len++] = ch;
if (ch >= '0' && ch <= '9') { if (ch >= '0' && ch <= '9') {
ii = ch - '0'; ii = ch - '0';
} else if (ch >= 'A' && ch <= 'F') { } else if (ch >= 'A' && ch <= 'F') {
@ -440,9 +442,10 @@ static int byte_scan(InputSrc *in, yystypepp * yylvalpp)
ival = (ival << 4) | ii; ival = (ival << 4) | ii;
} else { } else {
if (! AlreadyComplained) { if (! AlreadyComplained) {
ShPpErrorToInfoLog("hexidecimal literal too long"); ShPpErrorToInfoLog("hexidecimal literal too big");
AlreadyComplained = 1; AlreadyComplained = 1;
} }
ival = 0xffffffff;
} }
ch = cpp->currentInput->getch(cpp->currentInput, yylvalpp); ch = cpp->currentInput->getch(cpp->currentInput, yylvalpp);
} while ((ch >= '0' && ch <= '9') || } while ((ch >= '0' && ch <= '9') ||
@ -451,38 +454,51 @@ static int byte_scan(InputSrc *in, yystypepp * yylvalpp)
} else { } else {
ShPpErrorToInfoLog("bad digit in hexidecimal literal"); ShPpErrorToInfoLog("bad digit in hexidecimal literal");
} }
if (ch == 'u' || ch == 'U') if (ch == 'u' || ch == 'U') {
yylvalpp->symbol_name[len++] = ch; if (len < MAX_TOKEN_LENGTH)
else yylvalpp->symbol_name[len++] = ch;
uint = 1;
} else
cpp->currentInput->ungetch(cpp->currentInput, ch, yylvalpp); cpp->currentInput->ungetch(cpp->currentInput, ch, yylvalpp);
yylvalpp->symbol_name[len] = '\0'; yylvalpp->symbol_name[len] = '\0';
yylvalpp->sc_int = (int)ival; yylvalpp->sc_int = (int)ival;
return CPP_INTCONSTANT; if (uint)
return CPP_UINTCONSTANT;
else
return CPP_INTCONSTANT;
} else if (ch >= '0' && ch <= '7') { // octal integer constants } else if (ch >= '0' && ch <= '7') { // octal integer constants
int uint = 0;
ival = 0; ival = 0;
do { do {
if (len >= MAX_SYMBOL_NAME_LEN)
break;
yylvalpp->symbol_name[len++] = ch;
if (ival <= 0x1fffffff) { if (ival <= 0x1fffffff) {
yylvalpp->symbol_name[len++] = ch;
ii = ch - '0'; ii = ch - '0';
ival = (ival << 3) | ii; ival = (ival << 3) | ii;
} else { } else {
if (!AlreadyComplained) { if (!AlreadyComplained) {
ShPpErrorToInfoLog("octal literal too long"); ShPpErrorToInfoLog("octal literal too big");
AlreadyComplained = 1; AlreadyComplained = 1;
} }
ival = 0xffffffff;
} }
ch = cpp->currentInput->getch(cpp->currentInput, yylvalpp); ch = cpp->currentInput->getch(cpp->currentInput, yylvalpp);
} while (ch >= '0' && ch <= '7'); } while (ch >= '0' && ch <= '7');
if (ch == '.' || ch == 'e' || ch == 'f' || ch == 'h' || ch == 'x'|| ch == 'E' || ch == 'F' || ch == 'l' || ch == 'L') if (ch == '.' || ch == 'e' || ch == 'f' || ch == 'h' || ch == 'x'|| ch == 'E' || ch == 'F' || ch == 'l' || ch == 'L')
return lFloatConst(yylvalpp->symbol_name, len, ch, yylvalpp); return lFloatConst(yylvalpp->symbol_name, len, ch, yylvalpp);
else if (ch == 'u' || ch == 'U') {
if (len < MAX_TOKEN_LENGTH)
yylvalpp->symbol_name[len++] = ch;
uint = 1;
} else
cpp->currentInput->ungetch(cpp->currentInput, ch, yylvalpp);
yylvalpp->symbol_name[len] = '\0'; yylvalpp->symbol_name[len] = '\0';
cpp->currentInput->ungetch(cpp->currentInput, ch, yylvalpp);
yylvalpp->sc_int = (int)ival; yylvalpp->sc_int = (int)ival;
return CPP_INTCONSTANT; if (uint)
return CPP_UINTCONSTANT;
else
return CPP_INTCONSTANT;
} else { } else {
cpp->currentInput->ungetch(cpp->currentInput, ch, yylvalpp); cpp->currentInput->ungetch(cpp->currentInput, ch, yylvalpp);
ch = '0'; ch = '0';
@ -491,25 +507,30 @@ static int byte_scan(InputSrc *in, yystypepp * yylvalpp)
case '1': case '2': case '3': case '4': case '1': case '2': case '3': case '4':
case '5': case '6': case '7': case '8': case '9': case '5': case '6': case '7': case '8': case '9':
do { do {
if (len < MAX_SYMBOL_NAME_LEN) { if (len < MAX_TOKEN_LENGTH) {
if (len > 0 || ch != '0') { if (len > 0 || ch != '0') {
yylvalpp->symbol_name[len] = ch; yylvalpp->symbol_name[len] = ch;
len++; len++;
} }
ch = cpp->currentInput->getch(cpp->currentInput, yylvalpp);
} else { } else {
ShPpErrorToInfoLog("token too long"); if (! AlreadyComplained) {
break; ShPpErrorToInfoLog("integer literal too long");
AlreadyComplained = 1;
}
} }
ch = cpp->currentInput->getch(cpp->currentInput, yylvalpp);
} while (ch >= '0' && ch <= '9'); } while (ch >= '0' && ch <= '9');
if (ch == '.' || ch == 'e' || ch == 'f' || ch == 'h' || ch == 'x'|| ch == 'E' || ch == 'F' || ch == 'l' || ch == 'L') { if (ch == '.' || ch == 'e' || ch == 'f' || ch == 'h' || ch == 'x'|| ch == 'E' || ch == 'F' || ch == 'l' || ch == 'L') {
return lFloatConst(yylvalpp->symbol_name, len, ch, yylvalpp); return lFloatConst(yylvalpp->symbol_name, len, ch, yylvalpp);
} else { } else {
// Finish handling signed and unsigned integers // Finish handling signed and unsigned integers
int numericLen = len; int numericLen = len;
if (ch == 'u' || ch == 'U') int uint = 0;
yylvalpp->symbol_name[len++] = ch; if (ch == 'u' || ch == 'U') {
else if (len < MAX_TOKEN_LENGTH)
yylvalpp->symbol_name[len++] = ch;
uint = 1;
} else
cpp->currentInput->ungetch(cpp->currentInput, ch, yylvalpp); cpp->currentInput->ungetch(cpp->currentInput, ch, yylvalpp);
yylvalpp->symbol_name[len] = '\0'; yylvalpp->symbol_name[len] = '\0';
@ -517,16 +538,18 @@ static int byte_scan(InputSrc *in, yystypepp * yylvalpp)
for (ii = 0; ii < numericLen; ii++) { for (ii = 0; ii < numericLen; ii++) {
ch = yylvalpp->symbol_name[ii] - '0'; ch = yylvalpp->symbol_name[ii] - '0';
if ((ival > 429496729) || (ival == 429496729 && ch >= 6)) { if ((ival > 429496729) || (ival == 429496729 && ch >= 6)) {
if (! AlreadyComplained) { ShPpErrorToInfoLog("integral literal too big");
ShPpErrorToInfoLog("integral literal too long"); ival = -1;
AlreadyComplained = 1; break;
} } else
} ival = ival * 10 + ch;
ival = ival * 10 + ch;
} }
yylvalpp->sc_int = (int)ival; yylvalpp->sc_int = (int)ival;
return CPP_INTCONSTANT; if (uint)
return CPP_UINTCONSTANT;
else
return CPP_INTCONSTANT;
} }
break; break;
case '-': case '-':
@ -737,39 +760,39 @@ static int byte_scan(InputSrc *in, yystypepp * yylvalpp)
break; break;
} }
} }
if (len < MAX_STRING_LEN) { if (len < MAX_TOKEN_LENGTH) {
string_val[len] = ch; tokenText[len] = ch;
len++; len++;
ch = cpp->currentInput->getch(cpp->currentInput, yylvalpp); ch = cpp->currentInput->getch(cpp->currentInput, yylvalpp);
} else } else
break; break;
}; };
string_val[len] = '\0'; tokenText[len] = '\0';
if (ch == '"') { if (ch == '"') {
yylvalpp->sc_ident = LookUpAddString(atable, string_val); yylvalpp->sc_ident = LookUpAddString(atable, tokenText);
return CPP_STRCONSTANT; return CPP_STRCONSTANT;
} else { } else {
ShPpErrorToInfoLog("end of line in string"); ShPpErrorToInfoLog("end of line in string");
return ERROR_SY; return CPP_ERROR_SY;
} }
} }
} }
} // byte_scan } // byte_scan
int yylex_CPP(char* buf, int maxSize) const char* PpTokenize(yystypepp* yylvalpp)
{ {
yystypepp yylvalpp;
int token = '\n'; int token = '\n';
for(;;) { for(;;) {
char* tokenString = 0; char* tokenString = 0;
token = cpp->currentInput->scan(cpp->currentInput, &yylvalpp); token = cpp->currentInput->scan(cpp->currentInput, yylvalpp);
if(check_EOF(token)) yylvalpp->ppToken = token;
if (check_EOF(token))
return 0; return 0;
if (token == '#') { if (token == '#') {
if (cpp->previous_token == '\n'|| cpp->previous_token == 0) { if (cpp->previous_token == '\n'|| cpp->previous_token == 0) {
token = readCPPline(&yylvalpp); token = readCPPline(yylvalpp);
if(check_EOF(token)) if(check_EOF(token))
return 0; return 0;
continue; continue;
@ -779,42 +802,34 @@ int yylex_CPP(char* buf, int maxSize)
} }
} }
cpp->previous_token = token; cpp->previous_token = token;
// expand macros
if (token == CPP_IDENTIFIER && MacroExpand(yylvalpp.sc_ident, &yylvalpp, 0) == 1) {
cpp->notAVersionToken = 1;
continue;
}
if (token == '\n') if (token == '\n')
continue; continue;
if (token == CPP_IDENTIFIER) { cpp->notAVersionToken = 1;
cpp->notAVersionToken = 1;
tokenString = GetStringOfAtom(atable,yylvalpp.sc_ident); // expand macros
} else if (token == CPP_FLOATCONSTANT||token == CPP_INTCONSTANT){ if (token == CPP_IDENTIFIER && MacroExpand(yylvalpp->sc_ident, yylvalpp, 0) == 1)
cpp->notAVersionToken = 1; continue;
tokenString = yylvalpp.symbol_name;
} else { if (token == CPP_IDENTIFIER)
cpp->notAVersionToken = 1; tokenString = GetStringOfAtom(atable, yylvalpp->sc_ident);
tokenString = GetStringOfAtom(atable,token); else if (token == CPP_INTCONSTANT || token == CPP_UINTCONSTANT ||
} token == CPP_FLOATCONSTANT || token == CPP_DOUBLECONSTANT)
tokenString = yylvalpp->symbol_name;
else
tokenString = GetStringOfAtom(atable, token);
if (tokenString) { if (tokenString) {
if ((signed)strlen(tokenString) >= maxSize) { if (tokenString[0] != 0)
cpp->tokensBeforeEOF = 1; cpp->tokensBeforeEOF = 1;
return maxSize;
} else if (strlen(tokenString) > 0) {
strcpy(buf, tokenString);
cpp->tokensBeforeEOF = 1;
return (int)strlen(tokenString);
}
return 0; return tokenString;
} }
} }
return 0; return 0;
} // yylex } // PpTokenize
//Checks if the token just read is EOF or not. //Checks if the token just read is EOF or not.
int check_EOF(int token) int check_EOF(int token)

View File

@ -81,9 +81,7 @@ NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
#if !defined(__SCANNER_H) #if !defined(__SCANNER_H)
#define __SCANNER_H 1 #define __SCANNER_H 1
#define MAX_SYMBOL_NAME_LEN 1025 #include "preprocess.h"
#define MAX_STRING_LEN 1025
#include "parser.h" #include "parser.h"
// Not really atom table stuff but needed first... // Not really atom table stuff but needed first...
@ -91,23 +89,8 @@ NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
extern "C" { extern "C" {
#endif #endif
typedef struct SourceLoc_Rec {
unsigned short file, line;
} SourceLoc;
int yyparse (void); int yyparse (void);
int yylex_CPP(char* buf, int maxSize);
typedef struct InputSrc {
struct InputSrc *prev;
int (*scan)(struct InputSrc *, yystypepp *);
int (*getch)(struct InputSrc *, yystypepp *);
void (*ungetch)(struct InputSrc *, int, yystypepp *);
int name; /* atom */
int line;
} InputSrc;
int InitScanner(CPPStruct *cpp); // Intialise the cpp scanner. int InitScanner(CPPStruct *cpp); // Intialise the cpp scanner.
int ScanFromString(char *); // Start scanning the input from the string mentioned. int ScanFromString(char *); // Start scanning the input from the string mentioned.
int check_EOF(int); // check if we hit a EOF abruptly int check_EOF(int); // check if we hit a EOF abruptly

View File

@ -81,7 +81,7 @@ NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
#if !defined(__SLGLOBALS_H) #if !defined(__SLGLOBALS_H)
#define __SLGLOBALS_H 1 #define __SLGLOBALS_H 1
typedef struct CPPStruct_Rec CPPStruct; #include "preprocess.h"
// TODO: threading: Multi-threading note: The existence of this global makes // TODO: threading: Multi-threading note: The existence of this global makes
// this preprocessing single-threaded only. // this preprocessing single-threaded only.
@ -101,7 +101,6 @@ extern CPPStruct *cpp;
#include "cpp.h" #include "cpp.h"
#include "tokens.h" #include "tokens.h"
#include "symbols.h" #include "symbols.h"
#include "compile.h"
#if !defined(NO_PARSER) #if !defined(NO_PARSER)
#include "parser.h" #include "parser.h"
#endif #endif

View File

@ -257,8 +257,10 @@ void RecordToken(TokenStream *pTok, int token, yystypepp * yylvalpp)
lAddByte(pTok, (unsigned char) *s++); lAddByte(pTok, (unsigned char) *s++);
lAddByte(pTok, 0); lAddByte(pTok, 0);
break; break;
case CPP_FLOATCONSTANT:
case CPP_INTCONSTANT: case CPP_INTCONSTANT:
case CPP_UINTCONSTANT:
case CPP_FLOATCONSTANT:
case CPP_DOUBLECONSTANT:
str = yylvalpp->symbol_name; str = yylvalpp->symbol_name;
while (*str){ while (*str){
lAddByte(pTok, (unsigned char) *str); lAddByte(pTok, (unsigned char) *str);
@ -293,8 +295,9 @@ void RewindTokenStream(TokenStream *pTok)
int ReadToken(TokenStream *pTok, yystypepp * yylvalpp) int ReadToken(TokenStream *pTok, yystypepp * yylvalpp)
{ {
char symbol_name[MAX_SYMBOL_NAME_LEN + 1]; //TODO: PP: why is this different than byte_scan
char string_val[MAX_STRING_LEN + 1];
char tokenText[MAX_TOKEN_LENGTH + 1];
int ltoken, len; int ltoken, len;
char ch; char ch;
@ -312,8 +315,8 @@ int ReadToken(TokenStream *pTok, yystypepp * yylvalpp)
(ch >= '0' && ch <= '9') || (ch >= '0' && ch <= '9') ||
ch == '_') ch == '_')
{ {
if (len < MAX_SYMBOL_NAME_LEN) { if (len < MAX_TOKEN_LENGTH) {
symbol_name[len] = ch; tokenText[len] = ch;
len++; len++;
ch = lReadByte(pTok); ch = lReadByte(pTok);
} else { } else {
@ -321,30 +324,31 @@ int ReadToken(TokenStream *pTok, yystypepp * yylvalpp)
break; break;
} }
} }
symbol_name[len] = '\0'; tokenText[len] = '\0';
assert(ch == '\0'); assert(ch == '\0');
yylvalpp->sc_ident = LookUpAddString(atable, symbol_name); yylvalpp->sc_ident = LookUpAddString(atable, tokenText);
return CPP_IDENTIFIER; return CPP_IDENTIFIER;
break; break;
case CPP_STRCONSTANT: case CPP_STRCONSTANT:
len = 0; len = 0;
while ((ch = lReadByte(pTok)) != 0) { while ((ch = lReadByte(pTok)) != 0) {
if (len < MAX_STRING_LEN) if (len < MAX_TOKEN_LENGTH)
string_val[len++] = ch; tokenText[len++] = ch;
else else
break; break;
} }
string_val[len] = 0; tokenText[len] = 0;
yylvalpp->sc_ident = LookUpAddString(atable, string_val); yylvalpp->sc_ident = LookUpAddString(atable, tokenText);
break; break;
case CPP_FLOATCONSTANT: case CPP_FLOATCONSTANT:
case CPP_DOUBLECONSTANT:
len = 0; len = 0;
ch = lReadByte(pTok); ch = lReadByte(pTok);
while ((ch >= '0' && ch <= '9')||(ch=='e'||ch=='E'||ch=='.')||(ch=='+'||ch=='-')) while ((ch >= '0' && ch <= '9') || ch=='e' || ch=='E' || ch=='.' || ch=='+' || ch=='-' || ch=='l' || ch=='L' || ch=='f'|| ch=='F')
{ {
if (len < MAX_SYMBOL_NAME_LEN) { if (len < MAX_TOKEN_LENGTH) {
symbol_name[len] = ch; tokenText[len] = ch;
len++; len++;
ch = lReadByte(pTok); ch = lReadByte(pTok);
} else { } else {
@ -352,18 +356,19 @@ int ReadToken(TokenStream *pTok, yystypepp * yylvalpp)
break; break;
} }
} }
symbol_name[len] = '\0'; tokenText[len] = '\0';
assert(ch == '\0'); assert(ch == '\0');
strcpy(yylvalpp->symbol_name,symbol_name); strcpy(yylvalpp->symbol_name, tokenText);
yylvalpp->sc_fval=(float)atof(yylvalpp->symbol_name); yylvalpp->sc_dval = atof(yylvalpp->symbol_name);
break; break;
case CPP_INTCONSTANT: case CPP_INTCONSTANT:
case CPP_UINTCONSTANT:
len = 0; len = 0;
ch = lReadByte(pTok); ch = lReadByte(pTok);
while ((ch >= '0' && ch <= '9')) while ((ch >= '0' && ch <= '9') || ch == 'u' || ch == 'U')
{ {
if (len < MAX_SYMBOL_NAME_LEN) { if (len < MAX_TOKEN_LENGTH) {
symbol_name[len] = ch; tokenText[len] = ch;
len++; len++;
ch = lReadByte(pTok); ch = lReadByte(pTok);
} else { } else {
@ -371,10 +376,10 @@ int ReadToken(TokenStream *pTok, yystypepp * yylvalpp)
break; break;
} }
} }
symbol_name[len] = '\0'; tokenText[len] = '\0';
assert(ch == '\0'); assert(ch == '\0');
strcpy(yylvalpp->symbol_name,symbol_name); strcpy(yylvalpp->symbol_name,tokenText);
yylvalpp->sc_int=atoi(yylvalpp->symbol_name); yylvalpp->sc_int = atoi(yylvalpp->symbol_name);
break; break;
case '(': case '(':
yylvalpp->sc_int = lReadByte(pTok); yylvalpp->sc_int = lReadByte(pTok);
@ -456,7 +461,7 @@ void UngetToken(int token, yystypepp * yylvalpp) {
void DumpTokenStream(FILE *fp, TokenStream *s, yystypepp * yylvalpp) { void DumpTokenStream(FILE *fp, TokenStream *s, yystypepp * yylvalpp) {
int token; int token;
const int maxSize = MAX_SYMBOL_NAME_LEN + 5; const int maxSize = MAX_TOKEN_LENGTH + 5;
char str[100]; char str[100];
if (fp == 0) fp = stdout; if (fp == 0) fp = stdout;
@ -471,10 +476,12 @@ void DumpTokenStream(FILE *fp, TokenStream *s, yystypepp * yylvalpp) {
snprintf(str, maxSize, "\"%s\"", GetAtomString(atable, yylvalpp->sc_ident)); snprintf(str, maxSize, "\"%s\"", GetAtomString(atable, yylvalpp->sc_ident));
break; break;
case CPP_FLOATCONSTANT: case CPP_FLOATCONSTANT:
//printf("%g9.6 ", yylvalpp->sc_fval); case CPP_DOUBLECONSTANT:
printf("%g9.6 ", yylvalpp->sc_dval);
break; break;
case CPP_INTCONSTANT: case CPP_INTCONSTANT:
//printf("%d ", yylvalpp->sc_int); case CPP_UINTCONSTANT:
printf("%d ", yylvalpp->sc_int);
break; break;
default: default:
if (token >= 127) if (token >= 127)