From 8bd1aa817cc25a9c3b05a888de2ccd8175bedd75 Mon Sep 17 00:00:00 2001 From: Ron Buckton Date: Tue, 26 Sep 2023 02:53:32 -0400 Subject: [PATCH 1/7] Use early error to avoid ASI for +,-,/, and /= --- spec.emu | 124 ++++++++++++++++++++++++++++++++++++++++++++++++++----- 1 file changed, 113 insertions(+), 11 deletions(-) diff --git a/spec.emu b/spec.emu index 35f5ab1..256ece3 100644 --- a/spec.emu +++ b/spec.emu @@ -351,23 +351,125 @@ contributors: Ron Buckton, Ecma International [+Await] AwaitExpression[?Yield] - ThrowExpressionInvalidPunctuator : one of `,` `<` `>` `<=` `>=` `==` `!=` `===` `!==` `+` `-` `*` `/` `%` `**` `<<` `>>` `>>>` `&` `|` `^` `&&` `||` `??` `=` `+=` `-=` `*=` `/=` `%=` `**=` `<<=` `>>=` `>>>=` `&=` `|=` `^=` `&&=` `||=` `??=` `?` + ThrowExpressionInvalidPunctuator : one of `,` `<` `>` `<=` `>=` `==` `!=` `===` `!==` `*` `%` `**` `<<` `>>` `>>>` `&` `|` `^` `&&` `||` `??` `=` `+=` `-=` `*=` `%=` `**=` `<<=` `>>=` `>>>=` `&=` `|=` `^=` `&&=` `||=` `??=` `?` + + +

The `throw` Operator

+ +

Runtime Semantics: Evaluation

+ UnaryExpression : `throw` UnaryExpression + + 1. Let _exprRef_ be ? Evaluation of |UnaryExpression|. + 1. Let _exprValue_ be ? GetValue(_exprRef_). + 1. Return ThrowCompletion(_exprValue_). + +
+
- -

The `throw` Operator

- -

Runtime Semantics: Evaluation

- UnaryExpression : `throw` UnaryExpression - - 1. Let _exprRef_ be ? Evaluation of |UnaryExpression|. - 1. Let _exprValue_ be ? GetValue(_exprRef_). - 1. Return ThrowCompletion(_exprValue_). - + + +

Multiplicative Operators

+ +

Static Semantics

+ +

Static Semantics: Early Errors

+ + MultiplicativeExpression : + MultiplicativeExpression MultiplicativeOperator ExponentiationExpression + +
    +
  • + It is a Syntax Error if the derived |MultiplicativeExpression| is UnaryExpression : `throw` UnaryExpression and the source text matched by |MultiplicativeOperator| is `/`. +
  • +
+ +

This production exists in order to prevent automatic semicolon insertion rules () from being applied to the following code:

+

+            a ?? throw b
+            /c/d
+          
+

so that it would be interpreted as two valid statements. The purpose is to maintain consistency with similar code using |ThrowStatement|:

+

+            throw b
+            /c/d
+          
+

which is a valid statement and where automatic semicolon insertion does not apply.

+
+
+
+
+ + +

Additive Operators

+ +

Static Semantics

+ +

Static Semantics: Early Errors

+ + AdditiveExpression : + AdditiveExpression `+` MultiplicativeExpression + AdditiveExpression `-` MultiplicativeExpression + +
    +
  • + It is a Syntax Error if the derived |AdditiveExpression| is UnaryExpression : `throw` UnaryExpression. +
  • +
+ +

This production exists in order to prevent automatic semicolon insertion rules () from being applied to the following code:

+

+            a ?? throw b
+            + c
+          
+

so that it would be interpreted as two valid statements. The purpose is to maintain consistency with similar code using |ThrowStatement|:

+

+            throw b
+            + c
+          
+

which is a valid statement and where automatic semicolon insertion does not apply.

+
+
+ + +

Assignment Operators

+ +

Static Semantics

+ +

Static Semantics: Early Errors

+ + AssignmentExpression : + LeftHandSideExpression `/=` AssignmentExpression + +
    +
  • + It is a Syntax Error if the derived |LeftHandSideExpression| is UnaryExpression : `throw` UnaryExpression. +
  • +
+ +

This production exists in order to prevent automatic semicolon insertion rules () from being applied to the following code:

+

+            a ?? throw b
+            /= c / d
+          
+

so that it would be interpreted as two valid statements. The purpose is to maintain consistency with similar code using |ThrowStatement|:

+

+            throw b
+            /= c / d
+          
+

which is a valid statement and where automatic semicolon insertion does not apply.

+
+
+
+ +
+ + +
From f0c47ab724dff786668e50760b25dca2b797ad80 Mon Sep 17 00:00:00 2001 From: Ron Buckton Date: Tue, 26 Sep 2023 03:58:48 -0400 Subject: [PATCH 2/7] Add SDO for better detection of 'throw' expressions --- spec.emu | 204 ++++++++++++++++++++++++++++++++++++++++++++++++++++--- 1 file changed, 196 insertions(+), 8 deletions(-) diff --git a/spec.emu b/spec.emu index 256ece3..c63bfaa 100644 --- a/spec.emu +++ b/spec.emu @@ -328,6 +328,199 @@ contributors: Ron Buckton, Ecma International 1. Return ~invalid~. + + +

Static Semantics: ContainsThrowOnRight ( ): a Boolean

+
+
+ + UpdateExpression : + LeftHandSideExpression + LeftHandSideExpression `++` + LeftHandSideExpression `--` + + + 1. Return *false*. + + + UpdateExpression : + `++` UnaryExpression + `--` UnaryExpression + + + 1. If ContainsThrowOnRight of |UnaryExpression| is *true*, return *true* + 1. Return *false*. + + AwaitExpression : `await` UnaryExpression + + 1. If ContainsThrowOnRight of |UnaryExpression| is *true*, return *true* + 1. Return *false*. + + + UnaryExpression : + `delete` UnaryExpression + `void` UnaryExpression + `typeof` UnaryExpression + `+` UnaryExpression + `-` UnaryExpression + `~` UnaryExpression + `!` UnaryExpression + + + 1. If ContainsThrowOnRight of |UnaryExpression| is *true*, return *true* + 1. Return *false*. + + UnaryExpression : `throw` UnaryExpression + + 1. Return *true*. + + ExponentiationExpression : UpdateExpression `**` ExponentiationExpression + + 1. If ContainsThrowOnRight of |ExponentationExpression| is *true*, return *true* + 1. Return *false*. + + + AdditiveExpression : + AdditiveExpression `+` MultiplicativeExpression + AdditiveExpression `-` MultiplicativeExpression + + + 1. If ContainsThrowOnRight of |MultiplicativeExpression| is *true*, return *true* + 1. Return *false*. + + + ShiftExpression : + ShiftExpression `<<` AdditiveExpression + ShiftExpression `>>` AdditiveExpression + ShiftExpression `>>>` AdditiveExpression + + + 1. If ContainsThrowOnRight of |AdditiveExpression| is *true*, return *true* + 1. Return *false*. + + + RelationalExpression : + RelationalExpression `<` ShiftExpression + RelationalExpression `>` ShiftExpression + RelationalExpression `<=` ShiftExpression + RelationalExpression `>=` ShiftExpression + RelationalExpression `instanceof` ShiftExpression + RelationalExpression `in` ShiftExpression + PrivateIdentifier `in` ShiftExpression + + + 1. If ContainsThrowOnRight of |ShiftExpression| is *true*, return *true*. + 1. Return *false*. + + + EqualityExpression : + EqualityExpression `==` RelationalExpression + EqualityExpression `!=` RelationalExpression + EqualityExpression `===` RelationalExpression + EqualityExpression `!==` RelationalExpression + + + 1. If ContainsThrowOnRight of |RelationalExpression| is *true*, return *true* + 1. Return *false*. + + BitwiseANDExpression : BitwiseANDExpression `&` EqualityExpression + + 1. If ContainsThrowOnRight of |EqualityExpression| is *true*, return *true*. + 1. Return *false*. + + BitwiseXORExpression : BitwiseXORExpression `^` BitwiseANDExpression + + 1. If ContainsThrowOnRight of |BitwiseANDExpression| is *true*, return *true*. + 1. Return *false*. + + BitwiseORExpression : BitwiseORExpression `^` BitwiseXORExpression + + 1. If ContainsThrowOnRight of |BitwiseXORExpression| is *true*, return *true*. + 1. Return *false*. + + LogicalANDExpression : LogicalANDExpression `&&` BitwiseORExpression + + 1. If ContainsThrowOnRight of |BitwiseORExpression| is *true*, return *true*. + 1. Return *false*. + + LogicalORExpression : LogicalORExpression `||` LogicalANDExpression + + 1. If ContainsThrowOnRight of |LogicalANDExpression| is *true*, return *true*. + 1. Return *false*. + + CoalesceExpression : CoalesceExpressionHead `??` BitwiseORExpression + + 1. If ContainsThrowOnRight of |BitwiseORExpression| is *true*, return *true*. + 1. Return *false*. + + ConditionalExpression : ShortCircuitExpression `?` AssignmentExpression `:` AssignmentExpression + + 1. If ContainsThrowOnRight of |AssignmentExpression| is *true*, return *true*. + 1. Return *false*. + + + AssignmentExpression : + LeftHandSideExpression `=` AssignmentExpression + LeftHandSideExpression AssignmentOperator AssignmentExpression + LeftHandSideExpression `&&=` AssignmentExpression + LeftHandSideExpression `||=` AssignmentExpression + LeftHandSideExpression `??=` AssignmentExpression + + + 1. If ContainsThrowOnRight of |AssignmentExpression| is *true*, return *true* + 1. Return *false*. + + + YieldExpression : + `yield` AssignmentExpression + `yield` `*` AssignmentExpression + + + 1. If ContainsThrowOnRight of |AssignmentExpression| is *true*, return *true* + 1. Return *false*. + + YieldExpression : `yield` + + 1. Return *false*. + + ArrowFunction : ArrowParameters `=>` ConciseBody + + 1. If ContainsThrowOnRight of |ConciseBody| is *true*, return *true* + 1. Return *false*. + + ConciseBody : ExpressionBody + + 1. If ContainsThrowOnRight of |ExpressionBody| is *true*, return *true* + 1. Return *false*. + + ConciseBody : `{` FunctionBody `}` + + 1. Return *false*. + + + AsyncArrowFunction : + `async` AsyncArrowBindingIdentifier `=>` AsyncConciseBody + CoverCallExpressionAndAsyncArrowHead `=>` AsyncConciseBody + + + 1. If ContainsThrowOnRight of |AsyncConciseBody| is *true*, return *true* + 1. Return *false*. + + AsyncConciseBody : ExpressionBody + + 1. If ContainsThrowOnRight of |ExpressionBody| is *true*, return *true* + 1. Return *false*. + + AsyncConciseBody : `{` AsyncFunctionBody `}` + + 1. Return *false*. + + Expression : Expression `,` AssignmentExpression + + 1. If ContainsThrowOnRight of |AssignmentExpression| is *true*, return *true* + 1. Return *false*. + +
@@ -369,7 +562,6 @@ contributors: Ron Buckton, Ecma International -

Multiplicative Operators

@@ -382,7 +574,7 @@ contributors: Ron Buckton, Ecma International
  • - It is a Syntax Error if the derived |MultiplicativeExpression| is UnaryExpression : `throw` UnaryExpression and the source text matched by |MultiplicativeOperator| is `/`. + It is a Syntax Error if ContainsThrowOnRight of |MultiplicativeExpression| is *true*.
@@ -415,7 +607,7 @@ contributors: Ron Buckton, Ecma International
  • - It is a Syntax Error if the derived |AdditiveExpression| is UnaryExpression : `throw` UnaryExpression. + It is a Syntax Error if ContainsThrowOnRight of |AdditiveExpression| is *true*.
@@ -447,7 +639,7 @@ contributors: Ron Buckton, Ecma International
  • - It is a Syntax Error if the derived |LeftHandSideExpression| is UnaryExpression : `throw` UnaryExpression. + It is a Syntax Error if ContainsThrowOnRight of |LeftHandSideExpression| is *true*.
@@ -465,10 +657,6 @@ contributors: Ron Buckton, Ecma International
- - - - From 631be2774e7997c5d8429cbe1bd4b33ea7b5fe58 Mon Sep 17 00:00:00 2001 From: Ron Buckton Date: Tue, 26 Sep 2023 04:14:41 -0400 Subject: [PATCH 3/7] Unban assignment operators as the grammar already forbids them --- spec.emu | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/spec.emu b/spec.emu index c63bfaa..86b727b 100644 --- a/spec.emu +++ b/spec.emu @@ -544,7 +544,7 @@ contributors: Ron Buckton, Ecma International [+Await] AwaitExpression[?Yield] - ThrowExpressionInvalidPunctuator : one of `,` `<` `>` `<=` `>=` `==` `!=` `===` `!==` `*` `%` `**` `<<` `>>` `>>>` `&` `|` `^` `&&` `||` `??` `=` `+=` `-=` `*=` `%=` `**=` `<<=` `>>=` `>>>=` `&=` `|=` `^=` `&&=` `||=` `??=` `?` + ThrowExpressionInvalidPunctuator : one of `,` `<` `>` `<=` `>=` `==` `!=` `===` `!==` `*` `%` `**` `<<` `>>` `>>>` `&` `|` `^` `&&` `||` `??` `?` From c8fb40c511b215f299e4c7213982b229edc4b72d Mon Sep 17 00:00:00 2001 From: Ron Buckton Date: Tue, 26 Sep 2023 04:17:14 -0400 Subject: [PATCH 4/7] Add ins markers around new sections --- spec.emu | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/spec.emu b/spec.emu index 86b727b..7b26c77 100644 --- a/spec.emu +++ b/spec.emu @@ -329,6 +329,7 @@ contributors: Ron Buckton, Ecma International +

Static Semantics: ContainsThrowOnRight ( ): a Boolean

@@ -521,6 +522,7 @@ contributors: Ron Buckton, Ecma International 1. Return *false*. + @@ -564,6 +566,7 @@ contributors: Ron Buckton, Ecma International

Multiplicative Operators

+

Static Semantics

@@ -592,10 +595,12 @@ contributors: Ron Buckton, Ecma International
+

Additive Operators

+

Static Semantics

@@ -625,10 +630,12 @@ contributors: Ron Buckton, Ecma International
+

Assignment Operators

+

Static Semantics

@@ -657,6 +664,7 @@ contributors: Ron Buckton, Ecma International
+
From fd58f0dc9e302908885184d5b415d7903d0664c2 Mon Sep 17 00:00:00 2001 From: Ron Buckton Date: Tue, 26 Sep 2023 20:48:57 -0400 Subject: [PATCH 5/7] Clean up 'ContainsThrowOnRight' and add EE for '/=' in AssignmentExpression --- spec.emu | 227 ++++++++++++++----------------------------------------- 1 file changed, 58 insertions(+), 169 deletions(-) diff --git a/spec.emu b/spec.emu index 7b26c77..38f8b44 100644 --- a/spec.emu +++ b/spec.emu @@ -69,12 +69,12 @@ contributors: Ron Buckton, Ecma International `delete` UnaryExpression `void` UnaryExpression `typeof` UnaryExpression - `throw` UnaryExpression `+` UnaryExpression `-` UnaryExpression `~` UnaryExpression `!` UnaryExpression AwaitExpression + ThrowExpression ExponentiationExpression : UpdateExpression `**` ExponentiationExpression @@ -253,12 +253,12 @@ contributors: Ron Buckton, Ecma International `delete` UnaryExpression `void` UnaryExpression `typeof` UnaryExpression - `throw` UnaryExpression `+` UnaryExpression `-` UnaryExpression `~` UnaryExpression `!` UnaryExpression AwaitExpression + ThrowExpression ExponentiationExpression : UpdateExpression `**` ExponentiationExpression @@ -334,6 +334,10 @@ contributors: Ron Buckton, Ecma International

Static Semantics: ContainsThrowOnRight ( ): a Boolean

+ ThrowExpression : `throw` UnaryExpression + + 1. Return *true*. + UpdateExpression : LeftHandSideExpression @@ -347,17 +351,7 @@ contributors: Ron Buckton, Ecma International UpdateExpression : `++` UnaryExpression `--` UnaryExpression - - - 1. If ContainsThrowOnRight of |UnaryExpression| is *true*, return *true* - 1. Return *false*. - - AwaitExpression : `await` UnaryExpression - - 1. If ContainsThrowOnRight of |UnaryExpression| is *true*, return *true* - 1. Return *false*. - - + UnaryExpression : `delete` UnaryExpression `void` UnaryExpression @@ -366,19 +360,22 @@ contributors: Ron Buckton, Ecma International `-` UnaryExpression `~` UnaryExpression `!` UnaryExpression + + AwaitExpression : + `await` UnaryExpression - 1. If ContainsThrowOnRight of |UnaryExpression| is *true*, return *true* - 1. Return *false*. + 1. Return ContainsThrowOnRight of |UnaryExpression|. - UnaryExpression : `throw` UnaryExpression - - 1. Return *true*. - - ExponentiationExpression : UpdateExpression `**` ExponentiationExpression + + ExponentiationExpression : + UpdateExpression `**` ExponentiationExpression + + MultiplicativeExpression : + MultiplicativeExpression MultiplicativeOperator ExponentiationExpression + - 1. If ContainsThrowOnRight of |ExponentationExpression| is *true*, return *true* - 1. Return *false*. + 1. Return ContainsThrowOnRight of |ExponentiationExpression|. AdditiveExpression : @@ -386,140 +383,7 @@ contributors: Ron Buckton, Ecma International AdditiveExpression `-` MultiplicativeExpression - 1. If ContainsThrowOnRight of |MultiplicativeExpression| is *true*, return *true* - 1. Return *false*. - - - ShiftExpression : - ShiftExpression `<<` AdditiveExpression - ShiftExpression `>>` AdditiveExpression - ShiftExpression `>>>` AdditiveExpression - - - 1. If ContainsThrowOnRight of |AdditiveExpression| is *true*, return *true* - 1. Return *false*. - - - RelationalExpression : - RelationalExpression `<` ShiftExpression - RelationalExpression `>` ShiftExpression - RelationalExpression `<=` ShiftExpression - RelationalExpression `>=` ShiftExpression - RelationalExpression `instanceof` ShiftExpression - RelationalExpression `in` ShiftExpression - PrivateIdentifier `in` ShiftExpression - - - 1. If ContainsThrowOnRight of |ShiftExpression| is *true*, return *true*. - 1. Return *false*. - - - EqualityExpression : - EqualityExpression `==` RelationalExpression - EqualityExpression `!=` RelationalExpression - EqualityExpression `===` RelationalExpression - EqualityExpression `!==` RelationalExpression - - - 1. If ContainsThrowOnRight of |RelationalExpression| is *true*, return *true* - 1. Return *false*. - - BitwiseANDExpression : BitwiseANDExpression `&` EqualityExpression - - 1. If ContainsThrowOnRight of |EqualityExpression| is *true*, return *true*. - 1. Return *false*. - - BitwiseXORExpression : BitwiseXORExpression `^` BitwiseANDExpression - - 1. If ContainsThrowOnRight of |BitwiseANDExpression| is *true*, return *true*. - 1. Return *false*. - - BitwiseORExpression : BitwiseORExpression `^` BitwiseXORExpression - - 1. If ContainsThrowOnRight of |BitwiseXORExpression| is *true*, return *true*. - 1. Return *false*. - - LogicalANDExpression : LogicalANDExpression `&&` BitwiseORExpression - - 1. If ContainsThrowOnRight of |BitwiseORExpression| is *true*, return *true*. - 1. Return *false*. - - LogicalORExpression : LogicalORExpression `||` LogicalANDExpression - - 1. If ContainsThrowOnRight of |LogicalANDExpression| is *true*, return *true*. - 1. Return *false*. - - CoalesceExpression : CoalesceExpressionHead `??` BitwiseORExpression - - 1. If ContainsThrowOnRight of |BitwiseORExpression| is *true*, return *true*. - 1. Return *false*. - - ConditionalExpression : ShortCircuitExpression `?` AssignmentExpression `:` AssignmentExpression - - 1. If ContainsThrowOnRight of |AssignmentExpression| is *true*, return *true*. - 1. Return *false*. - - - AssignmentExpression : - LeftHandSideExpression `=` AssignmentExpression - LeftHandSideExpression AssignmentOperator AssignmentExpression - LeftHandSideExpression `&&=` AssignmentExpression - LeftHandSideExpression `||=` AssignmentExpression - LeftHandSideExpression `??=` AssignmentExpression - - - 1. If ContainsThrowOnRight of |AssignmentExpression| is *true*, return *true* - 1. Return *false*. - - - YieldExpression : - `yield` AssignmentExpression - `yield` `*` AssignmentExpression - - - 1. If ContainsThrowOnRight of |AssignmentExpression| is *true*, return *true* - 1. Return *false*. - - YieldExpression : `yield` - - 1. Return *false*. - - ArrowFunction : ArrowParameters `=>` ConciseBody - - 1. If ContainsThrowOnRight of |ConciseBody| is *true*, return *true* - 1. Return *false*. - - ConciseBody : ExpressionBody - - 1. If ContainsThrowOnRight of |ExpressionBody| is *true*, return *true* - 1. Return *false*. - - ConciseBody : `{` FunctionBody `}` - - 1. Return *false*. - - - AsyncArrowFunction : - `async` AsyncArrowBindingIdentifier `=>` AsyncConciseBody - CoverCallExpressionAndAsyncArrowHead `=>` AsyncConciseBody - - - 1. If ContainsThrowOnRight of |AsyncConciseBody| is *true*, return *true* - 1. Return *false*. - - AsyncConciseBody : ExpressionBody - - 1. If ContainsThrowOnRight of |ExpressionBody| is *true*, return *true* - 1. Return *false*. - - AsyncConciseBody : `{` AsyncFunctionBody `}` - - 1. Return *false*. - - Expression : Expression `,` AssignmentExpression - - 1. If ContainsThrowOnRight of |AssignmentExpression| is *true*, return *true* - 1. Return *false*. + 1. Return ContainsThrowOnRight of |MultiplicativeExpression|. @@ -538,23 +402,28 @@ contributors: Ron Buckton, Ecma International `delete` UnaryExpression[?Yield, ?Await] `void` UnaryExpression[?Yield, ?Await] `typeof` UnaryExpression[?Yield, ?Await] - `throw` UnaryExpression[?Yield, ?Await] [lookahead ∉ ThrowExpressionInvalidPunctuator] `+` UnaryExpression[?Yield, ?Await] `-` UnaryExpression[?Yield, ?Await] `~` UnaryExpression[?Yield, ?Await] `!` UnaryExpression[?Yield, ?Await] [+Await] AwaitExpression[?Yield] - - - ThrowExpressionInvalidPunctuator : one of `,` `<` `>` `<=` `>=` `==` `!=` `===` `!==` `*` `%` `**` `<<` `>>` `>>>` `&` `|` `^` `&&` `||` `??` `?` - + ThrowExpression[?Yield, ?Await] +

The `throw` Operator

+

Syntax

+ + ThrowExpression[Yield, Await] : + `throw` UnaryExpression[?Yield, ?Await] [lookahead ∉ ThrowExpressionInvalidPunctuator] + + ThrowExpressionInvalidPunctuator : one of `,` `<` `>` `<=` `>=` `==` `!=` `===` `!==` `*` `%` `**` `<<` `>>` `>>>` `&` `|` `^` `&&` `||` `??` `?` + +

Runtime Semantics: Evaluation

- UnaryExpression : `throw` UnaryExpression + ThrowExpression : `throw` UnaryExpression 1. Let _exprRef_ be ? Evaluation of |UnaryExpression|. 1. Let _exprValue_ be ? GetValue(_exprRef_). @@ -562,14 +431,15 @@ contributors: Ron Buckton, Ecma International
+

Multiplicative Operators

- +

Static Semantics

- +

Static Semantics: Early Errors

MultiplicativeExpression : @@ -601,9 +471,9 @@ contributors: Ron Buckton, Ecma International

Additive Operators

- +

Static Semantics

- +

Static Semantics: Early Errors

AdditiveExpression : @@ -635,6 +505,25 @@ contributors: Ron Buckton, Ecma International

Assignment Operators

+

Syntax

+ + AssignmentExpression[In, Yield, Await] : + ConditionalExpression[?In, ?Yield, ?Await] + [+Yield] YieldExpression[?In, ?Await] + ArrowFunction[?In, ?Yield, ?Await] + AsyncArrowFunction[?In, ?Yield, ?Await] + LeftHandSideExpression[?Yield, ?Await] `=` AssignmentExpression[?In, ?Yield, ?Await] #assignment + LeftHandSideExpression[?Yield, ?Await] AssignmentOperator AssignmentExpression[?In, ?Yield, ?Await] + LeftHandSideExpression[?Yield, ?Await] `&&=` AssignmentExpression[?In, ?Yield, ?Await] + LeftHandSideExpression[?Yield, ?Await] `||=` AssignmentExpression[?In, ?Yield, ?Await] + LeftHandSideExpression[?Yield, ?Await] `??=` AssignmentExpression[?In, ?Yield, ?Await] + ThrowExpression[?Yield, ?Await] `/=` AssignmentExpression[?In, ?Yield, ?Await] + + // emu-format ignore + AssignmentOperator : one of + `*=` `/=` `%=` `+=` `-=` `<<=` `>>=` `>>>=` `&=` `^=` `|=` `**=` + +

Static Semantics

@@ -642,17 +531,17 @@ contributors: Ron Buckton, Ecma International

Static Semantics: Early Errors

AssignmentExpression : - LeftHandSideExpression `/=` AssignmentExpression + ThrowExpression `/=` AssignmentExpression
  • - It is a Syntax Error if ContainsThrowOnRight of |LeftHandSideExpression| is *true*. + It is a Syntax Error if any source text is matched by this production.

This production exists in order to prevent automatic semicolon insertion rules () from being applied to the following code:


-            a ?? throw b
+            a = throw b
             /= c / d
           

so that it would be interpreted as two valid statements. The purpose is to maintain consistency with similar code using |ThrowStatement|:

From c284d1607888a47a81b40b43e68cda2964122161 Mon Sep 17 00:00:00 2001 From: Ron Buckton Date: Wed, 27 Sep 2023 04:03:34 -0400 Subject: [PATCH 6/7] Remove unneeded grammar/steps from ContainsThrowOnRight --- spec.emu | 20 -------------------- 1 file changed, 20 deletions(-) diff --git a/spec.emu b/spec.emu index 38f8b44..5af8ba2 100644 --- a/spec.emu +++ b/spec.emu @@ -347,26 +347,6 @@ contributors: Ron Buckton, Ecma International 1. Return *false*. - - UpdateExpression : - `++` UnaryExpression - `--` UnaryExpression - - UnaryExpression : - `delete` UnaryExpression - `void` UnaryExpression - `typeof` UnaryExpression - `+` UnaryExpression - `-` UnaryExpression - `~` UnaryExpression - `!` UnaryExpression - - AwaitExpression : - `await` UnaryExpression - - - 1. Return ContainsThrowOnRight of |UnaryExpression|. - ExponentiationExpression : UpdateExpression `**` ExponentiationExpression From 8b9a910167439e289d5d6d48f40165309bb2d9fd Mon Sep 17 00:00:00 2001 From: Ron Buckton Date: Wed, 27 Sep 2023 15:17:27 -0400 Subject: [PATCH 7/7] Add '/' check for static semantics rule in MultiplicativeExpression --- spec.emu | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/spec.emu b/spec.emu index 5af8ba2..672f3e6 100644 --- a/spec.emu +++ b/spec.emu @@ -427,7 +427,7 @@ contributors: Ron Buckton, Ecma International
  • - It is a Syntax Error if ContainsThrowOnRight of |MultiplicativeExpression| is *true*. + It is a Syntax Error if the source text matched by |MultiplicativeOperator| is `/` and ContainsThrowOnRight of |MultiplicativeExpression| is *true*.