Documentation
¶
Overview ¶
Package syntax implements the moejs front end: a hand-written lexer, a recursive-descent parser producing a compact AST, strict-mode early errors, and a scope-resolution pass whose annotations the compiler consumes directly.
Source is always strict-mode ECMAScript. ParseModule parses an ES module; ParseScript parses a strict-mode script for the runtime's RunString helper.
Index ¶
- Constants
- func DecodeWTF8(s string) []uint16
- func Dump(n Node) string
- func Inspect(n Node, f func(Node) bool)
- func IsASCII(s string) bool
- func Walk(v Visitor, n Node)
- type ArrayLit
- type ArrayPattern
- type AssignExpr
- type AssignPattern
- type AwaitExpr
- type BigIntLit
- type BinaryExpr
- type BindKind
- type Binding
- type BlockStmt
- type BoolLit
- type BreakStmt
- type CallExpr
- type Class
- type ClassDecl
- type ClassMember
- type ClassMemberKind
- type CondExpr
- type ContinueStmt
- type DebuggerStmt
- type DeclKind
- type Declarator
- type DoWhileStmt
- type EmptyStmt
- type Error
- type ExportAll
- type ExportDecl
- type ExportDefault
- type ExportEntry
- type ExportNamed
- type ExportSpec
- type Expr
- type ExprStmt
- type File
- type ForInOfStmt
- type ForStmt
- type FuncDecl
- type FuncKind
- type Function
- type Ident
- type IfStmt
- type ImportCall
- type ImportDecl
- type ImportMeta
- type ImportSpec
- type LabeledStmt
- type LogicalExpr
- type MemberExpr
- type Module
- type NewExpr
- type NewTarget
- type Node
- type NullLit
- type NumberLit
- type ObjectLit
- type ObjectPattern
- type OptChain
- type Options
- type Pattern
- type PatternProp
- type PrivateName
- type Program
- type PropKind
- type Property
- type RegexLit
- type ReturnStmt
- type Scope
- type ScopeKind
- type Script
- type SeqExpr
- type Span
- type SpreadElem
- type Stmt
- type StringLit
- type SuperExpr
- type SwitchCase
- type SwitchStmt
- type TaggedTemplate
- type TemplateElement
- type TemplateLit
- type ThisExpr
- type ThrowStmt
- type Token
- type TryStmt
- type UnaryExpr
- type UpdateExpr
- type VarDecl
- type Visitor
- type WhileStmt
- type YieldExpr
Constants ¶
const InvalidCooked = "\xff"
InvalidCooked is the Cooked text of a tagged template chunk with an invalid escape, whose cooked value is undefined. The byte 0xFF never occurs in WTF-8.
const MaxNestingDepth = 10000
MaxNestingDepth bounds the parser's recursion. Every nested statement, function, assignment expression, unary operator, `new`, class or binding pattern costs one unit, so a source-level construct costs one to three (`(` is an assignment expression and a unary operand). Real plugin code nests a few dozen levels; a 1 MB run of `(` used to overflow the Go stack, which is a fatal error that kills the process. The scope pass and the compiler recurse over the tree the parser produced, so the bound covers them as well.
Variables ¶
This section is empty.
Functions ¶
func DecodeWTF8 ¶
DecodeWTF8 converts a WTF-8 string (as produced for StringLit.Value and template cooked text) to UTF-16 code units. Lone surrogates round-trip.
func Dump ¶
Dump renders a node as an S-expression for golden tests and debugging. Statements are placed on their own lines and indented; expressions are printed inline.
Types ¶
type ArrayLit ¶
ArrayLit is an array literal. A nil element is a hole; *SpreadElem elements are spreads.
type ArrayPattern ¶
ArrayPattern is [a, , b = 1, ...rest]. A nil element is an elision.
type AssignExpr ¶
type AssignExpr struct {
Span
Op Token
ParenTarget bool // Target is a parenthesised identifier: not an IdentifierRef, so the value is not named after it
Target Pattern
Value Expr
}
AssignExpr is `=` or a compound assignment. Target is *Ident, *MemberExpr, or (for `=` only) a destructuring pattern.
type AssignPattern ¶
AssignPattern is Target = Default inside a pattern or parameter list.
type BigIntLit ¶
BigIntLit is a BigInt literal; Digits is the value in decimal without a sign, leading zeros or separators, or in hex after "0x" for a 0x, 0o or 0b literal too large for 64 bits.
type BinaryExpr ¶
BinaryExpr is an arithmetic, bitwise, comparison, `in` or `instanceof` expression.
type BindKind ¶
type BindKind uint8
BindKind classifies bindings.
const ( BindVar BindKind = iota // var, hoisted to the function/module scope BindLet // let BindConst // const BindParam // formal parameter BindFunction // function declaration, instantiated at scope entry (see Scope.Funcs) BindCatch // catch parameter BindClass // class declaration (the outer, mutable binding) BindFuncName // name of a named function expression, immutable, visible inside it BindImport // import binding (unsupported) BindPrivate // private name "#x" of a class (ScopeClass) BindHidden // resolver-created binding of the class/super machinery, named "%..." BindArgs // the function's arguments object (Function.ArgumentsBinding) )
type Binding ¶
type Binding struct {
Name string
Kind BindKind
Scope *Scope // declaring scope
Slot int // index in Scope.Bindings
Pos int // position of the (first) declaring identifier
Captured bool // referenced from a function nested inside the declaring function
NeedsTDZ bool // let/const/class that may be read before initialisation
Exported bool // module binding named by an export entry
// contains filtered or unexported fields
}
Binding is a declared name. Every Ident that declares or references it points here.
type BlockStmt ¶
BlockStmt is `{ ... }`. Scope is nil unless the block declares lexical bindings (let/const/class/function).
type Class ¶
type Class struct {
Span
Name *Ident
Super Expr
Members []*ClassMember
// Scope annotations. Scope (kind ScopeClass) holds the inner name
// binding, one binding per private name (named "#x") and the hidden
// bindings of the class machinery; the heritage, the computed keys and
// every member function are resolved inside it.
Scope *Scope
NameBinding *Binding // inner immutable class-name binding (named classes)
Ctor *Function // the constructor; synthesized (DefaultCtor) when the body has none
Fields *Function // FuncClassFields: instance fields and the private-method brand (nil when none)
Static *Function // FuncClassStatic: static fields and blocks in order (nil when none)
FieldsBinding *Binding // hidden binding holding the Fields closure, read by the constructor
BrandBinding *Binding // hidden binding holding the brand of the instance private methods (nil when none)
}
Class is a class declaration or expression.
type ClassMember ¶
type ClassMember struct {
Span
Kind ClassMemberKind
Static bool
Key Expr // *Ident, *StringLit, *NumberLit, *BigIntLit, *PrivateName, or computed Expr
Computed bool
Value Expr // *Function for methods, initializer for fields (may be nil)
Body *BlockStmt // static block body
// Scope annotations. KeyBinding is the hidden binding that carries a
// computed field key from class definition to the field initializer.
// Block is a static block's body as an arrow function nested in
// Class.Static, which gives it its own var scope and the static
// initializer's this, home object and new.target.
KeyBinding *Binding
Block *Function
}
ClassMember is one entry of a class body.
type ClassMemberKind ¶
type ClassMemberKind uint8
ClassMemberKind classifies class body entries.
const ( ClassMethod ClassMemberKind = iota ClassGetter ClassSetter ClassField ClassStaticBlock )
type ContinueStmt ¶
ContinueStmt is continue, optionally labelled.
type Declarator ¶
Declarator is one `Target = Init` of a variable declaration.
type Error ¶
type Error struct {
Name string // file name given to ParseModule/ParseScript
Pos int // byte offset into the source
Line int // 1-based line
Col int // 1-based column in code points
Msg string
}
Error is a syntax error with a position. Msg always starts with "SyntaxError: " so that Error() reads like a compiler diagnostic and Message() yields the text a JS SyntaxError object should carry.
type ExportDecl ¶
ExportDecl is `export <declaration>`.
type ExportDefault ¶
ExportDefault is `export default ...`. Decl is a *FuncDecl or *ClassDecl for named/anonymous declarations, or an Expr.
type ExportEntry ¶
type ExportEntry struct {
Name string // exported name
Local string // local binding name ("*default*" for an anonymous default export)
Binding *Binding // module-scope binding
Pos int // position of the export specifier or declaration
}
ExportEntry describes one exported name of a module.
type ExportNamed ¶
type ExportNamed struct {
Span
Specs []*ExportSpec
Source *StringLit
}
ExportNamed is `export { ... }` optionally `from "..."` (unsupported).
type ExportSpec ¶
ExportSpec is `Local as Exported` (Exported may be spelled as a string).
type Expr ¶
type Expr interface {
Node
// contains filtered or unexported methods
}
Expr is an expression node.
type File ¶
File is a parsed source text with a line-start table for mapping byte offsets to (line, col).
type ForInOfStmt ¶
type ForInOfStmt struct {
Span
Of bool
Await bool // for await
Left Node
Right Expr
Body Stmt
Scope *Scope
}
ForInOfStmt is for-in (Of == false) or for-of. Left is a *VarDecl with a single initializer-less declarator, or a Pattern. Scope is nil unless Left is a let/const declaration.
type ForStmt ¶
ForStmt is the classic for loop. Init is nil, *VarDecl or an Expr. Scope is nil unless Init is a let/const declaration.
type FuncKind ¶
type FuncKind uint8
FuncKind distinguishes the syntactic forms of a function.
const ( FuncNormal FuncKind = iota FuncArrow FuncMethod FuncGetter FuncSetter FuncClassConstructor // FuncClassFields and FuncClassStatic are the synthetic methods the // resolver creates to run a class's instance field initializers and its // static fields and blocks (Class.Fields, Class.Static). They have no // source of their own and no Body. FuncClassFields FuncClassStatic )
type Function ¶
type Function struct {
Span
Name *Ident // nil when anonymous
Params []Pattern
Rest Pattern // rest parameter target or nil
Body *BlockStmt // nil for a concise arrow body
ExprBody Expr // concise arrow body
Kind FuncKind
IsArrow bool
IsAsync bool
IsGenerator bool
IsStrict bool // always true (strict mode only)
// Scope annotations.
Scope *Scope // parameters, var declarations and body-level lexical declarations (Body.Scope when kept apart)
SelfBinding *Binding
UsesThis bool // `this` (or super/new.target) appears in the body or in a nested arrow
UsesArguments bool // `arguments` appears in the body or in a nested arrow
HasDirectEval bool // a call to an unresolved `eval` appears (unsupported)
ParamCount int // formal parameters excluding rest
Length int // ES `length`: formals before the first default or rest
HasSimpleParams bool // every formal is a plain identifier without default; no rest
HasRest bool
// Class, super and new.target annotations. The hidden bindings live in
// the function scope (registers or captured slots like any binding) and
// are nil when unused.
Derived bool // constructor of a class with an extends clause
DefaultCtor bool // constructor synthesized for a class without one
ThisBinding *Binding // derived constructor: `this`, in TDZ until super() returns
CalleeBinding *Binding // derived constructor: the active function, read by super()
NewTargetBinding *Binding // new.target, used here or in a nested arrow
HomeBinding *Binding // [[HomeObject]], for super property access here or in a nested arrow
}
Function is any function: declaration body, expression, arrow or method. FuncDecl wraps it in statement position. Span covers the whole source text from the first token (`function`, `async`, the method name or the arrow parameters) to the end of the body, for Function.prototype.toString.
func (*Function) ArgumentsBinding ¶
ArgumentsBinding returns the binding of the function's own arguments object (BindArgs, declared in Scope), nil when nothing references it. Arrows have none: their `arguments` is the enclosing function's. Strict code declares nothing else named arguments.
type Ident ¶
Ident is an identifier. In reference position the scope pass fills Binding (nil means global/unresolvable). In binding position (declarations, parameters, patterns) Binding is the binding it declares. Non-computed property keys and member names are also Idents but are never resolved.
func BoundNames ¶
BoundNames returns the identifiers bound by a pattern in source order.
type ImportCall ¶
ImportCall is a dynamic `import(x)` (not supported yet).
type ImportDecl ¶
type ImportDecl struct {
Span
Default *Ident
Namespace *Ident
Specs []*ImportSpec
Source *StringLit
}
ImportDecl is an import declaration (unsupported).
type ImportSpec ¶
ImportSpec is `Imported as Local`.
type LabeledStmt ¶
LabeledStmt is `Label: Body`.
type LogicalExpr ¶
LogicalExpr is && || ??; Y is evaluated conditionally.
type MemberExpr ¶
MemberExpr is property access. Prop is an *Ident (never resolved) or a *PrivateName when !Computed. Optional marks `a?.b`.
type Module ¶
type Module struct {
Program
// Exports lists every export entry in source order. Filled by the scope
// pass; Binding is the module-scope binding the export reads.
Exports []*ExportEntry
// Async is set by the scope pass when the body awaits outside any
// function (top-level await): the module evaluates asynchronously.
Async bool
}
Module is a parsed ES module.
func ParseModule ¶
ParseModule parses src as a strict-mode ES module, runs the early-error and scope-resolution passes, and returns the annotated tree. The error, when non-nil, is always a *Error.
type NewTarget ¶
NewTarget is `new.target`. Binding is the enclosing non-arrow function's Function.NewTargetBinding.
type NumberLit ¶
NumberLit is a numeric literal. Legacy octal forms are rejected by the lexer, so Value is always the exact ES mathematical value.
type ObjectPattern ¶
type ObjectPattern struct {
Span
Props []*PatternProp
Rest Pattern // *Ident or (assignment only) *MemberExpr, or nil
}
ObjectPattern is { a, b: c, ...rest }.
type OptChain ¶
OptChain wraps the whole of an optional chain `a?.b.c()`; when any Optional link short-circuits, the value of the OptChain is undefined.
type Options ¶
type Options struct {
// AllowUnsupported keeps the parser from rejecting syntax the engine
// does not implement yet (generators, async, ...). The AST is still
// produced, so supporting a feature lifts its restriction rather than
// touching the parser.
AllowUnsupported bool
}
Options controls parsing.
type Pattern ¶
type Pattern interface {
Node
// contains filtered or unexported methods
}
Pattern is a binding or assignment target: *Ident, *MemberExpr (assignment targets only), *ObjectPattern, *ArrayPattern or *AssignPattern.
type PatternProp ¶
PatternProp is one entry of an object pattern.
type PrivateName ¶
PrivateName is `#x` in a member, `#x in o` or class element position. Binding is the class-scope binding of the private name (named "#x").
type Program ¶
type Program struct {
Span
File *File
Body []Stmt
Scope *Scope // module or script scope; filled by the scope pass
}
Program is the shared body of Module and Script.
type Property ¶
type Property struct {
Span
Kind PropKind
Key Expr // *Ident, *StringLit, *NumberLit, *BigIntLit, or any Expr when Computed; nil for PropSpread
Computed bool
Value Expr // value, method *Function, spread operand, or cover default
}
Property is one object literal entry.
type RegexLit ¶
RegexLit is a regular expression literal. Flags are validated for the set dgimsuvy without duplicates (u and v exclusive) and the pattern by internal/regexpsyntax.
type Scope ¶
type Scope struct {
Kind ScopeKind
Parent *Scope
Func *Function // enclosing function; nil at module/script level
Node Node // owning node: *Module, *Script, *Function, *BlockStmt, *SwitchStmt, *TryStmt, *ForStmt, *ForInOfStmt, *Class
Bindings []*Binding
Funcs []*FuncDecl // hoisted function declarations to instantiate on entry, in source order
Children []*Scope
// contains filtered or unexported fields
}
Scope is a node of the scope tree.
type ScopeKind ¶
type ScopeKind uint8
ScopeKind classifies scopes.
const ( ScopeModule ScopeKind = iota // module top level ScopeScript // strict-mode script top level ScopeFunction // parameters, var declarations and body-level lexical declarations ScopeBlock // block or switch case block with lexical declarations ScopeCatch // catch parameter ScopeFor // for/for-in/for-of head with let/const ScopeClass // class body: inner name, private names and hidden class bindings )
type Span ¶
type Span struct {
Pos, End int
}
Span is the half-open byte range [Pos, End) of a node in the source. Every node embeds it; File.Position maps offsets to (line, col).
type SpreadElem ¶
SpreadElem is `...X` in an array literal or argument list.
type Stmt ¶
type Stmt interface {
Node
// contains filtered or unexported methods
}
Stmt is a statement or declaration node.
type StringLit ¶
StringLit is a string literal. Value is the cooked text in WTF-8 (see wtf8.go): UTF-8, except that lone surrogates written as escapes are encoded as three-byte sequences so that DecodeWTF8 recovers the exact UTF-16 code units.
type SuperExpr ¶
type SuperExpr struct{ Span }
SuperExpr is `super` in a SuperCall `super(args)` or a SuperProperty `super.x` / `super[x]` (the parser rejects any other use).
type SwitchCase ¶
SwitchCase is one case (Test == nil for default).
type SwitchStmt ¶
type SwitchStmt struct {
Span
Disc Expr
Cases []*SwitchCase
Scope *Scope
}
SwitchStmt is switch. Scope is nil unless the case block declares lexical bindings; such bindings always need TDZ checks.
type TaggedTemplate ¶
type TaggedTemplate struct {
Span
Tag Expr
Quasi *TemplateLit
}
TaggedTemplate is tag`...`.
type TemplateElement ¶
type TemplateElement struct {
Span
Cooked string // WTF-8 cooked text, or InvalidCooked
Raw string // raw text with CR/CRLF normalised to LF
}
TemplateElement is one text chunk of a template literal.
type TemplateLit ¶
type TemplateLit struct {
Span
Quasis []TemplateElement
Exprs []Expr
}
TemplateLit is an untagged template literal. len(Quasis) == len(Exprs)+1.
type ThisExpr ¶
ThisExpr is `this`. Binding is set in a derived class constructor (and the arrows nested in it), where `this` is the constructor's Function.ThisBinding; nil means the ordinary this value.
type Token ¶
type Token uint8
Token is a lexical token kind. Punctuators and keywords each have their own kind so the parser switches on small integers rather than comparing text.
const ( EOF Token = iota Illegal // Punctuators. LBrace // { RBrace // } LParen // ( RParen // ) LBrack // [ RBrack // ] Dot // . Ellipsis // ... Semicolon // ; Comma // , Lt // < Gt // > LtEq // <= GtEq // >= Eq // == NotEq // != StrictEq // === StrictNeq // !== Plus // + Minus // - Mul // * Div // / Rem // % Exp // ** Inc // ++ Dec // -- Shl // << Shr // >> UShr // >>> BitAnd // & BitOr // | BitXor // ^ Not // ! BitNot // ~ LogAnd // && LogOr // || Nullish // ?? Question // ? QuestionDot // ?. Colon // : Assign // = AddAssign // += SubAssign // -= MulAssign // *= DivAssign // /= RemAssign // %= ExpAssign // **= ShlAssign // <<= ShrAssign // >>= UShrAssign // >>>= AndAssign // &= OrAssign // |= XorAssign // ^= LogAndAssign LogOrAssign NullishAssign Arrow // => Hash // # (private names, unsupported but tokenised for a clear error) // Literals and names. Identifier PrivateIdent EscapedWord // a reserved word spelled with \u escapes: only an IdentifierName Number BigInt String Template // a template chunk; see Lexer.template Regex KwAwait KwBreak KwCase KwCatch KwClass KwConst KwContinue KwDebugger KwDefault KwDelete KwDo KwElse KwEnum KwExport KwExtends KwFalse KwFinally KwFor KwFunction KwIf KwImport KwIn KwInstanceof KwNew KwNull KwReturn KwSuper KwSwitch KwThis KwThrow KwTrue KwTry KwTypeof KwVar KwVoid KwWhile KwWith KwYield // Strict-mode future reserved words. KwImplements KwInterface KwLet KwPackage KwPrivate KwProtected KwPublic KwStatic )
Token kinds. The order groups punctuators, then literals, then keywords so that IsKeyword is a range check.
type TryStmt ¶
type TryStmt struct {
Span
Block *BlockStmt
Param Pattern
Handler *BlockStmt
Finalizer *BlockStmt
CatchScope *Scope
}
TryStmt is try/catch/finally. Param is nil for `catch {` or when there is no catch clause; CatchScope holds the catch parameter bindings.
type UpdateExpr ¶
UpdateExpr is ++ or -- in prefix or postfix form.
type VarDecl ¶
type VarDecl struct {
Span
Kind DeclKind
Decls []*Declarator
}
VarDecl is a var/let/const declaration.