Commit 021f7381 authored by vegorov's avatar vegorov Committed by Commit bot

Treat HArgumentsObject as a safe use during Uint32 analysis phase.

Deoptimization infrastructure already handles it correctly.

This change fixes repetitive deoptimizations in the code like this:

    var u32 = new Uint32Array(1);
    u32[0] = -1;

    function tr(x) { return x|0; }
    function ld() { return tr(u32[0]); }

    while (true) ld();

Currently inlined tr will contain HArgumentsObject that is considered uint32-unsafe use and prevents u32[0] from becoming uint32 load - instead a speculative int32 load is generated which just deopts.

BUG=

Review URL: https://codereview.chromium.org/1077113002

Cr-Commit-Position: refs/heads/master@{#27781}
parent 0f432ebb
......@@ -2223,10 +2223,8 @@ void Deoptimizer::DoTranslateObject(TranslationIterator* iterator,
" object @0x%08" V8PRIxPTR ": [field #%d] <- ",
reinterpret_cast<intptr_t>(object_slot),
field_index);
PrintF(trace_scope_->file(),
"%" V8PRIdPTR " ; uint %s (%s)\n", value,
converter.NameOfCPURegister(input_reg),
TraceValueType(is_smi));
PrintF(trace_scope_->file(), "%" V8PRIuPTR " ; uint %s (%s)\n", value,
converter.NameOfCPURegister(input_reg), TraceValueType(is_smi));
}
if (is_smi) {
intptr_t tagged_value =
......@@ -2311,8 +2309,7 @@ void Deoptimizer::DoTranslateObject(TranslationIterator* iterator,
" object @0x%08" V8PRIxPTR ": [field #%d] <- ",
reinterpret_cast<intptr_t>(object_slot),
field_index);
PrintF(trace_scope_->file(),
"%" V8PRIdPTR " ; [sp + %d] (uint %s)\n",
PrintF(trace_scope_->file(), "%" V8PRIuPTR " ; [sp + %d] (uint %s)\n",
value, input_offset, TraceValueType(is_smi));
}
if (is_smi) {
......
......@@ -36,7 +36,7 @@ bool HUint32AnalysisPhase::IsSafeUint32Use(HValue* val, HValue* use) {
// Operations that operate on bits are safe.
if (use->IsBitwise() || use->IsShl() || use->IsSar() || use->IsShr()) {
return true;
} else if (use->IsSimulate()) {
} else if (use->IsSimulate() || use->IsArgumentsObject()) {
// Deoptimization has special support for uint32.
return true;
} else if (use->IsChange()) {
......
......@@ -171,3 +171,34 @@ FillOldArrayWithHeapNumbers(1);
%OptimizeFunctionOnNextCall(FillOldArrayWithHeapNumbers);
FillOldArrayWithHeapNumbers(old_array.length);
gc();
// Test that HArgumentsObject does not prevent uint32 optimization and
// that arguments object with uint32 values inside is correctly materialized.
function Pack(x, y) {
try { // Prevent inlining.
return [x, y];
} catch (e) {
}
}
function InnerWithArguments(x, f) {
"use strict";
x >>>= 8;
return f(arguments[0], x|0);
}
function Outer(v, f) {
return InnerWithArguments(v >>> 0, f);
}
assertArrayEquals([0x0100, 0x01], Outer(0x0100, Pack));
assertArrayEquals([0x0100, 0x01], Outer(0x0100, Pack));
assertArrayEquals([0x0100, 0x01], Outer(0x0100, Pack));
%OptimizeFunctionOnNextCall(Outer);
assertArrayEquals([0x0100, 0x01], Outer(0x0100, Pack));
assertArrayEquals([0xFFFFFFFF, 0x00FFFFFF], Outer(-1, Pack));
// Cause deopt inside InnerWithArguments by passing different pack function.
assertArrayEquals([0xFFFFFFFF, 0x00FFFFFF], Outer(-1, function (x, y) {
return [x, y];
}));
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