Skip to content

14 ECMAScript Language: Functions and Classes

Note

Various ECMAScript language elements cause the creation of ECMAScript function objects (9.2). Evaluation of such functions starts with the execution of their [[Call]] internal method (9.2.1).

14.1 Function Definitions

Syntax

FunctionDeclaration[Yield, Await, Default] : function BindingIdentifier[?Yield, ?Await] ( FormalParameters[~Yield, ~Await] ) { FunctionBody[~Yield, ~Await] } [+Default] function ( FormalParameters[~Yield, ~Await] ) { FunctionBody[~Yield, ~Await] } FunctionExpression : function BindingIdentifier[~Yield, ~Await]opt ( FormalParameters[~Yield, ~Await] ) { FunctionBody[~Yield, ~Await] } UniqueFormalParameters[Yield, Await] : FormalParameters[?Yield, ?Await] FormalParameters[Yield, Await] : [empty] FunctionRestParameter[?Yield, ?Await] FormalParameterList[?Yield, ?Await] FormalParameterList[?Yield, ?Await] , FormalParameterList[?Yield, ?Await] , FunctionRestParameter[?Yield, ?Await] FormalParameterList[Yield, Await] : FormalParameter[?Yield, ?Await] FormalParameterList[?Yield, ?Await] , FormalParameter[?Yield, ?Await] FunctionRestParameter[Yield, Await] : BindingRestElement[?Yield, ?Await] FormalParameter[Yield, Await] : BindingElement[?Yield, ?Await] FunctionBody[Yield, Await] : FunctionStatementList[?Yield, ?Await] FunctionStatementList[Yield, Await] : StatementList[?Yield, ?Await, +Return]opt

14.1.1 Directive Prologues and the Use Strict Directive

A Directive Prologue is the longest sequence of ExpressionStatements occurring as the initial StatementListItems or ModuleItems of a FunctionBody, a ScriptBody, or a ModuleBody and where each ExpressionStatement in the sequence consists entirely of a StringLiteral token followed by a semicolon. The semicolon may appear explicitly or may be inserted by automatic semicolon insertion. A Directive Prologue may be an empty sequence.

A Use Strict Directive is an ExpressionStatement in a Directive Prologue whose StringLiteral is either the exact code unit sequences "use strict" or 'use strict'. A Use Strict Directive may not contain an EscapeSequence or LineContinuation.

A Directive Prologue may contain more than one Use Strict Directive. However, an implementation may issue a warning if this occurs.

Note

The ExpressionStatements of a Directive Prologue are evaluated normally during evaluation of the containing production. Implementations may define implementation specific meanings for ExpressionStatements which are not a Use Strict Directive and which occur in a Directive Prologue. If an appropriate notification mechanism exists, an implementation should issue a warning if it encounters in a Directive Prologue an ExpressionStatement that is not a Use Strict Directive and which does not have a meaning defined by the implementation.

14.1.2 Static Semantics: Early Errors

FunctionDeclaration : function BindingIdentifier ( FormalParameters ) { FunctionBody } FunctionDeclaration : function ( FormalParameters ) { FunctionBody } FunctionExpression : function BindingIdentifieropt ( FormalParameters ) { FunctionBody }
  • If the source code matching this production is strict mode code, the Early Error rules for UniqueFormalParameters : FormalParameters are applied.
  • If the source code matching this production is strict mode code, it is a Syntax Error if BindingIdentifier is the IdentifierName eval or the IdentifierName arguments.
  • It is a Syntax Error if ContainsUseStrict of FunctionBody is true and IsSimpleParameterList of FormalParameters is false.
  • It is a Syntax Error if any element of the BoundNames of FormalParameters also occurs in the LexicallyDeclaredNames of FunctionBody.
  • It is a Syntax Error if FormalParameters Contains SuperProperty is true.
  • It is a Syntax Error if FunctionBody Contains SuperProperty is true.
  • It is a Syntax Error if FormalParameters Contains SuperCall is true.
  • It is a Syntax Error if FunctionBody Contains SuperCall is true.
Note 1

The LexicallyDeclaredNames of a FunctionBody does not include identifiers bound using var or function declarations.

UniqueFormalParameters : FormalParameters
  • It is a Syntax Error if BoundNames of FormalParameters contains any duplicate elements.
FormalParameters : FormalParameterList
  • It is a Syntax Error if IsSimpleParameterList of FormalParameterList is false and BoundNames of FormalParameterList contains any duplicate elements.
Note 2

Multiple occurrences of the same BindingIdentifier in a FormalParameterList is only allowed for functions which have simple parameter lists and which are not defined in strict mode code.

FunctionBody : FunctionStatementList
  • It is a Syntax Error if the LexicallyDeclaredNames of FunctionStatementList contains any duplicate entries.
  • It is a Syntax Error if any element of the LexicallyDeclaredNames of FunctionStatementList also occurs in the VarDeclaredNames of FunctionStatementList.
  • It is a Syntax Error if ContainsDuplicateLabels of FunctionStatementList with argument « » is true.
  • It is a Syntax Error if ContainsUndefinedBreakTarget of FunctionStatementList with argument « » is true.
  • It is a Syntax Error if ContainsUndefinedContinueTarget of FunctionStatementList with arguments « » and « » is true.

14.1.3 Static Semantics: BoundNames

FunctionDeclaration : function BindingIdentifier ( FormalParameters ) { FunctionBody }
  1. Return the BoundNames of BindingIdentifier.
FunctionDeclaration : function ( FormalParameters ) { FunctionBody }
  1. Return « "*default*" ».
Note

"*default*" is used within this specification as a synthetic name for hoistable anonymous functions that are defined using export declarations.

FormalParameters : [empty]
  1. Return a new empty List.
FormalParameters : FormalParameterList , FunctionRestParameter
  1. Let names be BoundNames of FormalParameterList.
  2. Append to names the BoundNames of FunctionRestParameter.
  3. Return names.
FormalParameterList : FormalParameterList , FormalParameter
  1. Let names be BoundNames of FormalParameterList.
  2. Append to names the BoundNames of FormalParameter.
  3. Return names.

14.1.4 Static Semantics: Contains

With parameter symbol.

FunctionDeclaration : function BindingIdentifier ( FormalParameters ) { FunctionBody } FunctionDeclaration : function ( FormalParameters ) { FunctionBody } FunctionExpression : function BindingIdentifieropt ( FormalParameters ) { FunctionBody }
  1. Return false.
Note

Static semantic rules that depend upon substructure generally do not look into function definitions.

14.1.5 Static Semantics: ContainsExpression

FormalParameters : [empty]
  1. Return false.
FormalParameters : FormalParameterList , FunctionRestParameter
  1. If ContainsExpression of FormalParameterList is true, return true.
  2. Return ContainsExpression of FunctionRestParameter.
FormalParameterList : FormalParameterList , FormalParameter
  1. If ContainsExpression of FormalParameterList is true, return true.
  2. Return ContainsExpression of FormalParameter.

14.1.6 Static Semantics: ContainsUseStrict

FunctionBody : FunctionStatementList
  1. If the Directive Prologue of FunctionStatementList contains a Use Strict Directive, return true; otherwise, return false.

14.1.7 Static Semantics: ExpectedArgumentCount

FormalParameters : [empty]
  1. Return 0.
FormalParameters : FormalParameterList , FunctionRestParameter
  1. Return ExpectedArgumentCount of FormalParameterList.
Note

The ExpectedArgumentCount of a FormalParameterList is the number of FormalParameters to the left of either the rest parameter or the first FormalParameter with an Initializer. A FormalParameter without an initializer is allowed after the first parameter with an initializer but such parameters are considered to be optional with undefined as their default value.

FormalParameterList : FormalParameterList , FormalParameter
  1. Let count be ExpectedArgumentCount of FormalParameterList.
  2. If HasInitializer of FormalParameterList is true or HasInitializer of FormalParameter is true, return count.
  3. Return count + 1.

14.1.8 Static Semantics: HasInitializer

FormalParameterList : FormalParameterList , FormalParameter
  1. If HasInitializer of FormalParameterList is true, return true.
  2. Return HasInitializer of FormalParameter.

14.1.9 Static Semantics: HasName

FunctionExpression : function ( FormalParameters ) { FunctionBody }
  1. Return false.
FunctionExpression : function BindingIdentifier ( FormalParameters ) { FunctionBody }
  1. Return true.

14.1.10 Static Semantics: IsAnonymousFunctionDefinition ( expr )

The abstract operation IsAnonymousFunctionDefinition determines if its argument is a function definition that does not bind a name. The argument expr is the result of parsing an AssignmentExpression or Initializer. The following steps are taken:

  1. If IsFunctionDefinition of expr is false, return false.
  2. Let hasName be the result of HasName of expr.
  3. If hasName is true, return false.
  4. Return true.

14.1.11 Static Semantics: IsConstantDeclaration

FunctionDeclaration : function BindingIdentifier ( FormalParameters ) { FunctionBody } FunctionDeclaration : function ( FormalParameters ) { FunctionBody }
  1. Return false.

14.1.12 Static Semantics: IsFunctionDefinition

FunctionExpression : function BindingIdentifieropt ( FormalParameters ) { FunctionBody }
  1. Return true.

14.1.13 Static Semantics: IsSimpleParameterList

FormalParameters : [empty]
  1. Return true.
FormalParameters : FormalParameterList , FunctionRestParameter
  1. Return false.
FormalParameterList : FormalParameterList , FormalParameter
  1. If IsSimpleParameterList of FormalParameterList is false, return false.
  2. Return IsSimpleParameterList of FormalParameter.
FormalParameter : BindingElement
  1. Return IsSimpleParameterList of BindingElement.

14.1.14 Static Semantics: LexicallyDeclaredNames

FunctionStatementList : [empty]
  1. Return a new empty List.
FunctionStatementList : StatementList
  1. Return TopLevelLexicallyDeclaredNames of StatementList.

14.1.15 Static Semantics: LexicallyScopedDeclarations

FunctionStatementList : [empty]
  1. Return a new empty List.
FunctionStatementList : StatementList
  1. Return the TopLevelLexicallyScopedDeclarations of StatementList.

14.1.16 Static Semantics: VarDeclaredNames

FunctionStatementList : [empty]
  1. Return a new empty List.
FunctionStatementList : StatementList
  1. Return TopLevelVarDeclaredNames of StatementList.

14.1.17 Static Semantics: VarScopedDeclarations

FunctionStatementList : [empty]
  1. Return a new empty List.
FunctionStatementList : StatementList
  1. Return the TopLevelVarScopedDeclarations of StatementList.

14.1.18 Runtime Semantics: EvaluateBody

With parameters functionObject and List argumentsList.

FunctionBody : FunctionStatementList
  1. Perform ? FunctionDeclarationInstantiation(functionObject, argumentsList).
  2. Return the result of evaluating FunctionStatementList.

14.1.19 Runtime Semantics: IteratorBindingInitialization

With parameters iteratorRecord and environment.

Note 1

When undefined is passed for environment it indicates that a PutValue operation should be used to assign the initialization value. This is the case for formal parameter lists of non-strict functions. In that case the formal parameter bindings are preinitialized in order to deal with the possibility of multiple parameters with the same name.

FormalParameters : [empty]
  1. Return NormalCompletion(empty).
FormalParameters : FormalParameterList , FunctionRestParameter
  1. Let restIndex be the result of performing IteratorBindingInitialization for FormalParameterList using iteratorRecord and environment as the arguments.
  2. ReturnIfAbrupt(restIndex).
  3. Return the result of performing IteratorBindingInitialization for FunctionRestParameter using iteratorRecord and environment as the arguments.
FormalParameterList : FormalParameterList , FormalParameter
  1. Let status be the result of performing IteratorBindingInitialization for FormalParameterList using iteratorRecord and environment as the arguments.
  2. ReturnIfAbrupt(status).
  3. Return the result of performing IteratorBindingInitialization for FormalParameter using iteratorRecord and environment as the arguments.
FormalParameter : BindingElement
  1. If ContainsExpression of BindingElement is false, return the result of performing IteratorBindingInitialization for BindingElement using iteratorRecord and environment as the arguments.
  2. Let currentContext be the running execution context.
  3. Let originalEnv be the VariableEnvironment of currentContext.
  4. Assert: The VariableEnvironment and LexicalEnvironment of currentContext are the same.
  5. Assert: environment and originalEnv are the same.
  6. Let paramVarEnv be NewDeclarativeEnvironment(originalEnv).
  7. Set the VariableEnvironment of currentContext to paramVarEnv.
  8. Set the LexicalEnvironment of currentContext to paramVarEnv.
  9. Let result be the result of performing IteratorBindingInitialization for BindingElement using iteratorRecord and environment as the arguments.
  10. Set the VariableEnvironment of currentContext to originalEnv.
  11. Set the LexicalEnvironment of currentContext to originalEnv.
  12. Return result.
Note 2

The new Environment Record created in step 6 is only used if the BindingElement contains a direct eval.

FunctionRestParameter : BindingRestElement
  1. If ContainsExpression of BindingRestElement is false, return the result of performing IteratorBindingInitialization for BindingRestElement using iteratorRecord and environment as the arguments.
  2. Let currentContext be the running execution context.
  3. Let originalEnv be the VariableEnvironment of currentContext.
  4. Assert: The VariableEnvironment and LexicalEnvironment of currentContext are the same.
  5. Assert: environment and originalEnv are the same.
  6. Let paramVarEnv be NewDeclarativeEnvironment(originalEnv).
  7. Set the VariableEnvironment of currentContext to paramVarEnv.
  8. Set the LexicalEnvironment of currentContext to paramVarEnv.
  9. Let result be the result of performing IteratorBindingInitialization for BindingRestElement using iteratorRecord and environment as the arguments.
  10. Set the VariableEnvironment of currentContext to originalEnv.
  11. Set the LexicalEnvironment of currentContext to originalEnv.
  12. Return result.
Note 3

The new Environment Record created in step 6 is only used if the BindingRestElement contains a direct eval.

14.1.20 Runtime Semantics: InstantiateFunctionObject

With parameter scope.

FunctionDeclaration : function BindingIdentifier ( FormalParameters ) { FunctionBody }
  1. If the function code for FunctionDeclaration is strict mode code, let strict be true. Otherwise let strict be false.
  2. Let name be StringValue of BindingIdentifier.
  3. Let F be FunctionCreate(Normal, FormalParameters, FunctionBody, scope, strict).
  4. Perform MakeConstructor(F).
  5. Perform SetFunctionName(F, name).
  6. Return F.
FunctionDeclaration : function ( FormalParameters ) { FunctionBody }
  1. Let F be FunctionCreate(Normal, FormalParameters, FunctionBody, scope, true).
  2. Perform MakeConstructor(F).
  3. Perform SetFunctionName(F, "default").
  4. Return F.
Note

An anonymous FunctionDeclaration can only occur as part of an export default declaration, and its function code is therefore always strict mode code.

14.1.21 Runtime Semantics: Evaluation

FunctionDeclaration : function BindingIdentifier ( FormalParameters ) { FunctionBody }
  1. Return NormalCompletion(empty).
Note 1

An alternative semantics is provided in B.3.3.

FunctionDeclaration : function ( FormalParameters ) { FunctionBody }
  1. Return NormalCompletion(empty).
FunctionExpression : function ( FormalParameters ) { FunctionBody }
  1. If the function code for FunctionExpression is strict mode code, let strict be true. Otherwise let strict be false.
  2. Let scope be the LexicalEnvironment of the running execution context.
  3. Let closure be FunctionCreate(Normal, FormalParameters, FunctionBody, scope, strict).
  4. Perform MakeConstructor(closure).
  5. Return closure.
FunctionExpression : function BindingIdentifier ( FormalParameters ) { FunctionBody }
  1. If the function code for FunctionExpression is strict mode code, let strict be true. Otherwise let strict be false.
  2. Let scope be the running execution context's LexicalEnvironment.
  3. Let funcEnv be NewDeclarativeEnvironment(scope).
  4. Let envRec be funcEnv's EnvironmentRecord.
  5. Let name be StringValue of BindingIdentifier.
  6. Perform envRec.CreateImmutableBinding(name, false).
  7. Let closure be FunctionCreate(Normal, FormalParameters, FunctionBody, funcEnv, strict).
  8. Perform MakeConstructor(closure).
  9. Perform SetFunctionName(closure, name).
  10. Perform envRec.InitializeBinding(name, closure).
  11. Return closure.
Note 2

The BindingIdentifier in a FunctionExpression can be referenced from inside the FunctionExpression's FunctionBody to allow the function to call itself recursively. However, unlike in a FunctionDeclaration, the BindingIdentifier in a FunctionExpression cannot be referenced from and does not affect the scope enclosing the FunctionExpression.

Note 3

A prototype property is automatically created for every function defined using a FunctionDeclaration or FunctionExpression, to allow for the possibility that the function will be used as a constructor.

FunctionStatementList : [empty]
  1. Return NormalCompletion(undefined).

14.2 Arrow Function Definitions

Syntax

ArrowFunction[In, Yield, Await] : ArrowParameters[?Yield, ?Await] [no LineTerminator here] => ConciseBody[?In] ArrowParameters[Yield, Await] : BindingIdentifier[?Yield, ?Await] CoverParenthesizedExpressionAndArrowParameterList[?Yield, ?Await] ConciseBody[In] : [lookahead ≠ { ] AssignmentExpression[?In, ~Yield, ~Await] { FunctionBody[~Yield, ~Await] }

Supplemental Syntax

When the production
ArrowParameters[Yield, Await] : CoverParenthesizedExpressionAndArrowParameterList[?Yield, ?Await]
is recognized the following grammar is used to refine the interpretation of CoverParenthesizedExpressionAndArrowParameterList:

ArrowFormalParameters[Yield, Await] : ( UniqueFormalParameters[?Yield, ?Await] )

14.2.1 Static Semantics: Early Errors

ArrowFunction : ArrowParameters => ConciseBody
  • It is a Syntax Error if ArrowParameters Contains YieldExpression is true.
  • It is a Syntax Error if ArrowParameters Contains AwaitExpression is true.
  • It is a Syntax Error if ContainsUseStrict of ConciseBody is true and IsSimpleParameterList of ArrowParameters is false.
  • It is a Syntax Error if any element of the BoundNames of ArrowParameters also occurs in the LexicallyDeclaredNames of ConciseBody.
ArrowParameters[Yield, Await] : CoverParenthesizedExpressionAndArrowParameterList[?Yield, ?Await]
  • It is a Syntax Error if the lexical token sequence matched by CoverParenthesizedExpressionAndArrowParameterList cannot be parsed with no tokens left over using ArrowFormalParameters as the goal symbol with its [Yield] and [Await] parameters set to the values used when parsing this CoverParenthesizedExpressionAndArrowParameterList.
  • All early error rules for ArrowFormalParameters and its derived productions also apply to CoveredFormalsList of CoverParenthesizedExpressionAndArrowParameterList.

14.2.2 Static Semantics: BoundNames

ArrowParameters : CoverParenthesizedExpressionAndArrowParameterList
  1. Let formals be CoveredFormalsList of CoverParenthesizedExpressionAndArrowParameterList.
  2. Return the BoundNames of formals.

14.2.3 Static Semantics: Contains

With parameter symbol.

ArrowFunction : ArrowParameters => ConciseBody
  1. If symbol is not one of NewTarget, SuperProperty, SuperCall, super or this, return false.
  2. If ArrowParameters Contains symbol is true, return true.
  3. Return ConciseBody Contains symbol.
Note

Normally, Contains does not look inside most function forms. However, Contains is used to detect new.target, this, and super usage within an ArrowFunction.

ArrowParameters : CoverParenthesizedExpressionAndArrowParameterList
  1. Let formals be CoveredFormalsList of CoverParenthesizedExpressionAndArrowParameterList.
  2. Return formals Contains symbol.

14.2.4 Static Semantics: ContainsExpression

ArrowParameters : BindingIdentifier
  1. Return false.

14.2.5 Static Semantics: ContainsUseStrict

ConciseBody : AssignmentExpression
  1. Return false.

14.2.6 Static Semantics: ExpectedArgumentCount

ArrowParameters : BindingIdentifier
  1. Return 1.

14.2.7 Static Semantics: HasName

ArrowFunction : ArrowParameters => ConciseBody
  1. Return false.

14.2.8 Static Semantics: IsSimpleParameterList

ArrowParameters : BindingIdentifier
  1. Return true.
ArrowParameters : CoverParenthesizedExpressionAndArrowParameterList
  1. Let formals be CoveredFormalsList of CoverParenthesizedExpressionAndArrowParameterList.
  2. Return IsSimpleParameterList of formals.

14.2.9 Static Semantics: CoveredFormalsList

ArrowParameters : BindingIdentifier
  1. Return this ArrowParameters.
CoverParenthesizedExpressionAndArrowParameterList[Yield, Await] : ( Expression ) ( ) ( ... BindingIdentifier ) ( ... BindingPattern ) ( Expression , ... BindingIdentifier ) ( Expression , ... BindingPattern )
  1. Return the result of parsing the lexical token stream matched by CoverParenthesizedExpressionAndArrowParameterList using ArrowFormalParameters as the goal symbol with its [Yield] and [Await] parameters set to the values used when parsing this CoverParenthesizedExpressionAndArrowParameterList.

14.2.10 Static Semantics: LexicallyDeclaredNames

ConciseBody : AssignmentExpression
  1. Return a new empty List.

14.2.11 Static Semantics: LexicallyScopedDeclarations

ConciseBody : AssignmentExpression
  1. Return a new empty List.

14.2.12 Static Semantics: VarDeclaredNames

ConciseBody : AssignmentExpression
  1. Return a new empty List.

14.2.13 Static Semantics: VarScopedDeclarations

ConciseBody : AssignmentExpression
  1. Return a new empty List.

14.2.14 Runtime Semantics: IteratorBindingInitialization

With parameters iteratorRecord and environment.

Note

When undefined is passed for environment it indicates that a PutValue operation should be used to assign the initialization value. This is the case for formal parameter lists of non-strict functions. In that case the formal parameter bindings are preinitialized in order to deal with the possibility of multiple parameters with the same name.

ArrowParameters : BindingIdentifier
  1. Assert: iteratorRecord.[[Done]] is false.
  2. Let next be IteratorStep(iteratorRecord.[[Iterator]]).
  3. If next is an abrupt completion, set iteratorRecord.[[Done]] to true.
  4. ReturnIfAbrupt(next).
  5. If next is false, set iteratorRecord.[[Done]] to true.
  6. Else,
    1. Let v be IteratorValue(next).
    2. If v is an abrupt completion, set iteratorRecord.[[Done]] to true.
    3. ReturnIfAbrupt(v).
  7. If iteratorRecord.[[Done]] is true, let v be undefined.
  8. Return the result of performing BindingInitialization for BindingIdentifier using v and environment as the arguments.

14.2.15 Runtime Semantics: EvaluateBody

With parameters functionObject and List argumentsList.

ConciseBody : AssignmentExpression
  1. Perform ? FunctionDeclarationInstantiation(functionObject, argumentsList).
  2. Let exprRef be the result of evaluating AssignmentExpression.
  3. Let exprValue be ? GetValue(exprRef).
  4. Return Completion{[[Type]]: return, [[Value]]: exprValue, [[Target]]: empty}.

14.2.16 Runtime Semantics: Evaluation

ArrowFunction : ArrowParameters => ConciseBody
  1. If the function code for this ArrowFunction is strict mode code, let strict be true. Otherwise let strict be false.
  2. Let scope be the LexicalEnvironment of the running execution context.
  3. Let parameters be CoveredFormalsList of ArrowParameters.
  4. Let closure be FunctionCreate(Arrow, parameters, ConciseBody, scope, strict).
  5. Return closure.
Note

An ArrowFunction does not define local bindings for arguments, super, this, or new.target. Any reference to arguments, super, this, or new.target within an ArrowFunction must resolve to a binding in a lexically enclosing environment. Typically this will be the Function Environment of an immediately enclosing function. Even though an ArrowFunction may contain references to super, the function object created in step 4 is not made into a method by performing MakeMethod. An ArrowFunction that references super is always contained within a non-ArrowFunction and the necessary state to implement super is accessible via the scope that is captured by the function object of the ArrowFunction.

14.3 Method Definitions

Syntax

MethodDefinition[Yield, Await] : PropertyName[?Yield, ?Await] ( UniqueFormalParameters[~Yield, ~Await] ) { FunctionBody[~Yield, ~Await] } GeneratorMethod[?Yield, ?Await] AsyncMethod[?Yield, ?Await] get PropertyName[?Yield, ?Await] ( ) { FunctionBody[~Yield, ~Await] } set PropertyName[?Yield, ?Await] ( PropertySetParameterList ) { FunctionBody[~Yield, ~Await] } PropertySetParameterList : FormalParameter[~Yield, ~Await]

14.3.1 Static Semantics: Early Errors

MethodDefinition : PropertyName ( UniqueFormalParameters ) { FunctionBody }
  • It is a Syntax Error if ContainsUseStrict of FunctionBody is true and IsSimpleParameterList of UniqueFormalParameters is false.
  • It is a Syntax Error if any element of the BoundNames of UniqueFormalParameters also occurs in the LexicallyDeclaredNames of FunctionBody.
MethodDefinition : set PropertyName ( PropertySetParameterList ) { FunctionBody }
  • It is a Syntax Error if BoundNames of PropertySetParameterList contains any duplicate elements.
  • It is a Syntax Error if ContainsUseStrict of FunctionBody is true and IsSimpleParameterList of PropertySetParameterList is false.
  • It is a Syntax Error if any element of the BoundNames of PropertySetParameterList also occurs in the LexicallyDeclaredNames of FunctionBody.

14.3.2 Static Semantics: ComputedPropertyContains

With parameter symbol.

MethodDefinition : PropertyName ( UniqueFormalParameters ) { FunctionBody } get PropertyName ( ) { FunctionBody } set PropertyName ( PropertySetParameterList ) { FunctionBody }
  1. Return the result of ComputedPropertyContains for PropertyName with argument symbol.

14.3.3 Static Semantics: ExpectedArgumentCount

PropertySetParameterList : FormalParameter
  1. If HasInitializer of FormalParameter is true, return 0.
  2. Return 1.

14.3.4 Static Semantics: HasDirectSuper

MethodDefinition : PropertyName ( UniqueFormalParameters ) { FunctionBody }
  1. If UniqueFormalParameters Contains SuperCall is true, return true.
  2. Return FunctionBody Contains SuperCall.
MethodDefinition : get PropertyName ( ) { FunctionBody }
  1. Return FunctionBody Contains SuperCall.
MethodDefinition : set PropertyName ( PropertySetParameterList ) { FunctionBody }
  1. If PropertySetParameterList Contains SuperCall is true, return true.
  2. Return FunctionBody Contains SuperCall.

14.3.5 Static Semantics: PropName

MethodDefinition : PropertyName ( UniqueFormalParameters ) { FunctionBody } get PropertyName ( ) { FunctionBody } set PropertyName ( PropertySetParameterList ) { FunctionBody }
  1. Return PropName of PropertyName.

14.3.6 Static Semantics: SpecialMethod

MethodDefinition : PropertyName ( UniqueFormalParameters ) { FunctionBody }
  1. Return false.
MethodDefinition : GeneratorMethod AsyncMethod get PropertyName ( ) { FunctionBody } set PropertyName ( PropertySetParameterList ) { FunctionBody }
  1. Return true.

14.3.7 Runtime Semantics: DefineMethod

With parameters object and optional parameter functionPrototype.

MethodDefinition : PropertyName ( UniqueFormalParameters ) { FunctionBody }
  1. Let propKey be the result of evaluating PropertyName.
  2. ReturnIfAbrupt(propKey).
  3. If the function code for this MethodDefinition is strict mode code, let strict be true. Otherwise let strict be false.
  4. Let scope be the running execution context's LexicalEnvironment.
  5. If functionPrototype was passed as a parameter, then
    1. Let kind be Normal.
    2. Let prototype be functionPrototype.
  6. Else,
    1. Let kind be Method.
    2. Let prototype be the intrinsic object %FunctionPrototype%.
  7. Let closure be FunctionCreate(kind, UniqueFormalParameters, FunctionBody, scope, strict, prototype).
  8. Perform MakeMethod(closure, object).
  9. Return the Record{[[Key]]: propKey, [[Closure]]: closure}.

14.3.8 Runtime Semantics: PropertyDefinitionEvaluation

With parameters object and enumerable.

MethodDefinition : PropertyName ( UniqueFormalParameters ) { FunctionBody }
  1. Let methodDef be DefineMethod of MethodDefinition with argument object.
  2. ReturnIfAbrupt(methodDef).
  3. Perform SetFunctionName(methodDef.[[Closure]], methodDef.[[Key]]).
  4. Let desc be the PropertyDescriptor{[[Value]]: methodDef.[[Closure]], [[Writable]]: true, [[Enumerable]]: enumerable, [[Configurable]]: true}.
  5. Return ? DefinePropertyOrThrow(object, methodDef.[[Key]], desc).
MethodDefinition : get PropertyName ( ) { FunctionBody }
  1. Let propKey be the result of evaluating PropertyName.
  2. ReturnIfAbrupt(propKey).
  3. If the function code for this MethodDefinition is strict mode code, let strict be true. Otherwise let strict be false.
  4. Let scope be the running execution context's LexicalEnvironment.
  5. Let formalParameterList be an instance of the production FormalParameters : [empty].
  6. Let closure be FunctionCreate(Method, formalParameterList, FunctionBody, scope, strict).
  7. Perform MakeMethod(closure, object).
  8. Perform SetFunctionName(closure, propKey, "get").
  9. Let desc be the PropertyDescriptor{[[Get]]: closure, [[Enumerable]]: enumerable, [[Configurable]]: true}.
  10. Return ? DefinePropertyOrThrow(object, propKey, desc).
MethodDefinition : set PropertyName ( PropertySetParameterList ) { FunctionBody }
  1. Let propKey be the result of evaluating PropertyName.
  2. ReturnIfAbrupt(propKey).
  3. If the function code for this MethodDefinition is strict mode code, let strict be true. Otherwise let strict be false.
  4. Let scope be the running execution context's LexicalEnvironment.
  5. Let closure be FunctionCreate(Method, PropertySetParameterList, FunctionBody, scope, strict).
  6. Perform MakeMethod(closure, object).
  7. Perform SetFunctionName(closure, propKey, "set").
  8. Let desc be the PropertyDescriptor{[[Set]]: closure, [[Enumerable]]: enumerable, [[Configurable]]: true}.
  9. Return ? DefinePropertyOrThrow(object, propKey, desc).

14.4 Generator Function Definitions

Syntax

GeneratorMethod[Yield, Await] : * PropertyName[?Yield, ?Await] ( UniqueFormalParameters[+Yield, ~Await] ) { GeneratorBody } GeneratorDeclaration[Yield, Await, Default] : function * BindingIdentifier[?Yield, ?Await] ( FormalParameters[+Yield, ~Await] ) { GeneratorBody } [+Default] function * ( FormalParameters[+Yield, ~Await] ) { GeneratorBody } GeneratorExpression : function * BindingIdentifier[+Yield, ~Await]opt ( FormalParameters[+Yield, ~Await] ) { GeneratorBody } GeneratorBody : FunctionBody[+Yield, ~Await] YieldExpression[In, Await] : yield yield [no LineTerminator here] AssignmentExpression[?In, +Yield, ?Await] yield [no LineTerminator here] * AssignmentExpression[?In, +Yield, ?Await] Note 1

The syntactic context immediately following yield requires use of the InputElementRegExpOrTemplateTail lexical goal.

Note 2

YieldExpression cannot be used within the FormalParameters of a generator function because any expressions that are part of FormalParameters are evaluated before the resulting generator object is in a resumable state.

Note 3

Abstract operations relating to generator objects are defined in 25.3.3.

14.4.1 Static Semantics: Early Errors

GeneratorMethod : * PropertyName ( UniqueFormalParameters ) { GeneratorBody }
  • It is a Syntax Error if HasDirectSuper of GeneratorMethod is true.
  • It is a Syntax Error if UniqueFormalParameters Contains YieldExpression is true.
  • It is a Syntax Error if ContainsUseStrict of GeneratorBody is true and IsSimpleParameterList of UniqueFormalParameters is false.
  • It is a Syntax Error if any element of the BoundNames of UniqueFormalParameters also occurs in the LexicallyDeclaredNames of GeneratorBody.
GeneratorDeclaration : function * BindingIdentifier ( FormalParameters ) { GeneratorBody } GeneratorDeclaration : function * ( FormalParameters ) { GeneratorBody } GeneratorExpression : function * BindingIdentifieropt ( FormalParameters ) { GeneratorBody }
  • If the source code matching this production is strict mode code, the Early Error rules for UniqueFormalParameters : FormalParameters are applied.
  • If the source code matching this production is strict mode code, it is a Syntax Error if BindingIdentifier is the IdentifierName eval or the IdentifierName arguments.
  • It is a Syntax Error if ContainsUseStrict of GeneratorBody is true and IsSimpleParameterList of FormalParameters is false.
  • It is a Syntax Error if any element of the BoundNames of FormalParameters also occurs in the LexicallyDeclaredNames of GeneratorBody.
  • It is a Syntax Error if FormalParameters Contains YieldExpression is true.
  • It is a Syntax Error if FormalParameters Contains SuperProperty is true.
  • It is a Syntax Error if GeneratorBody Contains SuperProperty is true.
  • It is a Syntax Error if FormalParameters Contains SuperCall is true.
  • It is a Syntax Error if GeneratorBody Contains SuperCall is true.

14.4.2 Static Semantics: BoundNames

GeneratorDeclaration : function * BindingIdentifier ( FormalParameters ) { GeneratorBody }
  1. Return the BoundNames of BindingIdentifier.
GeneratorDeclaration : function * ( FormalParameters ) { GeneratorBody }
  1. Return « "*default*" ».
Note

"*default*" is used within this specification as a synthetic name for hoistable anonymous functions that are defined using export declarations.

14.4.3 Static Semantics: ComputedPropertyContains

With parameter symbol.

GeneratorMethod : * PropertyName ( UniqueFormalParameters ) { GeneratorBody }
  1. Return the result of ComputedPropertyContains for PropertyName with argument symbol.

14.4.4 Static Semantics: Contains

With parameter symbol.

GeneratorDeclaration : function * BindingIdentifier ( FormalParameters ) { GeneratorBody } GeneratorDeclaration : function * ( FormalParameters ) { GeneratorBody } GeneratorExpression : function * BindingIdentifieropt ( FormalParameters ) { GeneratorBody }
  1. Return false.
Note

Static semantic rules that depend upon substructure generally do not look into function definitions.

14.4.5 Static Semantics: HasDirectSuper

GeneratorMethod : * PropertyName ( UniqueFormalParameters ) { GeneratorBody }
  1. If UniqueFormalParameters Contains SuperCall is true, return true.
  2. Return GeneratorBody Contains SuperCall.

14.4.6 Static Semantics: HasName

GeneratorExpression : function * ( FormalParameters ) { GeneratorBody }
  1. Return false.
GeneratorExpression : function * BindingIdentifier ( FormalParameters ) { GeneratorBody }
  1. Return true.

14.4.7 Static Semantics: IsConstantDeclaration

GeneratorDeclaration : function * BindingIdentifier ( FormalParameters ) { GeneratorBody } GeneratorDeclaration : function * ( FormalParameters ) { GeneratorBody }
  1. Return false.

14.4.8 Static Semantics: IsFunctionDefinition

GeneratorExpression : function * BindingIdentifieropt ( FormalParameters ) { GeneratorBody }
  1. Return true.

14.4.9 Static Semantics: PropName

GeneratorMethod : * PropertyName ( UniqueFormalParameters ) { GeneratorBody }
  1. Return PropName of PropertyName.

14.4.10 Runtime Semantics: EvaluateBody

With parameters functionObject and List argumentsList.

GeneratorBody : FunctionBody
  1. Perform ? FunctionDeclarationInstantiation(functionObject, argumentsList).
  2. Let G be ? OrdinaryCreateFromConstructor(functionObject, "%GeneratorPrototype%", « [[GeneratorState]], [[GeneratorContext]] »).
  3. Perform GeneratorStart(G, FunctionBody).
  4. Return Completion{[[Type]]: return, [[Value]]: G, [[Target]]: empty}.

14.4.11 Runtime Semantics: InstantiateFunctionObject

With parameter scope.

GeneratorDeclaration : function * BindingIdentifier ( FormalParameters ) { GeneratorBody }
  1. If the function code for GeneratorDeclaration is strict mode code, let strict be true. Otherwise let strict be false.
  2. Let name be StringValue of BindingIdentifier.
  3. Let F be GeneratorFunctionCreate(Normal, FormalParameters, GeneratorBody, scope, strict).
  4. Let prototype be ObjectCreate(%GeneratorPrototype%).
  5. Perform DefinePropertyOrThrow(F, "prototype", PropertyDescriptor{[[Value]]: prototype, [[Writable]]: true, [[Enumerable]]: false, [[Configurable]]: false}).
  6. Perform SetFunctionName(F, name).
  7. Return F.
GeneratorDeclaration : function * ( FormalParameters ) { GeneratorBody }
  1. Let F be GeneratorFunctionCreate(Normal, FormalParameters, GeneratorBody, scope, true).
  2. Let prototype be ObjectCreate(%GeneratorPrototype%).
  3. Perform DefinePropertyOrThrow(F, "prototype", PropertyDescriptor{[[Value]]: prototype, [[Writable]]: true, [[Enumerable]]: false, [[Configurable]]: false}).
  4. Perform SetFunctionName(F, "default").
  5. Return F.
Note

An anonymous GeneratorDeclaration can only occur as part of an export default declaration, and its function code is therefore always strict mode code.

14.4.12 Runtime Semantics: PropertyDefinitionEvaluation

With parameters object and enumerable.

GeneratorMethod : * PropertyName ( UniqueFormalParameters ) { GeneratorBody }
  1. Let propKey be the result of evaluating PropertyName.
  2. ReturnIfAbrupt(propKey).
  3. If the function code for this GeneratorMethod is strict mode code, let strict be true. Otherwise let strict be false.
  4. Let scope be the running execution context's LexicalEnvironment.
  5. Let closure be GeneratorFunctionCreate(Method, UniqueFormalParameters, GeneratorBody, scope, strict).
  6. Perform MakeMethod(closure, object).
  7. Let prototype be ObjectCreate(%GeneratorPrototype%).
  8. Perform DefinePropertyOrThrow(closure, "prototype", PropertyDescriptor{[[Value]]: prototype, [[Writable]]: true, [[Enumerable]]: false, [[Configurable]]: false}).
  9. Perform SetFunctionName(closure, propKey).
  10. Let desc be the PropertyDescriptor{[[Value]]: closure, [[Writable]]: true, [[Enumerable]]: enumerable, [[Configurable]]: true}.
  11. Return ? DefinePropertyOrThrow(object, propKey, desc).

14.4.13 Runtime Semantics: Evaluation

GeneratorExpression : function * ( FormalParameters ) { GeneratorBody }
  1. If the function code for this GeneratorExpression is strict mode code, let strict be true. Otherwise let strict be false.
  2. Let scope be the LexicalEnvironment of the running execution context.
  3. Let closure be GeneratorFunctionCreate(Normal, FormalParameters, GeneratorBody, scope, strict).
  4. Let prototype be ObjectCreate(%GeneratorPrototype%).
  5. Perform DefinePropertyOrThrow(closure, "prototype", PropertyDescriptor{[[Value]]: prototype, [[Writable]]: true, [[Enumerable]]: false, [[Configurable]]: false}).
  6. Return closure.
GeneratorExpression : function * BindingIdentifier ( FormalParameters ) { GeneratorBody }
  1. If the function code for this GeneratorExpression is strict mode code, let strict be true. Otherwise let strict be false.
  2. Let scope be the running execution context's LexicalEnvironment.
  3. Let funcEnv be NewDeclarativeEnvironment(scope).
  4. Let envRec be funcEnv's EnvironmentRecord.
  5. Let name be StringValue of BindingIdentifier.
  6. Perform envRec.CreateImmutableBinding(name, false).
  7. Let closure be GeneratorFunctionCreate(Normal, FormalParameters, GeneratorBody, funcEnv, strict).
  8. Let prototype be ObjectCreate(%GeneratorPrototype%).
  9. Perform DefinePropertyOrThrow(closure, "prototype", PropertyDescriptor{[[Value]]: prototype, [[Writable]]: true, [[Enumerable]]: false, [[Configurable]]: false}).
  10. Perform SetFunctionName(closure, name).
  11. Perform envRec.InitializeBinding(name, closure).
  12. Return closure.
Note

The BindingIdentifier in a GeneratorExpression can be referenced from inside the GeneratorExpression's FunctionBody to allow the generator code to call itself recursively. However, unlike in a GeneratorDeclaration, the BindingIdentifier in a GeneratorExpression cannot be referenced from and does not affect the scope enclosing the GeneratorExpression.

YieldExpression : yield
  1. Return ? GeneratorYield(CreateIterResultObject(undefined, false)).
YieldExpression : yield AssignmentExpression
  1. Let exprRef be the result of evaluating AssignmentExpression.
  2. Let value be ? GetValue(exprRef).
  3. Return ? GeneratorYield(CreateIterResultObject(value, false)).
YieldExpression : yield * AssignmentExpression
  1. Let exprRef be the result of evaluating AssignmentExpression.
  2. Let value be ? GetValue(exprRef).
  3. Let iterator be ? GetIterator(value).
  4. Let received be NormalCompletion(undefined).
  5. Repeat,
    1. If received.[[Type]] is normal, then
      1. Let innerResult be ? IteratorNext(iterator, received.[[Value]]).
      2. Let done be ? IteratorComplete(innerResult).
      3. If done is true, then
        1. Return ? IteratorValue(innerResult).
      4. Set received to GeneratorYield(innerResult).
    2. Else if received.[[Type]] is throw, then
      1. Let throw be ? GetMethod(iterator, "throw").
      2. If throw is not undefined, then
        1. Let innerResult be ? Call(throw, iterator, « received.[[Value]] »).
        2. NOTE: Exceptions from the inner iterator throw method are propagated. Normal completions from an inner throw method are processed similarly to an inner next.
        3. If Type(innerResult) is not Object, throw a TypeError exception.
        4. Let done be ? IteratorComplete(innerResult).
        5. If done is true, then
          1. Return ? IteratorValue(innerResult).
        6. Set received to GeneratorYield(innerResult).
      3. Else,
        1. NOTE: If iterator does not have a throw method, this throw is going to terminate the yield* loop. But first we need to give iterator a chance to clean up.
        2. Perform ? IteratorClose(iterator, Completion{[[Type]]: normal, [[Value]]: empty, [[Target]]: empty}).
        3. NOTE: The next step throws a TypeError to indicate that there was a yield* protocol violation: iterator does not have a throw method.
        4. Throw a TypeError exception.
    3. Else,
      1. Assert: received.[[Type]] is return.
      2. Let return be ? GetMethod(iterator, "return").
      3. If return is undefined, return Completion(received).
      4. Let innerReturnResult be ? Call(return, iterator, « received.[[Value]] »).
      5. If Type(innerReturnResult) is not Object, throw a TypeError exception.
      6. Let done be ? IteratorComplete(innerReturnResult).
      7. If done is true, then
        1. Let value be ? IteratorValue(innerReturnResult).
        2. Return Completion{[[Type]]: return, [[Value]]: value, [[Target]]: empty}.
      8. Set received to GeneratorYield(innerReturnResult).

14.5 Class Definitions

Syntax

ClassDeclaration[Yield, Await, Default] : class BindingIdentifier[?Yield, ?Await] ClassTail[?Yield, ?Await] [+Default] class ClassTail[?Yield, ?Await] ClassExpression[Yield, Await] : class BindingIdentifier[?Yield, ?Await]opt ClassTail[?Yield, ?Await] ClassTail[Yield, Await] : ClassHeritage[?Yield, ?Await]opt { ClassBody[?Yield, ?Await]opt } ClassHeritage[Yield, Await] : extends LeftHandSideExpression[?Yield, ?Await] ClassBody[Yield, Await] : ClassElementList[?Yield, ?Await] ClassElementList[Yield, Await] : ClassElement[?Yield, ?Await] ClassElementList[?Yield, ?Await] ClassElement[?Yield, ?Await] ClassElement[Yield, Await] : MethodDefinition[?Yield, ?Await] static MethodDefinition[?Yield, ?Await] ; Note

A class definition is always strict mode code.

14.5.1 Static Semantics: Early Errors

ClassTail : ClassHeritageopt { ClassBody }
  • It is a Syntax Error if ClassHeritage is not present and the following algorithm evaluates to true:

    1. Let constructor be ConstructorMethod of ClassBody.
    2. If constructor is empty, return false.
    3. Return HasDirectSuper of constructor.
ClassBody : ClassElementList
  • It is a Syntax Error if PrototypePropertyNameList of ClassElementList contains more than one occurrence of "constructor".
ClassElement : MethodDefinition
  • It is a Syntax Error if PropName of MethodDefinition is not "constructor" and HasDirectSuper of MethodDefinition is true.
  • It is a Syntax Error if PropName of MethodDefinition is "constructor" and SpecialMethod of MethodDefinition is true.
ClassElement : static MethodDefinition
  • It is a Syntax Error if HasDirectSuper of MethodDefinition is true.
  • It is a Syntax Error if PropName of MethodDefinition is "prototype".

14.5.2 Static Semantics: BoundNames

ClassDeclaration : class BindingIdentifier ClassTail
  1. Return the BoundNames of BindingIdentifier.
ClassDeclaration : class ClassTail
  1. Return « "*default*" ».

14.5.3 Static Semantics: ConstructorMethod

ClassElementList : ClassElement
  1. If ClassElement is ClassElement : ; , return empty.
  2. If IsStatic of ClassElement is true, return empty.
  3. If PropName of ClassElement is not "constructor", return empty.
  4. Return ClassElement.
ClassElementList : ClassElementList ClassElement
  1. Let head be ConstructorMethod of ClassElementList.
  2. If head is not empty, return head.
  3. If ClassElement is ClassElement : ; , return empty.
  4. If IsStatic of ClassElement is true, return empty.
  5. If PropName of ClassElement is not "constructor", return empty.
  6. Return ClassElement.
Note

Early Error rules ensure that there is only one method definition named "constructor" and that it is not an accessor property or generator definition.

14.5.4 Static Semantics: Contains

With parameter symbol.

ClassTail : ClassHeritageopt { ClassBody }
  1. If symbol is ClassBody, return true.
  2. If symbol is ClassHeritage, then
    1. If ClassHeritage is present, return true; otherwise return false.
  3. Let inHeritage be ClassHeritage Contains symbol.
  4. If inHeritage is true, return true.
  5. Return the result of ComputedPropertyContains for ClassBody with argument symbol.
Note

Static semantic rules that depend upon substructure generally do not look into class bodies except for PropertyNames.

14.5.5 Static Semantics: ComputedPropertyContains

With parameter symbol.

ClassElementList : ClassElementList ClassElement
  1. Let inList be the result of ComputedPropertyContains for ClassElementList with argument symbol.
  2. If inList is true, return true.
  3. Return the result of ComputedPropertyContains for ClassElement with argument symbol.
ClassElement : MethodDefinition
  1. Return the result of ComputedPropertyContains for MethodDefinition with argument symbol.
ClassElement : static MethodDefinition
  1. Return the result of ComputedPropertyContains for MethodDefinition with argument symbol.
ClassElement : ;
  1. Return false.

14.5.6 Static Semantics: HasName

ClassExpression : class ClassTail
  1. Return false.
ClassExpression : class BindingIdentifier ClassTail
  1. Return true.

14.5.7 Static Semantics: IsConstantDeclaration

ClassDeclaration : class BindingIdentifier ClassTail ClassDeclaration : class ClassTail
  1. Return false.

14.5.8 Static Semantics: IsFunctionDefinition

ClassExpression : class BindingIdentifieropt ClassTail
  1. Return true.

14.5.9 Static Semantics: IsStatic

ClassElement : MethodDefinition
  1. Return false.
ClassElement : static MethodDefinition
  1. Return true.
ClassElement : ;
  1. Return false.

14.5.10 Static Semantics: NonConstructorMethodDefinitions

ClassElementList : ClassElement
  1. If ClassElement is ClassElement : ; , return a new empty List.
  2. If IsStatic of ClassElement is false and PropName of ClassElement is "constructor", return a new empty List.
  3. Return a List containing ClassElement.
ClassElementList : ClassElementList ClassElement
  1. Let list be NonConstructorMethodDefinitions of ClassElementList.
  2. If ClassElement is ClassElement : ; , return list.
  3. If IsStatic of ClassElement is false and PropName of ClassElement is "constructor", return list.
  4. Append ClassElement to the end of list.
  5. Return list.

14.5.11 Static Semantics: PrototypePropertyNameList

ClassElementList : ClassElement
  1. If PropName of ClassElement is empty, return a new empty List.
  2. If IsStatic of ClassElement is true, return a new empty List.
  3. Return a List containing PropName of ClassElement.
ClassElementList : ClassElementList ClassElement
  1. Let list be PrototypePropertyNameList of ClassElementList.
  2. If PropName of ClassElement is empty, return list.
  3. If IsStatic of ClassElement is true, return list.
  4. Append PropName of ClassElement to the end of list.
  5. Return list.

14.5.12 Static Semantics: PropName

ClassElement : ;
  1. Return empty.

14.5.13 Runtime Semantics: ClassDefinitionEvaluation

With parameter className.

ClassTail : ClassHeritageopt { ClassBodyopt }
  1. Let lex be the LexicalEnvironment of the running execution context.
  2. Let classScope be NewDeclarativeEnvironment(lex).
  3. Let classScopeEnvRec be classScope's EnvironmentRecord.
  4. If className is not undefined, then
    1. Perform classScopeEnvRec.CreateImmutableBinding(className, true).
  5. If ClassHeritage_opt is not present, then
    1. Let protoParent be the intrinsic object %ObjectPrototype%.
    2. Let constructorParent be the intrinsic object %FunctionPrototype%.
  6. Else,
    1. Set the running execution context's LexicalEnvironment to classScope.
    2. Let superclass be the result of evaluating ClassHeritage.
    3. Set the running execution context's LexicalEnvironment to lex.
    4. ReturnIfAbrupt(superclass).
    5. If superclass is null, then
      1. Let protoParent be null.
      2. Let constructorParent be the intrinsic object %FunctionPrototype%.
    6. Else if IsConstructor(superclass) is false, throw a TypeError exception.
    7. Else,
      1. Let protoParent be ? Get(superclass, "prototype").
      2. If Type(protoParent) is neither Object nor Null, throw a TypeError exception.
      3. Let constructorParent be superclass.
  7. Let proto be ObjectCreate(protoParent).
  8. If ClassBody_opt is not present, let constructor be empty.
  9. Else, let constructor be ConstructorMethod of ClassBody.
  10. If constructor is empty, then
    1. If ClassHeritage_opt is present, then
      1. Set constructor to the result of parsing the source text
        constructor(... args){ super (...args);}
        using the syntactic grammar with the goal symbol MethodDefinition[~Yield, ~Await].
    2. Else,
      1. Set constructor to the result of parsing the source text
        constructor( ){ }
        using the syntactic grammar with the goal symbol MethodDefinition[~Yield, ~Await].
  11. Set the running execution context's LexicalEnvironment to classScope.
  12. Let constructorInfo be the result of performing DefineMethod for constructor with arguments proto and constructorParent as the optional functionPrototype argument.
  13. Assert: constructorInfo is not an abrupt completion.
  14. Let F be constructorInfo.[[Closure]].
  15. If ClassHeritage_opt is present, set F.[[ConstructorKind]] to "derived".
  16. Perform MakeConstructor(F, false, proto).
  17. Perform MakeClassConstructor(F).
  18. Perform CreateMethodProperty(proto, "constructor", F).
  19. If ClassBody_opt is not present, let methods be a new empty List.
  20. Else, let methods be NonConstructorMethodDefinitions of ClassBody.
  21. For each ClassElement m in order from methods, do
    1. If IsStatic of m is false, then
      1. Let status be the result of performing PropertyDefinitionEvaluation for m with arguments proto and false.
    2. Else,
      1. Let status be the result of performing PropertyDefinitionEvaluation for m with arguments F and false.
    3. If status is an abrupt completion, then
      1. Set the running execution context's LexicalEnvironment to lex.
      2. Return Completion(status).
  22. Set the running execution context's LexicalEnvironment to lex.
  23. If className is not undefined, then
    1. Perform classScopeEnvRec.InitializeBinding(className, F).
  24. Return F.

14.5.14 Runtime Semantics: BindingClassDeclarationEvaluation

ClassDeclaration : class BindingIdentifier ClassTail
  1. Let className be StringValue of BindingIdentifier.
  2. Let value be the result of ClassDefinitionEvaluation of ClassTail with argument className.
  3. ReturnIfAbrupt(value).
  4. Let hasNameProperty be ? HasOwnProperty(value, "name").
  5. If hasNameProperty is false, perform SetFunctionName(value, className).
  6. Let env be the running execution context's LexicalEnvironment.
  7. Perform ? InitializeBoundName(className, value, env).
  8. Return value.
ClassDeclaration : class ClassTail
  1. Return the result of ClassDefinitionEvaluation of ClassTail with argument undefined.
Note

ClassDeclaration : class ClassTail only occurs as part of an ExportDeclaration and the setting of a name property and establishing its binding are handled as part of the evaluation action for that production. See 15.2.3.11.

14.5.15 Runtime Semantics: Evaluation

ClassDeclaration : class BindingIdentifier ClassTail
  1. Let status be the result of BindingClassDeclarationEvaluation of this ClassDeclaration.
  2. ReturnIfAbrupt(status).
  3. Return NormalCompletion(empty).
Note 1

ClassDeclaration : class ClassTail only occurs as part of an ExportDeclaration and is never directly evaluated.

ClassExpression : class BindingIdentifieropt ClassTail
  1. If BindingIdentifier_opt is not present, let className be undefined.
  2. Else, let className be StringValue of BindingIdentifier.
  3. Let value be the result of ClassDefinitionEvaluation of ClassTail with argument className.
  4. ReturnIfAbrupt(value).
  5. If className is not undefined, then
    1. Let hasNameProperty be ? HasOwnProperty(value, "name").
    2. If hasNameProperty is false, then
      1. Perform SetFunctionName(value, className).
  6. Return NormalCompletion(value).
Note 2

If the class definition included a name static method then that method is not over-written with a name data property for the class name.

14.6 Async Function Definitions

Syntax

AsyncFunctionDeclaration[Yield, Await, Default] : async [no LineTerminator here] function BindingIdentifier[?Yield, ?Await] ( FormalParameters[~Yield, ?Await] ) { AsyncFunctionBody } [+Default] async [no LineTerminator here] function ( FormalParameters[~Yield, ?Await] ) { AsyncFunctionBody } AsyncFunctionExpression : async [no LineTerminator here] function ( FormalParameters[~Yield, +Await] ) { AsyncFunctionBody } async [no LineTerminator here] function BindingIdentifier[~Yield, +Await] ( FormalParameters[~Yield, +Await] ) { AsyncFunctionBody } AsyncMethod[Yield, Await] : async [no LineTerminator here] PropertyName[?Yield, ?Await] ( UniqueFormalParameters[~Yield, +Await] ) { AsyncFunctionBody } AsyncFunctionBody : FunctionBody[~Yield, +Await] AwaitExpression[Yield] : await UnaryExpression[?Yield, +Await] Note 1

await is parsed as an AwaitExpression when the [Await] parameter in present. The [Await] parameter is present in the following contexts:

  • In an AsyncFunctionBody.
  • In the FormalParameters of an AsyncFunctionDeclaration and AsyncFunctionExpression. AwaitExpression in this position is a Syntax error via static semantics.

When Module is the syntactic goal symbol and the [Await] parameter is absent, await is parsed as a keyword and will be a Syntax error. When Script is the syntactic goal symbol, await may be parsed as an identifier when the [Await] parameter is absent. This includes the following contexts:

  • Anywhere outside of an AsyncFunctionBody or FormalParameters of an AsyncFunctionDeclaration or AsyncFunctionExpression.
  • In the BindingIdentifier of a FunctionExpression or GeneratorExpression.
Note 2

Unlike YieldExpression, it is a Syntax Error to omit the operand of an AwaitExpression. You must await something.

14.6.1 Static Semantics: Early Errors

AsyncMethod : async [no LineTerminator here] PropertyName ( UniqueFormalParameters ) { AsyncFunctionBody }
  • It is a Syntax Error if ContainsUseStrict of AsyncFunctionBody is true and IsSimpleParameterList of UniqueFormalParameters is false.
  • It is a Syntax Error if HasDirectSuper of AsyncMethod is true.
  • It is a Syntax Error if UniqueFormalParameters Contains AwaitExpression is true.
  • It is a Syntax Error if any element of the BoundNames of UniqueFormalParameters also occurs in the LexicallyDeclaredNames of AsyncFunctionBody.
AsyncFunctionDeclaration : async [no LineTerminator here] function BindingIdentifier ( FormalParameters ) { AsyncFunctionBody } AsyncFunctionDeclaration : async [no LineTerminator here] function ( FormalParameters ) { AsyncFunctionBody } AsyncFunctionExpression : async [no LineTerminator here] function ( FormalParameters ) { AsyncFunctionBody } AsyncFunctionExpression : async [no LineTerminator here] function BindingIdentifier ( FormalParameters ) { AsyncFunctionBody }
  • It is a Syntax Error if ContainsUseStrict of AsyncFunctionBody is true and IsSimpleParameterList of FormalParameters is false.
  • It is a Syntax Error if FormalParameters Contains AwaitExpression is true.
  • If the source code matching this production is strict code, the Early Error rules for UniqueFormalParameters : FormalParameters are applied.
  • If the source code matching this production is strict code, it is a Syntax Error if BindingIdentifier is the IdentifierName eval or the IdentifierName arguments.
  • It is a Syntax Error if any element of the BoundNames of FormalParameters also occurs in the LexicallyDeclaredNames of AsyncFunctionBody.
  • It is a Syntax Error if FormalParameters Contains SuperProperty is true.
  • It is a Syntax Error if AsyncFunctionBody Contains SuperProperty is true.
  • It is a Syntax Error if FormalParameters Contains SuperCall is true.
  • It is a Syntax Error if AsyncFunctionBody Contains SuperCall is true.

14.6.2 Static Semantics: BoundNames

AsyncFunctionDeclaration : async [no LineTerminator here] function BindingIdentifier ( FormalParameters ) { AsyncFunctionBody }
  1. Return the BoundNames of BindingIdentifier.
AsyncFunctionDeclaration : async [no LineTerminator here] function ( FormalParameters ) { AsyncFunctionBody }
  1. Return «"*default*"».
Note
"*default*" is used within this specification as a synthetic name for hoistable anonymous functions that are defined using export declarations.

14.6.3 Static Semantics: ComputedPropertyContains

With parameter symbol.

AsyncMethod : async [no LineTerminator here] PropertyName ( UniqueFormalParameters ) { AsyncFunctionBody }
  1. Return the result of ComputedPropertyContains for PropertyName with argument symbol.

14.6.4 Static Semantics: Contains

With parameter symbol.

AsyncFunctionDeclaration : async [no LineTerminator here] function BindingIdentifier ( FormalParameters ) { AsyncFunctionBody } AsyncFunctionDeclaration : async [no LineTerminator here] function ( FormalParameters ) { AsyncFunctionBody } AsyncFunctionExpression : async [no LineTerminator here] function ( FormalParameters ) { AsyncFunctionBody } AsyncFunctionExpression : async [no LineTerminator here] function BindingIdentifier ( FormalParameters ) { AsyncFunctionBody }
  1. Return false.

14.6.5 Static Semantics: HasDirectSuper

AsyncMethod : async [no LineTerminator here] PropertyName ( UniqueFormalParameters ) { AsyncFunctionBody }
  1. If UniqueFormalParameters Contains SuperCall is true, return true.

14.6.6 Static Semantics: HasName

AsyncFunctionExpression : async [no LineTerminator here] function ( FormalParameters ) { AsyncFunctionBody }
  1. Return false.
AsyncFunctionExpression : async [no LineTerminator here] function BindingIdentifier ( FormalParameters ) { AsyncFunctionBody }
  1. Return true.

14.6.7 Static Semantics: IsConstantDeclaration

AsyncFunctionDeclaration : async [no LineTerminator here] function BindingIdentifier ( FormalParameters ) { AsyncFunctionBody } AsyncFunctionDeclaration : async [no LineTerminator here] function ( FormalParameters ) { AsyncFunctionBody }
  1. Return false.

14.6.8 Static Semantics: IsFunctionDefinition

AsyncFunctionExpression : async [no LineTerminator here] function ( FormalParameters ) { AsyncFunctionBody } AsyncFunctionExpression : async [no LineTerminator here] function BindingIdentifier ( FormalParameters ) { AsyncFunctionBody }
  1. Return true.

14.6.9 Static Semantics: PropName

AsyncMethod : async [no LineTerminator here] PropertyName ( UniqueFormalParameters ) { AsyncFunctionBody }
  1. Return PropName of PropertyName.

14.6.10 Runtime Semantics: InstantiateFunctionObject

With parameter scope.

AsyncFunctionDeclaration : async [no LineTerminator here] function BindingIdentifier ( FormalParameters ) { AsyncFunctionBody }
  1. If the function code for AsyncFunctionDeclaration is strict mode code, let strict be true. Otherwise, let strict be false.
  2. Let name be StringValue of BindingIdentifier.
  3. Let F be ! AsyncFunctionCreate(Normal, FormalParameters, AsyncFunctionBody, scope, strict).
  4. Perform ! SetFunctionName(F, name).
  5. Return F.
AsyncFunctionDeclaration : async [no LineTerminator here] function ( FormalParameters ) { AsyncFunctionBody }
  1. If the function code for AsyncFunctionDeclaration is strict mode code, let strict be true. Otherwise, let strict be false.
  2. Let F be ! AsyncFunctionCreate(Normal, FormalParameters, AsyncFunctionBody, scope, strict).
  3. Perform ! SetFunctionName(F, "default").
  4. Return F.

14.6.11 Runtime Semantics: EvaluateBody

With parameters functionObject and List argumentsList.

AsyncFunctionBody : FunctionBody
  1. Let promiseCapability be ! NewPromiseCapability(%Promise%).
  2. Let declResult be ! FunctionDeclarationInstantiation(functionObject, argumentsList).
  3. If declResult is not an abrupt completion, then
    1. Perform ! AsyncFunctionStart(promiseCapability, FunctionBody).
  4. Else declResult is an abrupt completion,
    1. Perform ! Call(promiseCapability.[[Reject]], undefined, «declResult.[[Value]]»).
  5. Return Completion{[[Type]]: return, [[Value]]: promiseCapability.[[Promise]], [[Target]]: empty}.

14.6.12 Runtime Semantics: PropertyDefinitionEvaluation

With parameters object and enumerable.

AsyncMethod : async [no LineTerminator here] PropertyName ( UniqueFormalParameters ) { AsyncFunctionBody }
  1. Let propKey be the result of evaluating PropertyName.
  2. ReturnIfAbrupt(propKey).
  3. If the function code for this AsyncMethod is strict mode code, let strict be true. Otherwise let strict be false.
  4. Let scope be the LexicalEnvironment of the running execution context.
  5. Let closure be ! AsyncFunctionCreate(Method, UniqueFormalParameters, AsyncFunctionBody, scope, strict).
  6. Perform ! MakeMethod(closure, object).
  7. Perform ! SetFunctionName(closure, propKey).
  8. Let desc be the PropertyDescriptor{[[Value]]: closure, [[Writable]]: true, [[Enumerable]]: enumerable, [[Configurable]]: true}.
  9. Return ? DefinePropertyOrThrow(object, propKey, desc).

14.6.13 Runtime Semantics: Evaluation

AsyncFunctionDeclaration : async [no LineTerminator here] function BindingIdentifier ( FormalParameters ) { AsyncFunctionBody }
  1. Return NormalCompletion(empty).
AsyncFunctionDeclaration : async [no LineTerminator here] function ( FormalParameters ) { AsyncFunctionBody }
  1. Return NormalCompletion(empty).
AsyncFunctionExpression : async [no LineTerminator here] function ( FormalParameters ) { AsyncFunctionBody }
  1. If the function code for AsyncFunctionExpression is strict mode code, let strict be true. Otherwise let strict be false.
  2. Let scope be the LexicalEnvironment of the running execution context.
  3. Let closure be ! AsyncFunctionCreate(Normal, FormalParameters, AsyncFunctionBody, scope, strict).
  4. Return closure.
AsyncFunctionExpression : async [no LineTerminator here] function BindingIdentifier ( FormalParameters ) { AsyncFunctionBody }
  1. If the function code for AsyncFunctionExpression is strict mode code, let strict be true. Otherwise let strict be false.
  2. Let scope be the LexicalEnvironment of the running execution context.
  3. Let funcEnv be ! NewDeclarativeEnvironment(scope).
  4. Let envRec be funcEnv's EnvironmentRecord.
  5. Let name be StringValue of BindingIdentifier.
  6. Perform ! envRec.CreateImmutableBinding(name).
  7. Let closure be ! AsyncFunctionCreate(Normal, FormalParameters, AsyncFunctionBody, funcEnv, strict).
  8. Perform ! SetFunctionName(closure, name).
  9. Perform ! envRec.InitializeBinding(name, closure).
  10. Return closure.
AwaitExpression : await UnaryExpression
  1. Let exprRef be the result of evaluating UnaryExpression.
  2. Let value be ? GetValue(exprRef).
  3. Return ? AsyncFunctionAwait(value).

14.7 Async Arrow Function Definitions

Syntax

AsyncArrowFunction[In, Yield, Await] : async [no LineTerminator here] AsyncArrowBindingIdentifier[?Yield] [no LineTerminator here] => AsyncConciseBody[?In] CoverCallExpressionAndAsyncArrowHead[?Yield, ?Await] [no LineTerminator here] => AsyncConciseBody[?In] AsyncConciseBody[In] : [lookahead ≠ {] AssignmentExpression[?In, ~Yield, +Await] { AsyncFunctionBody } AsyncArrowBindingIdentifier[Yield] : BindingIdentifier[?Yield, +Await] CoverCallExpressionAndAsyncArrowHead[Yield, Await] : MemberExpression[?Yield, ?Await] Arguments[?Yield, ?Await]

Supplemental Syntax

When processing an instance of the production AsyncArrowFunction : CoverCallExpressionAndAsyncArrowHead [no LineTerminator here] => AsyncConciseBody the interpretation of CoverCallExpressionAndAsyncArrowHead is refined using the following grammar:

AsyncArrowHead : async [no LineTerminator here] ArrowFormalParameters[~Yield, +Await]

14.7.1 Static Semantics: Early Errors

AsyncArrowFunction : async [no LineTerminator here] AsyncArrowBindingIdentifier [no LineTerminator here] => AsyncConciseBody
  • It is a Syntax Error if any element of the BoundNames of AsyncArrowBindingIdentifier also occurs in the LexicallyDeclaredNames of AsyncConciseBody.
AsyncArrowFunction : CoverCallExpressionAndAsyncArrowHead [no LineTerminator here] => AsyncConciseBody
  • It is a Syntax Error if CoverCallExpressionAndAsyncArrowHead Contains YieldExpression is true.
  • It is a Syntax Error if CoverCallExpressionAndAsyncArrowHead Contains AwaitExpression is true.
  • It is a Syntax Error if the lexical token sequence matched by CoverCallExpressionAndAsyncArrowHead cannot be parsed with no tokens left over using AsyncArrowHead as the goal symbol.
  • It is a Syntax Error if any element of the BoundNames of CoverCallExpressionAndAsyncArrowHead also occurs in the LexicallyDeclaredNames of AsyncConciseBody.
  • It is a Syntax Error if ContainsUseStrict of AsyncConciseBody is true and IsSimpleParameterList of CoverCallExpressionAndAsyncArrowHead is false.
  • All Early Error rules for AsyncArrowHead and its derived productions apply to CoveredAsyncArrowHead of CoverCallExpressionAndAsyncArrowHead.

14.7.2 Static Semantics: CoveredAsyncArrowHead

CoverCallExpressionAndAsyncArrowHead : MemberExpression Arguments
  1. Return the result of parsing the lexical token stream matched by CoverCallExpressionAndAsyncArrowHead using AsyncArrowHead as the goal symbol.

14.7.3 Static Semantics: BoundNames

CoverCallExpressionAndAsyncArrowHead : MemberExpression Arguments
  1. Let head be CoveredAsyncArrowHead of CoverCallExpressionAndAsyncArrowHead.
  2. Return the BoundNames of head.

14.7.4 Static Semantics: Contains

With parameter symbol.

AsyncArrowFunction : async [no LineTerminator here] AsyncArrowBindingIdentifier [no LineTerminator here] => AsyncConciseBody
  1. If symbol is not one of NewTarget, SuperProperty, SuperCall, super, or this, return false.
  2. Return AsyncConciseBody Contains symbol.
AsyncArrowFunction : CoverCallExpressionAndAsyncArrowHead [no LineTerminator here] => AsyncConciseBody
  1. If symbol is not one of NewTarget, SuperProperty, SuperCall, super, or this, return false.
Note
Normally, Contains does not look inside most function forms. However, Contains is used to detect new.target, this, and super usage within an AsyncArrowFunction.

14.7.5 Static Semantics: ContainsExpression

AsyncArrowBindingIdentifier : BindingIdentifier
  1. Return false.

14.7.6 Static Semantics: ExpectedArgumentCount

AsyncArrowBindingIdentifier : BindingIdentifier
  1. Return 1.

14.7.7 Static Semantics: HasName

AsyncArrowFunction : async [no LineTerminator here] AsyncArrowBindingIdentifier [no LineTerminator here] => AsyncConciseBody AsyncArrowFunction : CoverCallExpressionAndAsyncArrowHead [no LineTerminator here] => AsyncConciseBody
  1. Return false.

14.7.8 Static Semantics: IsSimpleParameterList

AsyncArrowBindingIdentifier[Yield] : BindingIdentifier[?Yield, +Await]
  1. Return true.
CoverCallExpressionAndAsyncArrowHead : MemberExpression Arguments
  1. Let head be CoveredAsyncArrowHead of CoverCallExpressionAndAsyncArrowHead.
  2. Return IsSimpleParameterList of head.

14.7.9 Static Semantics: LexicallyDeclaredNames

AsyncConciseBody : [lookahead ≠ {] AssignmentExpression
  1. Return a new empty List.

14.7.10 Static Semantics: LexicallyScopedDeclarations

AsyncConciseBody : [lookahead ≠ {] AssignmentExpression
  1. Return a new empty List.

14.7.11 Static Semantics: VarDeclaredNames

AsyncConciseBody : [lookahead ≠ {] AssignmentExpression
  1. Return a new empty List.

14.7.12 Static Semantics: VarScopedDeclarations

AsyncConciseBody : [lookahead ≠ {] AssignmentExpression
  1. Return a new empty List.

14.7.13 Runtime Semantics: IteratorBindingInitialization

With parameters iteratorRecord and environment.

AsyncArrowBindingIdentifier : BindingIdentifier
  1. Assert: iteratorRecord.[[Done]] is false.
  2. Let next be ? IteratorStep(iteratorRecord.[[Iterator]]).
  3. If next is an abrupt completion, set iteratorRecord.[[Done]] to true.
  4. ReturnIfAbrupt(next).
  5. If next is false, set iteratorRecord.[[Done]] to true.
  6. Else,
    1. Let v be ? IteratorValue(next).
    2. If v is an abrupt completion, set iteratorRecord.[[Done]] to true.
    3. ReturnIfAbrupt(v).
  7. If iteratorRecord.[[Done]] is true, let v be undefined.
  8. Return the result of performing BindingInitialization for BindingIdentifier using v and environment as the arguments.

14.7.14 Runtime Semantics: EvaluateBody

With parameters functionObject and List argumentsList.

AsyncConciseBody : [lookahead ≠ {] AssignmentExpression
  1. Let promiseCapability be ! NewPromiseCapability(%Promise%).
  2. Let declResult be ! FunctionDeclarationInstantiation(functionObject, argumentsList).
  3. If declResult is not an abrupt completion, then
    1. Perform ! AsyncFunctionStart(promiseCapability, AssignmentExpression).
  4. Else declResult is an abrupt completion,
    1. Perform ! Call(promiseCapability.[[Reject]], undefined, «declResult.[[Value]]»).
  5. Return Completion{[[Type]]: return, [[Value]]: promiseCapability.[[Promise]], [[Target]]: empty}.
AsyncConciseBody : { AsyncFunctionBody }
  1. Return the result of EvaluateBody of AsyncFunctionBody passing functionObject and argumentsList as the arguments.

14.7.15 Runtime Semantics: Evaluation

AsyncArrowFunction : async [no LineTerminator here] AsyncArrowBindingIdentifier [no LineTerminator here] => AsyncConciseBody
  1. If the function code for this AsyncArrowFunction is strict mode code, let strict be true. Otherwise, let strict be false.
  2. Let scope be the LexicalEnvironment of the running execution context.
  3. Let parameters be AsyncArrowBindingIdentifier.
  4. Let closure be ! AsyncFunctionCreate(Arrow, parameters, AsyncConciseBody, scope, strict).
  5. Return closure.
AsyncArrowFunction : CoverCallExpressionAndAsyncArrowHead [no LineTerminator here] => AsyncConciseBody
  1. If the function code for this AsyncArrowFunction is strict mode code, let strict be true. Otherwise, let strict be false.
  2. Let scope be the LexicalEnvironment of the running execution context.
  3. Let head be CoveredAsyncArrowHead of CoverCallExpressionAndAsyncArrowHead.
  4. Let parameters be the ArrowFormalParameters of head.
  5. Let closure be ! AsyncFunctionCreate(Arrow, parameters, AsyncConciseBody, scope, strict).
  6. Return closure.

14.8 Tail Position Calls

14.8.1 Static Semantics: IsInTailPosition( call )

The abstract operation IsInTailPosition with argument call performs the following steps:

  1. Assert: call is a Parse Node.
  2. If the source code matching call is non-strict code, return false.
  3. If call is not contained within a FunctionBody, ConciseBody, or AsyncConciseBody, return false.
  4. Let body be the FunctionBody, ConciseBody, or AsyncConciseBody that most closely contains call.
  5. If body is the FunctionBody of a GeneratorBody, return false.
  6. If body is the FunctionBody of an AsyncFunctionBody, return false.
  7. If body is an AsyncConciseBody, return false.
  8. Return the result of HasCallInTailPosition of body with argument call.
Note

Tail Position calls are only defined in strict mode code because of a common non-standard language extension (see 9.2.7) that enables observation of the chain of caller contexts.

14.8.2 Static Semantics: HasCallInTailPosition

With parameter call.

Note

call is a Parse Node that represents a specific range of source text. When the following algorithms compare call to another Parse Node, it is a test of whether they represent the same source text.

14.8.2.1 Statement Rules

ConciseBody : AssignmentExpression
  1. Return HasCallInTailPosition of AssignmentExpression with argument call.
StatementList : StatementList StatementListItem
  1. Let has be HasCallInTailPosition of StatementList with argument call.
  2. If has is true, return true.
  3. Return HasCallInTailPosition of StatementListItem with argument call.
FunctionStatementList : [empty] StatementListItem : Declaration Statement : VariableStatement EmptyStatement ExpressionStatement ContinueStatement BreakStatement ThrowStatement DebuggerStatement Block : { } ReturnStatement : return ; LabelledItem : FunctionDeclaration IterationStatement : for ( LeftHandSideExpression of AssignmentExpression ) Statement for ( var ForBinding of AssignmentExpression ) Statement for ( ForDeclaration of AssignmentExpression ) Statement CaseBlock : { }
  1. Return false.
IfStatement : if ( Expression ) Statement else Statement
  1. Let has be HasCallInTailPosition of the first Statement with argument call.
  2. If has is true, return true.
  3. Return HasCallInTailPosition of the second Statement with argument call.
IfStatement : if ( Expression ) Statement IterationStatement : do Statement while ( Expression ) ; while ( Expression ) Statement for ( Expressionopt ; Expressionopt ; Expressionopt ) Statement for ( var VariableDeclarationList ; Expressionopt ; Expressionopt ) Statement for ( LexicalDeclaration Expressionopt ; Expressionopt ) Statement for ( LeftHandSideExpression in Expression ) Statement for ( var ForBinding in Expression ) Statement for ( ForDeclaration in Expression ) Statement WithStatement : with ( Expression ) Statement
  1. Return HasCallInTailPosition of Statement with argument call.
LabelledStatement : LabelIdentifier : LabelledItem
  1. Return HasCallInTailPosition of LabelledItem with argument call.
ReturnStatement : return Expression ;
  1. Return HasCallInTailPosition of Expression with argument call.
SwitchStatement : switch ( Expression ) CaseBlock
  1. Return HasCallInTailPosition of CaseBlock with argument call.
CaseBlock : { CaseClausesopt DefaultClause CaseClausesopt }
  1. Let has be false.
  2. If the first CaseClauses is present, let has be HasCallInTailPosition of the first CaseClauses with argument call.
  3. If has is true, return true.
  4. Let has be HasCallInTailPosition of the DefaultClause with argument call.
  5. If has is true, return true.
  6. If the second CaseClauses is present, let has be HasCallInTailPosition of the second CaseClauses with argument call.
  7. Return has.
CaseClauses : CaseClauses CaseClause
  1. Let has be HasCallInTailPosition of CaseClauses with argument call.
  2. If has is true, return true.
  3. Return HasCallInTailPosition of CaseClause with argument call.
CaseClause : case Expression : StatementListopt DefaultClause : default : StatementListopt
  1. If StatementList is present, return HasCallInTailPosition of StatementList with argument call.
  2. Return false.
TryStatement : try Block Catch
  1. Return HasCallInTailPosition of Catch with argument call.
TryStatement : try Block Finally TryStatement : try Block Catch Finally
  1. Return HasCallInTailPosition of Finally with argument call.
Catch : catch ( CatchParameter ) Block
  1. Return HasCallInTailPosition of Block with argument call.

14.8.2.2 Expression Rules

Note

A potential tail position call that is immediately followed by return GetValue of the call result is also a possible tail position call. Function calls cannot return reference values, so such a GetValue operation will always return the same value as the actual function call result.

AssignmentExpression : YieldExpression ArrowFunction AsyncArrowFunction LeftHandSideExpression = AssignmentExpression LeftHandSideExpression AssignmentOperator AssignmentExpression BitwiseANDExpression : BitwiseANDExpression & EqualityExpression BitwiseXORExpression : BitwiseXORExpression ^ BitwiseANDExpression BitwiseORExpression : BitwiseORExpression | BitwiseXORExpression EqualityExpression : EqualityExpression == RelationalExpression EqualityExpression != RelationalExpression EqualityExpression === RelationalExpression EqualityExpression !== RelationalExpression RelationalExpression : RelationalExpression < ShiftExpression RelationalExpression > ShiftExpression RelationalExpression <= ShiftExpression RelationalExpression >= ShiftExpression RelationalExpression instanceof ShiftExpression RelationalExpression in ShiftExpression ShiftExpression : ShiftExpression << AdditiveExpression ShiftExpression >> AdditiveExpression ShiftExpression >>> AdditiveExpression AdditiveExpression : AdditiveExpression + MultiplicativeExpression AdditiveExpression - MultiplicativeExpression MultiplicativeExpression : MultiplicativeExpression MultiplicativeOperator ExponentiationExpression ExponentiationExpression : UpdateExpression ** ExponentiationExpression UpdateExpression : LeftHandSideExpression ++ LeftHandSideExpression -- ++ UnaryExpression -- UnaryExpression UnaryExpression : delete UnaryExpression void UnaryExpression typeof UnaryExpression + UnaryExpression - UnaryExpression ~ UnaryExpression ! UnaryExpression AwaitExpression CallExpression : SuperCall CallExpression [ Expression ] CallExpression . IdentifierName NewExpression : new NewExpression MemberExpression : MemberExpression [ Expression ] MemberExpression . IdentifierName SuperProperty MetaProperty new MemberExpression Arguments PrimaryExpression : this IdentifierReference Literal ArrayLiteral ObjectLiteral FunctionExpression ClassExpression GeneratorExpression AsyncFunctionExpression RegularExpressionLiteral TemplateLiteral
  1. Return false.
Expression : AssignmentExpression Expression , AssignmentExpression
  1. Return HasCallInTailPosition of AssignmentExpression with argument call.
ConditionalExpression : LogicalORExpression ? AssignmentExpression : AssignmentExpression
  1. Let has be HasCallInTailPosition of the first AssignmentExpression with argument call.
  2. If has is true, return true.
  3. Return HasCallInTailPosition of the second AssignmentExpression with argument call.
LogicalANDExpression : LogicalANDExpression && BitwiseORExpression
  1. Return HasCallInTailPosition of BitwiseORExpression with argument call.
LogicalORExpression : LogicalORExpression || LogicalANDExpression
  1. Return HasCallInTailPosition of LogicalANDExpression with argument call.
CallExpression : CoverCallExpressionAndAsyncArrowHead CallExpression Arguments CallExpression TemplateLiteral
  1. If this CallExpression is call, return true.
  2. Return false.
MemberExpression : MemberExpression TemplateLiteral
  1. If this MemberExpression is call, return true.
  2. Return false.
PrimaryExpression : CoverParenthesizedExpressionAndArrowParameterList
  1. Let expr be CoveredParenthesizedExpression of CoverParenthesizedExpressionAndArrowParameterList.
  2. Return HasCallInTailPosition of expr with argument call.
ParenthesizedExpression : ( Expression )
  1. Return HasCallInTailPosition of Expression with argument call.

14.8.3 Runtime Semantics: PrepareForTailCall ( )

The abstract operation PrepareForTailCall performs the following steps:

  1. Let leafContext be the running execution context.
  2. Suspend leafContext.
  3. Pop leafContext from the execution context stack. The execution context now on the top of the stack becomes the running execution context.
  4. Assert: leafContext has no further use. It will never be activated as the running execution context.

A tail position call must either release any transient internal resources associated with the currently executing function execution context before invoking the target function or reuse those resources in support of the target function.

Note

For example, a tail position call should only grow an implementation's activation record stack by the amount that the size of the target function's activation record exceeds the size of the calling function's activation record. If the target function's activation record is smaller, then the total size of the stack should decrease.