From 38329a703831e2bd12b92b1f175991904c99b34c Mon Sep 17 00:00:00 2001 From: jugglinmike Date: Thu, 21 Apr 2016 15:54:25 -0400 Subject: [PATCH] Add tests for TryStatement binding restrictions (#577) This changeset includes tests for early errors and those generated dynamically by eval. It also accounts for relevant AnnexB extensions. --- .../var-env-lower-lex-catch-non-strict.js | 32 +++++++++++++++++++ .../try/catch-redeclared-for-in-var.js | 28 ++++++++++++++++ .../try/catch-redeclared-for-var.js | 28 ++++++++++++++++ .../var-env-lower-lex-catch-non-strict.js | 21 ++++++++++++ .../statements/try/early-catch-duplicates.js | 14 ++++++++ .../statements/try/early-catch-lex.js | 15 +++++++++ .../statements/try/early-catch-var.js | 19 +++++++++++ 7 files changed, 157 insertions(+) create mode 100644 test/annexB/language/eval-code/direct/var-env-lower-lex-catch-non-strict.js create mode 100644 test/annexB/language/statements/try/catch-redeclared-for-in-var.js create mode 100644 test/annexB/language/statements/try/catch-redeclared-for-var.js create mode 100644 test/language/eval-code/direct/var-env-lower-lex-catch-non-strict.js create mode 100644 test/language/statements/try/early-catch-duplicates.js create mode 100644 test/language/statements/try/early-catch-lex.js create mode 100644 test/language/statements/try/early-catch-var.js diff --git a/test/annexB/language/eval-code/direct/var-env-lower-lex-catch-non-strict.js b/test/annexB/language/eval-code/direct/var-env-lower-lex-catch-non-strict.js new file mode 100644 index 0000000000..a9e16da021 --- /dev/null +++ b/test/annexB/language/eval-code/direct/var-env-lower-lex-catch-non-strict.js @@ -0,0 +1,32 @@ +// 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-variablestatements-in-catch-blocks +es6id: B3.5 +description: Re-declaration of catch parameter +info: > + [...] + + This modified behaviour also applies to var and function declarations + introduced by direct evals contained within the Block of a Catch clause. + This change is accomplished by modify the algorithm of 18.2.1.2 as follows: + + Step 5.d.ii.2.a.i is replaced by: + + i. If thisEnvRec is not the Environment Record for a Catch clause, throw a + SyntaxError exception. + ii. If name is bound by any syntactic form other than a + FunctionDeclaration, a VariableStatement, the VariableDeclarationList + of a for statement, or the ForBinding of a for-in statement, throw a + SyntaxError exception. +flags: [noStrict] +---*/ + +try { + throw null; +} catch (err) { + eval('function err() {}'); + eval('var err;'); + eval('for (var err; false; ) {}'); + eval('for (var err in []) {}'); +} diff --git a/test/annexB/language/statements/try/catch-redeclared-for-in-var.js b/test/annexB/language/statements/try/catch-redeclared-for-in-var.js new file mode 100644 index 0000000000..9c13d145b4 --- /dev/null +++ b/test/annexB/language/statements/try/catch-redeclared-for-in-var.js @@ -0,0 +1,28 @@ +// 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-variablestatements-in-catch-blocks +es6id: B3.5 +description: Re-declaration of catch parameter (for-in statement) +info: > + It is a Syntax Error if any element of the BoundNames of CatchParameter + also occurs in the VarDeclaredNames of Block, unless that element is only + bound by a VariableStatement or the VariableDeclarationList of a for + statement, or the ForBinding of a for-in statement. +---*/ + +var before, during, after; + +try { + throw 'exception'; +} catch (err) { + before = err; + for (var err in { propertyName: null }) { + during = err; + } + after = err; +} + +assert.sameValue(before, 'exception'); +assert.sameValue(during, 'propertyName', 'during loop body evaluation'); +assert.sameValue(after, 'propertyName', 'after loop body evaluation'); diff --git a/test/annexB/language/statements/try/catch-redeclared-for-var.js b/test/annexB/language/statements/try/catch-redeclared-for-var.js new file mode 100644 index 0000000000..68b7e40041 --- /dev/null +++ b/test/annexB/language/statements/try/catch-redeclared-for-var.js @@ -0,0 +1,28 @@ +// 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-variablestatements-in-catch-blocks +es6id: B3.5 +description: Re-declaration of catch parameter (for-in statement) +info: > + It is a Syntax Error if any element of the BoundNames of CatchParameter + also occurs in the VarDeclaredNames of Block, unless that element is only + bound by a VariableStatement or the VariableDeclarationList of a for + statement, or the ForBinding of a for-in statement. +---*/ + +var before, during, after; + +try { + throw 'exception'; +} catch (err) { + before = err; + for (var err = 'loop initializer'; err !== 'increment'; err = 'increment') { + during = err; + } + after = err; +} + +assert.sameValue(before, 'exception'); +assert.sameValue(during, 'loop initializer'); +assert.sameValue(after, 'increment'); diff --git a/test/language/eval-code/direct/var-env-lower-lex-catch-non-strict.js b/test/language/eval-code/direct/var-env-lower-lex-catch-non-strict.js new file mode 100644 index 0000000000..bccdbe5024 --- /dev/null +++ b/test/language/eval-code/direct/var-env-lower-lex-catch-non-strict.js @@ -0,0 +1,21 @@ +// 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-evaldeclarationinstantiation +es6id: 18.2.1.2 +description: Variable collision with lexical binding in lower scope +info: > + Annex B extensions permit re-declarations from FunctionDeclaration, + VariableStatement, the VariableDeclarationList of a for statement, and the + ForBinding of a for-in statement. Bindings from the ForBinding of a for-of + statement are restricted regardless of the application of Annex B. +flags: [noStrict] +---*/ + +assert.throws(SyntaxError, function() { + try { + throw null; + } catch (err) { + eval('for (var err of []) {}'); + } +}); diff --git a/test/language/statements/try/early-catch-duplicates.js b/test/language/statements/try/early-catch-duplicates.js new file mode 100644 index 0000000000..59fedeeafd --- /dev/null +++ b/test/language/statements/try/early-catch-duplicates.js @@ -0,0 +1,14 @@ +// 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-try-statement-static-semantics-early-errors +es6id: 13.15.1 +description: > + It is a Syntax Error if BoundNames of CatchParameter contains any duplicate + elements. +negative: SyntaxError +---*/ + +$ERROR('This code should not be executed.'); + +try { } catch ([x, x]) {} diff --git a/test/language/statements/try/early-catch-lex.js b/test/language/statements/try/early-catch-lex.js new file mode 100644 index 0000000000..e685e3369b --- /dev/null +++ b/test/language/statements/try/early-catch-lex.js @@ -0,0 +1,15 @@ +// 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-try-statement-static-semantics-early-errors +es6id: 13.15.1 +description: > + It is a Syntax Error if any element of the BoundNames of CatchParameter + also occurs in the LexicallyDeclaredNames of Block. +negative: SyntaxError +features: [let] +---*/ + +$ERROR('This code should not be executed.'); + +try { } catch (x) { let x; } diff --git a/test/language/statements/try/early-catch-var.js b/test/language/statements/try/early-catch-var.js new file mode 100644 index 0000000000..51d772c12d --- /dev/null +++ b/test/language/statements/try/early-catch-var.js @@ -0,0 +1,19 @@ +// 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-try-statement-static-semantics-early-errors +es6id: 13.15.1 +description: > + It is a Syntax Error if any element of the BoundNames of CatchParameter + also occurs in the VarDeclaredNames of Block. +info: > + Annex B extensions permit re-declarations from VariableStatement, the + VariableDeclarationList of a for statement, and the ForBinding of a for-of + statement. Bindings from the ForBinding of a for-in statement are + restricted regardless of the application of Annex B. +negative: SyntaxError +---*/ + +$ERROR('This code should not be executed.'); + +try { } catch (x) { for (var x of []) {} }