diff options
author | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-04-19 00:47:55 +0000 |
---|---|---|
committer | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-04-19 00:47:55 +0000 |
commit | 26a029d407be480d791972afb5975cf62c9360a6 (patch) | |
tree | f435a8308119effd964b339f76abb83a57c29483 /js/src/frontend/TokenKind.h | |
parent | Initial commit. (diff) | |
download | firefox-26a029d407be480d791972afb5975cf62c9360a6.tar.xz firefox-26a029d407be480d791972afb5975cf62c9360a6.zip |
Adding upstream version 124.0.1.upstream/124.0.1
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'js/src/frontend/TokenKind.h')
-rw-r--r-- | js/src/frontend/TokenKind.h | 333 |
1 files changed, 333 insertions, 0 deletions
diff --git a/js/src/frontend/TokenKind.h b/js/src/frontend/TokenKind.h new file mode 100644 index 0000000000..8117603f34 --- /dev/null +++ b/js/src/frontend/TokenKind.h @@ -0,0 +1,333 @@ +/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- + * vim: set ts=8 sts=2 et sw=2 tw=80: + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ + +#ifndef frontend_TokenKind_h +#define frontend_TokenKind_h + +#include <stdint.h> + +#include "js/TypeDecls.h" // IF_RECORD_TUPLE + +/* + * List of token kinds and their ranges. + * + * The format for each line is: + * + * MACRO(<TOKEN_KIND_NAME>, <DESCRIPTION>) + * + * or + * + * RANGE(<TOKEN_RANGE_NAME>, <TOKEN_KIND_NAME>) + * + * where ; + * <TOKEN_KIND_NAME> is a legal C identifier of the token, that will be used in + * the JS engine source. + * + * <DESCRIPTION> is a string that describe about the token, and will be used in + * error message. + * + * <TOKEN_RANGE_NAME> is a legal C identifier of the range that will be used to + * JS engine source. It should end with `First` or `Last`. This is used to check + * TokenKind by range-testing: + * BinOpFirst <= tt && tt <= BinOpLast + * + * Second argument of `RANGE` is the actual value of the <TOKEN_RANGE_NAME>, + * should be same as one of <TOKEN_KIND_NAME> in other `MACRO`s. + * + * To use this macro, define two macros for `MACRO` and `RANGE`, and pass them + * as arguments. + * + * #define EMIT_TOKEN(name, desc) ... + * #define EMIT_RANGE(name, value) ... + * FOR_EACH_TOKEN_KIND_WITH_RANGE(EMIT_TOKEN, EMIT_RANGE) + * #undef EMIT_TOKEN + * #undef EMIT_RANGE + * + * If you don't need range data, use FOR_EACH_TOKEN_KIND instead. + * + * #define EMIT_TOKEN(name, desc) ... + * FOR_EACH_TOKEN_KIND(EMIT_TOKEN) + * #undef EMIT_TOKEN + * + * Note that this list does not contain Limit. + */ +#define FOR_EACH_TOKEN_KIND_WITH_RANGE(MACRO, RANGE) \ + MACRO(Eof, "end of script") \ + \ + /* only returned by peekTokenSameLine() */ \ + MACRO(Eol, "line terminator") \ + \ + MACRO(Semi, "';'") \ + MACRO(Comma, "','") \ + MACRO(Hook, "'?'") /* conditional */ \ + MACRO(Colon, "':'") /* conditional */ \ + MACRO(Inc, "'++'") /* increment */ \ + MACRO(Dec, "'--'") /* decrement */ \ + MACRO(Dot, "'.'") /* member operator */ \ + MACRO(TripleDot, "'...'") /* rest arguments and spread operator */ \ + MACRO(OptionalChain, "'?.'") \ + MACRO(LeftBracket, "'['") \ + IF_RECORD_TUPLE(MACRO(HashBracket, "'#['")) \ + MACRO(RightBracket, "']'") \ + MACRO(LeftCurly, "'{'") \ + IF_RECORD_TUPLE(MACRO(HashCurly, "'#{'")) \ + MACRO(RightCurly, "'}'") \ + MACRO(LeftParen, "'('") \ + MACRO(RightParen, "')'") \ + MACRO(Name, "identifier") \ + MACRO(PrivateName, "private identifier") \ + MACRO(Number, "numeric literal") \ + MACRO(String, "string literal") \ + MACRO(BigInt, "bigint literal") \ + IF_DECORATORS(MACRO(At, "'@'")) \ + \ + /* start of template literal with substitutions */ \ + MACRO(TemplateHead, "'${'") \ + /* template literal without substitutions */ \ + MACRO(NoSubsTemplate, "template literal") \ + \ + MACRO(RegExp, "regular expression literal") \ + MACRO(True, "boolean literal 'true'") \ + RANGE(ReservedWordLiteralFirst, True) \ + MACRO(False, "boolean literal 'false'") \ + MACRO(Null, "null literal") \ + RANGE(ReservedWordLiteralLast, Null) \ + MACRO(This, "keyword 'this'") \ + RANGE(KeywordFirst, This) \ + MACRO(Function, "keyword 'function'") \ + MACRO(If, "keyword 'if'") \ + MACRO(Else, "keyword 'else'") \ + MACRO(Switch, "keyword 'switch'") \ + MACRO(Case, "keyword 'case'") \ + MACRO(Default, "keyword 'default'") \ + MACRO(While, "keyword 'while'") \ + MACRO(Do, "keyword 'do'") \ + MACRO(For, "keyword 'for'") \ + MACRO(Break, "keyword 'break'") \ + MACRO(Continue, "keyword 'continue'") \ + MACRO(Var, "keyword 'var'") \ + MACRO(Const, "keyword 'const'") \ + MACRO(With, "keyword 'with'") \ + MACRO(Return, "keyword 'return'") \ + MACRO(New, "keyword 'new'") \ + MACRO(Delete, "keyword 'delete'") \ + MACRO(Try, "keyword 'try'") \ + MACRO(Catch, "keyword 'catch'") \ + MACRO(Finally, "keyword 'finally'") \ + MACRO(Throw, "keyword 'throw'") \ + MACRO(Debugger, "keyword 'debugger'") \ + MACRO(Export, "keyword 'export'") \ + MACRO(Import, "keyword 'import'") \ + MACRO(Class, "keyword 'class'") \ + MACRO(Extends, "keyword 'extends'") \ + MACRO(Super, "keyword 'super'") \ + RANGE(KeywordLast, Super) \ + \ + /* contextual keywords */ \ + MACRO(As, "'as'") \ + RANGE(ContextualKeywordFirst, As) \ + /* TODO: Move to alphabetical order when IF_DECORATORS is removed */ \ + IF_DECORATORS(MACRO(Accessor, "'accessor'")) \ + MACRO(Assert, "'assert'") \ + MACRO(Async, "'async'") \ + MACRO(Await, "'await'") \ + MACRO(Each, "'each'") \ + MACRO(From, "'from'") \ + MACRO(Get, "'get'") \ + MACRO(Let, "'let'") \ + MACRO(Meta, "'meta'") \ + MACRO(Of, "'of'") \ + MACRO(Set, "'set'") \ + MACRO(Static, "'static'") \ + MACRO(Target, "'target'") \ + MACRO(Yield, "'yield'") \ + RANGE(ContextualKeywordLast, Yield) \ + \ + /* future reserved words */ \ + MACRO(Enum, "reserved word 'enum'") \ + RANGE(FutureReservedKeywordFirst, Enum) \ + RANGE(FutureReservedKeywordLast, Enum) \ + \ + /* reserved words in strict mode */ \ + MACRO(Implements, "reserved word 'implements'") \ + RANGE(StrictReservedKeywordFirst, Implements) \ + MACRO(Interface, "reserved word 'interface'") \ + MACRO(Package, "reserved word 'package'") \ + MACRO(Private, "reserved word 'private'") \ + MACRO(Protected, "reserved word 'protected'") \ + MACRO(Public, "reserved word 'public'") \ + RANGE(StrictReservedKeywordLast, Public) \ + \ + /* \ + * The following token types occupy contiguous ranges to enable easy \ + * range-testing. \ + */ \ + /* \ + * Binary operators. \ + * This list must be kept in the same order in several places: \ + * - the binary operators in ParseNode.h \ + * - the precedence list in Parser.cpp \ + * - the JSOp code list in BytecodeEmitter.cpp \ + */ \ + MACRO(Coalesce, "'\?\?'") /* escapes to avoid trigraphs warning */ \ + RANGE(BinOpFirst, Coalesce) \ + MACRO(Or, "'||'") /* logical or */ \ + MACRO(And, "'&&'") /* logical and */ \ + MACRO(BitOr, "'|'") /* bitwise-or */ \ + MACRO(BitXor, "'^'") /* bitwise-xor */ \ + MACRO(BitAnd, "'&'") /* bitwise-and */ \ + \ + /* Equality operation tokens, per TokenKindIsEquality. */ \ + MACRO(StrictEq, "'==='") \ + RANGE(EqualityStart, StrictEq) \ + MACRO(Eq, "'=='") \ + MACRO(StrictNe, "'!=='") \ + MACRO(Ne, "'!='") \ + RANGE(EqualityLast, Ne) \ + \ + /* Relational ops, per TokenKindIsRelational. */ \ + MACRO(Lt, "'<'") \ + RANGE(RelOpStart, Lt) \ + MACRO(Le, "'<='") \ + MACRO(Gt, "'>'") \ + MACRO(Ge, "'>='") \ + RANGE(RelOpLast, Ge) \ + \ + MACRO(InstanceOf, "keyword 'instanceof'") \ + RANGE(KeywordBinOpFirst, InstanceOf) \ + MACRO(In, "keyword 'in'") \ + MACRO(PrivateIn, "keyword 'in' (private)") \ + RANGE(KeywordBinOpLast, PrivateIn) \ + \ + /* Shift ops, per TokenKindIsShift. */ \ + MACRO(Lsh, "'<<'") \ + RANGE(ShiftOpStart, Lsh) \ + MACRO(Rsh, "'>>'") \ + MACRO(Ursh, "'>>>'") \ + RANGE(ShiftOpLast, Ursh) \ + \ + MACRO(Add, "'+'") \ + MACRO(Sub, "'-'") \ + MACRO(Mul, "'*'") \ + MACRO(Div, "'/'") \ + MACRO(Mod, "'%'") \ + MACRO(Pow, "'**'") \ + RANGE(BinOpLast, Pow) \ + \ + /* Unary operation tokens. */ \ + MACRO(TypeOf, "keyword 'typeof'") \ + RANGE(KeywordUnOpFirst, TypeOf) \ + MACRO(Void, "keyword 'void'") \ + RANGE(KeywordUnOpLast, Void) \ + MACRO(Not, "'!'") \ + MACRO(BitNot, "'~'") \ + \ + MACRO(Arrow, "'=>'") /* function arrow */ \ + \ + /* Assignment ops, per TokenKindIsAssignment */ \ + MACRO(Assign, "'='") \ + RANGE(AssignmentStart, Assign) \ + MACRO(AddAssign, "'+='") \ + MACRO(SubAssign, "'-='") \ + MACRO(CoalesceAssign, "'\?\?='") /* avoid trigraphs warning */ \ + MACRO(OrAssign, "'||='") \ + MACRO(AndAssign, "'&&='") \ + MACRO(BitOrAssign, "'|='") \ + MACRO(BitXorAssign, "'^='") \ + MACRO(BitAndAssign, "'&='") \ + MACRO(LshAssign, "'<<='") \ + MACRO(RshAssign, "'>>='") \ + MACRO(UrshAssign, "'>>>='") \ + MACRO(MulAssign, "'*='") \ + MACRO(DivAssign, "'/='") \ + MACRO(ModAssign, "'%='") \ + MACRO(PowAssign, "'**='") \ + RANGE(AssignmentLast, PowAssign) + +#define TOKEN_KIND_RANGE_EMIT_NONE(name, value) +#define FOR_EACH_TOKEN_KIND(MACRO) \ + FOR_EACH_TOKEN_KIND_WITH_RANGE(MACRO, TOKEN_KIND_RANGE_EMIT_NONE) + +namespace js { +namespace frontend { + +// Values of this type are used to index into arrays such as isExprEnding[], +// so the first value must be zero. +enum class TokenKind : uint8_t { +#define EMIT_ENUM(name, desc) name, +#define EMIT_ENUM_RANGE(name, value) name = value, + FOR_EACH_TOKEN_KIND_WITH_RANGE(EMIT_ENUM, EMIT_ENUM_RANGE) +#undef EMIT_ENUM +#undef EMIT_ENUM_RANGE + Limit // domain size +}; + +inline bool TokenKindIsBinaryOp(TokenKind tt) { + return TokenKind::BinOpFirst <= tt && tt <= TokenKind::BinOpLast; +} + +inline bool TokenKindIsEquality(TokenKind tt) { + return TokenKind::EqualityStart <= tt && tt <= TokenKind::EqualityLast; +} + +inline bool TokenKindIsRelational(TokenKind tt) { + return TokenKind::RelOpStart <= tt && tt <= TokenKind::RelOpLast; +} + +inline bool TokenKindIsShift(TokenKind tt) { + return TokenKind::ShiftOpStart <= tt && tt <= TokenKind::ShiftOpLast; +} + +inline bool TokenKindIsAssignment(TokenKind tt) { + return TokenKind::AssignmentStart <= tt && tt <= TokenKind::AssignmentLast; +} + +[[nodiscard]] inline bool TokenKindIsKeyword(TokenKind tt) { + return (TokenKind::KeywordFirst <= tt && tt <= TokenKind::KeywordLast) || + (TokenKind::KeywordBinOpFirst <= tt && + tt <= TokenKind::KeywordBinOpLast) || + (TokenKind::KeywordUnOpFirst <= tt && + tt <= TokenKind::KeywordUnOpLast); +} + +[[nodiscard]] inline bool TokenKindIsContextualKeyword(TokenKind tt) { + return TokenKind::ContextualKeywordFirst <= tt && + tt <= TokenKind::ContextualKeywordLast; +} + +[[nodiscard]] inline bool TokenKindIsFutureReservedWord(TokenKind tt) { + return TokenKind::FutureReservedKeywordFirst <= tt && + tt <= TokenKind::FutureReservedKeywordLast; +} + +[[nodiscard]] inline bool TokenKindIsStrictReservedWord(TokenKind tt) { + return TokenKind::StrictReservedKeywordFirst <= tt && + tt <= TokenKind::StrictReservedKeywordLast; +} + +[[nodiscard]] inline bool TokenKindIsReservedWordLiteral(TokenKind tt) { + return TokenKind::ReservedWordLiteralFirst <= tt && + tt <= TokenKind::ReservedWordLiteralLast; +} + +[[nodiscard]] inline bool TokenKindIsReservedWord(TokenKind tt) { + return TokenKindIsKeyword(tt) || TokenKindIsFutureReservedWord(tt) || + TokenKindIsReservedWordLiteral(tt); +} + +[[nodiscard]] inline bool TokenKindIsPossibleIdentifier(TokenKind tt) { + return tt == TokenKind::Name || TokenKindIsContextualKeyword(tt) || + TokenKindIsStrictReservedWord(tt); +} + +[[nodiscard]] inline bool TokenKindIsPossibleIdentifierName(TokenKind tt) { + return TokenKindIsPossibleIdentifier(tt) || TokenKindIsReservedWord(tt); +} + +} // namespace frontend +} // namespace js + +#endif /* frontend_TokenKind_h */ |