13 Function Definition
Syntax
FunctionDeclaration :
function
Identifier (
FormalParameterListopt )
{
FunctionBody }
FunctionExpression :
function
Identifieropt (
FormalParameterListopt )
{
FunctionBody }
FormalParameterList :
Identifier
FormalParameterList ,
Identifier
FunctionBody :
SourceElementsopt
Semantics
The production
FunctionDeclaration : function
Identifier (
FormalParameterListopt )
{
FunctionBody }
is instantiated as follows during Declaration Binding
instantiation (10.5):
- Return the result of creating a new Function object as specified in 13.2 with parameters specified
by FormalParameterListopt, and body specified by FunctionBody. Pass in the VariableEnvironment of the running execution context as the Scope. Pass in true as the
Strict flag if the FunctionDeclaration is contained in strict code or if its
FunctionBody is strict code.
The production
FunctionExpression : function
(
FormalParameterListopt )
{
FunctionBody }
is evaluated
as follows:
- Return the result of creating a new Function object as specified in 13.2 with parameters specified
by FormalParameterListopt and body specified by FunctionBody. Pass in the LexicalEnvironment of the running execution context as the Scope. Pass in true as the
Strict flag if the FunctionExpression is contained in strict code or if its
FunctionBody is strict code.
The production
FunctionExpression : function
Identifier (
FormalParameterListopt )
{
FunctionBody }
is evaluated as follows:
- Let funcEnv be the result of calling NewDeclarativeEnvironment passing the running
execution context's Lexical Environment as the argument
- Let envRec be funcEnv’s environment record.
- Call the CreateImmutableBinding concrete method of envRec passing the String value of Identifier as the
argument.
- Let closure be the result of creating a new Function object as specified in 13.2 with
parameters specified by FormalParameterListopt and body specified by FunctionBody. Pass in
funcEnv as the Scope. Pass in true as the Strict flag if the FunctionExpression is
contained in strict code or if its FunctionBody is strict
code.
- Call the InitializeImmutableBinding concrete method of envRec passing the String value of Identifier and
closure as the arguments.
- Return closure.
NOTE The Identifier 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 Identifier in a FunctionExpression cannot be referenced from and does not affect the scope enclosing the FunctionExpression.
The production FunctionBody : SourceElementsopt is evaluated as follows:
- The code of this FunctionBody is strict mode code if it is part of a
FunctionDeclaration or FunctionExpression that is contained in strict mode code or
if the Directive Prologue (14.1) of its SourceElements contains a
Use Strict Directive or if any of the conditions in 10.1.1 apply. If
the code of this FunctionBody is strict mode code, SourceElements is evaluated in
the following steps as strict mode code. Otherwise, SourceElements is evaluated in the
following steps as non-strict mode code.
- If SourceElements is present return the result of evaluating SourceElements.
- Else return (normal, undefined, empty).
13.1 Strict Mode Restrictions
It is a SyntaxError if any Identifier value occurs more than once within a FormalParameterList of a strict mode FunctionDeclaration or FunctionExpression.
It is a SyntaxError if the Identifier "eval"
or the Identifier "arguments"
occurs within a FormalParameterList of a strict
mode FunctionDeclaration or FunctionExpression.
It is a SyntaxError if the Identifier "eval"
or the Identifier "arguments"
occurs as the Identifier of a strict mode FunctionDeclaration or FunctionExpression.
13.2 Creating Function Objects
Given an optional parameter list specified by FormalParameterList, a body specified by FunctionBody, a Lexical Environment specified by Scope, and
a Boolean flag Strict, a Function object is constructed as follows:
- Create a new native ECMAScript object and let F be that object.
- Set all the internal methods, except for [[Get]], of F as described in 8.12.
- Set the [[Class]] internal property of F to
"Function"
.
- Set the [[Prototype]] internal property of F to the standard built-in Function prototype object as specified in
15.3.3.1.
- Set the [[Get]] internal property of F as described in 15.3.5.4.
- Set the [[Call]] internal property of F as described in 13.2.1.
- Set the [[Construct]] internal property of F as described in 13.2.2.
- Set the [[HasInstance]] internal property of F as described in 15.3.5.3.
- Set the [[Scope]] internal property of F to the value of Scope.
- Let names be a List containing, in left to right textual order, the Strings corresponding
to the identifiers of FormalParameterList. If no parameters are specified, let names be the empty
list.
- Set the [[FormalParameters]] internal property of F to names.
- Set the [[Code]] internal property of F to FunctionBody.
- Set the [[Extensible]] internal property of F to true.
- Let len be the number of formal parameters specified in FormalParameterList. If no parameters are
specified, let len be 0.
- Call the [[DefineOwnProperty]] internal method of F with arguments
"length"
, Property Descriptor {[[Value]]: len, [[Writable]]: false, [[Enumerable]]:
false, [[Configurable]]: false}, and false.
- Let proto be the result of creating a new object as would be constructed by the expression
new
Object()
where Object
is the standard built-in constructor with that name.
- Call the [[DefineOwnProperty]] internal method of proto with arguments
"constructor"
, Property Descriptor {[[Value]]: F, { [[Writable]]: true, [[Enumerable]]:
false, [[Configurable]]: true}, and false.
- Call the [[DefineOwnProperty]] internal method of F with arguments
"prototype"
, Property Descriptor {[[Value]]: proto, { [[Writable]]: true, [[Enumerable]]:
false, [[Configurable]]: false}, and false.
- If Strict is true, then
- Let thrower be the [[ThrowTypeError]] function Object (13.2.3).
- Call the [[DefineOwnProperty]] internal method of F with arguments
"caller"
, PropertyDescriptor
{[[Get]]: thrower, [[Set]]: thrower, [[Enumerable]]: false, [[Configurable]]: false},
and false.
- Call the [[DefineOwnProperty]] internal method of F with arguments
"arguments"
,
PropertyDescriptor {[[Get]]: thrower, [[Set]]: thrower, [[Enumerable]]: false,
[[Configurable]]: false}, and false.
- Return F.
NOTE A prototype
property is automatically created for every function, to allow for
the possibility that the function will be used as a constructor.
When the [[Call]] internal method for a Function object F is called with a this value and a list of arguments,
the following steps are taken:
- Let funcCtx be the result of establishing a new execution context for function code using the value of
F's [[FormalParameters]] internal property, the passed arguments List args, and
the this value as described in 10.4.3.
- Let result be the result of evaluating the FunctionBody that is the value of F's [[Code]]
internal property. If F does not have a [[Code]] internal property or if its value is an empty
FunctionBody, then result is (normal, undefined, empty).
- Exit the execution context funcCtx, restoring the previous execution context.
- If result.type is throw then throw result.value.
- If result.type is return then return result.value.
- Otherwise result.type must be normal. Return
undefined.
13.2.2 [[Construct]]
When the [[Construct]] internal method for a Function object F is called with a possibly empty list of
arguments, the following steps are taken:
- Let obj be a newly created native ECMAScript object.
- Set all the internal methods of obj as specified in 8.12.
- Set the [[Class]] internal property of obj to
"Object"
.
- Set the [[Extensible]] internal property of obj to true.
- Let proto be the value of calling the [[Get]] internal property of F with argument
"prototype"
.
- If Type(proto) is Object, set the [[Prototype]] internal property of obj to
proto.
- If Type(proto) is not Object, set the [[Prototype]] internal property of obj to the
standard built-in Object prototype object as described in 15.2.4.
- Let result be the result of calling the [[Call]] internal property of F, providing obj as the
this value and providing the argument list passed into [[Construct]] as args.
- If Type(result) is Object then return result.
- Return obj.
13.2.3 The [[ThrowTypeError]]
Function Object
The [[ThrowTypeError]] object is a unique function object that is defined once as follows:
- Create a new native ECMAScript object and let F be that object.
- Set all the internal methods of F as described in 8.12.
- Set the [[Class]] internal property of F to
"Function"
.
- Set the [[Prototype]] internal property of F to the standard built-in Function prototype object as specified in
15.3.3.1.
- Set the [[Call]] internal property of F as described in 13.2.1.
- Set the [[Scope]] internal property of F to the Global Environment.
- Set the [[FormalParameters]] internal property of F to an empty List.
- Set the [[Code]] internal property of F to be a FunctionBody that unconditionally throws a
TypeError exception and performs no other action.
- Call the [[DefineOwnProperty]] internal method of F with arguments
"length"
, Property Descriptor {[[Value]]: 0, [[Writable]]: false, [[Enumerable]]:
false, [[Configurable]]: false}, and false.
- Set the [[Extensible]] internal property of F to false.
- Let [[ThrowTypeError]] be F.