Commit 1f4104fb by John Kessenich

Fix memory corruption problem in the preprocessor, removing custom…

Fix memory corruption problem in the preprocessor, removing custom hash-tables/etc. and replacing with std containers. git-svn-id: https://cvs.khronos.org/svn/repos/ogl/trunk/ecosystem/public/sdk/tools/glslang@23623 e7fa87d3-cd2b-0410-9028-fcbf551c1848
parent ab308035
...@@ -84,10 +84,9 @@ NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. ...@@ -84,10 +84,9 @@ NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
namespace glslang { namespace glslang {
TPpContext::TPpContext(TParseContext& pc) : TPpContext::TPpContext(TParseContext& pc) :
preamble(0), strings(0), notAVersionToken(false), parseContext(pc), preamble(0), strings(0), notAVersionToken(false), parseContext(pc)
ScopeList(0), CurrentScope(0), GlobalScope(0)
{ {
InitAtomTable(&atomTable, 0); InitAtomTable();
InitScanner(this); InitScanner(this);
ifdepth = 0; ifdepth = 0;
...@@ -98,9 +97,8 @@ TPpContext::TPpContext(TParseContext& pc) : ...@@ -98,9 +97,8 @@ TPpContext::TPpContext(TParseContext& pc) :
TPpContext::~TPpContext() TPpContext::~TPpContext()
{ {
FinalCPP();
delete [] preamble; delete [] preamble;
FreeAtomTable(&atomTable);
FreeScanner();
} }
void TPpContext::setPreamble(const char* p, size_t l) void TPpContext::setPreamble(const char* p, size_t l)
......
...@@ -80,6 +80,8 @@ NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. ...@@ -80,6 +80,8 @@ NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
#include "../ParseHelper.h" #include "../ParseHelper.h"
#include <hash_map>
namespace glslang { namespace glslang {
class TPpToken { class TPpToken {
...@@ -141,42 +143,8 @@ public: ...@@ -141,42 +143,8 @@ public:
}; };
// //
// From PpAtom.cpp // From Pp.cpp
// //
struct StringTable {
char *strings;
int nextFree;
int size;
};
struct HashEntry {
int index; // String table offset of string representation
int value; // Atom (symbol) value
};
static const int hashTableMaxCollisions = 3;
struct HashTable {
HashEntry *entry;
int size;
int entries;
int counts[hashTableMaxCollisions + 1];
};
struct AtomTable {
StringTable stable; // String table.
HashTable htable; // Hashes string to atom number and token value. Multiple strings can
// have the same token value but each unique string is a unique atom.
int *amap; // Maps atom value to offset in string table. Atoms all map to unique
// strings except for some undefined values in the lower, fixed part
// of the atom table that map to "<undefined>". The lowest 256 atoms
// correspond to single character ASCII values except for alphanumeric
// characters and '_', which can be other tokens. Next come the
// language tokens with their atom values equal to the token value.
// Then come predefined atoms, followed by user specified identifiers.
int *arev; // Reversed atom for symbol table use.
int nextFree;
int size;
};
struct MacroSymbol { struct MacroSymbol {
int argc; int argc;
...@@ -186,19 +154,9 @@ public: ...@@ -186,19 +154,9 @@ public:
unsigned undef:1; unsigned undef:1;
}; };
typedef enum symbolkind {
MACRO_S
} symbolkind;
struct Symbol { struct Symbol {
Symbol *left, *right; int atom;
Symbol *next;
int name; // Name atom
TSourceLoc loc;
symbolkind kind;
union {
MacroSymbol mac; MacroSymbol mac;
} details;
}; };
struct SymbolList { struct SymbolList {
...@@ -206,18 +164,9 @@ public: ...@@ -206,18 +164,9 @@ public:
Symbol *symb; Symbol *symb;
}; };
struct Scope { MemoryPool *pool;
Scope *next, *prev; // doubly-linked list of all scopes typedef std::hash_map<int, Symbol*> TSymbol;
Scope *parent; TSymbol symbols; // this has light use... just defined macros
Scope *funScope; // Points to base scope of enclosing function
MemoryPool *pool; // pool used for allocation in this scope
Symbol *symbols;
int level; // 0 = super globals, 1 = globals, etc.
// Only used at global scope (level 1):
SymbolList *programs; // List of programs for this compilation.
};
protected: protected:
char* preamble; // string to parse, all before line 1 of string 0, it is 0 if no preamble char* preamble; // string to parse, all before line 1 of string 0, it is 0 if no preamble
...@@ -277,11 +226,9 @@ protected: ...@@ -277,11 +226,9 @@ protected:
int compatibilityAtom; int compatibilityAtom;
int esAtom; int esAtom;
int extensionAtom; int extensionAtom;
Scope *macros;
TSourceLoc ifloc; /* outermost #if */ TSourceLoc ifloc; /* outermost #if */
int InitCPP(); int InitCPP();
int FreeCPP();
int FinalCPP(); int FinalCPP();
int CPPdefine(TPpToken * yylvalpp); int CPPdefine(TPpToken * yylvalpp);
int CPPundef(TPpToken * yylvalpp); int CPPundef(TPpToken * yylvalpp);
...@@ -307,18 +254,9 @@ protected: ...@@ -307,18 +254,9 @@ protected:
// //
// from PpSymbols.cpp // from PpSymbols.cpp
// //
Scope *ScopeList; Symbol *NewSymbol(int name);
Scope *CurrentScope; Symbol *AddSymbol(int atom);
Scope *GlobalScope; Symbol *LookUpSymbol(int atom);
Scope *NewScopeInPool(MemoryPool *pool);
void PushScope(Scope *fScope);
Scope *PopScope(void);
Symbol *NewSymbol(TSourceLoc *loc, Scope *fScope, int name, symbolkind kind);
void lAddToTree(Symbol **fSymbols, Symbol *fSymb, AtomTable *atable);
Symbol *AddSymbol(TSourceLoc *loc, Scope *fScope, int atom, symbolkind kind);
Symbol *LookUpLocalSymbol(Scope *fScope, int atom);
Symbol *LookUpSymbol(Scope *fScope, int atom);
// //
// From PpTokens.cpp // From PpTokens.cpp
...@@ -356,7 +294,6 @@ protected: ...@@ -356,7 +294,6 @@ protected:
char *p; char *p;
}; };
int InitScanner(TPpContext *cpp); int InitScanner(TPpContext *cpp);
int FreeScanner(void);
static int str_getch(TPpContext*, StringInputSrc *in); static int str_getch(TPpContext*, StringInputSrc *in);
static void str_ungetch(TPpContext*, StringInputSrc *in, int ch, TPpToken *type); static void str_ungetch(TPpContext*, StringInputSrc *in, int ch, TPpToken *type);
int ScanFromString(char *s); int ScanFromString(char *s);
...@@ -367,18 +304,15 @@ protected: ...@@ -367,18 +304,15 @@ protected:
// //
// From PpAtom.cpp // From PpAtom.cpp
// //
AtomTable atomTable; typedef std::hash_map<const TString, int> TAtomMap;
int InitAtomTable(AtomTable *atable, int htsize); typedef TVector<const TString*> TStringMap;
void FreeAtomTable(AtomTable *atable); TAtomMap atomMap;
int AddAtom(AtomTable *atable, const char *s); TStringMap stringMap;
int AddAtomFixed(AtomTable *atable, const char *s, int atom); int nextAtom;
void PrintAtomTable(AtomTable *atable); void InitAtomTable();
int IncreaseHashTableSize(TPpContext::AtomTable *atable); int AddAtomFixed(const char *s, int atom);
int LookUpAddStringHash(AtomTable *atable, const char *s); int LookUpAddString(const char *s);
int LookUpAddString(AtomTable *atable, const char *s); const char *GetAtomString(int atom);
const char *GetAtomString(AtomTable *atable, int atom);
int GetReversedAtom(AtomTable *atable, int atom);
char* GetStringOfAtom(AtomTable *atable, int atom);
// //
// From PpMemory.cpp // From PpMemory.cpp
......
...@@ -122,11 +122,6 @@ int TPpContext::InitScanner(TPpContext *cpp) ...@@ -122,11 +122,6 @@ int TPpContext::InitScanner(TPpContext *cpp)
return 1; return 1;
} // InitScanner } // InitScanner
int TPpContext::FreeScanner(void)
{
return (FreeCPP());
}
/* /*
* str_getch() * str_getch()
* takes care of reading from multiple strings. * takes care of reading from multiple strings.
...@@ -386,7 +381,7 @@ int TPpContext::byte_scan(TPpContext* pp, InputSrc *in, TPpToken * yylvalpp) ...@@ -386,7 +381,7 @@ int TPpContext::byte_scan(TPpContext* pp, InputSrc *in, TPpToken * yylvalpp)
tokenText[len] = '\0'; tokenText[len] = '\0';
pp->currentInput->ungetch(pp, pp->currentInput, ch, yylvalpp); pp->currentInput->ungetch(pp, pp->currentInput, ch, yylvalpp);
yylvalpp->atom = pp->LookUpAddString(&pp->atomTable, tokenText); yylvalpp->atom = pp->LookUpAddString(tokenText);
return CPP_IDENTIFIER; return CPP_IDENTIFIER;
case '0': case '0':
...@@ -769,7 +764,7 @@ int TPpContext::byte_scan(TPpContext* pp, InputSrc *in, TPpToken * yylvalpp) ...@@ -769,7 +764,7 @@ int TPpContext::byte_scan(TPpContext* pp, InputSrc *in, TPpToken * yylvalpp)
}; };
tokenText[len] = '\0'; tokenText[len] = '\0';
if (ch == '"') { if (ch == '"') {
yylvalpp->atom = pp->LookUpAddString(&pp->atomTable, tokenText); yylvalpp->atom = pp->LookUpAddString(tokenText);
return CPP_STRCONSTANT; return CPP_STRCONSTANT;
} else { } else {
pp->parseContext.error(yylvalpp->loc, "end of line in string", "string", ""); pp->parseContext.error(yylvalpp->loc, "end of line in string", "string", "");
...@@ -785,7 +780,7 @@ const char* TPpContext::tokenize(TPpToken* yylvalpp) ...@@ -785,7 +780,7 @@ const char* TPpContext::tokenize(TPpToken* yylvalpp)
for(;;) { for(;;) {
char* tokenString = 0; const char* tokenString = 0;
token = currentInput->scan(this, currentInput, yylvalpp); token = currentInput->scan(this, currentInput, yylvalpp);
yylvalpp->ppToken = token; yylvalpp->ppToken = token;
if (check_EOF(token)) if (check_EOF(token))
...@@ -813,12 +808,12 @@ const char* TPpContext::tokenize(TPpToken* yylvalpp) ...@@ -813,12 +808,12 @@ const char* TPpContext::tokenize(TPpToken* yylvalpp)
continue; continue;
if (token == CPP_IDENTIFIER) if (token == CPP_IDENTIFIER)
tokenString = GetStringOfAtom(&atomTable, yylvalpp->atom); tokenString = GetAtomString(yylvalpp->atom);
else if (token == CPP_INTCONSTANT || token == CPP_UINTCONSTANT || else if (token == CPP_INTCONSTANT || token == CPP_UINTCONSTANT ||
token == CPP_FLOATCONSTANT || token == CPP_DOUBLECONSTANT) token == CPP_FLOATCONSTANT || token == CPP_DOUBLECONSTANT)
tokenString = yylvalpp->name; tokenString = yylvalpp->name;
else else
tokenString = GetStringOfAtom(&atomTable, token); tokenString = GetAtomString(token);
if (tokenString) { if (tokenString) {
if (tokenString[0] != 0) if (tokenString[0] != 0)
......
...@@ -90,237 +90,46 @@ NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. ...@@ -90,237 +90,46 @@ NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
/////////////////////////////////// Symbol Table Variables: /////////////////////////////////// /////////////////////////////////// Symbol Table Variables: ///////////////////////////////////
/////////////////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////////////////////
namespace {
using namespace glslang;
void unlinkScope(void *_scope, void* scopeList)
{
TPpContext::Scope *scope = (TPpContext::Scope*)_scope;
if (scope->next)
scope->next->prev = scope->prev;
if (scope->prev)
scope->prev->next = scope->next;
else
*(TPpContext::Scope**)scopeList = scope->next;
}
} // end anonymous namespace
namespace glslang { namespace glslang {
/* /*
* NewScope() * Allocate a new symbol node;
* *
*/ */
TPpContext::Scope* TPpContext::NewScopeInPool(MemoryPool *pool) TPpContext::Symbol* TPpContext::NewSymbol(int atom)
{
Scope *lScope;
lScope = (Scope*)mem_Alloc(pool, sizeof(Scope));
lScope->pool = pool;
lScope->parent = NULL;
lScope->funScope = NULL;
lScope->symbols = NULL;
lScope->level = 0;
lScope->programs = NULL;
if ((lScope->next = ScopeList))
ScopeList->prev = lScope;
lScope->prev = 0;
ScopeList = lScope;
mem_AddCleanup(pool, unlinkScope, lScope, &ScopeList);
return lScope;
} // NewScope
/*
* PushScope()
*
*/
void TPpContext::PushScope(Scope *fScope)
{
Scope *lScope;
if (CurrentScope) {
fScope->level = CurrentScope->level + 1;
if (fScope->level == 1) {
if (!GlobalScope) {
/* HACK - CTD -- if GlobalScope==NULL and level==1, we're
* defining a function in the superglobal scope. Things
* will break if we leave the level as 1, so we arbitrarily
* set it to 2 */
fScope->level = 2;
}
}
if (fScope->level >= 2) {
lScope = fScope;
while (lScope->level > 2)
lScope = lScope->next;
fScope->funScope = lScope;
}
} else {
fScope->level = 0;
}
fScope->parent = CurrentScope;
CurrentScope = fScope;
} // PushScope
/*
* PopScope()
*
*/
TPpContext::Scope* TPpContext::PopScope(void)
{
Scope *lScope;
lScope = CurrentScope;
if (CurrentScope)
CurrentScope = CurrentScope->parent;
return lScope;
} // PopScope
/*
* NewSymbol() - Allocate a new symbol node;
*
*/
TPpContext::Symbol* TPpContext::NewSymbol(TSourceLoc *loc, Scope *fScope, int name, symbolkind kind)
{ {
Symbol *lSymb; Symbol *lSymb;
char *pch; char *pch;
int ii; int ii;
lSymb = (Symbol *) mem_Alloc(fScope->pool, sizeof(Symbol)); lSymb = (Symbol *) mem_Alloc(pool, sizeof(Symbol));
lSymb->left = NULL; lSymb->atom = atom;
lSymb->right = NULL;
lSymb->next = NULL;
lSymb->name = name;
lSymb->loc = *loc;
lSymb->kind = kind;
// Clear union area:
pch = (char *) &lSymb->details; // Clear macro
for (ii = 0; ii < sizeof(lSymb->details); ii++) pch = (char *) &lSymb->mac;
for (ii = 0; ii < sizeof(lSymb->mac); ii++)
*pch++ = 0; *pch++ = 0;
return lSymb;
} // NewSymbol
/*
* lAddToTree() - Using a binary tree is not a good idea for basic atom values because they
* are generated in order. We'll fix this later (by reversing the bit pattern).
*/
void TPpContext::lAddToTree(Symbol **fSymbols, Symbol *fSymb, AtomTable *atable)
{
TPpContext::Symbol *lSymb;
int lrev, frev;
lSymb = *fSymbols;
if (lSymb) {
frev = GetReversedAtom(atable, fSymb->name);
while (lSymb) {
lrev = GetReversedAtom(atable, lSymb->name);
if (lrev == frev) {
printf("GetAtomString(atable, fSymb->name)");
break;
} else {
if (lrev > frev) {
if (lSymb->left) {
lSymb = lSymb->left;
} else {
lSymb->left = fSymb;
break;
}
} else {
if (lSymb->right) {
lSymb = lSymb->right;
} else {
lSymb->right = fSymb;
break;
}
}
}
}
} else {
*fSymbols = fSymb;
}
} // lAddToTree
/*
* AddSymbol() - Add a variable, type, or function name to a scope.
*
*/
TPpContext::Symbol* TPpContext::AddSymbol(TSourceLoc *loc, Scope *fScope, int atom, symbolkind kind)
{
Symbol *lSymb;
if (!fScope)
fScope = CurrentScope;
lSymb = NewSymbol(loc, fScope, atom, kind);
lAddToTree(&fScope->symbols, lSymb, &atomTable);
return lSymb; return lSymb;
} // AddSymbol }
/*********************************************************************************************/
/************************************ Symbol Semantic Functions ******************************/
/*********************************************************************************************/
/*
* LookUpLocalSymbol()
*
*/
TPpContext::Symbol* TPpContext::LookUpLocalSymbol(Scope *fScope, int atom) TPpContext::Symbol* TPpContext::AddSymbol(int atom)
{ {
Symbol *lSymb; Symbol *lSymb;
int rname, ratom;
ratom = GetReversedAtom(&atomTable, atom); lSymb = NewSymbol(atom);
if (!fScope) symbols[lSymb->atom] = lSymb;
fScope = CurrentScope;
lSymb = fScope->symbols;
while (lSymb) {
rname = GetReversedAtom(&atomTable, lSymb->name);
if (rname == ratom) {
return lSymb;
} else {
if (rname > ratom) {
lSymb = lSymb->left;
} else {
lSymb = lSymb->right;
}
}
}
return NULL;
} // LookUpLocalSymbol
/* return lSymb;
* LookUpSymbol() }
*
*/
TPpContext::Symbol* TPpContext::LookUpSymbol(Scope *fScope, int atom) TPpContext::Symbol* TPpContext::LookUpSymbol(int atom)
{ {
Symbol *lSymb; TSymbol::iterator it = symbols.find(atom);
if (it == symbols.end())
if (!fScope) return 0;
fScope = CurrentScope; else
while (fScope) { return it->second;
lSymb = LookUpLocalSymbol(fScope, atom); }
if (lSymb)
return lSymb;
fScope = fScope->parent;
}
return NULL;
} // LookUpSymbol
} // end namespace glslang } // end namespace glslang
...@@ -256,7 +256,7 @@ void TPpContext::RecordToken(TokenStream *pTok, int token, TPpToken * yylvalpp) ...@@ -256,7 +256,7 @@ void TPpContext::RecordToken(TokenStream *pTok, int token, TPpToken * yylvalpp)
case CPP_IDENTIFIER: case CPP_IDENTIFIER:
case CPP_TYPEIDENTIFIER: case CPP_TYPEIDENTIFIER:
case CPP_STRCONSTANT: case CPP_STRCONSTANT:
s = GetAtomString(&atomTable, yylvalpp->atom); s = GetAtomString(yylvalpp->atom);
while (*s) while (*s)
lAddByte(pTok, (unsigned char) *s++); lAddByte(pTok, (unsigned char) *s++);
lAddByte(pTok, 0); lAddByte(pTok, 0);
...@@ -331,7 +331,7 @@ int TPpContext::ReadToken(TokenStream *pTok, TPpToken *yylvalpp) ...@@ -331,7 +331,7 @@ int TPpContext::ReadToken(TokenStream *pTok, TPpToken *yylvalpp)
} }
tokenText[len] = '\0'; tokenText[len] = '\0';
assert(ch == '\0'); assert(ch == '\0');
yylvalpp->atom = LookUpAddString(&atomTable, tokenText); yylvalpp->atom = LookUpAddString(tokenText);
return CPP_IDENTIFIER; return CPP_IDENTIFIER;
break; break;
case CPP_STRCONSTANT: case CPP_STRCONSTANT:
...@@ -344,7 +344,7 @@ int TPpContext::ReadToken(TokenStream *pTok, TPpToken *yylvalpp) ...@@ -344,7 +344,7 @@ int TPpContext::ReadToken(TokenStream *pTok, TPpToken *yylvalpp)
} }
tokenText[len] = 0; tokenText[len] = 0;
yylvalpp->atom = LookUpAddString(&atomTable, tokenText); yylvalpp->atom = LookUpAddString(tokenText);
break; break;
case CPP_FLOATCONSTANT: case CPP_FLOATCONSTANT:
case CPP_DOUBLECONSTANT: case CPP_DOUBLECONSTANT:
...@@ -465,10 +465,10 @@ void TPpContext::DumpTokenStream(FILE *fp, TokenStream *s, TPpToken * yylvalpp) ...@@ -465,10 +465,10 @@ void TPpContext::DumpTokenStream(FILE *fp, TokenStream *s, TPpToken * yylvalpp)
switch (token) { switch (token) {
case CPP_IDENTIFIER: case CPP_IDENTIFIER:
case CPP_TYPEIDENTIFIER: case CPP_TYPEIDENTIFIER:
printf("%s ", GetAtomString(&atomTable, yylvalpp->atom)); printf("%s ", GetAtomString(yylvalpp->atom));
break; break;
case CPP_STRCONSTANT: case CPP_STRCONSTANT:
printf("\"%s\"", GetAtomString(&atomTable, yylvalpp->atom)); printf("\"%s\"", GetAtomString(yylvalpp->atom));
break; break;
case CPP_FLOATCONSTANT: case CPP_FLOATCONSTANT:
case CPP_DOUBLECONSTANT: case CPP_DOUBLECONSTANT:
...@@ -480,7 +480,7 @@ void TPpContext::DumpTokenStream(FILE *fp, TokenStream *s, TPpToken * yylvalpp) ...@@ -480,7 +480,7 @@ void TPpContext::DumpTokenStream(FILE *fp, TokenStream *s, TPpToken * yylvalpp)
break; break;
default: default:
if (token >= 127) if (token >= 127)
printf("%s ", GetAtomString(&atomTable, token)); printf("%s ", GetAtomString(token));
else else
printf("%c", token); printf("%c", token);
break; break;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment