From b3e3959d14814f42ee2197c504c322bcbe12347d Mon Sep 17 00:00:00 2001 From: Aneesh Divakarakurup Date: Wed, 6 Sep 2017 15:29:25 -0700 Subject: [PATCH] [CVE-2017-11767] Do not instantiate param scope if only the function expression symbol is captured If a split scope happens because of the function expression being captured then the param scope may not have any locals in closure as the function expression symbol belongs to the function expression scope. In this case we don't have to instantiate the param scope in split scope. --- lib/Runtime/ByteCode/ByteCodeEmitter.cpp | 15 ++++++++++++++- test/es6/default-splitscope.js | 8 ++++++++ 2 files changed, 22 insertions(+), 1 deletion(-) diff --git a/lib/Runtime/ByteCode/ByteCodeEmitter.cpp b/lib/Runtime/ByteCode/ByteCodeEmitter.cpp index b52b157ebe9..4f7ed55b5fa 100644 --- a/lib/Runtime/ByteCode/ByteCodeEmitter.cpp +++ b/lib/Runtime/ByteCode/ByteCodeEmitter.cpp @@ -4219,7 +4219,20 @@ void ByteCodeGenerator::StartEmitFunction(ParseNode *pnodeFnc) { bodyScope->SetMustInstantiate(funcInfo->frameSlotsRegister != Js::Constants::NoRegister); } - paramScope->SetMustInstantiate(!pnodeFnc->sxFnc.IsBodyAndParamScopeMerged()); + + if (!pnodeFnc->sxFnc.IsBodyAndParamScopeMerged()) + { + if (funcInfo->frameObjRegister != Js::Constants::NoRegister) + { + paramScope->SetMustInstantiate(true); + } + else + { + // In the case of function expression being captured in the param scope the hasownlocalinclosure will be false for param scope, + // as function expression symbol stays in the function expression scope. We don't have to set mustinstantiate for param scope in that case. + paramScope->SetMustInstantiate(paramScope->GetHasOwnLocalInClosure()); + } + } } else { diff --git a/test/es6/default-splitscope.js b/test/es6/default-splitscope.js index 22510ff1651..6399a859f2e 100644 --- a/test/es6/default-splitscope.js +++ b/test/es6/default-splitscope.js @@ -186,6 +186,14 @@ var tests = [ }; f13(); + var f14 = function f15(a = (function() { + return f15(1); + })()) { + with({}) { + }; + return a === 1 ? 10 : a; + }; + assert.areEqual(10, f14(), "Function expresison is captured in the param scope when no other formals are captured"); } }, {