summaryrefslogtreecommitdiffstats
path: root/js/src/frontend/TokenStream.h
diff options
context:
space:
mode:
Diffstat (limited to 'js/src/frontend/TokenStream.h')
-rw-r--r--js/src/frontend/TokenStream.h135
1 files changed, 29 insertions, 106 deletions
diff --git a/js/src/frontend/TokenStream.h b/js/src/frontend/TokenStream.h
index e0119c83d..e92de4b03 100644
--- a/js/src/frontend/TokenStream.h
+++ b/js/src/frontend/TokenStream.h
@@ -26,14 +26,13 @@
#include "js/UniquePtr.h"
#include "js/Vector.h"
#include "vm/RegExpObject.h"
+#include "vm/String.h"
struct KeywordInfo;
namespace js {
namespace frontend {
-class AutoAwaitIsKeyword;
-
struct TokenPos {
uint32_t begin; // Offset of the token's first char.
uint32_t end; // Offset of 1 past the token's last char.
@@ -120,9 +119,6 @@ struct Token
// TOK_DIV.
Operand,
- // Treat keywords as names by returning TOK_NAME.
- KeywordIsName,
-
// Treat subsequent characters as the tail of a template literal, after
// a template substitution, beginning with a "}", continuing with zero
// or more template literal characters, and ending with either "${" or
@@ -164,10 +160,6 @@ struct Token
// If a semicolon is inserted automatically, the next token is already
// gotten with None, but we expect Operand.
OperandIsNone,
-
- // If name of method definition is `get` or `set`, the next token is
- // already gotten with KeywordIsName, but we expect None.
- NoneIsKeywordIsName,
};
friend class TokenStream;
@@ -224,11 +216,6 @@ struct Token
return u.name->JSAtom::asPropertyName(); // poor-man's type verification
}
- bool nameContainsEscape() const {
- PropertyName* n = name();
- return pos.begin + n->length() != pos.end;
- }
-
JSAtom* atom() const {
MOZ_ASSERT(type == TOK_STRING ||
type == TOK_TEMPLATE_HEAD ||
@@ -254,10 +241,22 @@ struct Token
};
class CompileError : public JSErrorReport {
-public:
+ public:
void throwError(JSContext* cx);
};
+extern const char*
+ReservedWordToCharZ(PropertyName* str);
+
+extern MOZ_MUST_USE bool
+IsFutureReservedWord(JSLinearString* str);
+
+extern MOZ_MUST_USE bool
+IsReservedWordLiteral(JSLinearString* str);
+
+extern MOZ_MUST_USE bool
+IsStrictReservedWord(JSLinearString* str);
+
// Ideally, tokenizing would be entirely independent of context. But the
// strict mode flag, which is in SharedContext, affects tokenizing, and
// TokenStream needs to see it.
@@ -344,25 +343,26 @@ class MOZ_STACK_CLASS TokenStream
JSVersion versionNumber() const { return VersionNumber(options().version); }
JSVersion versionWithFlags() const { return options().version; }
+ private:
+ PropertyName* reservedWordToPropertyName(TokenKind tt) const;
+
+ public:
PropertyName* currentName() const {
- if (isCurrentTokenType(TOK_YIELD))
- return cx->names().yield;
- MOZ_ASSERT(isCurrentTokenType(TOK_NAME));
- return currentToken().name();
+ if (isCurrentTokenType(TOK_NAME)) {
+ return currentToken().name();
+ }
+
+ MOZ_ASSERT(TokenKindIsPossibleIdentifierName(currentToken().type));
+ return reservedWordToPropertyName(currentToken().type);
}
PropertyName* nextName() const {
- if (nextToken().type == TOK_YIELD)
- return cx->names().yield;
- MOZ_ASSERT(nextToken().type == TOK_NAME);
- return nextToken().name();
- }
+ if (nextToken().type != TOK_NAME) {
+ return nextToken().name();
+ }
- bool nextNameContainsEscape() const {
- if (nextToken().type == TOK_YIELD)
- return false;
- MOZ_ASSERT(nextToken().type == TOK_NAME);
- return nextToken().nameContainsEscape();
+ MOZ_ASSERT(TokenKindIsPossibleIdentifierName(nextToken().type));
+ return reservedWordToPropertyName(nextToken().type);
}
bool isCurrentTokenAssignment() const {
@@ -498,9 +498,6 @@ class MOZ_STACK_CLASS TokenStream
{}
};
- bool awaitIsKeyword = false;
- friend class AutoAwaitIsKeyword;
-
uint32_t invalidTemplateEscapeOffset = 0;
InvalidEscapeType invalidTemplateEscapeType = InvalidEscapeType::None;
@@ -508,14 +505,12 @@ class MOZ_STACK_CLASS TokenStream
typedef Token::Modifier Modifier;
static constexpr Modifier None = Token::None;
static constexpr Modifier Operand = Token::Operand;
- static constexpr Modifier KeywordIsName = Token::KeywordIsName;
static constexpr Modifier TemplateTail = Token::TemplateTail;
typedef Token::ModifierException ModifierException;
static constexpr ModifierException NoException = Token::NoException;
static constexpr ModifierException NoneIsOperand = Token::NoneIsOperand;
static constexpr ModifierException OperandIsNone = Token::OperandIsNone;
- static constexpr ModifierException NoneIsKeywordIsName = Token::NoneIsKeywordIsName;
void addModifierException(ModifierException modifierException) {
#ifdef DEBUG
@@ -544,10 +539,6 @@ class MOZ_STACK_CLASS TokenStream
MOZ_ASSERT(next.type != TOK_DIV && next.type != TOK_REGEXP,
"next token requires contextual specifier to be parsed unambiguously");
break;
- case NoneIsKeywordIsName:
- MOZ_ASSERT(next.modifier == KeywordIsName);
- MOZ_ASSERT(next.type != TOK_NAME);
- break;
default:
MOZ_CRASH("unexpected modifier exception");
}
@@ -574,12 +565,6 @@ class MOZ_STACK_CLASS TokenStream
return;
}
- if (lookaheadToken.modifierException == NoneIsKeywordIsName) {
- // getToken() permissibly following getToken(KeywordIsName).
- if (modifier == None && lookaheadToken.modifier == KeywordIsName)
- return;
- }
-
MOZ_ASSERT_UNREACHABLE("this token was previously looked up with a "
"different modifier, potentially making "
"tokenization non-deterministic");
@@ -714,36 +699,6 @@ class MOZ_STACK_CLASS TokenStream
MOZ_ALWAYS_TRUE(matched);
}
- // Like matchToken(..., TOK_NAME) but further matching the name token only
- // if it has the given characters, without containing escape sequences.
- // If the name token has the given characters yet *does* contain an escape,
- // a syntax error will be reported.
- //
- // This latter behavior makes this method unsuitable for use in any context
- // where ASI might occur. In such places, an escaped "contextual keyword"
- // on a new line is the start of an ExpressionStatement, not a continuation
- // of a StatementListItem (or ImportDeclaration or ExportDeclaration, in
- // modules).
- MOZ_MUST_USE bool matchContextualKeyword(bool* matchedp, Handle<PropertyName*> keyword,
- Modifier modifier = None)
- {
- TokenKind token;
- if (!getToken(&token, modifier))
- return false;
- if (token == TOK_NAME && currentToken().name() == keyword) {
- if (currentToken().nameContainsEscape()) {
- reportError(JSMSG_ESCAPED_KEYWORD);
- return false;
- }
-
- *matchedp = true;
- } else {
- *matchedp = false;
- ungetToken();
- }
- return true;
- }
-
MOZ_MUST_USE bool nextTokenEndsExpr(bool* endsExpr) {
TokenKind tt;
if (!peekToken(&tt))
@@ -809,19 +764,6 @@ class MOZ_STACK_CLASS TokenStream
return sourceMapURL_.get();
}
- // If |atom| is not a keyword in this version, return true with *ttp
- // unchanged.
- //
- // If it is a reserved word in this version and strictness mode, and thus
- // can't be present in correct code, report a SyntaxError and return false.
- //
- // If it is a keyword, like "if", return true with the keyword's TokenKind
- // in *ttp.
- MOZ_MUST_USE bool checkForKeyword(JSAtom* atom, TokenKind* ttp);
-
- // Same semantics as above, but for the provided keyword.
- MOZ_MUST_USE bool checkForKeyword(const KeywordInfo* kw, TokenKind* ttp);
-
// This class maps a userbuf offset (which is 0-indexed) to a line number
// (which is 1-indexed) and a column index (which is 0-indexed).
class SourceCoords
@@ -1103,25 +1045,6 @@ class MOZ_STACK_CLASS TokenStream
StrictModeGetter* strictModeGetter; // used to test for strict mode
};
-class MOZ_STACK_CLASS AutoAwaitIsKeyword
-{
-private:
- TokenStream* ts_;
- bool oldAwaitIsKeyword_;
-
-public:
- AutoAwaitIsKeyword(TokenStream* ts, bool awaitIsKeyword) {
- ts_ = ts;
- oldAwaitIsKeyword_ = ts_->awaitIsKeyword;
- ts_->awaitIsKeyword = awaitIsKeyword;
- }
-
- ~AutoAwaitIsKeyword() {
- ts_->awaitIsKeyword = oldAwaitIsKeyword_;
- ts_ = nullptr;
- }
-};
-
extern const char*
TokenKindToDesc(TokenKind tt);