diff options
Diffstat (limited to 'gfx/angle/src/compiler/preprocessor/MacroExpander.cpp')
-rwxr-xr-x | gfx/angle/src/compiler/preprocessor/MacroExpander.cpp | 151 |
1 files changed, 31 insertions, 120 deletions
diff --git a/gfx/angle/src/compiler/preprocessor/MacroExpander.cpp b/gfx/angle/src/compiler/preprocessor/MacroExpander.cpp index 2f854f5a6..3c0423e72 100755 --- a/gfx/angle/src/compiler/preprocessor/MacroExpander.cpp +++ b/gfx/angle/src/compiler/preprocessor/MacroExpander.cpp @@ -4,22 +4,17 @@ // found in the LICENSE file. // -#include "compiler/preprocessor/MacroExpander.h" +#include "MacroExpander.h" #include <algorithm> +#include <sstream> -#include "common/debug.h" -#include "compiler/preprocessor/DiagnosticsBase.h" -#include "compiler/preprocessor/Token.h" +#include "DiagnosticsBase.h" +#include "Token.h" namespace pp { -namespace -{ - -const size_t kMaxContextTokens = 10000; - class TokenLexer : public Lexer { public: @@ -45,52 +40,22 @@ class TokenLexer : public Lexer } private: + PP_DISALLOW_COPY_AND_ASSIGN(TokenLexer); + TokenVector mTokens; TokenVector::const_iterator mIter; }; -} // anonymous namespace - -class MacroExpander::ScopedMacroReenabler final : angle::NonCopyable -{ - public: - ScopedMacroReenabler(MacroExpander *expander); - ~ScopedMacroReenabler(); - - private: - MacroExpander *mExpander; -}; - -MacroExpander::ScopedMacroReenabler::ScopedMacroReenabler(MacroExpander *expander) - : mExpander(expander) -{ - mExpander->mDeferReenablingMacros = true; -} - -MacroExpander::ScopedMacroReenabler::~ScopedMacroReenabler() -{ - mExpander->mDeferReenablingMacros = false; - for (auto *macro : mExpander->mMacrosToReenable) - { - macro->disabled = false; - } - mExpander->mMacrosToReenable.clear(); -} - MacroExpander::MacroExpander(Lexer *lexer, MacroSet *macroSet, Diagnostics *diagnostics) - : mLexer(lexer), - mMacroSet(macroSet), - mDiagnostics(diagnostics), - mTotalTokensInContexts(0), - mDeferReenablingMacros(false) + : mLexer(lexer), mMacroSet(macroSet), mDiagnostics(diagnostics) { } MacroExpander::~MacroExpander() { - for (MacroContext *context : mContextStack) + for (std::size_t i = 0; i < mContextStack.size(); ++i) { - delete context; + delete mContextStack[i]; } } @@ -117,15 +82,10 @@ void MacroExpander::lex(Token *token) token->setExpansionDisabled(true); break; } - - // Bump the expansion count before peeking if the next token is a '(' - // otherwise there could be a #undef of the macro before the next token. - macro.expansionCount++; if ((macro.type == Macro::kTypeFunc) && !isNextTokenLeftParen()) { // If the token immediately after the macro name is not a '(', // this macro should not be expanded. - macro.expansionCount--; break; } @@ -154,7 +114,6 @@ void MacroExpander::getToken(Token *token) } else { - ASSERT(mTotalTokensInContexts == 0); mLexer->lex(token); } } @@ -165,11 +124,11 @@ void MacroExpander::ungetToken(const Token &token) { MacroContext *context = mContextStack.back(); context->unget(); - ASSERT(context->replacements[context->index] == token); + assert(context->replacements[context->index] == token); } else { - ASSERT(!mReserveToken.get()); + assert(!mReserveToken.get()); mReserveToken.reset(new Token(token)); } } @@ -187,10 +146,10 @@ bool MacroExpander::isNextTokenLeftParen() bool MacroExpander::pushMacro(const Macro ¯o, const Token &identifier) { - ASSERT(!macro.disabled); - ASSERT(!identifier.expansionDisabled()); - ASSERT(identifier.type == Token::IDENTIFIER); - ASSERT(identifier.text == macro.name); + assert(!macro.disabled); + assert(!identifier.expansionDisabled()); + assert(identifier.type == Token::IDENTIFIER); + assert(identifier.text == macro.name); std::vector<Token> replacements; if (!expandMacro(macro, identifier, &replacements)) @@ -203,30 +162,19 @@ bool MacroExpander::pushMacro(const Macro ¯o, const Token &identifier) context->macro = ¯o; context->replacements.swap(replacements); mContextStack.push_back(context); - mTotalTokensInContexts += context->replacements.size(); return true; } void MacroExpander::popMacro() { - ASSERT(!mContextStack.empty()); + assert(!mContextStack.empty()); MacroContext *context = mContextStack.back(); mContextStack.pop_back(); - ASSERT(context->empty()); - ASSERT(context->macro->disabled); - ASSERT(context->macro->expansionCount > 0); - if (mDeferReenablingMacros) - { - mMacrosToReenable.push_back(context->macro); - } - else - { - context->macro->disabled = false; - } - context->macro->expansionCount--; - mTotalTokensInContexts -= context->replacements.size(); + assert(context->empty()); + assert(context->macro->disabled); + context->macro->disabled = false; delete context; } @@ -251,21 +199,25 @@ bool MacroExpander::expandMacro(const Macro ¯o, const char kLine[] = "__LINE__"; const char kFile[] = "__FILE__"; - ASSERT(replacements->size() == 1); + assert(replacements->size() == 1); Token& repl = replacements->front(); if (macro.name == kLine) { - repl.text = ToString(identifier.location.line); + std::ostringstream stream; + stream << identifier.location.line; + repl.text = stream.str(); } else if (macro.name == kFile) { - repl.text = ToString(identifier.location.file); + std::ostringstream stream; + stream << identifier.location.file; + repl.text = stream.str(); } } } else { - ASSERT(macro.type == Macro::kTypeFunc); + assert(macro.type == Macro::kTypeFunc); std::vector<MacroArg> args; args.reserve(macro.parameters.size()); if (!collectMacroArgs(macro, identifier, &args, &replacementLocation)) @@ -296,17 +248,10 @@ bool MacroExpander::collectMacroArgs(const Macro ¯o, { Token token; getToken(&token); - ASSERT(token.type == '('); + assert(token.type == '('); args->push_back(MacroArg()); - - // Defer reenabling macros until args collection is finished to avoid the possibility of - // infinite recursion. Otherwise infinite recursion might happen when expanding the args after - // macros have been popped from the context stack when parsing the args. - ScopedMacroReenabler deferReenablingMacros(this); - - int openParens = 1; - while (openParens != 0) + for (int openParens = 1; openParens != 0; ) { getToken(&token); @@ -372,9 +317,9 @@ bool MacroExpander::collectMacroArgs(const Macro ¯o, // Pre-expand each argument before substitution. // This step expands each argument individually before they are // inserted into the macro body. - size_t numTokens = 0; - for (auto &arg : *args) + for (std::size_t i = 0; i < args->size(); ++i) { + MacroArg &arg = args->at(i); TokenLexer lexer(&arg); MacroExpander expander(&lexer, mMacroSet, mDiagnostics); @@ -384,12 +329,6 @@ bool MacroExpander::collectMacroArgs(const Macro ¯o, { arg.push_back(token); expander.lex(&token); - numTokens++; - if (numTokens + mTotalTokensInContexts > kMaxContextTokens) - { - mDiagnostics->report(Diagnostics::PP_OUT_OF_MEMORY, token.location, token.text); - return false; - } } } return true; @@ -401,14 +340,6 @@ void MacroExpander::replaceMacroParams(const Macro ¯o, { for (std::size_t i = 0; i < macro.replacements.size(); ++i) { - if (!replacements->empty() && - replacements->size() + mTotalTokensInContexts > kMaxContextTokens) - { - const Token &token = replacements->back(); - mDiagnostics->report(Diagnostics::PP_OUT_OF_MEMORY, token.location, token.text); - return; - } - const Token &repl = macro.replacements[i]; if (repl.type != Token::IDENTIFIER) { @@ -441,25 +372,5 @@ void MacroExpander::replaceMacroParams(const Macro ¯o, } } -MacroExpander::MacroContext::MacroContext() : macro(0), index(0) -{ -} - -bool MacroExpander::MacroContext::empty() const -{ - return index == replacements.size(); -} - -const Token &MacroExpander::MacroContext::get() -{ - return replacements[index++]; -} - -void MacroExpander::MacroContext::unget() -{ - ASSERT(index > 0); - --index; -} - } // namespace pp |