Commit a15ad0d3 authored by Benedikt Meurer's avatar Benedikt Meurer Committed by Commit Bot

[turbofan] Reduce overhead of megamorphic property accesses.

We had an optimization in Crankshaft where we would call into the
megamorphic handler stub directly if an inline cache was already
found to be megamorphic when it hit the optimizing compiler. This
way we could avoid the dispatch overhead when we know that there's
no point in checking for the other states anyways. However we somehow
missed to port this optimization to TurboFan.

Now this change introduces support to call into LoadIC_Megamorphic and
KeyedLoadIC_Megamorphic directly (plus the trampoline versions), which
saves quite a lot of overhead for the cases where the map/name pair is
found in the megamorphic stub cache, and it's quite a simple change. We
can later extend this to also handle the StoreIC and KeyedStoreIC cases
if that turns out to be beneficial.

This improves the score on the Octane/TypeScript test by around ~2%
and the TypeScript test in the web-tooling-benchmark by around ~4%. On
the ARES-6 Air test the steady state mean improves by 2-4%, and on the
ARES-6 ML test the steady state mean seems to also improve by 1-2%, but
that might be within noise.

On a micro-benchmark that just runs `o.x` in a hot loop on a set of 9
different objects, which all have `x` as the first property and are
all in fast mode, we improve by around ~30%, and are now almost on par
with JavaScriptCore.

Bug: v8:6344, v8:6936
Change-Id: Iaa4c6e34c37e78da217ee75f32f6acc95a834250
Reviewed-on: https://chromium-review.googlesource.com/1215623Reviewed-by: 's avatarJaroslav Sevcik <jarin@chromium.org>
Reviewed-by: 's avatarJakob Kummerow <jkummerow@chromium.org>
Commit-Queue: Benedikt Meurer <bmeurer@chromium.org>
Cr-Commit-Position: refs/heads/master@{#55803}
parent 0fb2d2b0
...@@ -206,7 +206,6 @@ namespace internal { ...@@ -206,7 +206,6 @@ namespace internal {
TFC(ToBooleanLazyDeoptContinuation, TypeConversionStackParameter, 1) \ TFC(ToBooleanLazyDeoptContinuation, TypeConversionStackParameter, 1) \
\ \
/* Handlers */ \ /* Handlers */ \
TFH(KeyedLoadIC_Megamorphic, LoadWithVector) \
TFH(KeyedLoadIC_PolymorphicName, LoadWithVector) \ TFH(KeyedLoadIC_PolymorphicName, LoadWithVector) \
TFH(KeyedLoadIC_Slow, LoadWithVector) \ TFH(KeyedLoadIC_Slow, LoadWithVector) \
TFH(KeyedStoreIC_Megamorphic, StoreWithVector) \ TFH(KeyedStoreIC_Megamorphic, StoreWithVector) \
...@@ -629,10 +628,14 @@ namespace internal { ...@@ -629,10 +628,14 @@ namespace internal {
\ \
/* ICs */ \ /* ICs */ \
TFH(LoadIC, LoadWithVector) \ TFH(LoadIC, LoadWithVector) \
TFH(LoadIC_Megamorphic, LoadWithVector) \
TFH(LoadIC_Noninlined, LoadWithVector) \ TFH(LoadIC_Noninlined, LoadWithVector) \
TFH(LoadICTrampoline, Load) \ TFH(LoadICTrampoline, Load) \
TFH(LoadICTrampoline_Megamorphic, Load) \
TFH(KeyedLoadIC, LoadWithVector) \ TFH(KeyedLoadIC, LoadWithVector) \
TFH(KeyedLoadIC_Megamorphic, LoadWithVector) \
TFH(KeyedLoadICTrampoline, Load) \ TFH(KeyedLoadICTrampoline, Load) \
TFH(KeyedLoadICTrampoline_Megamorphic, Load) \
TFH(StoreGlobalIC, StoreGlobalWithVector) \ TFH(StoreGlobalIC, StoreGlobalWithVector) \
TFH(StoreGlobalICTrampoline, StoreGlobal) \ TFH(StoreGlobalICTrampoline, StoreGlobal) \
TFH(StoreIC, StoreWithVector) \ TFH(StoreIC, StoreWithVector) \
......
...@@ -21,13 +21,16 @@ namespace internal { ...@@ -21,13 +21,16 @@ namespace internal {
} }
IC_BUILTIN(LoadIC) IC_BUILTIN(LoadIC)
IC_BUILTIN(LoadIC_Megamorphic)
IC_BUILTIN(LoadIC_Noninlined) IC_BUILTIN(LoadIC_Noninlined)
IC_BUILTIN(LoadIC_Uninitialized) IC_BUILTIN(LoadIC_Uninitialized)
IC_BUILTIN(KeyedLoadIC)
IC_BUILTIN(LoadICTrampoline) IC_BUILTIN(LoadICTrampoline)
IC_BUILTIN(KeyedLoadICTrampoline) IC_BUILTIN(LoadICTrampoline_Megamorphic)
IC_BUILTIN(KeyedLoadIC)
IC_BUILTIN(KeyedLoadIC_Megamorphic) IC_BUILTIN(KeyedLoadIC_Megamorphic)
IC_BUILTIN(KeyedLoadIC_PolymorphicName) IC_BUILTIN(KeyedLoadIC_PolymorphicName)
IC_BUILTIN(KeyedLoadICTrampoline)
IC_BUILTIN(KeyedLoadICTrampoline_Megamorphic)
IC_BUILTIN(StoreGlobalIC) IC_BUILTIN(StoreGlobalIC)
IC_BUILTIN(StoreGlobalICTrampoline) IC_BUILTIN(StoreGlobalICTrampoline)
IC_BUILTIN(StoreIC) IC_BUILTIN(StoreIC)
......
...@@ -571,7 +571,9 @@ Node* BytecodeGraphBuilder::BuildLoadNativeContextField(int index) { ...@@ -571,7 +571,9 @@ Node* BytecodeGraphBuilder::BuildLoadNativeContextField(int index) {
} }
VectorSlotPair BytecodeGraphBuilder::CreateVectorSlotPair(int slot_id) { VectorSlotPair BytecodeGraphBuilder::CreateVectorSlotPair(int slot_id) {
return VectorSlotPair(feedback_vector(), FeedbackVector::ToSlot(slot_id)); FeedbackSlot slot = FeedbackVector::ToSlot(slot_id);
FeedbackNexus nexus(feedback_vector(), slot);
return VectorSlotPair(feedback_vector(), slot, nexus.ic_state());
} }
void BytecodeGraphBuilder::CreateGraph() { void BytecodeGraphBuilder::CreateGraph() {
......
...@@ -148,12 +148,16 @@ void JSGenericLowering::LowerJSLoadProperty(Node* node) { ...@@ -148,12 +148,16 @@ void JSGenericLowering::LowerJSLoadProperty(Node* node) {
Node* outer_state = frame_state->InputAt(kFrameStateOuterStateInput); Node* outer_state = frame_state->InputAt(kFrameStateOuterStateInput);
node->InsertInput(zone(), 2, jsgraph()->SmiConstant(p.feedback().index())); node->InsertInput(zone(), 2, jsgraph()->SmiConstant(p.feedback().index()));
if (outer_state->opcode() != IrOpcode::kFrameState) { if (outer_state->opcode() != IrOpcode::kFrameState) {
Callable callable = Callable callable = Builtins::CallableFor(
Builtins::CallableFor(isolate(), Builtins::kKeyedLoadICTrampoline); isolate(), p.feedback().ic_state() == MEGAMORPHIC
? Builtins::kKeyedLoadICTrampoline_Megamorphic
: Builtins::kKeyedLoadICTrampoline);
ReplaceWithStubCall(node, callable, flags); ReplaceWithStubCall(node, callable, flags);
} else { } else {
Callable callable = Callable callable = Builtins::CallableFor(
Builtins::CallableFor(isolate(), Builtins::kKeyedLoadIC); isolate(), p.feedback().ic_state() == MEGAMORPHIC
? Builtins::kKeyedLoadIC_Megamorphic
: Builtins::kKeyedLoadIC);
Node* vector = jsgraph()->HeapConstant(p.feedback().vector()); Node* vector = jsgraph()->HeapConstant(p.feedback().vector());
node->InsertInput(zone(), 3, vector); node->InsertInput(zone(), 3, vector);
ReplaceWithStubCall(node, callable, flags); ReplaceWithStubCall(node, callable, flags);
...@@ -168,18 +172,22 @@ void JSGenericLowering::LowerJSLoadNamed(Node* node) { ...@@ -168,18 +172,22 @@ void JSGenericLowering::LowerJSLoadNamed(Node* node) {
node->InsertInput(zone(), 1, jsgraph()->HeapConstant(p.name())); node->InsertInput(zone(), 1, jsgraph()->HeapConstant(p.name()));
node->InsertInput(zone(), 2, jsgraph()->SmiConstant(p.feedback().index())); node->InsertInput(zone(), 2, jsgraph()->SmiConstant(p.feedback().index()));
if (outer_state->opcode() != IrOpcode::kFrameState) { if (outer_state->opcode() != IrOpcode::kFrameState) {
Callable callable = Callable callable = Builtins::CallableFor(
Builtins::CallableFor(isolate(), Builtins::kLoadICTrampoline); isolate(), p.feedback().ic_state() == MEGAMORPHIC
? Builtins::kLoadICTrampoline_Megamorphic
: Builtins::kLoadICTrampoline);
ReplaceWithStubCall(node, callable, flags); ReplaceWithStubCall(node, callable, flags);
} else { } else {
Callable callable = Builtins::CallableFor(isolate(), Builtins::kLoadIC); Callable callable =
Builtins::CallableFor(isolate(), p.feedback().ic_state() == MEGAMORPHIC
? Builtins::kLoadIC_Megamorphic
: Builtins::kLoadIC);
Node* vector = jsgraph()->HeapConstant(p.feedback().vector()); Node* vector = jsgraph()->HeapConstant(p.feedback().vector());
node->InsertInput(zone(), 3, vector); node->InsertInput(zone(), 3, vector);
ReplaceWithStubCall(node, callable, flags); ReplaceWithStubCall(node, callable, flags);
} }
} }
void JSGenericLowering::LowerJSLoadGlobal(Node* node) { void JSGenericLowering::LowerJSLoadGlobal(Node* node) {
CallDescriptor::Flags flags = FrameStateFlagForCall(node); CallDescriptor::Flags flags = FrameStateFlagForCall(node);
const LoadGlobalParameters& p = LoadGlobalParametersOf(node->op()); const LoadGlobalParameters& p = LoadGlobalParametersOf(node->op());
......
...@@ -266,7 +266,7 @@ NamedAccess const& NamedAccessOf(const Operator* op) { ...@@ -266,7 +266,7 @@ NamedAccess const& NamedAccessOf(const Operator* op) {
std::ostream& operator<<(std::ostream& os, PropertyAccess const& p) { std::ostream& operator<<(std::ostream& os, PropertyAccess const& p) {
return os << p.language_mode(); return os << p.language_mode() << ", " << p.feedback();
} }
......
...@@ -546,10 +546,11 @@ InlineCacheState FeedbackNexus::StateFromFeedback() const { ...@@ -546,10 +546,11 @@ InlineCacheState FeedbackNexus::StateFromFeedback() const {
switch (kind()) { switch (kind()) {
case FeedbackSlotKind::kCreateClosure: case FeedbackSlotKind::kCreateClosure:
return MONOMORPHIC;
case FeedbackSlotKind::kLiteral: case FeedbackSlotKind::kLiteral:
// CreateClosure and literal slots don't have a notion of state. if (feedback->IsSmi()) return UNINITIALIZED;
UNREACHABLE(); return MONOMORPHIC;
break;
case FeedbackSlotKind::kStoreGlobalSloppy: case FeedbackSlotKind::kStoreGlobalSloppy:
case FeedbackSlotKind::kStoreGlobalStrict: case FeedbackSlotKind::kStoreGlobalStrict:
......
...@@ -709,6 +709,27 @@ enum InlineCacheState { ...@@ -709,6 +709,27 @@ enum InlineCacheState {
GENERIC, GENERIC,
}; };
// Printing support.
inline const char* InlineCacheState2String(InlineCacheState state) {
switch (state) {
case UNINITIALIZED:
return "UNINITIALIZED";
case PREMONOMORPHIC:
return "PREMONOMORPHIC";
case MONOMORPHIC:
return "MONOMORPHIC";
case RECOMPUTE_HANDLER:
return "RECOMPUTE_HANDLER";
case POLYMORPHIC:
return "POLYMORPHIC";
case MEGAMORPHIC:
return "MEGAMORPHIC";
case GENERIC:
return "GENERIC";
}
UNREACHABLE();
}
enum WhereToStart { kStartAtReceiver, kStartAtPrototype }; enum WhereToStart { kStartAtReceiver, kStartAtPrototype };
enum ResultSentinel { kNotFound = -1, kUnsupported = -2 }; enum ResultSentinel { kNotFound = -1, kUnsupported = -2 };
......
...@@ -3197,6 +3197,31 @@ void AccessorAssembler::GenerateLoadIC() { ...@@ -3197,6 +3197,31 @@ void AccessorAssembler::GenerateLoadIC() {
LoadIC(&p); LoadIC(&p);
} }
void AccessorAssembler::GenerateLoadIC_Megamorphic() {
typedef LoadWithVectorDescriptor Descriptor;
Node* receiver = Parameter(Descriptor::kReceiver);
Node* name = Parameter(Descriptor::kName);
Node* slot = Parameter(Descriptor::kSlot);
Node* vector = Parameter(Descriptor::kVector);
Node* context = Parameter(Descriptor::kContext);
ExitPoint direct_exit(this);
TVARIABLE(MaybeObject, var_handler);
Label if_handler(this, &var_handler), miss(this, Label::kDeferred);
TryProbeStubCache(isolate()->load_stub_cache(), receiver, name, &if_handler,
&var_handler, &miss);
BIND(&if_handler);
LoadICParameters p(context, receiver, name, slot, vector);
HandleLoadICHandlerCase(&p, CAST(var_handler.value()), &miss, &direct_exit);
BIND(&miss);
direct_exit.ReturnCallRuntime(Runtime::kLoadIC_Miss, context, receiver, name,
slot, vector);
}
void AccessorAssembler::GenerateLoadIC_Noninlined() { void AccessorAssembler::GenerateLoadIC_Noninlined() {
typedef LoadWithVectorDescriptor Descriptor; typedef LoadWithVectorDescriptor Descriptor;
...@@ -3252,6 +3277,19 @@ void AccessorAssembler::GenerateLoadICTrampoline() { ...@@ -3252,6 +3277,19 @@ void AccessorAssembler::GenerateLoadICTrampoline() {
TailCallBuiltin(Builtins::kLoadIC, context, receiver, name, slot, vector); TailCallBuiltin(Builtins::kLoadIC, context, receiver, name, slot, vector);
} }
void AccessorAssembler::GenerateLoadICTrampoline_Megamorphic() {
typedef LoadDescriptor Descriptor;
Node* receiver = Parameter(Descriptor::kReceiver);
Node* name = Parameter(Descriptor::kName);
Node* slot = Parameter(Descriptor::kSlot);
Node* context = Parameter(Descriptor::kContext);
Node* vector = LoadFeedbackVectorForStub();
TailCallBuiltin(Builtins::kLoadIC_Megamorphic, context, receiver, name, slot,
vector);
}
void AccessorAssembler::GenerateLoadGlobalIC(TypeofMode typeof_mode) { void AccessorAssembler::GenerateLoadGlobalIC(TypeofMode typeof_mode) {
typedef LoadGlobalWithVectorDescriptor Descriptor; typedef LoadGlobalWithVectorDescriptor Descriptor;
...@@ -3294,6 +3332,19 @@ void AccessorAssembler::GenerateKeyedLoadIC() { ...@@ -3294,6 +3332,19 @@ void AccessorAssembler::GenerateKeyedLoadIC() {
KeyedLoadIC(&p); KeyedLoadIC(&p);
} }
void AccessorAssembler::GenerateKeyedLoadIC_Megamorphic() {
typedef LoadWithVectorDescriptor Descriptor;
Node* receiver = Parameter(Descriptor::kReceiver);
Node* name = Parameter(Descriptor::kName);
Node* slot = Parameter(Descriptor::kSlot);
Node* vector = Parameter(Descriptor::kVector);
Node* context = Parameter(Descriptor::kContext);
LoadICParameters p(context, receiver, name, slot, vector);
KeyedLoadICGeneric(&p);
}
void AccessorAssembler::GenerateKeyedLoadICTrampoline() { void AccessorAssembler::GenerateKeyedLoadICTrampoline() {
typedef LoadDescriptor Descriptor; typedef LoadDescriptor Descriptor;
...@@ -3307,17 +3358,17 @@ void AccessorAssembler::GenerateKeyedLoadICTrampoline() { ...@@ -3307,17 +3358,17 @@ void AccessorAssembler::GenerateKeyedLoadICTrampoline() {
vector); vector);
} }
void AccessorAssembler::GenerateKeyedLoadIC_Megamorphic() { void AccessorAssembler::GenerateKeyedLoadICTrampoline_Megamorphic() {
typedef LoadWithVectorDescriptor Descriptor; typedef LoadDescriptor Descriptor;
Node* receiver = Parameter(Descriptor::kReceiver); Node* receiver = Parameter(Descriptor::kReceiver);
Node* name = Parameter(Descriptor::kName); Node* name = Parameter(Descriptor::kName);
Node* slot = Parameter(Descriptor::kSlot); Node* slot = Parameter(Descriptor::kSlot);
Node* vector = Parameter(Descriptor::kVector);
Node* context = Parameter(Descriptor::kContext); Node* context = Parameter(Descriptor::kContext);
Node* vector = LoadFeedbackVectorForStub();
LoadICParameters p(context, receiver, name, slot, vector); TailCallBuiltin(Builtins::kKeyedLoadIC_Megamorphic, context, receiver, name,
KeyedLoadICGeneric(&p); slot, vector);
} }
void AccessorAssembler::GenerateKeyedLoadIC_PolymorphicName() { void AccessorAssembler::GenerateKeyedLoadIC_PolymorphicName() {
......
...@@ -28,13 +28,16 @@ class AccessorAssembler : public CodeStubAssembler { ...@@ -28,13 +28,16 @@ class AccessorAssembler : public CodeStubAssembler {
: CodeStubAssembler(state) {} : CodeStubAssembler(state) {}
void GenerateLoadIC(); void GenerateLoadIC();
void GenerateLoadIC_Megamorphic();
void GenerateLoadIC_Noninlined(); void GenerateLoadIC_Noninlined();
void GenerateLoadIC_Uninitialized(); void GenerateLoadIC_Uninitialized();
void GenerateLoadICTrampoline(); void GenerateLoadICTrampoline();
void GenerateLoadICTrampoline_Megamorphic();
void GenerateKeyedLoadIC(); void GenerateKeyedLoadIC();
void GenerateKeyedLoadICTrampoline();
void GenerateKeyedLoadIC_Megamorphic(); void GenerateKeyedLoadIC_Megamorphic();
void GenerateKeyedLoadIC_PolymorphicName(); void GenerateKeyedLoadIC_PolymorphicName();
void GenerateKeyedLoadICTrampoline();
void GenerateKeyedLoadICTrampoline_Megamorphic();
void GenerateStoreIC(); void GenerateStoreIC();
void GenerateStoreICTrampoline(); void GenerateStoreICTrampoline();
void GenerateStoreGlobalIC(); void GenerateStoreGlobalIC();
......
...@@ -1088,29 +1088,6 @@ void FeedbackVector::FeedbackSlotPrint(std::ostream& os, ...@@ -1088,29 +1088,6 @@ void FeedbackVector::FeedbackSlotPrint(std::ostream& os,
nexus.Print(os); nexus.Print(os);
} }
namespace {
const char* ICState2String(InlineCacheState state) {
switch (state) {
case UNINITIALIZED:
return "UNINITIALIZED";
case PREMONOMORPHIC:
return "PREMONOMORPHIC";
case MONOMORPHIC:
return "MONOMORPHIC";
case RECOMPUTE_HANDLER:
return "RECOMPUTE_HANDLER";
case POLYMORPHIC:
return "POLYMORPHIC";
case MEGAMORPHIC:
return "MEGAMORPHIC";
case GENERIC:
return "GENERIC";
}
UNREACHABLE();
}
} // anonymous namespace
void FeedbackNexus::Print(std::ostream& os) { // NOLINT void FeedbackNexus::Print(std::ostream& os) { // NOLINT
switch (kind()) { switch (kind()) {
case FeedbackSlotKind::kCall: case FeedbackSlotKind::kCall:
...@@ -1129,7 +1106,7 @@ void FeedbackNexus::Print(std::ostream& os) { // NOLINT ...@@ -1129,7 +1106,7 @@ void FeedbackNexus::Print(std::ostream& os) { // NOLINT
case FeedbackSlotKind::kStoreKeyedStrict: case FeedbackSlotKind::kStoreKeyedStrict:
case FeedbackSlotKind::kStoreInArrayLiteral: case FeedbackSlotKind::kStoreInArrayLiteral:
case FeedbackSlotKind::kCloneObject: { case FeedbackSlotKind::kCloneObject: {
os << ICState2String(StateFromFeedback()); os << InlineCacheState2String(StateFromFeedback());
break; break;
} }
case FeedbackSlotKind::kBinaryOp: { case FeedbackSlotKind::kBinaryOp: {
......
...@@ -17,22 +17,24 @@ int VectorSlotPair::index() const { ...@@ -17,22 +17,24 @@ int VectorSlotPair::index() const {
bool operator==(VectorSlotPair const& lhs, VectorSlotPair const& rhs) { bool operator==(VectorSlotPair const& lhs, VectorSlotPair const& rhs) {
return lhs.slot() == rhs.slot() && return lhs.slot() == rhs.slot() &&
lhs.vector().location() == rhs.vector().location(); lhs.vector().location() == rhs.vector().location() &&
lhs.ic_state() == rhs.ic_state();
} }
bool operator!=(VectorSlotPair const& lhs, VectorSlotPair const& rhs) { bool operator!=(VectorSlotPair const& lhs, VectorSlotPair const& rhs) {
return !(lhs == rhs); return !(lhs == rhs);
} }
std::ostream& operator<<(std::ostream& os, const VectorSlotPair& pair) { std::ostream& operator<<(std::ostream& os, const VectorSlotPair& p) {
if (pair.IsValid()) { if (p.IsValid()) {
return os << "VectorSlotPair(" << pair.slot() << ")"; return os << "VectorSlotPair(" << p.slot() << ", "
<< InlineCacheState2String(p.ic_state()) << ")";
} }
return os << "VectorSlotPair(INVALID)"; return os << "VectorSlotPair(INVALID)";
} }
size_t hash_value(VectorSlotPair const& p) { size_t hash_value(VectorSlotPair const& p) {
return base::hash_combine(p.slot(), p.vector().location()); return base::hash_combine(p.slot(), p.vector().location(), p.ic_state());
} }
} // namespace internal } // namespace internal
......
...@@ -19,25 +19,28 @@ class FeedbackVector; ...@@ -19,25 +19,28 @@ class FeedbackVector;
class V8_EXPORT_PRIVATE VectorSlotPair { class V8_EXPORT_PRIVATE VectorSlotPair {
public: public:
VectorSlotPair(); VectorSlotPair();
VectorSlotPair(Handle<FeedbackVector> vector, FeedbackSlot slot) VectorSlotPair(Handle<FeedbackVector> vector, FeedbackSlot slot,
: vector_(vector), slot_(slot) {} InlineCacheState ic_state)
: vector_(vector), slot_(slot), ic_state_(ic_state) {}
bool IsValid() const { return !vector_.is_null() && !slot_.IsInvalid(); } bool IsValid() const { return !vector_.is_null() && !slot_.IsInvalid(); }
Handle<FeedbackVector> vector() const { return vector_; } Handle<FeedbackVector> vector() const { return vector_; }
FeedbackSlot slot() const { return slot_; } FeedbackSlot slot() const { return slot_; }
InlineCacheState ic_state() const { return ic_state_; }
int index() const; int index() const;
private: private:
Handle<FeedbackVector> vector_; Handle<FeedbackVector> vector_;
FeedbackSlot slot_; FeedbackSlot slot_;
InlineCacheState ic_state_ = UNINITIALIZED;
}; };
bool operator==(VectorSlotPair const&, VectorSlotPair const&); bool operator==(VectorSlotPair const&, VectorSlotPair const&);
bool operator!=(VectorSlotPair const&, VectorSlotPair const&); bool operator!=(VectorSlotPair const&, VectorSlotPair const&);
std::ostream& operator<<(std::ostream& os, const VectorSlotPair& pair); std::ostream& operator<<(std::ostream& os, VectorSlotPair const&);
size_t hash_value(VectorSlotPair const&); size_t hash_value(VectorSlotPair const&);
......
...@@ -124,7 +124,7 @@ class JSCallReducerTest : public TypedGraphTest { ...@@ -124,7 +124,7 @@ class JSCallReducerTest : public TypedGraphTest {
// overwriting existing metadata. // overwriting existing metadata.
shared->set_raw_outer_scope_info_or_feedback_metadata(*metadata); shared->set_raw_outer_scope_info_or_feedback_metadata(*metadata);
Handle<FeedbackVector> vector = FeedbackVector::New(isolate(), shared); Handle<FeedbackVector> vector = FeedbackVector::New(isolate(), shared);
VectorSlotPair feedback(vector, FeedbackSlot(0)); VectorSlotPair feedback(vector, FeedbackSlot(0), UNINITIALIZED);
return javascript()->Call(arity, CallFrequency(), feedback, return javascript()->Call(arity, CallFrequency(), feedback,
ConvertReceiverMode::kAny, ConvertReceiverMode::kAny,
SpeculationMode::kAllowSpeculation); SpeculationMode::kAllowSpeculation);
......
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