Skip to content

Commit 4336e29

Browse files
committed
[1.8>1.9] [MERGE #4568 @aneeshdk] Fixing usage of arguments inside eval in arrow functions
Merge pull request #4568 from aneeshdk:ArrowEvalArgumentsIssue When an inner arrow function has eval it may end up using arguments symbol. So we have to mark the parent that arguments is in use.
2 parents a0d8bdd + fff4751 commit 4336e29

File tree

2 files changed

+93
-1
lines changed

2 files changed

+93
-1
lines changed

lib/Parser/Parse.cpp

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3787,6 +3787,7 @@ ParseNodePtr Parser::ParsePostfixOperators(
37873787
ReferenceSpecialName(wellKnownPropertyPids._newTarget);
37883788
ReferenceSpecialName(wellKnownPropertyPids._super);
37893789
ReferenceSpecialName(wellKnownPropertyPids._superConstructor);
3790+
ReferenceSpecialName(wellKnownPropertyPids.arguments);
37903791
}
37913792

37923793
pnode->sxCall.callOfConstants = callOfConstants;
@@ -3809,6 +3810,7 @@ ParseNodePtr Parser::ParsePostfixOperators(
38093810
ReferenceSpecialName(wellKnownPropertyPids._newTarget);
38103811
ReferenceSpecialName(wellKnownPropertyPids._super);
38113812
ReferenceSpecialName(wellKnownPropertyPids._superConstructor);
3813+
ReferenceSpecialName(wellKnownPropertyPids.arguments);
38123814
}
38133815
pToken->tk = tkNone; // This is no longer an identifier
38143816
}
@@ -5116,7 +5118,7 @@ ParseNodePtr Parser::ParseFncDecl(ushort flags, LPCOLESTR pNameHint, const bool
51165118
// binding of "arguments. To ensure the arguments object of the enclosing
51175119
// non-lambda function is loaded propagate the UsesArguments flag up to
51185120
// the parent function
5119-
if (fLambda && pnodeFnc->sxFnc.UsesArguments())
5121+
if (fLambda && (pnodeFnc->sxFnc.UsesArguments() || pnodeFnc->sxFnc.CallsEval()))
51205122
{
51215123
ParseNodePtr pnodeFncParent = GetCurrentFunctionNode();
51225124

test/es6/lambda1.js

Lines changed: 90 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -557,6 +557,96 @@ var tests = [
557557
var l = () => await (5)
558558
assert.areEqual('() => await (5)', '' + l, "Regular lambda should also work, though this await looks like a function call");
559559
}
560+
},
561+
{
562+
name: "Accessing arguments symbol in eval inside lambda",
563+
body: function () {
564+
function f1(a) {
565+
b = () => eval("arguments[0]");
566+
assert.areEqual(b(), 1, "Eval should be able to access the arguments symbol");
567+
}
568+
f1(1);
569+
570+
function f2(a) {
571+
b = (x = eval("arguments[0]")) => x;
572+
assert.areEqual(b(), 2, "Eval in param scope should be able to access the arguments symbol")
573+
}
574+
f2(2);
575+
576+
function f3(arguments = [3]) {
577+
b = () => eval("arguments[0]");
578+
assert.areEqual(b(), 3, "Eval should be able to access the arguments param symbol");
579+
}
580+
f3();
581+
582+
function f4() {
583+
var arguments = [4];
584+
b = () => eval("arguments[0]");
585+
assert.areEqual(b(), 4, "Eval should be able to access the arguments from the body");
586+
}
587+
f4(100);
588+
589+
function f5() {
590+
b = () => {
591+
return eval("arguments()");
592+
}
593+
assert.areEqual(b()[0], 5, "Eval should be able to access the arguments function definition from the body");
594+
function arguments() {
595+
return [5];
596+
}
597+
}
598+
f5();
599+
600+
function f6() {
601+
b = () => {
602+
return eval("arguments");
603+
}
604+
assert.areEqual(b()[0], 6, "Eval should be able to access the arguments function definition in block");
605+
606+
{
607+
function arguments() {
608+
return [100];
609+
}
610+
}
611+
}
612+
f6(6);
613+
614+
function f7() {
615+
b = () => eval("arguments[0]");
616+
assert.areEqual(b(), 7, "Eval should be able to access the built-in arguments from the body");
617+
var arguments = [100];
618+
}
619+
f7(7);
620+
621+
function f8() {
622+
b = (arguments = [8]) => eval("arguments");
623+
assert.areEqual(b()[0], 8, "Eval should be able to access the arguments lambda param");
624+
}
625+
f8(100);
626+
627+
function f9() {
628+
b = (arguments = [9], c = eval("arguments")) => c;
629+
assert.areEqual(b()[0], 9, "Eval should be able to access the arguments lambda param in the param scope");
630+
}
631+
f9();
632+
633+
function f10() {
634+
b = () => {
635+
assert.areEqual(eval("arguments"), undefined, "Eval should access arguments from the lambda body itself");
636+
var arguments = 100;
637+
}
638+
}
639+
f10(100);
640+
641+
function f11() {
642+
arguments;
643+
b = () => {
644+
assert.areEqual(eval("arguments"), undefined, "Eval should access arguments from the lambda body itself when the parent function uses arguments");
645+
var arguments = 100;
646+
}
647+
}
648+
f11(100);
649+
}
560650
}
561651
];
562652

0 commit comments

Comments
 (0)