[parser] Fix destructured parameters in arrowheads
Always unmark arrowhead parameters as assigned directly after their initialization as the parser doesn't know when it first sees the "assignment" that it may be in an arrowhead. Bug: chromium:1003403, v8:8510 Change-Id: Iad5a4136d5ec06331fc43b81a809fd72cee2dd65 Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/1815131 Commit-Queue: Dan Elphick <delphick@chromium.org> Reviewed-by: Toon Verwaest <verwaest@chromium.org> Cr-Commit-Position: refs/heads/master@{#63947}
This commit is contained in:
parent
0ceee9ad28
commit
f674045458
@ -84,6 +84,9 @@ class Variable final : public ZoneObject {
|
||||
MaybeAssignedFlag maybe_assigned() const {
|
||||
return MaybeAssignedFlagField::decode(bit_field_);
|
||||
}
|
||||
void clear_maybe_assigned() {
|
||||
bit_field_ = MaybeAssignedFlagField::update(bit_field_, kNotAssigned);
|
||||
}
|
||||
void SetMaybeAssigned() {
|
||||
if (mode() == VariableMode::kConst) return;
|
||||
|
||||
|
@ -3599,7 +3599,19 @@ void ParserBase<Impl>::ParseFormalParameter(FormalParametersT* parameters) {
|
||||
auto declaration_end = scope()->declarations()->end();
|
||||
int initializer_end = end_position();
|
||||
for (; declaration_it != declaration_end; ++declaration_it) {
|
||||
declaration_it->var()->set_initializer_position(initializer_end);
|
||||
Variable* var = declaration_it->var();
|
||||
|
||||
// The first time a variable is initialized (i.e. when the initializer
|
||||
// position is unset), clear its maybe_assigned flag as it is not a true
|
||||
// assignment. Since this is done directly on the Variable objects, it has
|
||||
// no effect on VariableProxy objects appearing on the left-hand side of
|
||||
// true assignments, so x will be still be marked as maybe_assigned for:
|
||||
// (x = 1, y = (x = 2)) => {}
|
||||
// and even:
|
||||
// (x = (x = 2)) => {}.
|
||||
if (var->initializer_position() == kNoSourcePosition)
|
||||
var->clear_maybe_assigned();
|
||||
var->set_initializer_position(initializer_end);
|
||||
}
|
||||
|
||||
impl()->AddFormalParameter(parameters, pattern, initializer, end_position(),
|
||||
|
@ -3608,6 +3608,14 @@ TEST(MaybeAssignedParameters) {
|
||||
"g(arg)}"},
|
||||
{true, "function f(arg) {g(arg); eval('arguments[0] = 42'); g(arg)}"},
|
||||
{true, "function f(arg) {g(arg); g(() => arguments[0] = 42); g(arg)}"},
|
||||
|
||||
// default values
|
||||
{false, "function f({x:arg = 1}) {}"},
|
||||
{true, "function f({x:arg = 1}, {y:b=(arg=2)}) {}"},
|
||||
{true, "function f({x:arg = (arg = 2)}) {}"},
|
||||
{false, "var f = ({x:arg = 1}) => {}"},
|
||||
{true, "var f = ({x:arg = 1}, {y:b=(arg=2)}) => {}"},
|
||||
{true, "var f = ({x:arg = (arg = 2)}) => {}"},
|
||||
};
|
||||
|
||||
const char* suffix = "; f";
|
||||
|
10
test/mjsunit/regress/regress-crbug-1003403.js
Normal file
10
test/mjsunit/regress/regress-crbug-1003403.js
Normal file
@ -0,0 +1,10 @@
|
||||
// Copyright 2019 the V8 project authors. All rights reserved.
|
||||
// Use of this source code is governed by a BSD-style license that can be
|
||||
// found in the LICENSE file.
|
||||
|
||||
// Flags: --enable-lazy-source-positions --stress-lazy-source-positions
|
||||
// Flags: --no-lazy
|
||||
({ x: b = 0 }) => {
|
||||
try { b; } catch (e) {}
|
||||
function a() { b }
|
||||
}
|
Loading…
Reference in New Issue
Block a user