Skip to content

Commit 51f9783

Browse files
committed
[GR-40878] Avoid appending a statement for an always-true delete expression.
PullRequest: js/2582
2 parents 75ee19a + cb9e680 commit 51f9783

File tree

3 files changed

+44
-8
lines changed

3 files changed

+44
-8
lines changed

graal-js/src/com.oracle.js.parser/src/com/oracle/js/parser/Parser.java

Lines changed: 4 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -117,7 +117,6 @@
117117
import java.util.Map;
118118
import java.util.function.Consumer;
119119

120-
import com.oracle.js.parser.ir.ClassElement;
121120
import org.graalvm.collections.Pair;
122121

123122
import com.oracle.js.parser.ir.AccessNode;
@@ -129,6 +128,7 @@
129128
import com.oracle.js.parser.ir.CallNode;
130129
import com.oracle.js.parser.ir.CaseNode;
131130
import com.oracle.js.parser.ir.CatchNode;
131+
import com.oracle.js.parser.ir.ClassElement;
132132
import com.oracle.js.parser.ir.ClassNode;
133133
import com.oracle.js.parser.ir.ContinueNode;
134134
import com.oracle.js.parser.ir.DebuggerNode;
@@ -5848,7 +5848,6 @@ private ParserException invalidLHSError(final Expression lhs) {
58485848
* @return Expression node.
58495849
*/
58505850
private Expression unaryExpression(boolean yield, boolean await, CoverExpressionError coverExpression) {
5851-
final int unaryLine = line;
58525851
final long unaryToken = token;
58535852

58545853
switch (type) {
@@ -5860,7 +5859,7 @@ private Expression unaryExpression(boolean yield, boolean await, CoverExpression
58605859
throw error(AbstractParser.message(MSG_UNEXPECTED_TOKEN, type.getNameOrType()));
58615860
}
58625861

5863-
return verifyDeleteExpression(unaryLine, unaryToken, expr);
5862+
return verifyDeleteExpression(unaryToken, expr);
58645863
}
58655864
case VOID:
58665865
case TYPEOF:
@@ -5913,7 +5912,7 @@ private Expression unaryExpression(boolean yield, boolean await, CoverExpression
59135912
return expression;
59145913
}
59155914

5916-
private Expression verifyDeleteExpression(final int unaryLine, final long unaryToken, final Expression expr) {
5915+
private Expression verifyDeleteExpression(final long unaryToken, final Expression expr) {
59175916
if (expr instanceof BaseNode || expr instanceof IdentNode) {
59185917
if (isStrictMode) {
59195918
if (expr instanceof IdentNode) {
@@ -5925,10 +5924,8 @@ private Expression verifyDeleteExpression(final int unaryLine, final long unaryT
59255924
throw error(AbstractParser.message(MSG_STRICT_CANT_DELETE_PRIVATE), unaryToken);
59265925
}
59275926
}
5928-
return new UnaryNode(unaryToken, expr);
59295927
}
5930-
appendStatement(new ExpressionStatement(unaryLine, unaryToken, finish, expr));
5931-
return LiteralNode.newInstance(unaryToken, finish, true);
5928+
return new UnaryNode(unaryToken, expr);
59325929
}
59335930

59345931
private Expression verifyIncDecExpression(final long unaryToken, final TokenType opType, final Expression lhs, final boolean isPostfix) {

graal-js/src/com.oracle.truffle.js.parser/src/com/oracle/truffle/js/parser/GraalJSTranslator.java

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2492,7 +2492,11 @@ private JavaScriptNode enterDeleteIdent(UnaryNode unaryNode) {
24922492
result = varRef.createDeleteNode();
24932493
} else {
24942494
// deleting a non-reference, always returns true
2495-
result = factory.createDual(context, transform(rhs), factory.createConstantBoolean(true));
2495+
if (rhs instanceof LiteralNode.PrimitiveLiteralNode<?>) {
2496+
result = factory.createConstantBoolean(true);
2497+
} else {
2498+
result = factory.createDual(context, transform(rhs), factory.createConstantBoolean(true));
2499+
}
24962500
}
24972501
return tagExpression(result, unaryNode);
24982502
}
Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
/*
2+
* Copyright (c) 2022, 2022, Oracle and/or its affiliates. All rights reserved.
3+
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4+
*
5+
* Licensed under the Universal Permissive License v 1.0 as shown at http://oss.oracle.com/licenses/upl.
6+
*/
7+
8+
/**
9+
* Verify correct parsing of a for-in statement with an always-true delete expression as (an invalid) lhs expr.
10+
*/
11+
12+
load("assert.js");
13+
14+
assertThrows(() => eval('for(x = delete 0 in "") {}'), SyntaxError); // Invalid left side value of for..in loop
15+
assertThrows(() => eval('for(x = delete 0 of "") {}'), SyntaxError); // Invalid left side value of for..of loop
16+
assertThrows(() => eval('(async function() { for await(x = delete 0 of "") {}})'), SyntaxError);
17+
18+
eval('for(var x = delete (Math.max([[1]], -14)) in new Array(4)) { this.v2 = x; }');
19+
assertThrows(() => eval('for(let x = delete (Math.max([[1]], -14)) in new Array(4)) { this.v2 = x; }'));
20+
eval('for(x = delete 0; !delete true; x = delete "") {}');
21+
22+
assertThrows(() => eval(`
23+
(async function() {
24+
for await(let b of async function(y) {
25+
"use strict";
26+
o0.a1[({
27+
valueOf: function() {
28+
for(x = delete "" in /x/g ) for (let i = 0; i < 999; i++) {}
29+
return 9;
30+
}
31+
})];
32+
}) for await(let a of /*MARR*/[null]) throw e;
33+
eval.message;
34+
})`
35+
), SyntaxError);

0 commit comments

Comments
 (0)