Commit f4739ea8 authored by petermarshall's avatar petermarshall Committed by Commit bot

[builtins] Fix crash on stack overflow in CheckSpreadAndPushToStack.

For x64, ia32 and x87 we would pop the return address before the stack
overflow check. This meant the stack couldn't be unwound properly if
it was going to overflow. This CL moves the pop of the return address
to after the stack overflow check.

Also adds a regression test to check that a RangeError is thrown.

BUG=689016

Review-Url: https://codereview.chromium.org/2681643004
Cr-Commit-Position: refs/heads/master@{#42984}
parent 44a381ad
......@@ -2842,7 +2842,6 @@ static void CheckSpreadAndPushToStack(MacroAssembler* masm) {
__ movd(xmm1, edi);
}
Register return_address = edi;
{
// Calculate the new nargs including the result of the spread.
__ mov(spread_len, FieldOperand(spread, FixedArray::kLengthOffset));
......@@ -2851,10 +2850,6 @@ static void CheckSpreadAndPushToStack(MacroAssembler* masm) {
__ bind(&push_args);
// argc += spread_len - 1. Subtract 1 for the spread itself.
__ lea(argc, Operand(argc, spread_len, times_1, -1));
// Pop the return address and spread argument.
__ PopReturnAddressTo(return_address);
__ Pop(scratch);
}
// Check for stack overflow.
......@@ -2877,6 +2872,11 @@ static void CheckSpreadAndPushToStack(MacroAssembler* masm) {
// Put the evaluated spread onto the stack as additional arguments.
{
Register return_address = edi;
// Pop the return address and spread argument.
__ PopReturnAddressTo(return_address);
__ Pop(scratch);
Register scratch2 = esi;
__ movd(xmm2, esi);
......
......@@ -2901,10 +2901,6 @@ static void CheckSpreadAndPushToStack(MacroAssembler* masm) {
__ bind(&push_args);
// rax += r9 - 1. Subtract 1 for the spread itself.
__ leap(rax, Operand(rax, r9, times_1, -1));
// Pop the return address and spread argument.
__ PopReturnAddressTo(r8);
__ Pop(rcx);
}
// Check for stack overflow.
......@@ -2927,6 +2923,10 @@ static void CheckSpreadAndPushToStack(MacroAssembler* masm) {
// Put the evaluated spread onto the stack as additional arguments.
{
// Pop the return address and spread argument.
__ PopReturnAddressTo(r8);
__ Pop(rcx);
__ Set(rcx, 0);
Label done, loop;
__ bind(&loop);
......
......@@ -2804,7 +2804,6 @@ static void CheckSpreadAndPushToStack(MacroAssembler* masm) {
__ lea(esp, Operand(esp, 2 * kFloatSize));
}
Register return_address = edi;
{
// Calculate the new nargs including the result of the spread.
__ mov(spread_len, FieldOperand(spread, FixedArray::kLengthOffset));
......@@ -2813,10 +2812,6 @@ static void CheckSpreadAndPushToStack(MacroAssembler* masm) {
__ bind(&push_args);
// argc += spread_len - 1. Subtract 1 for the spread itself.
__ lea(argc, Operand(argc, spread_len, times_1, -1));
// Pop the return address and spread argument.
__ PopReturnAddressTo(return_address);
__ Pop(scratch);
}
// Check for stack overflow.
......@@ -2839,6 +2834,11 @@ static void CheckSpreadAndPushToStack(MacroAssembler* masm) {
// Put the evaluated spread onto the stack as additional arguments.
{
Register return_address = edi;
// Pop the return address and spread argument.
__ PopReturnAddressTo(return_address);
__ Pop(scratch);
Register scratch2 = esi;
// Save esi to stX0, edx/edi in stX1/stX2 now.
__ push(esi);
......
// Copyright 2017 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.
(function() {
function f() {}
assertThrows(function() {
f(...Array(1000000));
}, RangeError);
})();
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment