diff options
author | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-04-07 19:33:14 +0000 |
---|---|---|
committer | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-04-07 19:33:14 +0000 |
commit | 36d22d82aa202bb199967e9512281e9a53db42c9 (patch) | |
tree | 105e8c98ddea1c1e4784a60a5a6410fa416be2de /js/src/tests/test262/annexB/language/function-code | |
parent | Initial commit. (diff) | |
download | firefox-esr-36d22d82aa202bb199967e9512281e9a53db42c9.tar.xz firefox-esr-36d22d82aa202bb199967e9512281e9a53db42c9.zip |
Adding upstream version 115.7.0esr.upstream/115.7.0esr
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'js/src/tests/test262/annexB/language/function-code')
161 files changed, 7277 insertions, 0 deletions
diff --git a/js/src/tests/test262/annexB/language/function-code/block-decl-func-block-scoping.js b/js/src/tests/test262/annexB/language/function-code/block-decl-func-block-scoping.js new file mode 100644 index 0000000000..6700dcec8d --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/block-decl-func-block-scoping.js @@ -0,0 +1,52 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-block-scoping.case +// - src/annex-b-fns/func/block.template +/*--- +description: A block-scoped binding is created (Block statement in function scope containing a function declaration) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + 13.2.14 Runtime Semantics: BlockDeclarationInstantiation + + [...] + 4. For each element d in declarations do + a. For each element dn of the BoundNames of d do + i. If IsConstantDeclaration of d is true, then + [...] + ii. Else, + 2. Perform ! envRec.CreateMutableBinding(dn, false). + + b. If d is a GeneratorDeclaration production or a FunctionDeclaration + production, then + i. Let fn be the sole element of the BoundNames of d. + ii. Let fo be the result of performing InstantiateFunctionObject for + d with argument env. + iii. Perform envRec.InitializeBinding(fn, fo). +---*/ +var initialBV, currentBV, varBinding; + +(function() { + + + { + function f() { initialBV = f; f = 123; currentBV = f; return 'decl'; } + } + + varBinding = f; + f(); +}()); + + +assert.sameValue( + initialBV(), + 'decl', + 'Block-scoped binding value is function object at execution time' +); +assert.sameValue(currentBV, 123, 'Block-scoped binding is mutable'); +assert.sameValue( + varBinding(), + 'decl', + 'Block-scoped binding is independent of outer var-scoped binding' +); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/block-decl-func-existing-block-fn-no-init.js b/js/src/tests/test262/annexB/language/function-code/block-decl-func-existing-block-fn-no-init.js new file mode 100644 index 0000000000..19c91c981a --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/block-decl-func-existing-block-fn-no-init.js @@ -0,0 +1,33 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-block-fn-no-init.case +// - src/annex-b-fns/func/block.template +/*--- +description: Does not re-initialize binding created by similar forms (Block statement in function scope containing a function declaration) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + [...] +---*/ +var init; + +(function() { + init = f; + + { + function f() {} + } + + { + function f() { } + } + + +}()); + +assert.sameValue(init, undefined); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/block-decl-func-existing-block-fn-update.js b/js/src/tests/test262/annexB/language/function-code/block-decl-func-existing-block-fn-update.js new file mode 100644 index 0000000000..4a090ca5a9 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/block-decl-func-existing-block-fn-update.js @@ -0,0 +1,42 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-block-fn-update.case +// - src/annex-b-fns/func/block.template +/*--- +description: Variable-scoped binding is updated (Block statement in function scope containing a function declaration) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var updated; + +(function() { + { + function f() { + return 'first declaration'; + } + } + + { + function f() { return 'second declaration'; } + } + + updated = f; +}()); + +assert.sameValue(typeof updated, 'function'); +assert.sameValue(updated(), 'second declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/block-decl-func-existing-fn-no-init.js b/js/src/tests/test262/annexB/language/function-code/block-decl-func-existing-fn-no-init.js new file mode 100644 index 0000000000..154d6d0cd4 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/block-decl-func-existing-fn-no-init.js @@ -0,0 +1,31 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-fn-no-init.case +// - src/annex-b-fns/func/block.template +/*--- +description: Existing variable binding is not modified (Block statement in function scope containing a function declaration) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + [...] +---*/ +var init; + +(function() { + init = f; + + { + function f() { return 'inner declaration'; } + } + + function f() { + return 'outer declaration'; + } +}()); + +assert.sameValue(init(), 'outer declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/block-decl-func-existing-fn-update.js b/js/src/tests/test262/annexB/language/function-code/block-decl-func-existing-fn-update.js new file mode 100644 index 0000000000..27b1ea9276 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/block-decl-func-existing-fn-update.js @@ -0,0 +1,42 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-fn-update.case +// - src/annex-b-fns/func/block.template +/*--- +description: Variable-scoped binding is updated following evaluation (Block statement in function scope containing a function declaration) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var after; + +(function() { + + + { + function f() { return 'inner declaration'; } + } + + after = f; + + function f() { + return 'outer declaration'; + } +}()); + +assert.sameValue(typeof after, 'function'); +assert.sameValue(after(), 'inner declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/block-decl-func-existing-var-no-init.js b/js/src/tests/test262/annexB/language/function-code/block-decl-func-existing-var-no-init.js new file mode 100644 index 0000000000..50547ff772 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/block-decl-func-existing-var-no-init.js @@ -0,0 +1,30 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-var-no-init.case +// - src/annex-b-fns/func/block.template +/*--- +description: Existing variable binding is not modified (Block statement in function scope containing a function declaration) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + [...] +---*/ +var init; + +(function() { + var f = 123; + init = f; + + { + function f() { } + } + + +}()); + +assert.sameValue(init, 123); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/block-decl-func-existing-var-update.js b/js/src/tests/test262/annexB/language/function-code/block-decl-func-existing-var-update.js new file mode 100644 index 0000000000..532e46b053 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/block-decl-func-existing-var-update.js @@ -0,0 +1,41 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-var-update.case +// - src/annex-b-fns/func/block.template +/*--- +description: Variable-scoped binding is updated following evaluation (Block statement in function scope containing a function declaration) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var after; + +(function() { + + + { + function f() { return 'function declaration'; } + } + + after = f; + + var f = 123; +}()); + +assert.sameValue(typeof after, 'function'); +assert.sameValue(after(), 'function declaration'); + + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/block-decl-func-init.js b/js/src/tests/test262/annexB/language/function-code/block-decl-func-init.js new file mode 100644 index 0000000000..ce86d2797b --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/block-decl-func-init.js @@ -0,0 +1,38 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-init.case +// - src/annex-b-fns/func/block.template +/*--- +description: Variable binding is initialized to `undefined` in outer scope (Block statement in function scope containing a function declaration) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + a. Perform ! varEnvRec.CreateMutableBinding(F, false). + b. Perform varEnvRec.InitializeBinding(F, undefined). + c. Append F to instantiatedVarNames. + [...] +---*/ +var init, changed; + +(function() { + init = f; + f = 123; + changed = f; + + { + function f() { } + } + + +}()); + +assert.sameValue(init, undefined, 'binding is initialized to `undefined`'); +assert.sameValue(changed, 123, 'binding is mutable'); +assert.throws(ReferenceError, function() { + f; +}, 'global binding is not created'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/block-decl-func-no-skip-try.js b/js/src/tests/test262/annexB/language/function-code/block-decl-func-no-skip-try.js new file mode 100644 index 0000000000..e0cf6d2e54 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/block-decl-func-no-skip-try.js @@ -0,0 +1,51 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-no-skip-try.case +// - src/annex-b-fns/func/block.template +/*--- +description: Extension is observed when creation of variable binding would not produce an early error (try statement) (Block statement in function scope containing a function declaration) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + a. Perform ! varEnvRec.CreateMutableBinding(F, false). + b. Perform varEnvRec.InitializeBinding(F, undefined). + c. Append F to instantiatedVarNames. + [...] + + B.3.5 VariableStatements in Catch Blocks + + [...] + - It is a Syntax Error if any element of the BoundNames of CatchParameter + also occurs in the VarDeclaredNames of Block unless CatchParameter is + CatchParameter:BindingIdentifier and that element is only bound by a + VariableStatement, the VariableDeclarationList of a for statement, or the + ForBinding of a for-in statement. +---*/ + +(function() { + assert.sameValue( + f, undefined, 'Initialized binding created prior to evaluation' + ); + + try { + throw null; + } catch (f) { + + { + function f() { return 123; } + } + + } + + assert.sameValue( + typeof f, + 'function', + 'binding value is updated following evaluation' + ); + assert.sameValue(f(), 123); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-arguments.js b/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-arguments.js new file mode 100644 index 0000000000..14772af5ff --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-arguments.js @@ -0,0 +1,59 @@ +// Copyright (C) 2017 the V8 project authors. All rights reserved. +// This code is governed by the BSD license found in the LICENSE file. + +/*--- +description: Functions named 'arguments' have legacy hoisting semantics +esid: sec-web-compat-functiondeclarationinstantiation +flags: [noStrict] +info: | + FunctionDeclarationInstantiation ( _func_, _argumentsList_ ) + + [...] + 7. Let _parameterNames_ be the BoundNames of _formals_. + [...] + 22. If argumentsObjectNeeded is true, then + f. Append "arguments" to parameterNames. + + Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the |FunctionDeclaration| _f_ with a |VariableStatement| that has _F_ + as a |BindingIdentifier| would not produce any Early Errors for _func_ and _F_ is + not an element of _parameterNames_, then + [...] +---*/ + +// Simple parameters +(function() { + assert.sameValue(arguments.toString(), "[object Arguments]"); + { + assert.sameValue(arguments(), undefined); + function arguments() {} + assert.sameValue(arguments(), undefined); + } + assert.sameValue(arguments.toString(), "[object Arguments]"); +}()); + +// Single named parameter +(function(x) { + assert.sameValue(arguments.toString(), "[object Arguments]"); + { + assert.sameValue(arguments(), undefined); + function arguments() {} + assert.sameValue(arguments(), undefined); + } + assert.sameValue(arguments.toString(), "[object Arguments]"); +}()); + +// Non-simple parameters +(function(..._) { + assert.sameValue(arguments.toString(), "[object Arguments]"); + { + assert.sameValue(arguments(), undefined); + function arguments() {} + assert.sameValue(arguments(), undefined); + } + assert.sameValue(arguments.toString(), "[object Arguments]"); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-dft-param.js b/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-dft-param.js new file mode 100644 index 0000000000..b6518043ca --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-dft-param.js @@ -0,0 +1,32 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-dft-param.case +// - src/annex-b-fns/func/block.template +/*--- +description: Extension not observed when there is a default parameter with the same name (Block statement in function scope containing a function declaration) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ +var init, after; + +(function(f = 123) { + init = f; + + { + function f() { } + } + + after = f; +}()); + +assert.sameValue(init, 123, 'binding is not initialized to `undefined`'); +assert.sameValue(after, 123, 'value is not updated following evaluation'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-early-err-block.js b/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-early-err-block.js new file mode 100644 index 0000000000..f97a906e23 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-early-err-block.js @@ -0,0 +1,47 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-block.case +// - src/annex-b-fns/func/block.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (Block statement) (Block statement in function scope containing a function declaration) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + { + let f = 123; + + { + function f() { } + } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-early-err-for-in.js b/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-early-err-for-in.js new file mode 100644 index 0000000000..aed0866402 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-early-err-for-in.js @@ -0,0 +1,46 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-for-in.case +// - src/annex-b-fns/func/block.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (for-of statement) (Block statement in function scope containing a function declaration) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + for (let f in { key: 0 }) { + + { + function f() { } + } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-early-err-for-of.js b/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-early-err-for-of.js new file mode 100644 index 0000000000..e715cb5204 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-early-err-for-of.js @@ -0,0 +1,46 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-for-of.case +// - src/annex-b-fns/func/block.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (for-of statement) (Block statement in function scope containing a function declaration) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + for (let f of [0]) { + + { + function f() { } + } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-early-err-for.js b/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-early-err-for.js new file mode 100644 index 0000000000..9a85550de4 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-early-err-for.js @@ -0,0 +1,47 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-for.case +// - src/annex-b-fns/func/block.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (for statement) (Block statement in function scope containing a function declaration) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + for (let f; ; ) { + + { + function f() { } + } + + break; + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-early-err-switch.js b/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-early-err-switch.js new file mode 100644 index 0000000000..cdd96eb131 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-early-err-switch.js @@ -0,0 +1,48 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-switch.case +// - src/annex-b-fns/func/block.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (switch statement) (Block statement in function scope containing a function declaration) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + switch (0) { + default: + let f; + + { + function f() { } + } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-early-err-try.js b/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-early-err-try.js new file mode 100644 index 0000000000..7acfcdcd79 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-early-err-try.js @@ -0,0 +1,58 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-try.case +// - src/annex-b-fns/func/block.template +/*--- +description: Extension is observed when creation of variable binding would not produce an early error (try statement) (Block statement in function scope containing a function declaration) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + a. Perform ! varEnvRec.CreateMutableBinding(F, false). + b. Perform varEnvRec.InitializeBinding(F, undefined). + c. Append F to instantiatedVarNames. + [...] + + B.3.5 VariableStatements in Catch Blocks + + [...] + - It is a Syntax Error if any element of the BoundNames of CatchParameter + also occurs in the VarDeclaredNames of Block unless CatchParameter is + CatchParameter:BindingIdentifier and that element is only bound by a + VariableStatement, the VariableDeclarationList of a for statement, or the + ForBinding of a for-in statement. +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + try { + throw {}; + } catch ({ f }) { + + { + function f() { } + } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-early-err.js b/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-early-err.js new file mode 100644 index 0000000000..28b12bc208 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-early-err.js @@ -0,0 +1,33 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err.case +// - src/annex-b-fns/func/block.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (Block statement in function scope containing a function declaration) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ +var init, after; + +(function() { + let f = 123; + init = f; + + { + function f() { } + } + + after = f; +}()); + +assert.sameValue(init, 123, 'binding is not initialized to `undefined`'); +assert.sameValue(after, 123, 'value is not updated following evaluation'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-param.js b/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-param.js new file mode 100644 index 0000000000..db5ac4fbab --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/block-decl-func-skip-param.js @@ -0,0 +1,32 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-param.case +// - src/annex-b-fns/func/block.template +/*--- +description: Extension not observed when there is a formal parameter with the same name (Block statement in function scope containing a function declaration) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ +var init, after; + +(function(f) { + init = f; + + { + function f() { } + } + + after = f; +}(123)); + +assert.sameValue(init, 123, 'binding is not initialized to `undefined`'); +assert.sameValue(after, 123, 'value is not updated following evaluation'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/block-decl-func-update.js b/js/src/tests/test262/annexB/language/function-code/block-decl-func-update.js new file mode 100644 index 0000000000..9b621f3e09 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/block-decl-func-update.js @@ -0,0 +1,38 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-update.case +// - src/annex-b-fns/func/block.template +/*--- +description: Variable binding value is updated following evaluation (Block statement in function scope containing a function declaration) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var after; + +(function() { + + + { + function f() { return 'declaration'; } + } + + after = f; +}()); + +assert.sameValue(typeof after, 'function'); +assert.sameValue(after(), 'declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/block-decl-nested-blocks-with-fun-decl.js b/js/src/tests/test262/annexB/language/function-code/block-decl-nested-blocks-with-fun-decl.js new file mode 100644 index 0000000000..c7e85de89a --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/block-decl-nested-blocks-with-fun-decl.js @@ -0,0 +1,42 @@ +// Copyright (C) 2018 André Bargull. All rights reserved. +// This code is governed by the BSD license found in the LICENSE file. + +/*--- +esid: sec-web-compat-functiondeclarationinstantiation +description: > + Nested function declarations, the second declaration is not Annex-B applicable. +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + 1. If strict is false, then + a. For each FunctionDeclaration f that is directly contained in the + StatementList of a Block, CaseClause, or DefaultClause, do + i. Let F be StringValue of the BindingIdentifier of FunctionDeclaration f. + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of parameterNames, then + ... +flags: [noStrict] +---*/ + +function g() { + // Create an outer block-statement. + { + // A lexically declared function declaration. + // This function is applicable for Annex-B semantics. + function f() { return 1; } + + // An inner block-statement with another function declaration. + // This function is not applicable for Annex-B semantics, because + // replacing it with |var f| would result in a SyntaxError. + { + function f() { return 2; } + } + } + + assert.sameValue(f(), 1); +} + +g(); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/block-decl-nostrict.js b/js/src/tests/test262/annexB/language/function-code/block-decl-nostrict.js new file mode 100644 index 0000000000..6c4a289682 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/block-decl-nostrict.js @@ -0,0 +1,40 @@ +// Copyright (C) 2016 the V8 project authors. All rights reserved. +// This code is governed by the BSD license found in the LICENSE file. +/*--- +esid: sec-web-compat-functiondeclarationinstantiation +description: > + AnnexB extension not honored in strict mode, Block statement + in function code containing a function declaration +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + 1. If strict is false, then + ... + +flags: [noStrict] +---*/ + +var err1, err2; + +(function() { + try { + f; + } catch (exception) { + err1 = exception; + } + + { + function f() { } + } + + try { + f; + } catch (exception) { + err2 = exception; + } +}()); + +assert.sameValue(err1, undefined); +assert.sameValue(err2, undefined); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/browser.js b/js/src/tests/test262/annexB/language/function-code/browser.js new file mode 100644 index 0000000000..e69de29bb2 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/browser.js diff --git a/js/src/tests/test262/annexB/language/function-code/function-redeclaration-block.js b/js/src/tests/test262/annexB/language/function-code/function-redeclaration-block.js new file mode 100644 index 0000000000..1e3a163cd3 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/function-redeclaration-block.js @@ -0,0 +1,20 @@ +// Copyright (C) 2019 Adrian Heine. All rights reserved. +// This code is governed by the BSD license found in the LICENSE file. +/*--- +description: In non-strict mode, duplicate LexicallyDeclaredNames in a block are allowed if they are bound by FunctionDeclarations +esid: sec-block-duplicates-allowed-static-semantics +es6id: B.3.3.4 +flags: [noStrict] +info: | + B.3.3.4 Changes to Block Static Semantics: Early Errors + + For web browser compatibility, that rule is modified with the addition of the **highlighted** text: + + Block: {StatementList} + + It is a Syntax Error if the LexicallyDeclaredNames of StatementList contains any duplicate entries, **unless the source code matching this production is not strict mode code and the duplicate entries are only bound by FunctionDeclarations**. +---*/ + +{ function a() {} function a() {} } + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/function-redeclaration-switch.js b/js/src/tests/test262/annexB/language/function-code/function-redeclaration-switch.js new file mode 100644 index 0000000000..2c03663358 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/function-redeclaration-switch.js @@ -0,0 +1,35 @@ +// Copyright (C) 2019 Adrian Heine. All rights reserved. +// This code is governed by the BSD license found in the LICENSE file. +/*--- +description: In non-strict mode, duplicate LexicallyDeclaredNames in a switch statement's CaseBlock are allowed if they are bound by FunctionDeclarations +esid: sec-switch-duplicates-allowed-static-semantics +es6id: B.3.3.5 +flags: [noStrict] +info: | + B.3.3.4 Changes to Block Static Semantics: Early Errors + + For web browser compatibility, that rule is modified with the addition of the **highlighted** text: + + Block: {StatementList} + + It is a Syntax Error if the LexicallyDeclaredNames of StatementList contains any duplicate entries, **unless the source code matching this production is not strict mode code and the duplicate entries are only bound by FunctionDeclarations**. + + + B.3.3.5 Changes to switch Statement Static Semantics: Early Errors + + For web browser compatibility, that rule is modified with the addition of the **highlighted** text: + + SwitchStatement: switch ( Expression ) CaseBlock + + It is a Syntax Error if the LexicallyDeclaredNames of CaseBlock contains any duplicate entries, **unless the source code matching this production is not strict mode code and the duplicate entries are only bound by FunctionDeclarations**. +---*/ + +let x +switch (x) { +case 1: + function a() {} +case 2: + function a() {} +} + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-block-scoping.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-block-scoping.js new file mode 100644 index 0000000000..298013f304 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-block-scoping.js @@ -0,0 +1,59 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-block-scoping.case +// - src/annex-b-fns/func/if-decl-else-decl-a.template +/*--- +description: A block-scoped binding is created (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + 13.2.14 Runtime Semantics: BlockDeclarationInstantiation + + [...] + 4. For each element d in declarations do + a. For each element dn of the BoundNames of d do + i. If IsConstantDeclaration of d is true, then + [...] + ii. Else, + 2. Perform ! envRec.CreateMutableBinding(dn, false). + + b. If d is a GeneratorDeclaration production or a FunctionDeclaration + production, then + i. Let fn be the sole element of the BoundNames of d. + ii. Let fo be the result of performing InstantiateFunctionObject for + d with argument env. + iii. Perform envRec.InitializeBinding(fn, fo). +---*/ +var initialBV, currentBV, varBinding; + +(function() { + + + if (true) function f() { initialBV = f; f = 123; currentBV = f; return 'decl'; } else function _f() {} + + varBinding = f; + f(); +}()); + + +assert.sameValue( + initialBV(), + 'decl', + 'Block-scoped binding value is function object at execution time' +); +assert.sameValue(currentBV, 123, 'Block-scoped binding is mutable'); +assert.sameValue( + varBinding(), + 'decl', + 'Block-scoped binding is independent of outer var-scoped binding' +); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-existing-block-fn-no-init.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-existing-block-fn-no-init.js new file mode 100644 index 0000000000..351f7cde4b --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-existing-block-fn-no-init.js @@ -0,0 +1,40 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-block-fn-no-init.case +// - src/annex-b-fns/func/if-decl-else-decl-a.template +/*--- +description: Does not re-initialize binding created by similar forms (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + [...] +---*/ +var init; + +(function() { + init = f; + + { + function f() {} + } + + if (true) function f() { } else function _f() {} + + +}()); + +assert.sameValue(init, undefined); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-existing-block-fn-update.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-existing-block-fn-update.js new file mode 100644 index 0000000000..9de2d7e5d5 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-existing-block-fn-update.js @@ -0,0 +1,49 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-block-fn-update.case +// - src/annex-b-fns/func/if-decl-else-decl-a.template +/*--- +description: Variable-scoped binding is updated (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var updated; + +(function() { + { + function f() { + return 'first declaration'; + } + } + + if (true) function f() { return 'second declaration'; } else function _f() {} + + updated = f; +}()); + +assert.sameValue(typeof updated, 'function'); +assert.sameValue(updated(), 'second declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-existing-fn-no-init.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-existing-fn-no-init.js new file mode 100644 index 0000000000..5974dc3858 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-existing-fn-no-init.js @@ -0,0 +1,38 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-fn-no-init.case +// - src/annex-b-fns/func/if-decl-else-decl-a.template +/*--- +description: Existing variable binding is not modified (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + [...] +---*/ +var init; + +(function() { + init = f; + + if (true) function f() { return 'inner declaration'; } else function _f() {} + + function f() { + return 'outer declaration'; + } +}()); + +assert.sameValue(init(), 'outer declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-existing-fn-update.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-existing-fn-update.js new file mode 100644 index 0000000000..a15ad9f4f1 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-existing-fn-update.js @@ -0,0 +1,49 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-fn-update.case +// - src/annex-b-fns/func/if-decl-else-decl-a.template +/*--- +description: Variable-scoped binding is updated following evaluation (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var after; + +(function() { + + + if (true) function f() { return 'inner declaration'; } else function _f() {} + + after = f; + + function f() { + return 'outer declaration'; + } +}()); + +assert.sameValue(typeof after, 'function'); +assert.sameValue(after(), 'inner declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-existing-var-no-init.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-existing-var-no-init.js new file mode 100644 index 0000000000..53ad53abf9 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-existing-var-no-init.js @@ -0,0 +1,37 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-var-no-init.case +// - src/annex-b-fns/func/if-decl-else-decl-a.template +/*--- +description: Existing variable binding is not modified (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + [...] +---*/ +var init; + +(function() { + var f = 123; + init = f; + + if (true) function f() { } else function _f() {} + + +}()); + +assert.sameValue(init, 123); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-existing-var-update.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-existing-var-update.js new file mode 100644 index 0000000000..40541fdc07 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-existing-var-update.js @@ -0,0 +1,48 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-var-update.case +// - src/annex-b-fns/func/if-decl-else-decl-a.template +/*--- +description: Variable-scoped binding is updated following evaluation (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var after; + +(function() { + + + if (true) function f() { return 'function declaration'; } else function _f() {} + + after = f; + + var f = 123; +}()); + +assert.sameValue(typeof after, 'function'); +assert.sameValue(after(), 'function declaration'); + + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-init.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-init.js new file mode 100644 index 0000000000..18f1176553 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-init.js @@ -0,0 +1,45 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-init.case +// - src/annex-b-fns/func/if-decl-else-decl-a.template +/*--- +description: Variable binding is initialized to `undefined` in outer scope (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + a. Perform ! varEnvRec.CreateMutableBinding(F, false). + b. Perform varEnvRec.InitializeBinding(F, undefined). + c. Append F to instantiatedVarNames. + [...] +---*/ +var init, changed; + +(function() { + init = f; + f = 123; + changed = f; + + if (true) function f() { } else function _f() {} + + +}()); + +assert.sameValue(init, undefined, 'binding is initialized to `undefined`'); +assert.sameValue(changed, 123, 'binding is mutable'); +assert.throws(ReferenceError, function() { + f; +}, 'global binding is not created'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-no-skip-try.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-no-skip-try.js new file mode 100644 index 0000000000..7d22f11253 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-no-skip-try.js @@ -0,0 +1,58 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-no-skip-try.case +// - src/annex-b-fns/func/if-decl-else-decl-a.template +/*--- +description: Extension is observed when creation of variable binding would not produce an early error (try statement) (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + a. Perform ! varEnvRec.CreateMutableBinding(F, false). + b. Perform varEnvRec.InitializeBinding(F, undefined). + c. Append F to instantiatedVarNames. + [...] + + B.3.5 VariableStatements in Catch Blocks + + [...] + - It is a Syntax Error if any element of the BoundNames of CatchParameter + also occurs in the VarDeclaredNames of Block unless CatchParameter is + CatchParameter:BindingIdentifier and that element is only bound by a + VariableStatement, the VariableDeclarationList of a for statement, or the + ForBinding of a for-in statement. +---*/ + +(function() { + assert.sameValue( + f, undefined, 'Initialized binding created prior to evaluation' + ); + + try { + throw null; + } catch (f) { + + if (true) function f() { return 123; } else function _f() {} + + } + + assert.sameValue( + typeof f, + 'function', + 'binding value is updated following evaluation' + ); + assert.sameValue(f(), 123); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-skip-dft-param.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-skip-dft-param.js new file mode 100644 index 0000000000..8c3bc7ebb7 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-skip-dft-param.js @@ -0,0 +1,39 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-dft-param.case +// - src/annex-b-fns/func/if-decl-else-decl-a.template +/*--- +description: Extension not observed when there is a default parameter with the same name (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ +var init, after; + +(function(f = 123) { + init = f; + + if (true) function f() { } else function _f() {} + + after = f; +}()); + +assert.sameValue(init, 123, 'binding is not initialized to `undefined`'); +assert.sameValue(after, 123, 'value is not updated following evaluation'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-skip-early-err-block.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-skip-early-err-block.js new file mode 100644 index 0000000000..b5b0aefa84 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-skip-early-err-block.js @@ -0,0 +1,54 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-block.case +// - src/annex-b-fns/func/if-decl-else-decl-a.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (Block statement) (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + { + let f = 123; + + if (true) function f() { } else function _f() {} + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-skip-early-err-for-in.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-skip-early-err-for-in.js new file mode 100644 index 0000000000..5772f7b450 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-skip-early-err-for-in.js @@ -0,0 +1,53 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-for-in.case +// - src/annex-b-fns/func/if-decl-else-decl-a.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (for-of statement) (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + for (let f in { key: 0 }) { + + if (true) function f() { } else function _f() {} + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-skip-early-err-for-of.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-skip-early-err-for-of.js new file mode 100644 index 0000000000..659b967860 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-skip-early-err-for-of.js @@ -0,0 +1,53 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-for-of.case +// - src/annex-b-fns/func/if-decl-else-decl-a.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (for-of statement) (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + for (let f of [0]) { + + if (true) function f() { } else function _f() {} + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-skip-early-err-for.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-skip-early-err-for.js new file mode 100644 index 0000000000..0b196cdbd6 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-skip-early-err-for.js @@ -0,0 +1,54 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-for.case +// - src/annex-b-fns/func/if-decl-else-decl-a.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (for statement) (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + for (let f; ; ) { + + if (true) function f() { } else function _f() {} + + break; + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-skip-early-err-switch.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-skip-early-err-switch.js new file mode 100644 index 0000000000..8a1ac1fb56 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-skip-early-err-switch.js @@ -0,0 +1,55 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-switch.case +// - src/annex-b-fns/func/if-decl-else-decl-a.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (switch statement) (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + switch (0) { + default: + let f; + + if (true) function f() { } else function _f() {} + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-skip-early-err-try.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-skip-early-err-try.js new file mode 100644 index 0000000000..1c72b31349 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-skip-early-err-try.js @@ -0,0 +1,65 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-try.case +// - src/annex-b-fns/func/if-decl-else-decl-a.template +/*--- +description: Extension is observed when creation of variable binding would not produce an early error (try statement) (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + a. Perform ! varEnvRec.CreateMutableBinding(F, false). + b. Perform varEnvRec.InitializeBinding(F, undefined). + c. Append F to instantiatedVarNames. + [...] + + B.3.5 VariableStatements in Catch Blocks + + [...] + - It is a Syntax Error if any element of the BoundNames of CatchParameter + also occurs in the VarDeclaredNames of Block unless CatchParameter is + CatchParameter:BindingIdentifier and that element is only bound by a + VariableStatement, the VariableDeclarationList of a for statement, or the + ForBinding of a for-in statement. +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + try { + throw {}; + } catch ({ f }) { + + if (true) function f() { } else function _f() {} + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-skip-early-err.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-skip-early-err.js new file mode 100644 index 0000000000..54639c774f --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-skip-early-err.js @@ -0,0 +1,40 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err.case +// - src/annex-b-fns/func/if-decl-else-decl-a.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ +var init, after; + +(function() { + let f = 123; + init = f; + + if (true) function f() { } else function _f() {} + + after = f; +}()); + +assert.sameValue(init, 123, 'binding is not initialized to `undefined`'); +assert.sameValue(after, 123, 'value is not updated following evaluation'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-skip-param.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-skip-param.js new file mode 100644 index 0000000000..10be89c4bf --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-skip-param.js @@ -0,0 +1,39 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-param.case +// - src/annex-b-fns/func/if-decl-else-decl-a.template +/*--- +description: Extension not observed when there is a formal parameter with the same name (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ +var init, after; + +(function(f) { + init = f; + + if (true) function f() { } else function _f() {} + + after = f; +}(123)); + +assert.sameValue(init, 123, 'binding is not initialized to `undefined`'); +assert.sameValue(after, 123, 'value is not updated following evaluation'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-update.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-update.js new file mode 100644 index 0000000000..2196f3670d --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-a-func-update.js @@ -0,0 +1,45 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-update.case +// - src/annex-b-fns/func/if-decl-else-decl-a.template +/*--- +description: Variable binding value is updated following evaluation (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var after; + +(function() { + + + if (true) function f() { return 'declaration'; } else function _f() {} + + after = f; +}()); + +assert.sameValue(typeof after, 'function'); +assert.sameValue(after(), 'declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-block-scoping.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-block-scoping.js new file mode 100644 index 0000000000..479cef98b6 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-block-scoping.js @@ -0,0 +1,59 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-block-scoping.case +// - src/annex-b-fns/func/if-decl-else-decl-b.template +/*--- +description: A block-scoped binding is created (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + 13.2.14 Runtime Semantics: BlockDeclarationInstantiation + + [...] + 4. For each element d in declarations do + a. For each element dn of the BoundNames of d do + i. If IsConstantDeclaration of d is true, then + [...] + ii. Else, + 2. Perform ! envRec.CreateMutableBinding(dn, false). + + b. If d is a GeneratorDeclaration production or a FunctionDeclaration + production, then + i. Let fn be the sole element of the BoundNames of d. + ii. Let fo be the result of performing InstantiateFunctionObject for + d with argument env. + iii. Perform envRec.InitializeBinding(fn, fo). +---*/ +var initialBV, currentBV, varBinding; + +(function() { + + + if (false) function _f() {} else function f() { initialBV = f; f = 123; currentBV = f; return 'decl'; } + + varBinding = f; + f(); +}()); + + +assert.sameValue( + initialBV(), + 'decl', + 'Block-scoped binding value is function object at execution time' +); +assert.sameValue(currentBV, 123, 'Block-scoped binding is mutable'); +assert.sameValue( + varBinding(), + 'decl', + 'Block-scoped binding is independent of outer var-scoped binding' +); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-existing-block-fn-no-init.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-existing-block-fn-no-init.js new file mode 100644 index 0000000000..1dfd9399c1 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-existing-block-fn-no-init.js @@ -0,0 +1,40 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-block-fn-no-init.case +// - src/annex-b-fns/func/if-decl-else-decl-b.template +/*--- +description: Does not re-initialize binding created by similar forms (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + [...] +---*/ +var init; + +(function() { + init = f; + + { + function f() {} + } + + if (false) function _f() {} else function f() { } + + +}()); + +assert.sameValue(init, undefined); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-existing-block-fn-update.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-existing-block-fn-update.js new file mode 100644 index 0000000000..720594506b --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-existing-block-fn-update.js @@ -0,0 +1,49 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-block-fn-update.case +// - src/annex-b-fns/func/if-decl-else-decl-b.template +/*--- +description: Variable-scoped binding is updated (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var updated; + +(function() { + { + function f() { + return 'first declaration'; + } + } + + if (false) function _f() {} else function f() { return 'second declaration'; } + + updated = f; +}()); + +assert.sameValue(typeof updated, 'function'); +assert.sameValue(updated(), 'second declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-existing-fn-no-init.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-existing-fn-no-init.js new file mode 100644 index 0000000000..1f4137a1e2 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-existing-fn-no-init.js @@ -0,0 +1,38 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-fn-no-init.case +// - src/annex-b-fns/func/if-decl-else-decl-b.template +/*--- +description: Existing variable binding is not modified (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + [...] +---*/ +var init; + +(function() { + init = f; + + if (false) function _f() {} else function f() { return 'inner declaration'; } + + function f() { + return 'outer declaration'; + } +}()); + +assert.sameValue(init(), 'outer declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-existing-fn-update.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-existing-fn-update.js new file mode 100644 index 0000000000..5bd63bde74 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-existing-fn-update.js @@ -0,0 +1,49 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-fn-update.case +// - src/annex-b-fns/func/if-decl-else-decl-b.template +/*--- +description: Variable-scoped binding is updated following evaluation (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var after; + +(function() { + + + if (false) function _f() {} else function f() { return 'inner declaration'; } + + after = f; + + function f() { + return 'outer declaration'; + } +}()); + +assert.sameValue(typeof after, 'function'); +assert.sameValue(after(), 'inner declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-existing-var-no-init.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-existing-var-no-init.js new file mode 100644 index 0000000000..48a39bf46d --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-existing-var-no-init.js @@ -0,0 +1,37 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-var-no-init.case +// - src/annex-b-fns/func/if-decl-else-decl-b.template +/*--- +description: Existing variable binding is not modified (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + [...] +---*/ +var init; + +(function() { + var f = 123; + init = f; + + if (false) function _f() {} else function f() { } + + +}()); + +assert.sameValue(init, 123); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-existing-var-update.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-existing-var-update.js new file mode 100644 index 0000000000..6a33e16a67 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-existing-var-update.js @@ -0,0 +1,48 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-var-update.case +// - src/annex-b-fns/func/if-decl-else-decl-b.template +/*--- +description: Variable-scoped binding is updated following evaluation (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var after; + +(function() { + + + if (false) function _f() {} else function f() { return 'function declaration'; } + + after = f; + + var f = 123; +}()); + +assert.sameValue(typeof after, 'function'); +assert.sameValue(after(), 'function declaration'); + + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-init.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-init.js new file mode 100644 index 0000000000..d1b30c8891 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-init.js @@ -0,0 +1,45 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-init.case +// - src/annex-b-fns/func/if-decl-else-decl-b.template +/*--- +description: Variable binding is initialized to `undefined` in outer scope (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + a. Perform ! varEnvRec.CreateMutableBinding(F, false). + b. Perform varEnvRec.InitializeBinding(F, undefined). + c. Append F to instantiatedVarNames. + [...] +---*/ +var init, changed; + +(function() { + init = f; + f = 123; + changed = f; + + if (false) function _f() {} else function f() { } + + +}()); + +assert.sameValue(init, undefined, 'binding is initialized to `undefined`'); +assert.sameValue(changed, 123, 'binding is mutable'); +assert.throws(ReferenceError, function() { + f; +}, 'global binding is not created'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-no-skip-try.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-no-skip-try.js new file mode 100644 index 0000000000..4e2237f997 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-no-skip-try.js @@ -0,0 +1,58 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-no-skip-try.case +// - src/annex-b-fns/func/if-decl-else-decl-b.template +/*--- +description: Extension is observed when creation of variable binding would not produce an early error (try statement) (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + a. Perform ! varEnvRec.CreateMutableBinding(F, false). + b. Perform varEnvRec.InitializeBinding(F, undefined). + c. Append F to instantiatedVarNames. + [...] + + B.3.5 VariableStatements in Catch Blocks + + [...] + - It is a Syntax Error if any element of the BoundNames of CatchParameter + also occurs in the VarDeclaredNames of Block unless CatchParameter is + CatchParameter:BindingIdentifier and that element is only bound by a + VariableStatement, the VariableDeclarationList of a for statement, or the + ForBinding of a for-in statement. +---*/ + +(function() { + assert.sameValue( + f, undefined, 'Initialized binding created prior to evaluation' + ); + + try { + throw null; + } catch (f) { + + if (false) function _f() {} else function f() { return 123; } + + } + + assert.sameValue( + typeof f, + 'function', + 'binding value is updated following evaluation' + ); + assert.sameValue(f(), 123); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-skip-dft-param.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-skip-dft-param.js new file mode 100644 index 0000000000..9a9b036e02 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-skip-dft-param.js @@ -0,0 +1,39 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-dft-param.case +// - src/annex-b-fns/func/if-decl-else-decl-b.template +/*--- +description: Extension not observed when there is a default parameter with the same name (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ +var init, after; + +(function(f = 123) { + init = f; + + if (false) function _f() {} else function f() { } + + after = f; +}()); + +assert.sameValue(init, 123, 'binding is not initialized to `undefined`'); +assert.sameValue(after, 123, 'value is not updated following evaluation'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-skip-early-err-block.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-skip-early-err-block.js new file mode 100644 index 0000000000..27323b1de3 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-skip-early-err-block.js @@ -0,0 +1,54 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-block.case +// - src/annex-b-fns/func/if-decl-else-decl-b.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (Block statement) (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + { + let f = 123; + + if (false) function _f() {} else function f() { } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-skip-early-err-for-in.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-skip-early-err-for-in.js new file mode 100644 index 0000000000..f9f4bf4e0c --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-skip-early-err-for-in.js @@ -0,0 +1,53 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-for-in.case +// - src/annex-b-fns/func/if-decl-else-decl-b.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (for-of statement) (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + for (let f in { key: 0 }) { + + if (false) function _f() {} else function f() { } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-skip-early-err-for-of.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-skip-early-err-for-of.js new file mode 100644 index 0000000000..de6f1953c0 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-skip-early-err-for-of.js @@ -0,0 +1,53 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-for-of.case +// - src/annex-b-fns/func/if-decl-else-decl-b.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (for-of statement) (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + for (let f of [0]) { + + if (false) function _f() {} else function f() { } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-skip-early-err-for.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-skip-early-err-for.js new file mode 100644 index 0000000000..7808944a3e --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-skip-early-err-for.js @@ -0,0 +1,54 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-for.case +// - src/annex-b-fns/func/if-decl-else-decl-b.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (for statement) (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + for (let f; ; ) { + + if (false) function _f() {} else function f() { } + + break; + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-skip-early-err-switch.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-skip-early-err-switch.js new file mode 100644 index 0000000000..b1c502a663 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-skip-early-err-switch.js @@ -0,0 +1,55 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-switch.case +// - src/annex-b-fns/func/if-decl-else-decl-b.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (switch statement) (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + switch (0) { + default: + let f; + + if (false) function _f() {} else function f() { } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-skip-early-err-try.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-skip-early-err-try.js new file mode 100644 index 0000000000..2a72aeb9ba --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-skip-early-err-try.js @@ -0,0 +1,65 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-try.case +// - src/annex-b-fns/func/if-decl-else-decl-b.template +/*--- +description: Extension is observed when creation of variable binding would not produce an early error (try statement) (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + a. Perform ! varEnvRec.CreateMutableBinding(F, false). + b. Perform varEnvRec.InitializeBinding(F, undefined). + c. Append F to instantiatedVarNames. + [...] + + B.3.5 VariableStatements in Catch Blocks + + [...] + - It is a Syntax Error if any element of the BoundNames of CatchParameter + also occurs in the VarDeclaredNames of Block unless CatchParameter is + CatchParameter:BindingIdentifier and that element is only bound by a + VariableStatement, the VariableDeclarationList of a for statement, or the + ForBinding of a for-in statement. +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + try { + throw {}; + } catch ({ f }) { + + if (false) function _f() {} else function f() { } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-skip-early-err.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-skip-early-err.js new file mode 100644 index 0000000000..e3c1a40a12 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-skip-early-err.js @@ -0,0 +1,40 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err.case +// - src/annex-b-fns/func/if-decl-else-decl-b.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ +var init, after; + +(function() { + let f = 123; + init = f; + + if (false) function _f() {} else function f() { } + + after = f; +}()); + +assert.sameValue(init, 123, 'binding is not initialized to `undefined`'); +assert.sameValue(after, 123, 'value is not updated following evaluation'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-skip-param.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-skip-param.js new file mode 100644 index 0000000000..8d4f4e1ebf --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-skip-param.js @@ -0,0 +1,39 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-param.case +// - src/annex-b-fns/func/if-decl-else-decl-b.template +/*--- +description: Extension not observed when there is a formal parameter with the same name (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ +var init, after; + +(function(f) { + init = f; + + if (false) function _f() {} else function f() { } + + after = f; +}(123)); + +assert.sameValue(init, 123, 'binding is not initialized to `undefined`'); +assert.sameValue(after, 123, 'value is not updated following evaluation'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-update.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-update.js new file mode 100644 index 0000000000..ddb511d8d4 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-decl-b-func-update.js @@ -0,0 +1,45 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-update.case +// - src/annex-b-fns/func/if-decl-else-decl-b.template +/*--- +description: Variable binding value is updated following evaluation (IfStatement with a declaration in both statement positions in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var after; + +(function() { + + + if (false) function _f() {} else function f() { return 'declaration'; } + + after = f; +}()); + +assert.sameValue(typeof after, 'function'); +assert.sameValue(after(), 'declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-block-scoping.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-block-scoping.js new file mode 100644 index 0000000000..1a0b2460a3 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-block-scoping.js @@ -0,0 +1,59 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-block-scoping.case +// - src/annex-b-fns/func/if-decl-else-stmt.template +/*--- +description: A block-scoped binding is created (IfStatement with a declaration in the first statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + 13.2.14 Runtime Semantics: BlockDeclarationInstantiation + + [...] + 4. For each element d in declarations do + a. For each element dn of the BoundNames of d do + i. If IsConstantDeclaration of d is true, then + [...] + ii. Else, + 2. Perform ! envRec.CreateMutableBinding(dn, false). + + b. If d is a GeneratorDeclaration production or a FunctionDeclaration + production, then + i. Let fn be the sole element of the BoundNames of d. + ii. Let fo be the result of performing InstantiateFunctionObject for + d with argument env. + iii. Perform envRec.InitializeBinding(fn, fo). +---*/ +var initialBV, currentBV, varBinding; + +(function() { + + + if (true) function f() { initialBV = f; f = 123; currentBV = f; return 'decl'; } else ; + + varBinding = f; + f(); +}()); + + +assert.sameValue( + initialBV(), + 'decl', + 'Block-scoped binding value is function object at execution time' +); +assert.sameValue(currentBV, 123, 'Block-scoped binding is mutable'); +assert.sameValue( + varBinding(), + 'decl', + 'Block-scoped binding is independent of outer var-scoped binding' +); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-existing-block-fn-no-init.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-existing-block-fn-no-init.js new file mode 100644 index 0000000000..b74fbff156 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-existing-block-fn-no-init.js @@ -0,0 +1,40 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-block-fn-no-init.case +// - src/annex-b-fns/func/if-decl-else-stmt.template +/*--- +description: Does not re-initialize binding created by similar forms (IfStatement with a declaration in the first statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + [...] +---*/ +var init; + +(function() { + init = f; + + { + function f() {} + } + + if (true) function f() { } else ; + + +}()); + +assert.sameValue(init, undefined); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-existing-block-fn-update.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-existing-block-fn-update.js new file mode 100644 index 0000000000..8d9a65d180 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-existing-block-fn-update.js @@ -0,0 +1,49 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-block-fn-update.case +// - src/annex-b-fns/func/if-decl-else-stmt.template +/*--- +description: Variable-scoped binding is updated (IfStatement with a declaration in the first statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var updated; + +(function() { + { + function f() { + return 'first declaration'; + } + } + + if (true) function f() { return 'second declaration'; } else ; + + updated = f; +}()); + +assert.sameValue(typeof updated, 'function'); +assert.sameValue(updated(), 'second declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-existing-fn-no-init.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-existing-fn-no-init.js new file mode 100644 index 0000000000..b4d745aa51 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-existing-fn-no-init.js @@ -0,0 +1,38 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-fn-no-init.case +// - src/annex-b-fns/func/if-decl-else-stmt.template +/*--- +description: Existing variable binding is not modified (IfStatement with a declaration in the first statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + [...] +---*/ +var init; + +(function() { + init = f; + + if (true) function f() { return 'inner declaration'; } else ; + + function f() { + return 'outer declaration'; + } +}()); + +assert.sameValue(init(), 'outer declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-existing-fn-update.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-existing-fn-update.js new file mode 100644 index 0000000000..f95dae5053 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-existing-fn-update.js @@ -0,0 +1,49 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-fn-update.case +// - src/annex-b-fns/func/if-decl-else-stmt.template +/*--- +description: Variable-scoped binding is updated following evaluation (IfStatement with a declaration in the first statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var after; + +(function() { + + + if (true) function f() { return 'inner declaration'; } else ; + + after = f; + + function f() { + return 'outer declaration'; + } +}()); + +assert.sameValue(typeof after, 'function'); +assert.sameValue(after(), 'inner declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-existing-var-no-init.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-existing-var-no-init.js new file mode 100644 index 0000000000..61dedaada8 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-existing-var-no-init.js @@ -0,0 +1,37 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-var-no-init.case +// - src/annex-b-fns/func/if-decl-else-stmt.template +/*--- +description: Existing variable binding is not modified (IfStatement with a declaration in the first statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + [...] +---*/ +var init; + +(function() { + var f = 123; + init = f; + + if (true) function f() { } else ; + + +}()); + +assert.sameValue(init, 123); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-existing-var-update.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-existing-var-update.js new file mode 100644 index 0000000000..296e77ea3c --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-existing-var-update.js @@ -0,0 +1,48 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-var-update.case +// - src/annex-b-fns/func/if-decl-else-stmt.template +/*--- +description: Variable-scoped binding is updated following evaluation (IfStatement with a declaration in the first statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var after; + +(function() { + + + if (true) function f() { return 'function declaration'; } else ; + + after = f; + + var f = 123; +}()); + +assert.sameValue(typeof after, 'function'); +assert.sameValue(after(), 'function declaration'); + + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-init.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-init.js new file mode 100644 index 0000000000..21bb3ff317 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-init.js @@ -0,0 +1,45 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-init.case +// - src/annex-b-fns/func/if-decl-else-stmt.template +/*--- +description: Variable binding is initialized to `undefined` in outer scope (IfStatement with a declaration in the first statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + a. Perform ! varEnvRec.CreateMutableBinding(F, false). + b. Perform varEnvRec.InitializeBinding(F, undefined). + c. Append F to instantiatedVarNames. + [...] +---*/ +var init, changed; + +(function() { + init = f; + f = 123; + changed = f; + + if (true) function f() { } else ; + + +}()); + +assert.sameValue(init, undefined, 'binding is initialized to `undefined`'); +assert.sameValue(changed, 123, 'binding is mutable'); +assert.throws(ReferenceError, function() { + f; +}, 'global binding is not created'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-no-skip-try.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-no-skip-try.js new file mode 100644 index 0000000000..6e6d3d6f76 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-no-skip-try.js @@ -0,0 +1,58 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-no-skip-try.case +// - src/annex-b-fns/func/if-decl-else-stmt.template +/*--- +description: Extension is observed when creation of variable binding would not produce an early error (try statement) (IfStatement with a declaration in the first statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + a. Perform ! varEnvRec.CreateMutableBinding(F, false). + b. Perform varEnvRec.InitializeBinding(F, undefined). + c. Append F to instantiatedVarNames. + [...] + + B.3.5 VariableStatements in Catch Blocks + + [...] + - It is a Syntax Error if any element of the BoundNames of CatchParameter + also occurs in the VarDeclaredNames of Block unless CatchParameter is + CatchParameter:BindingIdentifier and that element is only bound by a + VariableStatement, the VariableDeclarationList of a for statement, or the + ForBinding of a for-in statement. +---*/ + +(function() { + assert.sameValue( + f, undefined, 'Initialized binding created prior to evaluation' + ); + + try { + throw null; + } catch (f) { + + if (true) function f() { return 123; } else ; + + } + + assert.sameValue( + typeof f, + 'function', + 'binding value is updated following evaluation' + ); + assert.sameValue(f(), 123); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-skip-dft-param.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-skip-dft-param.js new file mode 100644 index 0000000000..c5b36b9656 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-skip-dft-param.js @@ -0,0 +1,39 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-dft-param.case +// - src/annex-b-fns/func/if-decl-else-stmt.template +/*--- +description: Extension not observed when there is a default parameter with the same name (IfStatement with a declaration in the first statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ +var init, after; + +(function(f = 123) { + init = f; + + if (true) function f() { } else ; + + after = f; +}()); + +assert.sameValue(init, 123, 'binding is not initialized to `undefined`'); +assert.sameValue(after, 123, 'value is not updated following evaluation'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-skip-early-err-block.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-skip-early-err-block.js new file mode 100644 index 0000000000..c34431e6fc --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-skip-early-err-block.js @@ -0,0 +1,54 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-block.case +// - src/annex-b-fns/func/if-decl-else-stmt.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (Block statement) (IfStatement with a declaration in the first statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + { + let f = 123; + + if (true) function f() { } else ; + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-skip-early-err-for-in.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-skip-early-err-for-in.js new file mode 100644 index 0000000000..58c7b94769 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-skip-early-err-for-in.js @@ -0,0 +1,53 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-for-in.case +// - src/annex-b-fns/func/if-decl-else-stmt.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (for-of statement) (IfStatement with a declaration in the first statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + for (let f in { key: 0 }) { + + if (true) function f() { } else ; + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-skip-early-err-for-of.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-skip-early-err-for-of.js new file mode 100644 index 0000000000..ddc0028253 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-skip-early-err-for-of.js @@ -0,0 +1,53 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-for-of.case +// - src/annex-b-fns/func/if-decl-else-stmt.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (for-of statement) (IfStatement with a declaration in the first statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + for (let f of [0]) { + + if (true) function f() { } else ; + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-skip-early-err-for.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-skip-early-err-for.js new file mode 100644 index 0000000000..e1c4f648de --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-skip-early-err-for.js @@ -0,0 +1,54 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-for.case +// - src/annex-b-fns/func/if-decl-else-stmt.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (for statement) (IfStatement with a declaration in the first statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + for (let f; ; ) { + + if (true) function f() { } else ; + + break; + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-skip-early-err-switch.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-skip-early-err-switch.js new file mode 100644 index 0000000000..cb73605211 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-skip-early-err-switch.js @@ -0,0 +1,55 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-switch.case +// - src/annex-b-fns/func/if-decl-else-stmt.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (switch statement) (IfStatement with a declaration in the first statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + switch (0) { + default: + let f; + + if (true) function f() { } else ; + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-skip-early-err-try.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-skip-early-err-try.js new file mode 100644 index 0000000000..7de1c6c72f --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-skip-early-err-try.js @@ -0,0 +1,65 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-try.case +// - src/annex-b-fns/func/if-decl-else-stmt.template +/*--- +description: Extension is observed when creation of variable binding would not produce an early error (try statement) (IfStatement with a declaration in the first statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + a. Perform ! varEnvRec.CreateMutableBinding(F, false). + b. Perform varEnvRec.InitializeBinding(F, undefined). + c. Append F to instantiatedVarNames. + [...] + + B.3.5 VariableStatements in Catch Blocks + + [...] + - It is a Syntax Error if any element of the BoundNames of CatchParameter + also occurs in the VarDeclaredNames of Block unless CatchParameter is + CatchParameter:BindingIdentifier and that element is only bound by a + VariableStatement, the VariableDeclarationList of a for statement, or the + ForBinding of a for-in statement. +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + try { + throw {}; + } catch ({ f }) { + + if (true) function f() { } else ; + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-skip-early-err.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-skip-early-err.js new file mode 100644 index 0000000000..0c86eea6a5 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-skip-early-err.js @@ -0,0 +1,40 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err.case +// - src/annex-b-fns/func/if-decl-else-stmt.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (IfStatement with a declaration in the first statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ +var init, after; + +(function() { + let f = 123; + init = f; + + if (true) function f() { } else ; + + after = f; +}()); + +assert.sameValue(init, 123, 'binding is not initialized to `undefined`'); +assert.sameValue(after, 123, 'value is not updated following evaluation'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-skip-param.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-skip-param.js new file mode 100644 index 0000000000..ca71166ab5 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-skip-param.js @@ -0,0 +1,39 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-param.case +// - src/annex-b-fns/func/if-decl-else-stmt.template +/*--- +description: Extension not observed when there is a formal parameter with the same name (IfStatement with a declaration in the first statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ +var init, after; + +(function(f) { + init = f; + + if (true) function f() { } else ; + + after = f; +}(123)); + +assert.sameValue(init, 123, 'binding is not initialized to `undefined`'); +assert.sameValue(after, 123, 'value is not updated following evaluation'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-update.js b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-update.js new file mode 100644 index 0000000000..5d784877be --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-else-stmt-func-update.js @@ -0,0 +1,45 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-update.case +// - src/annex-b-fns/func/if-decl-else-stmt.template +/*--- +description: Variable binding value is updated following evaluation (IfStatement with a declaration in the first statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var after; + +(function() { + + + if (true) function f() { return 'declaration'; } else ; + + after = f; +}()); + +assert.sameValue(typeof after, 'function'); +assert.sameValue(after(), 'declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-block-scoping.js b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-block-scoping.js new file mode 100644 index 0000000000..9fb86796d4 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-block-scoping.js @@ -0,0 +1,59 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-block-scoping.case +// - src/annex-b-fns/func/if-decl-no-else.template +/*--- +description: A block-scoped binding is created (IfStatement without an else clause in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + 13.2.14 Runtime Semantics: BlockDeclarationInstantiation + + [...] + 4. For each element d in declarations do + a. For each element dn of the BoundNames of d do + i. If IsConstantDeclaration of d is true, then + [...] + ii. Else, + 2. Perform ! envRec.CreateMutableBinding(dn, false). + + b. If d is a GeneratorDeclaration production or a FunctionDeclaration + production, then + i. Let fn be the sole element of the BoundNames of d. + ii. Let fo be the result of performing InstantiateFunctionObject for + d with argument env. + iii. Perform envRec.InitializeBinding(fn, fo). +---*/ +var initialBV, currentBV, varBinding; + +(function() { + + + if (true) function f() { initialBV = f; f = 123; currentBV = f; return 'decl'; } + + varBinding = f; + f(); +}()); + + +assert.sameValue( + initialBV(), + 'decl', + 'Block-scoped binding value is function object at execution time' +); +assert.sameValue(currentBV, 123, 'Block-scoped binding is mutable'); +assert.sameValue( + varBinding(), + 'decl', + 'Block-scoped binding is independent of outer var-scoped binding' +); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-existing-block-fn-no-init.js b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-existing-block-fn-no-init.js new file mode 100644 index 0000000000..4c4f4d622d --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-existing-block-fn-no-init.js @@ -0,0 +1,40 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-block-fn-no-init.case +// - src/annex-b-fns/func/if-decl-no-else.template +/*--- +description: Does not re-initialize binding created by similar forms (IfStatement without an else clause in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + [...] +---*/ +var init; + +(function() { + init = f; + + { + function f() {} + } + + if (true) function f() { } + + +}()); + +assert.sameValue(init, undefined); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-existing-block-fn-update.js b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-existing-block-fn-update.js new file mode 100644 index 0000000000..6b22f948b0 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-existing-block-fn-update.js @@ -0,0 +1,49 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-block-fn-update.case +// - src/annex-b-fns/func/if-decl-no-else.template +/*--- +description: Variable-scoped binding is updated (IfStatement without an else clause in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var updated; + +(function() { + { + function f() { + return 'first declaration'; + } + } + + if (true) function f() { return 'second declaration'; } + + updated = f; +}()); + +assert.sameValue(typeof updated, 'function'); +assert.sameValue(updated(), 'second declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-existing-fn-no-init.js b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-existing-fn-no-init.js new file mode 100644 index 0000000000..c0d9cb2d12 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-existing-fn-no-init.js @@ -0,0 +1,38 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-fn-no-init.case +// - src/annex-b-fns/func/if-decl-no-else.template +/*--- +description: Existing variable binding is not modified (IfStatement without an else clause in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + [...] +---*/ +var init; + +(function() { + init = f; + + if (true) function f() { return 'inner declaration'; } + + function f() { + return 'outer declaration'; + } +}()); + +assert.sameValue(init(), 'outer declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-existing-fn-update.js b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-existing-fn-update.js new file mode 100644 index 0000000000..e90a392aa4 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-existing-fn-update.js @@ -0,0 +1,49 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-fn-update.case +// - src/annex-b-fns/func/if-decl-no-else.template +/*--- +description: Variable-scoped binding is updated following evaluation (IfStatement without an else clause in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var after; + +(function() { + + + if (true) function f() { return 'inner declaration'; } + + after = f; + + function f() { + return 'outer declaration'; + } +}()); + +assert.sameValue(typeof after, 'function'); +assert.sameValue(after(), 'inner declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-existing-var-no-init.js b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-existing-var-no-init.js new file mode 100644 index 0000000000..9f7d817a74 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-existing-var-no-init.js @@ -0,0 +1,37 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-var-no-init.case +// - src/annex-b-fns/func/if-decl-no-else.template +/*--- +description: Existing variable binding is not modified (IfStatement without an else clause in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + [...] +---*/ +var init; + +(function() { + var f = 123; + init = f; + + if (true) function f() { } + + +}()); + +assert.sameValue(init, 123); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-existing-var-update.js b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-existing-var-update.js new file mode 100644 index 0000000000..50f36bdcc6 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-existing-var-update.js @@ -0,0 +1,48 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-var-update.case +// - src/annex-b-fns/func/if-decl-no-else.template +/*--- +description: Variable-scoped binding is updated following evaluation (IfStatement without an else clause in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var after; + +(function() { + + + if (true) function f() { return 'function declaration'; } + + after = f; + + var f = 123; +}()); + +assert.sameValue(typeof after, 'function'); +assert.sameValue(after(), 'function declaration'); + + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-init.js b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-init.js new file mode 100644 index 0000000000..1e83b641d0 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-init.js @@ -0,0 +1,45 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-init.case +// - src/annex-b-fns/func/if-decl-no-else.template +/*--- +description: Variable binding is initialized to `undefined` in outer scope (IfStatement without an else clause in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + a. Perform ! varEnvRec.CreateMutableBinding(F, false). + b. Perform varEnvRec.InitializeBinding(F, undefined). + c. Append F to instantiatedVarNames. + [...] +---*/ +var init, changed; + +(function() { + init = f; + f = 123; + changed = f; + + if (true) function f() { } + + +}()); + +assert.sameValue(init, undefined, 'binding is initialized to `undefined`'); +assert.sameValue(changed, 123, 'binding is mutable'); +assert.throws(ReferenceError, function() { + f; +}, 'global binding is not created'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-no-skip-try.js b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-no-skip-try.js new file mode 100644 index 0000000000..2b5b9b54f2 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-no-skip-try.js @@ -0,0 +1,58 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-no-skip-try.case +// - src/annex-b-fns/func/if-decl-no-else.template +/*--- +description: Extension is observed when creation of variable binding would not produce an early error (try statement) (IfStatement without an else clause in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + a. Perform ! varEnvRec.CreateMutableBinding(F, false). + b. Perform varEnvRec.InitializeBinding(F, undefined). + c. Append F to instantiatedVarNames. + [...] + + B.3.5 VariableStatements in Catch Blocks + + [...] + - It is a Syntax Error if any element of the BoundNames of CatchParameter + also occurs in the VarDeclaredNames of Block unless CatchParameter is + CatchParameter:BindingIdentifier and that element is only bound by a + VariableStatement, the VariableDeclarationList of a for statement, or the + ForBinding of a for-in statement. +---*/ + +(function() { + assert.sameValue( + f, undefined, 'Initialized binding created prior to evaluation' + ); + + try { + throw null; + } catch (f) { + + if (true) function f() { return 123; } + + } + + assert.sameValue( + typeof f, + 'function', + 'binding value is updated following evaluation' + ); + assert.sameValue(f(), 123); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-skip-dft-param.js b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-skip-dft-param.js new file mode 100644 index 0000000000..f69e1063be --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-skip-dft-param.js @@ -0,0 +1,39 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-dft-param.case +// - src/annex-b-fns/func/if-decl-no-else.template +/*--- +description: Extension not observed when there is a default parameter with the same name (IfStatement without an else clause in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ +var init, after; + +(function(f = 123) { + init = f; + + if (true) function f() { } + + after = f; +}()); + +assert.sameValue(init, 123, 'binding is not initialized to `undefined`'); +assert.sameValue(after, 123, 'value is not updated following evaluation'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-skip-early-err-block.js b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-skip-early-err-block.js new file mode 100644 index 0000000000..050d97c218 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-skip-early-err-block.js @@ -0,0 +1,54 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-block.case +// - src/annex-b-fns/func/if-decl-no-else.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (Block statement) (IfStatement without an else clause in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + { + let f = 123; + + if (true) function f() { } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-skip-early-err-for-in.js b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-skip-early-err-for-in.js new file mode 100644 index 0000000000..97fe839a55 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-skip-early-err-for-in.js @@ -0,0 +1,53 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-for-in.case +// - src/annex-b-fns/func/if-decl-no-else.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (for-of statement) (IfStatement without an else clause in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + for (let f in { key: 0 }) { + + if (true) function f() { } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-skip-early-err-for-of.js b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-skip-early-err-for-of.js new file mode 100644 index 0000000000..4fb50227e5 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-skip-early-err-for-of.js @@ -0,0 +1,53 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-for-of.case +// - src/annex-b-fns/func/if-decl-no-else.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (for-of statement) (IfStatement without an else clause in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + for (let f of [0]) { + + if (true) function f() { } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-skip-early-err-for.js b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-skip-early-err-for.js new file mode 100644 index 0000000000..1029f5f034 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-skip-early-err-for.js @@ -0,0 +1,54 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-for.case +// - src/annex-b-fns/func/if-decl-no-else.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (for statement) (IfStatement without an else clause in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + for (let f; ; ) { + + if (true) function f() { } + + break; + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-skip-early-err-switch.js b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-skip-early-err-switch.js new file mode 100644 index 0000000000..1b0c0b8d78 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-skip-early-err-switch.js @@ -0,0 +1,55 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-switch.case +// - src/annex-b-fns/func/if-decl-no-else.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (switch statement) (IfStatement without an else clause in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + switch (0) { + default: + let f; + + if (true) function f() { } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-skip-early-err-try.js b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-skip-early-err-try.js new file mode 100644 index 0000000000..562e29900b --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-skip-early-err-try.js @@ -0,0 +1,65 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-try.case +// - src/annex-b-fns/func/if-decl-no-else.template +/*--- +description: Extension is observed when creation of variable binding would not produce an early error (try statement) (IfStatement without an else clause in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + a. Perform ! varEnvRec.CreateMutableBinding(F, false). + b. Perform varEnvRec.InitializeBinding(F, undefined). + c. Append F to instantiatedVarNames. + [...] + + B.3.5 VariableStatements in Catch Blocks + + [...] + - It is a Syntax Error if any element of the BoundNames of CatchParameter + also occurs in the VarDeclaredNames of Block unless CatchParameter is + CatchParameter:BindingIdentifier and that element is only bound by a + VariableStatement, the VariableDeclarationList of a for statement, or the + ForBinding of a for-in statement. +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + try { + throw {}; + } catch ({ f }) { + + if (true) function f() { } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-skip-early-err.js b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-skip-early-err.js new file mode 100644 index 0000000000..00459a239a --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-skip-early-err.js @@ -0,0 +1,40 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err.case +// - src/annex-b-fns/func/if-decl-no-else.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (IfStatement without an else clause in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ +var init, after; + +(function() { + let f = 123; + init = f; + + if (true) function f() { } + + after = f; +}()); + +assert.sameValue(init, 123, 'binding is not initialized to `undefined`'); +assert.sameValue(after, 123, 'value is not updated following evaluation'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-skip-param.js b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-skip-param.js new file mode 100644 index 0000000000..00ba2976ac --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-skip-param.js @@ -0,0 +1,39 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-param.case +// - src/annex-b-fns/func/if-decl-no-else.template +/*--- +description: Extension not observed when there is a formal parameter with the same name (IfStatement without an else clause in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ +var init, after; + +(function(f) { + init = f; + + if (true) function f() { } + + after = f; +}(123)); + +assert.sameValue(init, 123, 'binding is not initialized to `undefined`'); +assert.sameValue(after, 123, 'value is not updated following evaluation'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-update.js b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-update.js new file mode 100644 index 0000000000..5038274c87 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-decl-no-else-func-update.js @@ -0,0 +1,45 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-update.case +// - src/annex-b-fns/func/if-decl-no-else.template +/*--- +description: Variable binding value is updated following evaluation (IfStatement without an else clause in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var after; + +(function() { + + + if (true) function f() { return 'declaration'; } + + after = f; +}()); + +assert.sameValue(typeof after, 'function'); +assert.sameValue(after(), 'declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-block-scoping.js b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-block-scoping.js new file mode 100644 index 0000000000..e8850b9c51 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-block-scoping.js @@ -0,0 +1,59 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-block-scoping.case +// - src/annex-b-fns/func/if-stmt-else-decl.template +/*--- +description: A block-scoped binding is created (IfStatement with a declaration in the second statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + 13.2.14 Runtime Semantics: BlockDeclarationInstantiation + + [...] + 4. For each element d in declarations do + a. For each element dn of the BoundNames of d do + i. If IsConstantDeclaration of d is true, then + [...] + ii. Else, + 2. Perform ! envRec.CreateMutableBinding(dn, false). + + b. If d is a GeneratorDeclaration production or a FunctionDeclaration + production, then + i. Let fn be the sole element of the BoundNames of d. + ii. Let fo be the result of performing InstantiateFunctionObject for + d with argument env. + iii. Perform envRec.InitializeBinding(fn, fo). +---*/ +var initialBV, currentBV, varBinding; + +(function() { + + + if (false) ; else function f() { initialBV = f; f = 123; currentBV = f; return 'decl'; } + + varBinding = f; + f(); +}()); + + +assert.sameValue( + initialBV(), + 'decl', + 'Block-scoped binding value is function object at execution time' +); +assert.sameValue(currentBV, 123, 'Block-scoped binding is mutable'); +assert.sameValue( + varBinding(), + 'decl', + 'Block-scoped binding is independent of outer var-scoped binding' +); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-existing-block-fn-no-init.js b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-existing-block-fn-no-init.js new file mode 100644 index 0000000000..b3292466ed --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-existing-block-fn-no-init.js @@ -0,0 +1,40 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-block-fn-no-init.case +// - src/annex-b-fns/func/if-stmt-else-decl.template +/*--- +description: Does not re-initialize binding created by similar forms (IfStatement with a declaration in the second statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + [...] +---*/ +var init; + +(function() { + init = f; + + { + function f() {} + } + + if (false) ; else function f() { } + + +}()); + +assert.sameValue(init, undefined); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-existing-block-fn-update.js b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-existing-block-fn-update.js new file mode 100644 index 0000000000..ce84f7ed1c --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-existing-block-fn-update.js @@ -0,0 +1,49 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-block-fn-update.case +// - src/annex-b-fns/func/if-stmt-else-decl.template +/*--- +description: Variable-scoped binding is updated (IfStatement with a declaration in the second statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var updated; + +(function() { + { + function f() { + return 'first declaration'; + } + } + + if (false) ; else function f() { return 'second declaration'; } + + updated = f; +}()); + +assert.sameValue(typeof updated, 'function'); +assert.sameValue(updated(), 'second declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-existing-fn-no-init.js b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-existing-fn-no-init.js new file mode 100644 index 0000000000..5c649b8ccc --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-existing-fn-no-init.js @@ -0,0 +1,38 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-fn-no-init.case +// - src/annex-b-fns/func/if-stmt-else-decl.template +/*--- +description: Existing variable binding is not modified (IfStatement with a declaration in the second statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + [...] +---*/ +var init; + +(function() { + init = f; + + if (false) ; else function f() { return 'inner declaration'; } + + function f() { + return 'outer declaration'; + } +}()); + +assert.sameValue(init(), 'outer declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-existing-fn-update.js b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-existing-fn-update.js new file mode 100644 index 0000000000..2bdf2fadb7 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-existing-fn-update.js @@ -0,0 +1,49 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-fn-update.case +// - src/annex-b-fns/func/if-stmt-else-decl.template +/*--- +description: Variable-scoped binding is updated following evaluation (IfStatement with a declaration in the second statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var after; + +(function() { + + + if (false) ; else function f() { return 'inner declaration'; } + + after = f; + + function f() { + return 'outer declaration'; + } +}()); + +assert.sameValue(typeof after, 'function'); +assert.sameValue(after(), 'inner declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-existing-var-no-init.js b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-existing-var-no-init.js new file mode 100644 index 0000000000..0d9635df28 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-existing-var-no-init.js @@ -0,0 +1,37 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-var-no-init.case +// - src/annex-b-fns/func/if-stmt-else-decl.template +/*--- +description: Existing variable binding is not modified (IfStatement with a declaration in the second statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + [...] +---*/ +var init; + +(function() { + var f = 123; + init = f; + + if (false) ; else function f() { } + + +}()); + +assert.sameValue(init, 123); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-existing-var-update.js b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-existing-var-update.js new file mode 100644 index 0000000000..03f9416a2a --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-existing-var-update.js @@ -0,0 +1,48 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-var-update.case +// - src/annex-b-fns/func/if-stmt-else-decl.template +/*--- +description: Variable-scoped binding is updated following evaluation (IfStatement with a declaration in the second statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var after; + +(function() { + + + if (false) ; else function f() { return 'function declaration'; } + + after = f; + + var f = 123; +}()); + +assert.sameValue(typeof after, 'function'); +assert.sameValue(after(), 'function declaration'); + + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-init.js b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-init.js new file mode 100644 index 0000000000..3816385413 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-init.js @@ -0,0 +1,45 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-init.case +// - src/annex-b-fns/func/if-stmt-else-decl.template +/*--- +description: Variable binding is initialized to `undefined` in outer scope (IfStatement with a declaration in the second statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + a. Perform ! varEnvRec.CreateMutableBinding(F, false). + b. Perform varEnvRec.InitializeBinding(F, undefined). + c. Append F to instantiatedVarNames. + [...] +---*/ +var init, changed; + +(function() { + init = f; + f = 123; + changed = f; + + if (false) ; else function f() { } + + +}()); + +assert.sameValue(init, undefined, 'binding is initialized to `undefined`'); +assert.sameValue(changed, 123, 'binding is mutable'); +assert.throws(ReferenceError, function() { + f; +}, 'global binding is not created'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-no-skip-try.js b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-no-skip-try.js new file mode 100644 index 0000000000..a574afb7f3 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-no-skip-try.js @@ -0,0 +1,58 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-no-skip-try.case +// - src/annex-b-fns/func/if-stmt-else-decl.template +/*--- +description: Extension is observed when creation of variable binding would not produce an early error (try statement) (IfStatement with a declaration in the second statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + a. Perform ! varEnvRec.CreateMutableBinding(F, false). + b. Perform varEnvRec.InitializeBinding(F, undefined). + c. Append F to instantiatedVarNames. + [...] + + B.3.5 VariableStatements in Catch Blocks + + [...] + - It is a Syntax Error if any element of the BoundNames of CatchParameter + also occurs in the VarDeclaredNames of Block unless CatchParameter is + CatchParameter:BindingIdentifier and that element is only bound by a + VariableStatement, the VariableDeclarationList of a for statement, or the + ForBinding of a for-in statement. +---*/ + +(function() { + assert.sameValue( + f, undefined, 'Initialized binding created prior to evaluation' + ); + + try { + throw null; + } catch (f) { + + if (false) ; else function f() { return 123; } + + } + + assert.sameValue( + typeof f, + 'function', + 'binding value is updated following evaluation' + ); + assert.sameValue(f(), 123); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-skip-dft-param.js b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-skip-dft-param.js new file mode 100644 index 0000000000..5e86815aec --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-skip-dft-param.js @@ -0,0 +1,39 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-dft-param.case +// - src/annex-b-fns/func/if-stmt-else-decl.template +/*--- +description: Extension not observed when there is a default parameter with the same name (IfStatement with a declaration in the second statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ +var init, after; + +(function(f = 123) { + init = f; + + if (false) ; else function f() { } + + after = f; +}()); + +assert.sameValue(init, 123, 'binding is not initialized to `undefined`'); +assert.sameValue(after, 123, 'value is not updated following evaluation'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-skip-early-err-block.js b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-skip-early-err-block.js new file mode 100644 index 0000000000..fbce2691eb --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-skip-early-err-block.js @@ -0,0 +1,54 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-block.case +// - src/annex-b-fns/func/if-stmt-else-decl.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (Block statement) (IfStatement with a declaration in the second statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + { + let f = 123; + + if (false) ; else function f() { } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-skip-early-err-for-in.js b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-skip-early-err-for-in.js new file mode 100644 index 0000000000..85ecefb417 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-skip-early-err-for-in.js @@ -0,0 +1,53 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-for-in.case +// - src/annex-b-fns/func/if-stmt-else-decl.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (for-of statement) (IfStatement with a declaration in the second statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + for (let f in { key: 0 }) { + + if (false) ; else function f() { } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-skip-early-err-for-of.js b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-skip-early-err-for-of.js new file mode 100644 index 0000000000..1c6ef0d10b --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-skip-early-err-for-of.js @@ -0,0 +1,53 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-for-of.case +// - src/annex-b-fns/func/if-stmt-else-decl.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (for-of statement) (IfStatement with a declaration in the second statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + for (let f of [0]) { + + if (false) ; else function f() { } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-skip-early-err-for.js b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-skip-early-err-for.js new file mode 100644 index 0000000000..4e80a4479e --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-skip-early-err-for.js @@ -0,0 +1,54 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-for.case +// - src/annex-b-fns/func/if-stmt-else-decl.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (for statement) (IfStatement with a declaration in the second statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + for (let f; ; ) { + + if (false) ; else function f() { } + + break; + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-skip-early-err-switch.js b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-skip-early-err-switch.js new file mode 100644 index 0000000000..9d97fa40f2 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-skip-early-err-switch.js @@ -0,0 +1,55 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-switch.case +// - src/annex-b-fns/func/if-stmt-else-decl.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (switch statement) (IfStatement with a declaration in the second statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + switch (0) { + default: + let f; + + if (false) ; else function f() { } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-skip-early-err-try.js b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-skip-early-err-try.js new file mode 100644 index 0000000000..ed0d06d49b --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-skip-early-err-try.js @@ -0,0 +1,65 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-try.case +// - src/annex-b-fns/func/if-stmt-else-decl.template +/*--- +description: Extension is observed when creation of variable binding would not produce an early error (try statement) (IfStatement with a declaration in the second statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + a. Perform ! varEnvRec.CreateMutableBinding(F, false). + b. Perform varEnvRec.InitializeBinding(F, undefined). + c. Append F to instantiatedVarNames. + [...] + + B.3.5 VariableStatements in Catch Blocks + + [...] + - It is a Syntax Error if any element of the BoundNames of CatchParameter + also occurs in the VarDeclaredNames of Block unless CatchParameter is + CatchParameter:BindingIdentifier and that element is only bound by a + VariableStatement, the VariableDeclarationList of a for statement, or the + ForBinding of a for-in statement. +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + try { + throw {}; + } catch ({ f }) { + + if (false) ; else function f() { } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-skip-early-err.js b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-skip-early-err.js new file mode 100644 index 0000000000..4a8ac7ef54 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-skip-early-err.js @@ -0,0 +1,40 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err.case +// - src/annex-b-fns/func/if-stmt-else-decl.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (IfStatement with a declaration in the second statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ +var init, after; + +(function() { + let f = 123; + init = f; + + if (false) ; else function f() { } + + after = f; +}()); + +assert.sameValue(init, 123, 'binding is not initialized to `undefined`'); +assert.sameValue(after, 123, 'value is not updated following evaluation'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-skip-param.js b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-skip-param.js new file mode 100644 index 0000000000..770713d5c1 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-skip-param.js @@ -0,0 +1,39 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-param.case +// - src/annex-b-fns/func/if-stmt-else-decl.template +/*--- +description: Extension not observed when there is a formal parameter with the same name (IfStatement with a declaration in the second statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ +var init, after; + +(function(f) { + init = f; + + if (false) ; else function f() { } + + after = f; +}(123)); + +assert.sameValue(init, 123, 'binding is not initialized to `undefined`'); +assert.sameValue(after, 123, 'value is not updated following evaluation'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-update.js b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-update.js new file mode 100644 index 0000000000..05feeb50a3 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/if-stmt-else-decl-func-update.js @@ -0,0 +1,45 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-update.case +// - src/annex-b-fns/func/if-stmt-else-decl.template +/*--- +description: Variable binding value is updated following evaluation (IfStatement with a declaration in the second statement position in function scope) +esid: sec-functiondeclarations-in-ifstatement-statement-clauses +flags: [generated, noStrict] +info: | + The following rules for IfStatement augment those in 13.6: + + IfStatement[Yield, Return]: + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else Statement[?Yield, ?Return] + if ( Expression[In, ?Yield] ) Statement[?Yield, ?Return] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] else FunctionDeclaration[?Yield] + if ( Expression[In, ?Yield] ) FunctionDeclaration[?Yield] + + + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var after; + +(function() { + + + if (false) ; else function f() { return 'declaration'; } + + after = f; +}()); + +assert.sameValue(typeof after, 'function'); +assert.sameValue(after(), 'declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/shell.js b/js/src/tests/test262/annexB/language/function-code/shell.js new file mode 100644 index 0000000000..e69de29bb2 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/shell.js diff --git a/js/src/tests/test262/annexB/language/function-code/switch-case-decl-nostrict.js b/js/src/tests/test262/annexB/language/function-code/switch-case-decl-nostrict.js new file mode 100644 index 0000000000..9a1d776960 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-case-decl-nostrict.js @@ -0,0 +1,41 @@ +// Copyright (C) 2016 the V8 project authors. All rights reserved. +// This code is governed by the BSD license found in the LICENSE file. +/*--- +esid: sec-web-compat-functiondeclarationinstantiation +description: > + AnnexB extension not honored in strict mode, Function declaration + in the `case` clause of a `switch` statement in function code +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + 1. If strict is false, then + ... + +flags: [noStrict] +---*/ + +var err1, err2; + +(function() { + try { + f; + } catch (exception) { + err1 = exception; + } + + switch (1) { + case 1: + function f() { } + } + + try { + f; + } catch (exception) { + err2 = exception; + } +}()); + +assert.sameValue(err1, undefined); +assert.sameValue(err2, undefined); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-case-func-block-scoping.js b/js/src/tests/test262/annexB/language/function-code/switch-case-func-block-scoping.js new file mode 100644 index 0000000000..5388791b85 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-case-func-block-scoping.js @@ -0,0 +1,53 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-block-scoping.case +// - src/annex-b-fns/func/switch-case.template +/*--- +description: A block-scoped binding is created (Function declaration in the `case` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + 13.2.14 Runtime Semantics: BlockDeclarationInstantiation + + [...] + 4. For each element d in declarations do + a. For each element dn of the BoundNames of d do + i. If IsConstantDeclaration of d is true, then + [...] + ii. Else, + 2. Perform ! envRec.CreateMutableBinding(dn, false). + + b. If d is a GeneratorDeclaration production or a FunctionDeclaration + production, then + i. Let fn be the sole element of the BoundNames of d. + ii. Let fo be the result of performing InstantiateFunctionObject for + d with argument env. + iii. Perform envRec.InitializeBinding(fn, fo). +---*/ +var initialBV, currentBV, varBinding; + +(function() { + + + switch (1) { + case 1: + function f() { initialBV = f; f = 123; currentBV = f; return 'decl'; } + } + + varBinding = f; + f(); +}()); + + +assert.sameValue( + initialBV(), + 'decl', + 'Block-scoped binding value is function object at execution time' +); +assert.sameValue(currentBV, 123, 'Block-scoped binding is mutable'); +assert.sameValue( + varBinding(), + 'decl', + 'Block-scoped binding is independent of outer var-scoped binding' +); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-case-func-existing-block-fn-no-init.js b/js/src/tests/test262/annexB/language/function-code/switch-case-func-existing-block-fn-no-init.js new file mode 100644 index 0000000000..15ef7e3fbc --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-case-func-existing-block-fn-no-init.js @@ -0,0 +1,34 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-block-fn-no-init.case +// - src/annex-b-fns/func/switch-case.template +/*--- +description: Does not re-initialize binding created by similar forms (Function declaration in the `case` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + [...] +---*/ +var init; + +(function() { + init = f; + + { + function f() {} + } + + switch (1) { + case 1: + function f() { } + } + + +}()); + +assert.sameValue(init, undefined); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-case-func-existing-block-fn-update.js b/js/src/tests/test262/annexB/language/function-code/switch-case-func-existing-block-fn-update.js new file mode 100644 index 0000000000..f667bf7507 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-case-func-existing-block-fn-update.js @@ -0,0 +1,43 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-block-fn-update.case +// - src/annex-b-fns/func/switch-case.template +/*--- +description: Variable-scoped binding is updated (Function declaration in the `case` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var updated; + +(function() { + { + function f() { + return 'first declaration'; + } + } + + switch (1) { + case 1: + function f() { return 'second declaration'; } + } + + updated = f; +}()); + +assert.sameValue(typeof updated, 'function'); +assert.sameValue(updated(), 'second declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-case-func-existing-fn-no-init.js b/js/src/tests/test262/annexB/language/function-code/switch-case-func-existing-fn-no-init.js new file mode 100644 index 0000000000..04d8d3e0c6 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-case-func-existing-fn-no-init.js @@ -0,0 +1,32 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-fn-no-init.case +// - src/annex-b-fns/func/switch-case.template +/*--- +description: Existing variable binding is not modified (Function declaration in the `case` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + [...] +---*/ +var init; + +(function() { + init = f; + + switch (1) { + case 1: + function f() { return 'inner declaration'; } + } + + function f() { + return 'outer declaration'; + } +}()); + +assert.sameValue(init(), 'outer declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-case-func-existing-fn-update.js b/js/src/tests/test262/annexB/language/function-code/switch-case-func-existing-fn-update.js new file mode 100644 index 0000000000..e76b044eb1 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-case-func-existing-fn-update.js @@ -0,0 +1,43 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-fn-update.case +// - src/annex-b-fns/func/switch-case.template +/*--- +description: Variable-scoped binding is updated following evaluation (Function declaration in the `case` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var after; + +(function() { + + + switch (1) { + case 1: + function f() { return 'inner declaration'; } + } + + after = f; + + function f() { + return 'outer declaration'; + } +}()); + +assert.sameValue(typeof after, 'function'); +assert.sameValue(after(), 'inner declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-case-func-existing-var-no-init.js b/js/src/tests/test262/annexB/language/function-code/switch-case-func-existing-var-no-init.js new file mode 100644 index 0000000000..603f17b7fc --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-case-func-existing-var-no-init.js @@ -0,0 +1,31 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-var-no-init.case +// - src/annex-b-fns/func/switch-case.template +/*--- +description: Existing variable binding is not modified (Function declaration in the `case` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + [...] +---*/ +var init; + +(function() { + var f = 123; + init = f; + + switch (1) { + case 1: + function f() { } + } + + +}()); + +assert.sameValue(init, 123); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-case-func-existing-var-update.js b/js/src/tests/test262/annexB/language/function-code/switch-case-func-existing-var-update.js new file mode 100644 index 0000000000..ec37b546af --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-case-func-existing-var-update.js @@ -0,0 +1,42 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-var-update.case +// - src/annex-b-fns/func/switch-case.template +/*--- +description: Variable-scoped binding is updated following evaluation (Function declaration in the `case` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var after; + +(function() { + + + switch (1) { + case 1: + function f() { return 'function declaration'; } + } + + after = f; + + var f = 123; +}()); + +assert.sameValue(typeof after, 'function'); +assert.sameValue(after(), 'function declaration'); + + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-case-func-init.js b/js/src/tests/test262/annexB/language/function-code/switch-case-func-init.js new file mode 100644 index 0000000000..9fa416ad1b --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-case-func-init.js @@ -0,0 +1,39 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-init.case +// - src/annex-b-fns/func/switch-case.template +/*--- +description: Variable binding is initialized to `undefined` in outer scope (Function declaration in the `case` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + a. Perform ! varEnvRec.CreateMutableBinding(F, false). + b. Perform varEnvRec.InitializeBinding(F, undefined). + c. Append F to instantiatedVarNames. + [...] +---*/ +var init, changed; + +(function() { + init = f; + f = 123; + changed = f; + + switch (1) { + case 1: + function f() { } + } + + +}()); + +assert.sameValue(init, undefined, 'binding is initialized to `undefined`'); +assert.sameValue(changed, 123, 'binding is mutable'); +assert.throws(ReferenceError, function() { + f; +}, 'global binding is not created'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-case-func-no-skip-try.js b/js/src/tests/test262/annexB/language/function-code/switch-case-func-no-skip-try.js new file mode 100644 index 0000000000..4edbd0a847 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-case-func-no-skip-try.js @@ -0,0 +1,52 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-no-skip-try.case +// - src/annex-b-fns/func/switch-case.template +/*--- +description: Extension is observed when creation of variable binding would not produce an early error (try statement) (Function declaration in the `case` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + a. Perform ! varEnvRec.CreateMutableBinding(F, false). + b. Perform varEnvRec.InitializeBinding(F, undefined). + c. Append F to instantiatedVarNames. + [...] + + B.3.5 VariableStatements in Catch Blocks + + [...] + - It is a Syntax Error if any element of the BoundNames of CatchParameter + also occurs in the VarDeclaredNames of Block unless CatchParameter is + CatchParameter:BindingIdentifier and that element is only bound by a + VariableStatement, the VariableDeclarationList of a for statement, or the + ForBinding of a for-in statement. +---*/ + +(function() { + assert.sameValue( + f, undefined, 'Initialized binding created prior to evaluation' + ); + + try { + throw null; + } catch (f) { + + switch (1) { + case 1: + function f() { return 123; } + } + + } + + assert.sameValue( + typeof f, + 'function', + 'binding value is updated following evaluation' + ); + assert.sameValue(f(), 123); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-case-func-skip-dft-param.js b/js/src/tests/test262/annexB/language/function-code/switch-case-func-skip-dft-param.js new file mode 100644 index 0000000000..f6ca9c65e2 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-case-func-skip-dft-param.js @@ -0,0 +1,33 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-dft-param.case +// - src/annex-b-fns/func/switch-case.template +/*--- +description: Extension not observed when there is a default parameter with the same name (Function declaration in the `case` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ +var init, after; + +(function(f = 123) { + init = f; + + switch (1) { + case 1: + function f() { } + } + + after = f; +}()); + +assert.sameValue(init, 123, 'binding is not initialized to `undefined`'); +assert.sameValue(after, 123, 'value is not updated following evaluation'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-case-func-skip-early-err-block.js b/js/src/tests/test262/annexB/language/function-code/switch-case-func-skip-early-err-block.js new file mode 100644 index 0000000000..5b8f50ed2f --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-case-func-skip-early-err-block.js @@ -0,0 +1,48 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-block.case +// - src/annex-b-fns/func/switch-case.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (Block statement) (Function declaration in the `case` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + { + let f = 123; + + switch (1) { + case 1: + function f() { } + } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-case-func-skip-early-err-for-in.js b/js/src/tests/test262/annexB/language/function-code/switch-case-func-skip-early-err-for-in.js new file mode 100644 index 0000000000..3aba8da1c9 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-case-func-skip-early-err-for-in.js @@ -0,0 +1,47 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-for-in.case +// - src/annex-b-fns/func/switch-case.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (for-of statement) (Function declaration in the `case` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + for (let f in { key: 0 }) { + + switch (1) { + case 1: + function f() { } + } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-case-func-skip-early-err-for-of.js b/js/src/tests/test262/annexB/language/function-code/switch-case-func-skip-early-err-for-of.js new file mode 100644 index 0000000000..f949da87cc --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-case-func-skip-early-err-for-of.js @@ -0,0 +1,47 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-for-of.case +// - src/annex-b-fns/func/switch-case.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (for-of statement) (Function declaration in the `case` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + for (let f of [0]) { + + switch (1) { + case 1: + function f() { } + } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-case-func-skip-early-err-for.js b/js/src/tests/test262/annexB/language/function-code/switch-case-func-skip-early-err-for.js new file mode 100644 index 0000000000..5ff85c5766 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-case-func-skip-early-err-for.js @@ -0,0 +1,48 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-for.case +// - src/annex-b-fns/func/switch-case.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (for statement) (Function declaration in the `case` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + for (let f; ; ) { + + switch (1) { + case 1: + function f() { } + } + + break; + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-case-func-skip-early-err-switch.js b/js/src/tests/test262/annexB/language/function-code/switch-case-func-skip-early-err-switch.js new file mode 100644 index 0000000000..1ecf8cbbef --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-case-func-skip-early-err-switch.js @@ -0,0 +1,49 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-switch.case +// - src/annex-b-fns/func/switch-case.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (switch statement) (Function declaration in the `case` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + switch (0) { + default: + let f; + + switch (1) { + case 1: + function f() { } + } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-case-func-skip-early-err-try.js b/js/src/tests/test262/annexB/language/function-code/switch-case-func-skip-early-err-try.js new file mode 100644 index 0000000000..eee62b5561 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-case-func-skip-early-err-try.js @@ -0,0 +1,59 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-try.case +// - src/annex-b-fns/func/switch-case.template +/*--- +description: Extension is observed when creation of variable binding would not produce an early error (try statement) (Function declaration in the `case` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + a. Perform ! varEnvRec.CreateMutableBinding(F, false). + b. Perform varEnvRec.InitializeBinding(F, undefined). + c. Append F to instantiatedVarNames. + [...] + + B.3.5 VariableStatements in Catch Blocks + + [...] + - It is a Syntax Error if any element of the BoundNames of CatchParameter + also occurs in the VarDeclaredNames of Block unless CatchParameter is + CatchParameter:BindingIdentifier and that element is only bound by a + VariableStatement, the VariableDeclarationList of a for statement, or the + ForBinding of a for-in statement. +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + try { + throw {}; + } catch ({ f }) { + + switch (1) { + case 1: + function f() { } + } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-case-func-skip-early-err.js b/js/src/tests/test262/annexB/language/function-code/switch-case-func-skip-early-err.js new file mode 100644 index 0000000000..87d64e1536 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-case-func-skip-early-err.js @@ -0,0 +1,34 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err.case +// - src/annex-b-fns/func/switch-case.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (Function declaration in the `case` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ +var init, after; + +(function() { + let f = 123; + init = f; + + switch (1) { + case 1: + function f() { } + } + + after = f; +}()); + +assert.sameValue(init, 123, 'binding is not initialized to `undefined`'); +assert.sameValue(after, 123, 'value is not updated following evaluation'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-case-func-skip-param.js b/js/src/tests/test262/annexB/language/function-code/switch-case-func-skip-param.js new file mode 100644 index 0000000000..2d5699418b --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-case-func-skip-param.js @@ -0,0 +1,33 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-param.case +// - src/annex-b-fns/func/switch-case.template +/*--- +description: Extension not observed when there is a formal parameter with the same name (Function declaration in the `case` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ +var init, after; + +(function(f) { + init = f; + + switch (1) { + case 1: + function f() { } + } + + after = f; +}(123)); + +assert.sameValue(init, 123, 'binding is not initialized to `undefined`'); +assert.sameValue(after, 123, 'value is not updated following evaluation'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-case-func-update.js b/js/src/tests/test262/annexB/language/function-code/switch-case-func-update.js new file mode 100644 index 0000000000..cea6aa60a9 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-case-func-update.js @@ -0,0 +1,39 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-update.case +// - src/annex-b-fns/func/switch-case.template +/*--- +description: Variable binding value is updated following evaluation (Function declaration in the `case` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var after; + +(function() { + + + switch (1) { + case 1: + function f() { return 'declaration'; } + } + + after = f; +}()); + +assert.sameValue(typeof after, 'function'); +assert.sameValue(after(), 'declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-dflt-decl-nostrict.js b/js/src/tests/test262/annexB/language/function-code/switch-dflt-decl-nostrict.js new file mode 100644 index 0000000000..fbcfb8ca05 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-dflt-decl-nostrict.js @@ -0,0 +1,41 @@ +// Copyright (C) 2016 the V8 project authors. All rights reserved. +// This code is governed by the BSD license found in the LICENSE file. +/*--- +esid: sec-web-compat-functiondeclarationinstantiation +description: > + AnnexB extension not honored in strict mode, Function declaration + in the `default` clause of a `switch` statement in function code +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + 1. If strict is false, then + ... + +flags: [noStrict] +---*/ + +var err1, err2; + +(function() { + try { + f; + } catch (exception) { + err1 = exception; + } + + switch (1) { + default: + function f() { } + } + + try { + f; + } catch (exception) { + err2 = exception; + } +}()); + +assert.sameValue(err1, undefined); +assert.sameValue(err2, undefined); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-block-scoping.js b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-block-scoping.js new file mode 100644 index 0000000000..c18abba71b --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-block-scoping.js @@ -0,0 +1,53 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-block-scoping.case +// - src/annex-b-fns/func/switch-dflt.template +/*--- +description: A block-scoped binding is created (Funtion declaration in the `default` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + 13.2.14 Runtime Semantics: BlockDeclarationInstantiation + + [...] + 4. For each element d in declarations do + a. For each element dn of the BoundNames of d do + i. If IsConstantDeclaration of d is true, then + [...] + ii. Else, + 2. Perform ! envRec.CreateMutableBinding(dn, false). + + b. If d is a GeneratorDeclaration production or a FunctionDeclaration + production, then + i. Let fn be the sole element of the BoundNames of d. + ii. Let fo be the result of performing InstantiateFunctionObject for + d with argument env. + iii. Perform envRec.InitializeBinding(fn, fo). +---*/ +var initialBV, currentBV, varBinding; + +(function() { + + + switch (1) { + default: + function f() { initialBV = f; f = 123; currentBV = f; return 'decl'; } + } + + varBinding = f; + f(); +}()); + + +assert.sameValue( + initialBV(), + 'decl', + 'Block-scoped binding value is function object at execution time' +); +assert.sameValue(currentBV, 123, 'Block-scoped binding is mutable'); +assert.sameValue( + varBinding(), + 'decl', + 'Block-scoped binding is independent of outer var-scoped binding' +); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-existing-block-fn-no-init.js b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-existing-block-fn-no-init.js new file mode 100644 index 0000000000..57d48d90ef --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-existing-block-fn-no-init.js @@ -0,0 +1,34 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-block-fn-no-init.case +// - src/annex-b-fns/func/switch-dflt.template +/*--- +description: Does not re-initialize binding created by similar forms (Funtion declaration in the `default` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + [...] +---*/ +var init; + +(function() { + init = f; + + { + function f() {} + } + + switch (1) { + default: + function f() { } + } + + +}()); + +assert.sameValue(init, undefined); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-existing-block-fn-update.js b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-existing-block-fn-update.js new file mode 100644 index 0000000000..83b4326ac3 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-existing-block-fn-update.js @@ -0,0 +1,43 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-block-fn-update.case +// - src/annex-b-fns/func/switch-dflt.template +/*--- +description: Variable-scoped binding is updated (Funtion declaration in the `default` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var updated; + +(function() { + { + function f() { + return 'first declaration'; + } + } + + switch (1) { + default: + function f() { return 'second declaration'; } + } + + updated = f; +}()); + +assert.sameValue(typeof updated, 'function'); +assert.sameValue(updated(), 'second declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-existing-fn-no-init.js b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-existing-fn-no-init.js new file mode 100644 index 0000000000..04afab4d5e --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-existing-fn-no-init.js @@ -0,0 +1,32 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-fn-no-init.case +// - src/annex-b-fns/func/switch-dflt.template +/*--- +description: Existing variable binding is not modified (Funtion declaration in the `default` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + [...] +---*/ +var init; + +(function() { + init = f; + + switch (1) { + default: + function f() { return 'inner declaration'; } + } + + function f() { + return 'outer declaration'; + } +}()); + +assert.sameValue(init(), 'outer declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-existing-fn-update.js b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-existing-fn-update.js new file mode 100644 index 0000000000..b88bf18fed --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-existing-fn-update.js @@ -0,0 +1,43 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-fn-update.case +// - src/annex-b-fns/func/switch-dflt.template +/*--- +description: Variable-scoped binding is updated following evaluation (Funtion declaration in the `default` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var after; + +(function() { + + + switch (1) { + default: + function f() { return 'inner declaration'; } + } + + after = f; + + function f() { + return 'outer declaration'; + } +}()); + +assert.sameValue(typeof after, 'function'); +assert.sameValue(after(), 'inner declaration'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-existing-var-no-init.js b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-existing-var-no-init.js new file mode 100644 index 0000000000..cb3c100f7f --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-existing-var-no-init.js @@ -0,0 +1,31 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-var-no-init.case +// - src/annex-b-fns/func/switch-dflt.template +/*--- +description: Existing variable binding is not modified (Funtion declaration in the `default` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + [...] +---*/ +var init; + +(function() { + var f = 123; + init = f; + + switch (1) { + default: + function f() { } + } + + +}()); + +assert.sameValue(init, 123); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-existing-var-update.js b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-existing-var-update.js new file mode 100644 index 0000000000..ca87f7f957 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-existing-var-update.js @@ -0,0 +1,42 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-existing-var-update.case +// - src/annex-b-fns/func/switch-dflt.template +/*--- +description: Variable-scoped binding is updated following evaluation (Funtion declaration in the `default` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var after; + +(function() { + + + switch (1) { + default: + function f() { return 'function declaration'; } + } + + after = f; + + var f = 123; +}()); + +assert.sameValue(typeof after, 'function'); +assert.sameValue(after(), 'function declaration'); + + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-init.js b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-init.js new file mode 100644 index 0000000000..cab3d64da2 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-init.js @@ -0,0 +1,39 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-init.case +// - src/annex-b-fns/func/switch-dflt.template +/*--- +description: Variable binding is initialized to `undefined` in outer scope (Funtion declaration in the `default` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + a. Perform ! varEnvRec.CreateMutableBinding(F, false). + b. Perform varEnvRec.InitializeBinding(F, undefined). + c. Append F to instantiatedVarNames. + [...] +---*/ +var init, changed; + +(function() { + init = f; + f = 123; + changed = f; + + switch (1) { + default: + function f() { } + } + + +}()); + +assert.sameValue(init, undefined, 'binding is initialized to `undefined`'); +assert.sameValue(changed, 123, 'binding is mutable'); +assert.throws(ReferenceError, function() { + f; +}, 'global binding is not created'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-no-skip-try.js b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-no-skip-try.js new file mode 100644 index 0000000000..93d2811ed0 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-no-skip-try.js @@ -0,0 +1,52 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-no-skip-try.case +// - src/annex-b-fns/func/switch-dflt.template +/*--- +description: Extension is observed when creation of variable binding would not produce an early error (try statement) (Funtion declaration in the `default` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + a. Perform ! varEnvRec.CreateMutableBinding(F, false). + b. Perform varEnvRec.InitializeBinding(F, undefined). + c. Append F to instantiatedVarNames. + [...] + + B.3.5 VariableStatements in Catch Blocks + + [...] + - It is a Syntax Error if any element of the BoundNames of CatchParameter + also occurs in the VarDeclaredNames of Block unless CatchParameter is + CatchParameter:BindingIdentifier and that element is only bound by a + VariableStatement, the VariableDeclarationList of a for statement, or the + ForBinding of a for-in statement. +---*/ + +(function() { + assert.sameValue( + f, undefined, 'Initialized binding created prior to evaluation' + ); + + try { + throw null; + } catch (f) { + + switch (1) { + default: + function f() { return 123; } + } + + } + + assert.sameValue( + typeof f, + 'function', + 'binding value is updated following evaluation' + ); + assert.sameValue(f(), 123); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-skip-dft-param.js b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-skip-dft-param.js new file mode 100644 index 0000000000..e4744d252a --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-skip-dft-param.js @@ -0,0 +1,33 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-dft-param.case +// - src/annex-b-fns/func/switch-dflt.template +/*--- +description: Extension not observed when there is a default parameter with the same name (Funtion declaration in the `default` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ +var init, after; + +(function(f = 123) { + init = f; + + switch (1) { + default: + function f() { } + } + + after = f; +}()); + +assert.sameValue(init, 123, 'binding is not initialized to `undefined`'); +assert.sameValue(after, 123, 'value is not updated following evaluation'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-skip-early-err-block.js b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-skip-early-err-block.js new file mode 100644 index 0000000000..14f8113e92 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-skip-early-err-block.js @@ -0,0 +1,48 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-block.case +// - src/annex-b-fns/func/switch-dflt.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (Block statement) (Funtion declaration in the `default` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + { + let f = 123; + + switch (1) { + default: + function f() { } + } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-skip-early-err-for-in.js b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-skip-early-err-for-in.js new file mode 100644 index 0000000000..0daaf4dbbe --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-skip-early-err-for-in.js @@ -0,0 +1,47 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-for-in.case +// - src/annex-b-fns/func/switch-dflt.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (for-of statement) (Funtion declaration in the `default` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + for (let f in { key: 0 }) { + + switch (1) { + default: + function f() { } + } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-skip-early-err-for-of.js b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-skip-early-err-for-of.js new file mode 100644 index 0000000000..ce5b5d9d3b --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-skip-early-err-for-of.js @@ -0,0 +1,47 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-for-of.case +// - src/annex-b-fns/func/switch-dflt.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (for-of statement) (Funtion declaration in the `default` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + for (let f of [0]) { + + switch (1) { + default: + function f() { } + } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-skip-early-err-for.js b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-skip-early-err-for.js new file mode 100644 index 0000000000..3fce6ca7fe --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-skip-early-err-for.js @@ -0,0 +1,48 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-for.case +// - src/annex-b-fns/func/switch-dflt.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (for statement) (Funtion declaration in the `default` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + for (let f; ; ) { + + switch (1) { + default: + function f() { } + } + + break; + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-skip-early-err-switch.js b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-skip-early-err-switch.js new file mode 100644 index 0000000000..41247388b1 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-skip-early-err-switch.js @@ -0,0 +1,49 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-switch.case +// - src/annex-b-fns/func/switch-dflt.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (switch statement) (Funtion declaration in the `default` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + switch (0) { + default: + let f; + + switch (1) { + default: + function f() { } + } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-skip-early-err-try.js b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-skip-early-err-try.js new file mode 100644 index 0000000000..888accb356 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-skip-early-err-try.js @@ -0,0 +1,59 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err-try.case +// - src/annex-b-fns/func/switch-dflt.template +/*--- +description: Extension is observed when creation of variable binding would not produce an early error (try statement) (Funtion declaration in the `default` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 2. If instantiatedVarNames does not contain F, then + a. Perform ! varEnvRec.CreateMutableBinding(F, false). + b. Perform varEnvRec.InitializeBinding(F, undefined). + c. Append F to instantiatedVarNames. + [...] + + B.3.5 VariableStatements in Catch Blocks + + [...] + - It is a Syntax Error if any element of the BoundNames of CatchParameter + also occurs in the VarDeclaredNames of Block unless CatchParameter is + CatchParameter:BindingIdentifier and that element is only bound by a + VariableStatement, the VariableDeclarationList of a for statement, or the + ForBinding of a for-in statement. +---*/ + +(function() { + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created prior to evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created prior to evaluation' + ); + + try { + throw {}; + } catch ({ f }) { + + switch (1) { + default: + function f() { } + } + + } + + assert.throws(ReferenceError, function() { + f; + }, 'An initialized binding is not created following evaluation'); + assert.sameValue( + typeof f, + 'undefined', + 'An uninitialized binding is not created following evaluation' + ); +}()); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-skip-early-err.js b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-skip-early-err.js new file mode 100644 index 0000000000..e18ab0ad06 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-skip-early-err.js @@ -0,0 +1,34 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-early-err.case +// - src/annex-b-fns/func/switch-dflt.template +/*--- +description: Extension not observed when creation of variable binding would produce an early error (Funtion declaration in the `default` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ +var init, after; + +(function() { + let f = 123; + init = f; + + switch (1) { + default: + function f() { } + } + + after = f; +}()); + +assert.sameValue(init, 123, 'binding is not initialized to `undefined`'); +assert.sameValue(after, 123, 'value is not updated following evaluation'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-skip-param.js b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-skip-param.js new file mode 100644 index 0000000000..cc12b43957 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-skip-param.js @@ -0,0 +1,33 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-skip-param.case +// - src/annex-b-fns/func/switch-dflt.template +/*--- +description: Extension not observed when there is a formal parameter with the same name (Funtion declaration in the `default` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + ii. If replacing the FunctionDeclaration f with a VariableStatement that + has F as a BindingIdentifier would not produce any Early Errors for + func and F is not an element of BoundNames of argumentsList, then + [...] +---*/ +var init, after; + +(function(f) { + init = f; + + switch (1) { + default: + function f() { } + } + + after = f; +}(123)); + +assert.sameValue(init, 123, 'binding is not initialized to `undefined`'); +assert.sameValue(after, 123, 'value is not updated following evaluation'); + +reportCompare(0, 0); diff --git a/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-update.js b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-update.js new file mode 100644 index 0000000000..08ab434109 --- /dev/null +++ b/js/src/tests/test262/annexB/language/function-code/switch-dflt-func-update.js @@ -0,0 +1,39 @@ +// This file was procedurally generated from the following sources: +// - src/annex-b-fns/func-update.case +// - src/annex-b-fns/func/switch-dflt.template +/*--- +description: Variable binding value is updated following evaluation (Funtion declaration in the `default` clause of a `switch` statement in function scope) +esid: sec-web-compat-functiondeclarationinstantiation +flags: [generated, noStrict] +info: | + B.3.3.1 Changes to FunctionDeclarationInstantiation + + [...] + 3. When the FunctionDeclaration f is evaluated, perform the following steps + in place of the FunctionDeclaration Evaluation algorithm provided in + 14.1.21: + a. Let fenv be the running execution context's VariableEnvironment. + b. Let fenvRec be fenv's EnvironmentRecord. + c. Let benv be the running execution context's LexicalEnvironment. + d. Let benvRec be benv's EnvironmentRecord. + e. Let fobj be ! benvRec.GetBindingValue(F, false). + f. Perform ! fenvRec.SetMutableBinding(F, fobj, false). + g. Return NormalCompletion(empty). +---*/ +var after; + +(function() { + + + switch (1) { + default: + function f() { return 'declaration'; } + } + + after = f; +}()); + +assert.sameValue(typeof after, 'function'); +assert.sameValue(after(), 'declaration'); + +reportCompare(0, 0); |