summaryrefslogtreecommitdiff
path: root/deps/v8/src/ic
diff options
context:
space:
mode:
Diffstat (limited to 'deps/v8/src/ic')
-rw-r--r--deps/v8/src/ic/accessor-assembler.cc392
-rw-r--r--deps/v8/src/ic/accessor-assembler.h15
-rw-r--r--deps/v8/src/ic/binary-op-assembler.cc123
-rw-r--r--deps/v8/src/ic/binary-op-assembler.h114
-rw-r--r--deps/v8/src/ic/call-optimization.cc15
-rw-r--r--deps/v8/src/ic/call-optimization.h9
-rw-r--r--deps/v8/src/ic/ic.cc39
-rw-r--r--deps/v8/src/ic/keyed-store-generic.cc23
-rw-r--r--deps/v8/src/ic/unary-op-assembler.cc63
-rw-r--r--deps/v8/src/ic/unary-op-assembler.h12
10 files changed, 526 insertions, 279 deletions
diff --git a/deps/v8/src/ic/accessor-assembler.cc b/deps/v8/src/ic/accessor-assembler.cc
index 8335bc5e88..1494102df9 100644
--- a/deps/v8/src/ic/accessor-assembler.cc
+++ b/deps/v8/src/ic/accessor-assembler.cc
@@ -255,17 +255,13 @@ void AccessorAssembler::HandleLoadField(TNode<JSObject> holder,
exit_point->Return(LoadObjectField(holder, offset));
BIND(&is_double);
- if (FLAG_unbox_double_fields) {
- *var_double_value = LoadObjectField<Float64T>(holder, offset);
- } else {
- TNode<Object> heap_number = LoadObjectField(holder, offset);
- // This is not an "old" Smi value from before a Smi->Double transition.
- // Rather, it's possible that since the last update of this IC, the Double
- // field transitioned to a Tagged field, and was then assigned a Smi.
- GotoIf(TaggedIsSmi(heap_number), miss);
- GotoIfNot(IsHeapNumber(CAST(heap_number)), miss);
- *var_double_value = LoadHeapNumberValue(CAST(heap_number));
- }
+ TNode<Object> heap_number = LoadObjectField(holder, offset);
+ // This is not an "old" Smi value from before a Smi->Double transition.
+ // Rather, it's possible that since the last update of this IC, the Double
+ // field transitioned to a Tagged field, and was then assigned a Smi.
+ GotoIf(TaggedIsSmi(heap_number), miss);
+ GotoIfNot(IsHeapNumber(CAST(heap_number)), miss);
+ *var_double_value = LoadHeapNumberValue(CAST(heap_number));
Goto(rebox_double);
}
@@ -278,13 +274,11 @@ void AccessorAssembler::HandleLoadField(TNode<JSObject> holder,
exit_point->Return(value);
BIND(&is_double);
- if (!FLAG_unbox_double_fields) {
- // This is not an "old" Smi value from before a Smi->Double transition.
- // Rather, it's possible that since the last update of this IC, the Double
- // field transitioned to a Tagged field, and was then assigned a Smi.
- GotoIf(TaggedIsSmi(value), miss);
- GotoIfNot(IsHeapNumber(CAST(value)), miss);
- }
+ // This is not an "old" Smi value from before a Smi->Double transition.
+ // Rather, it's possible that since the last update of this IC, the Double
+ // field transitioned to a Tagged field, and was then assigned a Smi.
+ GotoIf(TaggedIsSmi(value), miss);
+ GotoIfNot(IsHeapNumber(CAST(value)), miss);
*var_double_value = LoadHeapNumberValue(CAST(value));
Goto(rebox_double);
}
@@ -941,6 +935,8 @@ void AccessorAssembler::HandleLoadICProtoHandler(
BIND(&is_smi);
{
+ // If the "maybe_holder_or_constant" in the handler is a smi, then it's
+ // guaranteed that it's not a holder object, but a constant value.
CSA_ASSERT(
this,
WordEqual(
@@ -1066,6 +1062,7 @@ void AccessorAssembler::HandleStoreICHandlerCase(
properties, CAST(p->name()), &dictionary_found, &var_name_index, miss);
BIND(&dictionary_found);
{
+ Label if_constant(this), done(this);
TNode<Uint32T> details =
LoadDetailsByKeyIndex(properties, var_name_index.value());
// Check that the property is a writable data property (no accessor).
@@ -1074,9 +1071,26 @@ void AccessorAssembler::HandleStoreICHandlerCase(
STATIC_ASSERT(kData == 0);
GotoIf(IsSetWord32(details, kTypeAndReadOnlyMask), miss);
+ if (V8_DICT_PROPERTY_CONST_TRACKING_BOOL) {
+ GotoIf(IsPropertyDetailsConst(details), &if_constant);
+ }
+
StoreValueByKeyIndex<NameDictionary>(properties, var_name_index.value(),
p->value());
Return(p->value());
+
+ if (V8_DICT_PROPERTY_CONST_TRACKING_BOOL) {
+ BIND(&if_constant);
+ {
+ TNode<Object> prev_value =
+ LoadValueByKeyIndex(properties, var_name_index.value());
+ BranchIfSameValue(prev_value, p->value(), &done, miss,
+ SameValueMode::kNumbersOnly);
+ }
+
+ BIND(&done);
+ Return(p->value());
+ }
}
BIND(&if_fast_smi);
@@ -1297,8 +1311,9 @@ void AccessorAssembler::CheckFieldType(TNode<DescriptorArray> descriptors,
}
TNode<BoolT> AccessorAssembler::IsPropertyDetailsConst(TNode<Uint32T> details) {
- return Word32Equal(DecodeWord32<PropertyDetails::ConstnessField>(details),
- Int32Constant(static_cast<int32_t>(VariableMode::kConst)));
+ return Word32Equal(
+ DecodeWord32<PropertyDetails::ConstnessField>(details),
+ Int32Constant(static_cast<int32_t>(PropertyConstness::kConst)));
}
void AccessorAssembler::OverwriteExistingFastDataProperty(
@@ -1346,36 +1361,21 @@ void AccessorAssembler::OverwriteExistingFastDataProperty(
BIND(&double_rep);
{
TNode<Float64T> double_value = ChangeNumberToFloat64(CAST(value));
- if (FLAG_unbox_double_fields) {
- if (do_transitioning_store) {
- StoreMap(object, object_map);
- } else {
- Label store_value(this);
- GotoIfNot(IsPropertyDetailsConst(details), &store_value);
- TNode<Float64T> current_value =
- LoadObjectField<Float64T>(object, field_offset);
- BranchIfSameNumberValue(current_value, double_value, &store_value,
- slow);
- BIND(&store_value);
- }
- StoreObjectFieldNoWriteBarrier(object, field_offset, double_value);
+ if (do_transitioning_store) {
+ TNode<HeapNumber> heap_number =
+ AllocateHeapNumberWithValue(double_value);
+ StoreMap(object, object_map);
+ StoreObjectField(object, field_offset, heap_number);
} else {
- if (do_transitioning_store) {
- TNode<HeapNumber> heap_number =
- AllocateHeapNumberWithValue(double_value);
- StoreMap(object, object_map);
- StoreObjectField(object, field_offset, heap_number);
- } else {
- TNode<HeapNumber> heap_number =
- CAST(LoadObjectField(object, field_offset));
- Label store_value(this);
- GotoIfNot(IsPropertyDetailsConst(details), &store_value);
- TNode<Float64T> current_value = LoadHeapNumberValue(heap_number);
- BranchIfSameNumberValue(current_value, double_value, &store_value,
- slow);
- BIND(&store_value);
- StoreHeapNumberValue(heap_number, double_value);
- }
+ TNode<HeapNumber> heap_number =
+ CAST(LoadObjectField(object, field_offset));
+ Label store_value(this);
+ GotoIfNot(IsPropertyDetailsConst(details), &store_value);
+ TNode<Float64T> current_value = LoadHeapNumberValue(heap_number);
+ BranchIfSameNumberValue(current_value, double_value, &store_value,
+ slow);
+ BIND(&store_value);
+ StoreHeapNumberValue(heap_number, double_value);
}
Goto(&done);
}
@@ -1883,13 +1883,6 @@ void AccessorAssembler::HandleStoreFieldAndReturn(
Label property_and_offset_ready(this);
- // If we are unboxing double fields, and this is an in-object field, the
- // property_storage and offset are already pointing to the double-valued
- // field.
- if (FLAG_unbox_double_fields) {
- GotoIf(is_inobject, &property_and_offset_ready);
- }
-
// Store the double value directly into the mutable HeapNumber.
TNode<Object> field = LoadObjectField(property_storage, offset);
CSA_ASSERT(this, IsHeapNumber(CAST(field)));
@@ -2762,12 +2755,15 @@ void AccessorAssembler::LoadIC(const LoadICParameters* p) {
TVARIABLE(MaybeObject, var_handler);
Label if_handler(this, &var_handler), non_inlined(this, Label::kDeferred),
- try_polymorphic(this), miss(this, Label::kDeferred);
+ try_polymorphic(this), miss(this, Label::kDeferred),
+ no_feedback(this, Label::kDeferred);
TNode<Map> lookup_start_object_map =
LoadReceiverMap(p->receiver_and_lookup_start_object());
GotoIf(IsDeprecatedMap(lookup_start_object_map), &miss);
+ GotoIf(IsUndefined(p->vector()), &no_feedback);
+
// Check monomorphic case.
TNode<MaybeObject> feedback =
TryMonomorphicCase(p->slot(), CAST(p->vector()), lookup_start_object_map,
@@ -2795,6 +2791,16 @@ void AccessorAssembler::LoadIC(const LoadICParameters* p) {
&if_handler, &miss, &direct_exit);
}
+ BIND(&no_feedback);
+ {
+ Comment("LoadIC_nofeedback");
+ // Call into the stub that implements the non-inlined parts of LoadIC.
+ direct_exit.ReturnCallStub(
+ Builtins::CallableFor(isolate(), Builtins::kLoadIC_NoFeedback),
+ p->context(), p->receiver(), p->name(),
+ SmiConstant(FeedbackSlotKind::kLoadProperty));
+ }
+
BIND(&miss);
direct_exit.ReturnCallRuntime(Runtime::kLoadIC_Miss, p->context(),
p->receiver_and_lookup_start_object(),
@@ -2890,8 +2896,7 @@ void AccessorAssembler::LoadIC_NoFeedback(const LoadICParameters* p,
// Special case for Function.prototype load, because it's very common
// for ICs that are only executed once (MyFunc.prototype.foo = ...).
Label not_function_prototype(this, Label::kDeferred);
- GotoIfNot(InstanceTypeEqual(instance_type, JS_FUNCTION_TYPE),
- &not_function_prototype);
+ GotoIfNot(IsJSFunctionInstanceType(instance_type), &not_function_prototype);
GotoIfNot(IsPrototypeString(p->name()), &not_function_prototype);
GotoIfPrototypeRequiresRuntimeLookup(CAST(lookup_start_object),
@@ -3068,36 +3073,15 @@ void AccessorAssembler::ScriptContextTableLookup(
ScriptContextTable::kFirstContextSlotIndex * kTaggedSize));
TNode<ScopeInfo> scope_info =
CAST(LoadContextElement(script_context, Context::SCOPE_INFO_INDEX));
- TNode<IntPtrT> length = LoadAndUntagFixedArrayBaseLength(scope_info);
- GotoIf(IntPtrLessThanOrEqual(length, IntPtrConstant(0)), &loop);
-
- TVARIABLE(IntPtrT, scope_var_index,
- IntPtrConstant(ScopeInfo::kVariablePartIndex - 1));
- TNode<IntPtrT> num_scope_vars = SmiUntag(CAST(LoadFixedArrayElement(
- scope_info, IntPtrConstant(ScopeInfo::Fields::kContextLocalCount))));
- TNode<IntPtrT> end_index = IntPtrAdd(
- num_scope_vars, IntPtrConstant(ScopeInfo::kVariablePartIndex));
- Label loop_scope_info(this, &scope_var_index);
- Goto(&loop_scope_info);
-
- BIND(&loop_scope_info);
- {
- scope_var_index = IntPtrAdd(scope_var_index.value(), IntPtrConstant(1));
- GotoIf(IntPtrGreaterThanOrEqual(scope_var_index.value(), end_index),
- &loop);
-
- TNode<Object> var_name =
- LoadFixedArrayElement(scope_info, scope_var_index.value(), 0);
- GotoIf(TaggedNotEqual(var_name, name), &loop_scope_info);
-
- TNode<IntPtrT> var_index =
- IntPtrAdd(IntPtrConstant(Context::MIN_CONTEXT_SLOTS),
- IntPtrSub(scope_var_index.value(),
- IntPtrConstant(ScopeInfo::kVariablePartIndex)));
- TNode<Object> result = LoadContextElement(script_context, var_index);
- GotoIf(IsTheHole(result), found_hole);
- Return(result);
- }
+
+ TNode<IntPtrT> context_local_index =
+ IndexOfLocalName(scope_info, name, &loop);
+
+ TNode<IntPtrT> var_index = IntPtrAdd(
+ IntPtrConstant(Context::MIN_CONTEXT_SLOTS), context_local_index);
+ TNode<Object> result = LoadContextElement(script_context, var_index);
+ GotoIf(IsTheHole(result), found_hole);
+ Return(result);
}
}
@@ -3435,7 +3419,10 @@ void AccessorAssembler::StoreIC(const StoreICParameters* p) {
}
void AccessorAssembler::StoreGlobalIC(const StoreICParameters* pp) {
- Label if_lexical_var(this), if_heapobject(this);
+ Label no_feedback(this, Label::kDeferred), if_lexical_var(this),
+ if_heapobject(this);
+ GotoIf(IsUndefined(pp->vector()), &no_feedback);
+
TNode<MaybeObject> maybe_weak_ref =
LoadFeedbackVectorSlot(CAST(pp->vector()), pp->slot());
Branch(TaggedIsSmi(maybe_weak_ref), &if_lexical_var, &if_heapobject);
@@ -3490,6 +3477,12 @@ void AccessorAssembler::StoreGlobalIC(const StoreICParameters* pp) {
StoreContextElement(script_context, slot_index, pp->value());
Return(pp->value());
}
+
+ BIND(&no_feedback);
+ {
+ TailCallRuntime(Runtime::kStoreGlobalICNoFeedback_Miss, pp->context(),
+ pp->value(), pp->name());
+ }
}
void AccessorAssembler::StoreGlobalIC_PropertyCellCase(
@@ -3517,8 +3510,7 @@ void AccessorAssembler::StoreGlobalIC_PropertyCellCase(
GotoIf(Word32Equal(type, Int32Constant(
static_cast<int>(PropertyCellType::kConstant))),
&constant);
-
- GotoIf(IsTheHole(cell_contents), miss);
+ CSA_ASSERT(this, Word32BinaryNot(IsTheHole(cell_contents)));
GotoIf(Word32Equal(
type, Int32Constant(static_cast<int>(PropertyCellType::kMutable))),
@@ -3550,6 +3542,9 @@ void AccessorAssembler::StoreGlobalIC_PropertyCellCase(
BIND(&constant);
{
+ // Since |value| is never the hole, the equality check below also handles an
+ // invalidated property cell correctly.
+ CSA_ASSERT(this, Word32BinaryNot(IsTheHole(value)));
GotoIfNot(TaggedEqual(cell_contents, value), miss);
exit_point->Return(value);
}
@@ -3842,6 +3837,18 @@ void AccessorAssembler::GenerateLoadICTrampoline() {
TailCallBuiltin(Builtins::kLoadIC, context, receiver, name, slot, vector);
}
+void AccessorAssembler::GenerateLoadICBaseline() {
+ using Descriptor = LoadBaselineDescriptor;
+
+ auto receiver = Parameter<Object>(Descriptor::kReceiver);
+ auto name = Parameter<Object>(Descriptor::kName);
+ auto slot = Parameter<TaggedIndex>(Descriptor::kSlot);
+ TNode<FeedbackVector> vector = LoadFeedbackVectorFromBaseline();
+ TNode<Context> context = LoadContextFromBaseline();
+
+ TailCallBuiltin(Builtins::kLoadIC, context, receiver, name, slot, vector);
+}
+
void AccessorAssembler::GenerateLoadICTrampoline_Megamorphic() {
using Descriptor = LoadDescriptor;
@@ -3870,6 +3877,20 @@ void AccessorAssembler::GenerateLoadSuperIC() {
LoadSuperIC(&p);
}
+void AccessorAssembler::GenerateLoadSuperICBaseline() {
+ using Descriptor = LoadWithReceiverBaselineDescriptor;
+
+ auto receiver = Parameter<Object>(Descriptor::kReceiver);
+ auto lookup_start_object = Parameter<Object>(Descriptor::kLookupStartObject);
+ auto name = Parameter<Object>(Descriptor::kName);
+ auto slot = Parameter<TaggedIndex>(Descriptor::kSlot);
+ TNode<FeedbackVector> vector = LoadFeedbackVectorFromBaseline();
+ TNode<Context> context = LoadContextFromBaseline();
+
+ TailCallBuiltin(Builtins::kLoadSuperIC, context, receiver,
+ lookup_start_object, name, slot, vector);
+}
+
void AccessorAssembler::GenerateLoadGlobalIC_NoFeedback() {
using Descriptor = LoadGlobalNoFeedbackDescriptor;
@@ -3912,6 +3933,79 @@ void AccessorAssembler::GenerateLoadGlobalICTrampoline(TypeofMode typeof_mode) {
TailCallStub(callable, context, name, slot, vector);
}
+void AccessorAssembler::GenerateLoadGlobalICBaseline(TypeofMode typeof_mode) {
+ using Descriptor = LoadGlobalBaselineDescriptor;
+
+ auto name = Parameter<Object>(Descriptor::kName);
+ auto slot = Parameter<TaggedIndex>(Descriptor::kSlot);
+ TNode<FeedbackVector> vector = LoadFeedbackVectorFromBaseline();
+ TNode<Context> context = LoadContextFromBaseline();
+
+ Callable callable =
+ CodeFactory::LoadGlobalICInOptimizedCode(isolate(), typeof_mode);
+ TailCallStub(callable, context, name, slot, vector);
+}
+
+void AccessorAssembler::GenerateLookupContextBaseline(TypeofMode typeof_mode) {
+ using Descriptor = LookupBaselineDescriptor;
+ auto depth = Parameter<TaggedIndex>(Descriptor::kDepth);
+ TNode<Context> context = LoadContextFromBaseline();
+
+ Label slowpath(this, Label::kDeferred);
+
+ // Check for context extensions to allow the fast path.
+ TNode<Context> slot_context = GotoIfHasContextExtensionUpToDepth(
+ context, Unsigned(TruncateWordToInt32(TaggedIndexToIntPtr(depth))),
+ &slowpath);
+
+ // Fast path does a normal load context.
+ {
+ auto slot = Parameter<TaggedIndex>(Descriptor::kSlot);
+ Return(LoadContextElement(slot_context, TaggedIndexToIntPtr(slot)));
+ }
+
+ // Slow path when we have to call out to the runtime.
+ BIND(&slowpath);
+ {
+ auto name = Parameter<Object>(Descriptor::kName);
+ Runtime::FunctionId function_id = typeof_mode == INSIDE_TYPEOF
+ ? Runtime::kLoadLookupSlotInsideTypeof
+ : Runtime::kLoadLookupSlot;
+ TailCallRuntime(function_id, context, name);
+ }
+}
+
+void AccessorAssembler::GenerateLookupGlobalICBaseline(TypeofMode typeof_mode) {
+ using Descriptor = LookupBaselineDescriptor;
+
+ auto name = Parameter<Object>(Descriptor::kName);
+ auto depth = Parameter<TaggedIndex>(Descriptor::kDepth);
+ auto slot = Parameter<TaggedIndex>(Descriptor::kSlot);
+ TNode<Context> context = LoadContextFromBaseline();
+
+ Label slowpath(this, Label::kDeferred);
+
+ // Check for context extensions to allow the fast path
+ GotoIfHasContextExtensionUpToDepth(
+ context, Unsigned(TruncateWordToInt32(TaggedIndexToIntPtr(depth))),
+ &slowpath);
+
+ // Fast path does a normal load global
+ {
+ Callable callable =
+ CodeFactory::LoadGlobalICInOptimizedCode(isolate(), typeof_mode);
+ TNode<FeedbackVector> vector = LoadFeedbackVectorFromBaseline();
+ TailCallStub(callable, context, name, slot, vector);
+ }
+
+ // Slow path when we have to call out to the runtime
+ BIND(&slowpath);
+ Runtime::FunctionId function_id = typeof_mode == INSIDE_TYPEOF
+ ? Runtime::kLoadLookupSlotInsideTypeof
+ : Runtime::kLoadLookupSlot;
+ TailCallRuntime(function_id, context, name);
+}
+
void AccessorAssembler::GenerateKeyedLoadIC() {
using Descriptor = LoadWithVectorDescriptor;
@@ -3951,6 +4045,19 @@ void AccessorAssembler::GenerateKeyedLoadICTrampoline() {
vector);
}
+void AccessorAssembler::GenerateKeyedLoadICBaseline() {
+ using Descriptor = LoadBaselineDescriptor;
+
+ auto receiver = Parameter<Object>(Descriptor::kReceiver);
+ auto name = Parameter<Object>(Descriptor::kName);
+ auto slot = Parameter<TaggedIndex>(Descriptor::kSlot);
+ TNode<FeedbackVector> vector = LoadFeedbackVectorFromBaseline();
+ TNode<Context> context = LoadContextFromBaseline();
+
+ TailCallBuiltin(Builtins::kKeyedLoadIC, context, receiver, name, slot,
+ vector);
+}
+
void AccessorAssembler::GenerateKeyedLoadICTrampoline_Megamorphic() {
using Descriptor = LoadDescriptor;
@@ -4002,6 +4109,18 @@ void AccessorAssembler::GenerateStoreGlobalICTrampoline() {
TailCallBuiltin(Builtins::kStoreGlobalIC, context, name, value, slot, vector);
}
+void AccessorAssembler::GenerateStoreGlobalICBaseline() {
+ using Descriptor = StoreGlobalBaselineDescriptor;
+
+ auto name = Parameter<Object>(Descriptor::kName);
+ auto value = Parameter<Object>(Descriptor::kValue);
+ auto slot = Parameter<TaggedIndex>(Descriptor::kSlot);
+ TNode<FeedbackVector> vector = LoadFeedbackVectorFromBaseline();
+ TNode<Context> context = LoadContextFromBaseline();
+
+ TailCallBuiltin(Builtins::kStoreGlobalIC, context, name, value, slot, vector);
+}
+
void AccessorAssembler::GenerateStoreIC() {
using Descriptor = StoreWithVectorDescriptor;
@@ -4030,6 +4149,20 @@ void AccessorAssembler::GenerateStoreICTrampoline() {
vector);
}
+void AccessorAssembler::GenerateStoreICBaseline() {
+ using Descriptor = StoreBaselineDescriptor;
+
+ auto receiver = Parameter<Object>(Descriptor::kReceiver);
+ auto name = Parameter<Object>(Descriptor::kName);
+ auto value = Parameter<Object>(Descriptor::kValue);
+ auto slot = Parameter<TaggedIndex>(Descriptor::kSlot);
+ TNode<FeedbackVector> vector = LoadFeedbackVectorFromBaseline();
+ TNode<Context> context = LoadContextFromBaseline();
+
+ TailCallBuiltin(Builtins::kStoreIC, context, receiver, name, value, slot,
+ vector);
+}
+
void AccessorAssembler::GenerateKeyedStoreIC() {
using Descriptor = StoreWithVectorDescriptor;
@@ -4058,6 +4191,20 @@ void AccessorAssembler::GenerateKeyedStoreICTrampoline() {
vector);
}
+void AccessorAssembler::GenerateKeyedStoreICBaseline() {
+ using Descriptor = StoreBaselineDescriptor;
+
+ auto receiver = Parameter<Object>(Descriptor::kReceiver);
+ auto name = Parameter<Object>(Descriptor::kName);
+ auto value = Parameter<Object>(Descriptor::kValue);
+ auto slot = Parameter<TaggedIndex>(Descriptor::kSlot);
+ TNode<FeedbackVector> vector = LoadFeedbackVectorFromBaseline();
+ TNode<Context> context = LoadContextFromBaseline();
+
+ TailCallBuiltin(Builtins::kKeyedStoreIC, context, receiver, name, value, slot,
+ vector);
+}
+
void AccessorAssembler::GenerateStoreInArrayLiteralIC() {
using Descriptor = StoreWithVectorDescriptor;
@@ -4072,6 +4219,21 @@ void AccessorAssembler::GenerateStoreInArrayLiteralIC() {
StoreInArrayLiteralIC(&p);
}
+void AccessorAssembler::GenerateStoreInArrayLiteralICBaseline() {
+ using Descriptor = StoreBaselineDescriptor;
+
+ auto array = Parameter<Object>(Descriptor::kReceiver);
+ auto index = Parameter<Object>(Descriptor::kName);
+ auto value = Parameter<Object>(Descriptor::kValue);
+ auto slot = Parameter<TaggedIndex>(Descriptor::kSlot);
+
+ TNode<FeedbackVector> vector = LoadFeedbackVectorFromBaseline();
+ TNode<Context> context = LoadContextFromBaseline();
+
+ TailCallBuiltin(Builtins::kStoreInArrayLiteralIC, context, array, index,
+ value, slot, vector);
+}
+
void AccessorAssembler::GenerateCloneObjectIC_Slow() {
using Descriptor = CloneObjectWithVectorDescriptor;
auto source = Parameter<Object>(Descriptor::kSource);
@@ -4125,6 +4287,20 @@ void AccessorAssembler::GenerateCloneObjectIC_Slow() {
Return(result);
}
+void AccessorAssembler::GenerateCloneObjectICBaseline() {
+ using Descriptor = CloneObjectBaselineDescriptor;
+
+ auto source = Parameter<Object>(Descriptor::kSource);
+ auto flags = Parameter<Smi>(Descriptor::kFlags);
+ auto slot = Parameter<TaggedIndex>(Descriptor::kSlot);
+
+ TNode<FeedbackVector> vector = LoadFeedbackVectorFromBaseline();
+ TNode<Context> context = LoadContextFromBaseline();
+
+ TailCallBuiltin(Builtins::kCloneObjectIC, context, source, flags, slot,
+ vector);
+}
+
void AccessorAssembler::GenerateCloneObjectIC() {
using Descriptor = CloneObjectWithVectorDescriptor;
auto source = Parameter<Object>(Descriptor::kSource);
@@ -4219,17 +4395,15 @@ void AccessorAssembler::GenerateCloneObjectIC() {
},
1, IndexAdvanceMode::kPost);
- // If mutable HeapNumbers can occur, we need to go through the {object}
- // again here and properly clone them. We use a second loop here to
- // ensure that the GC (and heap verifier) always sees properly initialized
- // objects, i.e. never hits undefined values in double fields.
- if (!FLAG_unbox_double_fields) {
- TNode<IntPtrT> start_offset = TimesTaggedSize(result_start);
- TNode<IntPtrT> end_offset =
- IntPtrAdd(TimesTaggedSize(source_size), field_offset_difference);
- ConstructorBuiltinsAssembler(state()).CopyMutableHeapNumbersInObject(
- object, start_offset, end_offset);
- }
+ // We need to go through the {object} again here and properly clone them. We
+ // use a second loop here to ensure that the GC (and heap verifier) always
+ // sees properly initialized objects, i.e. never hits undefined values in
+ // double fields.
+ TNode<IntPtrT> start_offset = TimesTaggedSize(result_start);
+ TNode<IntPtrT> end_offset =
+ IntPtrAdd(TimesTaggedSize(source_size), field_offset_difference);
+ ConstructorBuiltinsAssembler(state()).CopyMutableHeapNumbersInObject(
+ object, start_offset, end_offset);
Return(object);
}
@@ -4286,6 +4460,18 @@ void AccessorAssembler::GenerateKeyedHasIC() {
KeyedLoadIC(&p, LoadAccessMode::kHas);
}
+void AccessorAssembler::GenerateKeyedHasICBaseline() {
+ using Descriptor = LoadBaselineDescriptor;
+
+ auto receiver = Parameter<Object>(Descriptor::kReceiver);
+ auto name = Parameter<Object>(Descriptor::kName);
+ auto slot = Parameter<TaggedIndex>(Descriptor::kSlot);
+ TNode<FeedbackVector> vector = LoadFeedbackVectorFromBaseline();
+ TNode<Context> context = LoadContextFromBaseline();
+
+ TailCallBuiltin(Builtins::kKeyedHasIC, context, receiver, name, slot, vector);
+}
+
void AccessorAssembler::GenerateKeyedHasIC_Megamorphic() {
using Descriptor = LoadWithVectorDescriptor;
diff --git a/deps/v8/src/ic/accessor-assembler.h b/deps/v8/src/ic/accessor-assembler.h
index bf506da478..64ad680882 100644
--- a/deps/v8/src/ic/accessor-assembler.h
+++ b/deps/v8/src/ic/accessor-assembler.h
@@ -31,30 +31,42 @@ class V8_EXPORT_PRIVATE AccessorAssembler : public CodeStubAssembler {
void GenerateLoadIC_NoFeedback();
void GenerateLoadGlobalIC_NoFeedback();
void GenerateLoadICTrampoline();
+ void GenerateLoadICBaseline();
void GenerateLoadICTrampoline_Megamorphic();
void GenerateLoadSuperIC();
+ void GenerateLoadSuperICBaseline();
void GenerateKeyedLoadIC();
void GenerateKeyedLoadIC_Megamorphic();
void GenerateKeyedLoadIC_PolymorphicName();
void GenerateKeyedLoadICTrampoline();
+ void GenerateKeyedLoadICBaseline();
void GenerateKeyedLoadICTrampoline_Megamorphic();
void GenerateStoreIC();
void GenerateStoreICTrampoline();
+ void GenerateStoreICBaseline();
void GenerateStoreGlobalIC();
void GenerateStoreGlobalICTrampoline();
+ void GenerateStoreGlobalICBaseline();
void GenerateCloneObjectIC();
+ void GenerateCloneObjectICBaseline();
void GenerateCloneObjectIC_Slow();
void GenerateKeyedHasIC();
+ void GenerateKeyedHasICBaseline();
void GenerateKeyedHasIC_Megamorphic();
void GenerateKeyedHasIC_PolymorphicName();
void GenerateLoadGlobalIC(TypeofMode typeof_mode);
void GenerateLoadGlobalICTrampoline(TypeofMode typeof_mode);
+ void GenerateLoadGlobalICBaseline(TypeofMode typeof_mode);
+ void GenerateLookupGlobalICBaseline(TypeofMode typeof_mode);
+ void GenerateLookupContextBaseline(TypeofMode typeof_mode);
void GenerateKeyedStoreIC();
void GenerateKeyedStoreICTrampoline();
+ void GenerateKeyedStoreICBaseline();
void GenerateStoreInArrayLiteralIC();
+ void GenerateStoreInArrayLiteralICBaseline();
void TryProbeStubCache(StubCache* stub_cache,
TNode<Object> lookup_start_object, TNode<Name> name,
@@ -243,6 +255,8 @@ class V8_EXPORT_PRIVATE AccessorAssembler : public CodeStubAssembler {
TNode<Object> value, Label* slow,
bool do_transitioning_store);
+ TNode<BoolT> IsPropertyDetailsConst(TNode<Uint32T> details);
+
void CheckFieldType(TNode<DescriptorArray> descriptors,
TNode<IntPtrT> name_index, TNode<Word32T> representation,
TNode<Object> value, Label* bailout);
@@ -454,7 +468,6 @@ class V8_EXPORT_PRIVATE AccessorAssembler : public CodeStubAssembler {
Label* unimplemented_elements_kind, Label* out_of_bounds,
Label* miss, ExitPoint* exit_point,
LoadAccessMode access_mode = LoadAccessMode::kLoad);
- TNode<BoolT> IsPropertyDetailsConst(TNode<Uint32T> details);
// Stub cache access helpers.
diff --git a/deps/v8/src/ic/binary-op-assembler.cc b/deps/v8/src/ic/binary-op-assembler.cc
index 8cba7172a2..3c0fc420ee 100644
--- a/deps/v8/src/ic/binary-op-assembler.cc
+++ b/deps/v8/src/ic/binary-op-assembler.cc
@@ -10,9 +10,9 @@ namespace v8 {
namespace internal {
TNode<Object> BinaryOpAssembler::Generate_AddWithFeedback(
- TNode<Context> context, TNode<Object> lhs, TNode<Object> rhs,
- TNode<UintPtrT> slot_id, TNode<HeapObject> maybe_feedback_vector,
- bool rhs_known_smi) {
+ const LazyNode<Context>& context, TNode<Object> lhs, TNode<Object> rhs,
+ TNode<UintPtrT> slot_id, const LazyNode<HeapObject>& maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode, bool rhs_known_smi) {
// Shared entry for floating point addition.
Label do_fadd(this), if_lhsisnotnumber(this, Label::kDeferred),
check_rhsisoddball(this, Label::kDeferred),
@@ -69,8 +69,8 @@ TNode<Object> BinaryOpAssembler::Generate_AddWithFeedback(
// Not overflowed.
{
var_type_feedback = SmiConstant(BinaryOperationFeedback::kSignedSmall);
- UpdateFeedback(var_type_feedback.value(), maybe_feedback_vector,
- slot_id);
+ UpdateFeedback(var_type_feedback.value(), maybe_feedback_vector(),
+ slot_id, update_feedback_mode);
var_result = smi_result;
Goto(&end);
}
@@ -118,7 +118,8 @@ TNode<Object> BinaryOpAssembler::Generate_AddWithFeedback(
BIND(&do_fadd);
{
var_type_feedback = SmiConstant(BinaryOperationFeedback::kNumber);
- UpdateFeedback(var_type_feedback.value(), maybe_feedback_vector, slot_id);
+ UpdateFeedback(var_type_feedback.value(), maybe_feedback_vector(), slot_id,
+ update_feedback_mode);
TNode<Float64T> value =
Float64Add(var_fadd_lhs.value(), var_fadd_rhs.value());
TNode<HeapNumber> result = AllocateHeapNumberWithValue(value);
@@ -169,10 +170,10 @@ TNode<Object> BinaryOpAssembler::Generate_AddWithFeedback(
&call_with_any_feedback);
var_type_feedback = SmiConstant(BinaryOperationFeedback::kString);
- UpdateFeedback(var_type_feedback.value(), maybe_feedback_vector,
- slot_id);
+ UpdateFeedback(var_type_feedback.value(), maybe_feedback_vector(),
+ slot_id, update_feedback_mode);
var_result =
- CallBuiltin(Builtins::kStringAdd_CheckNone, context, lhs, rhs);
+ CallBuiltin(Builtins::kStringAdd_CheckNone, context(), lhs, rhs);
Goto(&end);
}
@@ -194,20 +195,21 @@ TNode<Object> BinaryOpAssembler::Generate_AddWithFeedback(
{
// Both {lhs} and {rhs} are of BigInt type.
Label bigint_too_big(this);
- var_result = CallBuiltin(Builtins::kBigIntAddNoThrow, context, lhs, rhs);
+ var_result = CallBuiltin(Builtins::kBigIntAddNoThrow, context(), lhs, rhs);
// Check for sentinel that signals BigIntTooBig exception.
GotoIf(TaggedIsSmi(var_result.value()), &bigint_too_big);
var_type_feedback = SmiConstant(BinaryOperationFeedback::kBigInt);
- UpdateFeedback(var_type_feedback.value(), maybe_feedback_vector, slot_id);
+ UpdateFeedback(var_type_feedback.value(), maybe_feedback_vector(), slot_id,
+ update_feedback_mode);
Goto(&end);
BIND(&bigint_too_big);
{
// Update feedback to prevent deopt loop.
UpdateFeedback(SmiConstant(BinaryOperationFeedback::kAny),
- maybe_feedback_vector, slot_id);
- ThrowRangeError(context, MessageTemplate::kBigIntTooBig);
+ maybe_feedback_vector(), slot_id, update_feedback_mode);
+ ThrowRangeError(context(), MessageTemplate::kBigIntTooBig);
}
}
@@ -225,8 +227,9 @@ TNode<Object> BinaryOpAssembler::Generate_AddWithFeedback(
BIND(&call_add_stub);
{
- UpdateFeedback(var_type_feedback.value(), maybe_feedback_vector, slot_id);
- var_result = CallBuiltin(Builtins::kAdd, context, lhs, rhs);
+ UpdateFeedback(var_type_feedback.value(), maybe_feedback_vector(), slot_id,
+ update_feedback_mode);
+ var_result = CallBuiltin(Builtins::kAdd, context(), lhs, rhs);
Goto(&end);
}
@@ -235,10 +238,10 @@ TNode<Object> BinaryOpAssembler::Generate_AddWithFeedback(
}
TNode<Object> BinaryOpAssembler::Generate_BinaryOperationWithFeedback(
- TNode<Context> context, TNode<Object> lhs, TNode<Object> rhs,
- TNode<UintPtrT> slot_id, TNode<HeapObject> maybe_feedback_vector,
+ const LazyNode<Context>& context, TNode<Object> lhs, TNode<Object> rhs,
+ TNode<UintPtrT> slot_id, const LazyNode<HeapObject>& maybe_feedback_vector,
const SmiOperation& smiOperation, const FloatOperation& floatOperation,
- Operation op, bool rhs_known_smi) {
+ Operation op, UpdateFeedbackMode update_feedback_mode, bool rhs_known_smi) {
Label do_float_operation(this), end(this), call_stub(this),
check_rhsisoddball(this, Label::kDeferred), call_with_any_feedback(this),
if_lhsisnotnumber(this, Label::kDeferred),
@@ -285,7 +288,8 @@ TNode<Object> BinaryOpAssembler::Generate_BinaryOperationWithFeedback(
{
Comment("perform smi operation");
var_result = smiOperation(lhs_smi, CAST(rhs), &var_type_feedback);
- UpdateFeedback(var_type_feedback.value(), maybe_feedback_vector, slot_id);
+ UpdateFeedback(var_type_feedback.value(), maybe_feedback_vector(),
+ slot_id, update_feedback_mode);
Goto(&end);
}
}
@@ -328,7 +332,8 @@ TNode<Object> BinaryOpAssembler::Generate_BinaryOperationWithFeedback(
BIND(&do_float_operation);
{
var_type_feedback = SmiConstant(BinaryOperationFeedback::kNumber);
- UpdateFeedback(var_type_feedback.value(), maybe_feedback_vector, slot_id);
+ UpdateFeedback(var_type_feedback.value(), maybe_feedback_vector(), slot_id,
+ update_feedback_mode);
TNode<Float64T> lhs_value = var_float_lhs.value();
TNode<Float64T> rhs_value = var_float_rhs.value();
TNode<Float64T> value = floatOperation(lhs_value, rhs_value);
@@ -392,11 +397,12 @@ TNode<Object> BinaryOpAssembler::Generate_BinaryOperationWithFeedback(
BIND(&if_both_bigint);
{
var_type_feedback = SmiConstant(BinaryOperationFeedback::kBigInt);
- UpdateFeedback(var_type_feedback.value(), maybe_feedback_vector, slot_id);
+ UpdateFeedback(var_type_feedback.value(), maybe_feedback_vector(), slot_id,
+ update_feedback_mode);
if (op == Operation::kSubtract) {
Label bigint_too_big(this);
var_result =
- CallBuiltin(Builtins::kBigIntSubtractNoThrow, context, lhs, rhs);
+ CallBuiltin(Builtins::kBigIntSubtractNoThrow, context(), lhs, rhs);
// Check for sentinel that signals BigIntTooBig exception.
GotoIf(TaggedIsSmi(var_result.value()), &bigint_too_big);
@@ -406,11 +412,11 @@ TNode<Object> BinaryOpAssembler::Generate_BinaryOperationWithFeedback(
{
// Update feedback to prevent deopt loop.
UpdateFeedback(SmiConstant(BinaryOperationFeedback::kAny),
- maybe_feedback_vector, slot_id);
- ThrowRangeError(context, MessageTemplate::kBigIntTooBig);
+ maybe_feedback_vector(), slot_id, update_feedback_mode);
+ ThrowRangeError(context(), MessageTemplate::kBigIntTooBig);
}
} else {
- var_result = CallRuntime(Runtime::kBigIntBinaryOp, context, lhs, rhs,
+ var_result = CallRuntime(Runtime::kBigIntBinaryOp, context(), lhs, rhs,
SmiConstant(op));
Goto(&end);
}
@@ -424,20 +430,21 @@ TNode<Object> BinaryOpAssembler::Generate_BinaryOperationWithFeedback(
BIND(&call_stub);
{
- UpdateFeedback(var_type_feedback.value(), maybe_feedback_vector, slot_id);
+ UpdateFeedback(var_type_feedback.value(), maybe_feedback_vector(), slot_id,
+ update_feedback_mode);
TNode<Object> result;
switch (op) {
case Operation::kSubtract:
- result = CallBuiltin(Builtins::kSubtract, context, lhs, rhs);
+ result = CallBuiltin(Builtins::kSubtract, context(), lhs, rhs);
break;
case Operation::kMultiply:
- result = CallBuiltin(Builtins::kMultiply, context, lhs, rhs);
+ result = CallBuiltin(Builtins::kMultiply, context(), lhs, rhs);
break;
case Operation::kDivide:
- result = CallBuiltin(Builtins::kDivide, context, lhs, rhs);
+ result = CallBuiltin(Builtins::kDivide, context(), lhs, rhs);
break;
case Operation::kModulus:
- result = CallBuiltin(Builtins::kModulus, context, lhs, rhs);
+ result = CallBuiltin(Builtins::kModulus, context(), lhs, rhs);
break;
default:
UNREACHABLE();
@@ -451,9 +458,9 @@ TNode<Object> BinaryOpAssembler::Generate_BinaryOperationWithFeedback(
}
TNode<Object> BinaryOpAssembler::Generate_SubtractWithFeedback(
- TNode<Context> context, TNode<Object> lhs, TNode<Object> rhs,
- TNode<UintPtrT> slot_id, TNode<HeapObject> maybe_feedback_vector,
- bool rhs_known_smi) {
+ const LazyNode<Context>& context, TNode<Object> lhs, TNode<Object> rhs,
+ TNode<UintPtrT> slot_id, const LazyNode<HeapObject>& maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode, bool rhs_known_smi) {
auto smiFunction = [=](TNode<Smi> lhs, TNode<Smi> rhs,
TVariable<Smi>* var_type_feedback) {
Label end(this);
@@ -483,13 +490,13 @@ TNode<Object> BinaryOpAssembler::Generate_SubtractWithFeedback(
};
return Generate_BinaryOperationWithFeedback(
context, lhs, rhs, slot_id, maybe_feedback_vector, smiFunction,
- floatFunction, Operation::kSubtract, rhs_known_smi);
+ floatFunction, Operation::kSubtract, update_feedback_mode, rhs_known_smi);
}
TNode<Object> BinaryOpAssembler::Generate_MultiplyWithFeedback(
- TNode<Context> context, TNode<Object> lhs, TNode<Object> rhs,
- TNode<UintPtrT> slot_id, TNode<HeapObject> maybe_feedback_vector,
- bool rhs_known_smi) {
+ const LazyNode<Context>& context, TNode<Object> lhs, TNode<Object> rhs,
+ TNode<UintPtrT> slot_id, const LazyNode<HeapObject>& maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode, bool rhs_known_smi) {
auto smiFunction = [=](TNode<Smi> lhs, TNode<Smi> rhs,
TVariable<Smi>* var_type_feedback) {
TNode<Number> result = SmiMul(lhs, rhs);
@@ -503,13 +510,14 @@ TNode<Object> BinaryOpAssembler::Generate_MultiplyWithFeedback(
};
return Generate_BinaryOperationWithFeedback(
context, lhs, rhs, slot_id, maybe_feedback_vector, smiFunction,
- floatFunction, Operation::kMultiply, rhs_known_smi);
+ floatFunction, Operation::kMultiply, update_feedback_mode, rhs_known_smi);
}
TNode<Object> BinaryOpAssembler::Generate_DivideWithFeedback(
- TNode<Context> context, TNode<Object> dividend, TNode<Object> divisor,
- TNode<UintPtrT> slot_id, TNode<HeapObject> maybe_feedback_vector,
- bool rhs_known_smi) {
+ const LazyNode<Context>& context, TNode<Object> dividend,
+ TNode<Object> divisor, TNode<UintPtrT> slot_id,
+ const LazyNode<HeapObject>& maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode, bool rhs_known_smi) {
auto smiFunction = [=](TNode<Smi> lhs, TNode<Smi> rhs,
TVariable<Smi>* var_type_feedback) {
TVARIABLE(Object, var_result);
@@ -539,13 +547,14 @@ TNode<Object> BinaryOpAssembler::Generate_DivideWithFeedback(
};
return Generate_BinaryOperationWithFeedback(
context, dividend, divisor, slot_id, maybe_feedback_vector, smiFunction,
- floatFunction, Operation::kDivide, rhs_known_smi);
+ floatFunction, Operation::kDivide, update_feedback_mode, rhs_known_smi);
}
TNode<Object> BinaryOpAssembler::Generate_ModulusWithFeedback(
- TNode<Context> context, TNode<Object> dividend, TNode<Object> divisor,
- TNode<UintPtrT> slot_id, TNode<HeapObject> maybe_feedback_vector,
- bool rhs_known_smi) {
+ const LazyNode<Context>& context, TNode<Object> dividend,
+ TNode<Object> divisor, TNode<UintPtrT> slot_id,
+ const LazyNode<HeapObject>& maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode, bool rhs_known_smi) {
auto smiFunction = [=](TNode<Smi> lhs, TNode<Smi> rhs,
TVariable<Smi>* var_type_feedback) {
TNode<Number> result = SmiMod(lhs, rhs);
@@ -559,22 +568,24 @@ TNode<Object> BinaryOpAssembler::Generate_ModulusWithFeedback(
};
return Generate_BinaryOperationWithFeedback(
context, dividend, divisor, slot_id, maybe_feedback_vector, smiFunction,
- floatFunction, Operation::kModulus, rhs_known_smi);
+ floatFunction, Operation::kModulus, update_feedback_mode, rhs_known_smi);
}
TNode<Object> BinaryOpAssembler::Generate_ExponentiateWithFeedback(
- TNode<Context> context, TNode<Object> base, TNode<Object> exponent,
- TNode<UintPtrT> slot_id, TNode<HeapObject> maybe_feedback_vector,
- bool rhs_known_smi) {
+ const LazyNode<Context>& context, TNode<Object> base,
+ TNode<Object> exponent, TNode<UintPtrT> slot_id,
+ const LazyNode<HeapObject>& maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode, bool rhs_known_smi) {
// We currently don't optimize exponentiation based on feedback.
TNode<Smi> dummy_feedback = SmiConstant(BinaryOperationFeedback::kAny);
- UpdateFeedback(dummy_feedback, maybe_feedback_vector, slot_id);
- return CallBuiltin(Builtins::kExponentiate, context, base, exponent);
+ UpdateFeedback(dummy_feedback, maybe_feedback_vector(), slot_id,
+ update_feedback_mode);
+ return CallBuiltin(Builtins::kExponentiate, context(), base, exponent);
}
TNode<Object> BinaryOpAssembler::Generate_BitwiseBinaryOpWithOptionalFeedback(
Operation bitwise_op, TNode<Object> left, TNode<Object> right,
- TNode<Context> context, TVariable<Smi>* feedback) {
+ const LazyNode<Context>& context, TVariable<Smi>* feedback) {
TVARIABLE(Object, result);
TVARIABLE(Smi, var_left_feedback);
TVARIABLE(Smi, var_right_feedback);
@@ -592,14 +603,14 @@ TNode<Object> BinaryOpAssembler::Generate_BitwiseBinaryOpWithOptionalFeedback(
Label if_left_bigint(this), do_bigint_op(this);
TaggedToWord32OrBigIntWithFeedback(
- context, left, &if_left_number, &var_left_word32, &if_left_bigint,
+ context(), left, &if_left_number, &var_left_word32, &if_left_bigint,
&var_left_bigint, feedback ? &var_left_feedback : nullptr);
Label right_is_bigint(this);
BIND(&if_left_number);
{
TaggedToWord32OrBigIntWithFeedback(
- context, right, &do_number_op, &var_right_word32, &right_is_bigint,
+ context(), right, &do_number_op, &var_right_word32, &right_is_bigint,
&var_right_bigint, feedback ? &var_right_feedback : nullptr);
}
@@ -631,7 +642,7 @@ TNode<Object> BinaryOpAssembler::Generate_BitwiseBinaryOpWithOptionalFeedback(
// BigInt cases.
BIND(&if_left_bigint);
{
- TaggedToNumericWithFeedback(context, right, &var_right_maybe_bigint,
+ TaggedToNumericWithFeedback(context(), right, &var_right_maybe_bigint,
&var_right_feedback);
var_left_maybe_bigint = var_left_bigint.value();
Goto(&do_bigint_op);
@@ -643,7 +654,7 @@ TNode<Object> BinaryOpAssembler::Generate_BitwiseBinaryOpWithOptionalFeedback(
*feedback = SmiOr(var_left_feedback.value(), var_right_feedback.value());
}
result = CallRuntime(
- Runtime::kBigIntBinaryOp, context, var_left_maybe_bigint.value(),
+ Runtime::kBigIntBinaryOp, context(), var_left_maybe_bigint.value(),
var_right_maybe_bigint.value(), SmiConstant(bitwise_op));
Goto(&done);
}
diff --git a/deps/v8/src/ic/binary-op-assembler.h b/deps/v8/src/ic/binary-op-assembler.h
index a3a1e40e2d..6dff319736 100644
--- a/deps/v8/src/ic/binary-op-assembler.h
+++ b/deps/v8/src/ic/binary-op-assembler.h
@@ -21,106 +21,113 @@ class BinaryOpAssembler : public CodeStubAssembler {
: CodeStubAssembler(state) {}
TNode<Object> Generate_AddWithFeedback(
- TNode<Context> context, TNode<Object> left, TNode<Object> right,
- TNode<UintPtrT> slot, TNode<HeapObject> maybe_feedback_vector,
- bool rhs_known_smi);
+ const LazyNode<Context>& context, TNode<Object> left, TNode<Object> right,
+ TNode<UintPtrT> slot, const LazyNode<HeapObject>& maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode, bool rhs_known_smi);
TNode<Object> Generate_SubtractWithFeedback(
- TNode<Context> context, TNode<Object> left, TNode<Object> right,
- TNode<UintPtrT> slot, TNode<HeapObject> maybe_feedback_vector,
- bool rhs_known_smi);
+ const LazyNode<Context>& context, TNode<Object> left, TNode<Object> right,
+ TNode<UintPtrT> slot, const LazyNode<HeapObject>& maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode, bool rhs_known_smi);
TNode<Object> Generate_MultiplyWithFeedback(
- TNode<Context> context, TNode<Object> left, TNode<Object> right,
- TNode<UintPtrT> slot, TNode<HeapObject> maybe_feedback_vector,
- bool rhs_known_smi);
+ const LazyNode<Context>& context, TNode<Object> left, TNode<Object> right,
+ TNode<UintPtrT> slot, const LazyNode<HeapObject>& maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode, bool rhs_known_smi);
TNode<Object> Generate_DivideWithFeedback(
- TNode<Context> context, TNode<Object> dividend, TNode<Object> divisor,
- TNode<UintPtrT> slot, TNode<HeapObject> maybe_feedback_vector,
- bool rhs_known_smi);
+ const LazyNode<Context>& context, TNode<Object> dividend,
+ TNode<Object> divisor, TNode<UintPtrT> slot,
+ const LazyNode<HeapObject>& maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode, bool rhs_known_smi);
TNode<Object> Generate_ModulusWithFeedback(
- TNode<Context> context, TNode<Object> dividend, TNode<Object> divisor,
- TNode<UintPtrT> slot, TNode<HeapObject> maybe_feedback_vector,
- bool rhs_known_smi);
+ const LazyNode<Context>& context, TNode<Object> dividend,
+ TNode<Object> divisor, TNode<UintPtrT> slot,
+ const LazyNode<HeapObject>& maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode, bool rhs_known_smi);
TNode<Object> Generate_ExponentiateWithFeedback(
- TNode<Context> context, TNode<Object> base, TNode<Object> exponent,
- TNode<UintPtrT> slot, TNode<HeapObject> maybe_feedback_vector,
- bool rhs_known_smi);
+ const LazyNode<Context>& context, TNode<Object> base,
+ TNode<Object> exponent, TNode<UintPtrT> slot,
+ const LazyNode<HeapObject>& maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode, bool rhs_known_smi);
TNode<Object> Generate_BitwiseOrWithFeedback(
- TNode<Context> context, TNode<Object> left, TNode<Object> right,
- TNode<UintPtrT> slot, TNode<HeapObject> maybe_feedback_vector,
- bool /* unused */) {
+ const LazyNode<Context>& context, TNode<Object> left, TNode<Object> right,
+ TNode<UintPtrT> slot, const LazyNode<HeapObject>& maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode, bool /* unused */) {
TVARIABLE(Smi, feedback);
TNode<Object> result = Generate_BitwiseBinaryOpWithFeedback(
Operation::kBitwiseOr, left, right, context, &feedback);
- UpdateFeedback(feedback.value(), maybe_feedback_vector, slot);
+ UpdateFeedback(feedback.value(), maybe_feedback_vector(), slot,
+ update_feedback_mode);
return result;
}
TNode<Object> Generate_BitwiseXorWithFeedback(
- TNode<Context> context, TNode<Object> left, TNode<Object> right,
- TNode<UintPtrT> slot, TNode<HeapObject> maybe_feedback_vector,
- bool /* unused */) {
+ const LazyNode<Context>& context, TNode<Object> left, TNode<Object> right,
+ TNode<UintPtrT> slot, const LazyNode<HeapObject>& maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode, bool /* unused */) {
TVARIABLE(Smi, feedback);
TNode<Object> result = Generate_BitwiseBinaryOpWithFeedback(
Operation::kBitwiseXor, left, right, context, &feedback);
- UpdateFeedback(feedback.value(), maybe_feedback_vector, slot);
+ UpdateFeedback(feedback.value(), maybe_feedback_vector(), slot,
+ update_feedback_mode);
return result;
}
TNode<Object> Generate_BitwiseAndWithFeedback(
- TNode<Context> context, TNode<Object> left, TNode<Object> right,
- TNode<UintPtrT> slot, TNode<HeapObject> maybe_feedback_vector,
- bool /* unused */) {
+ const LazyNode<Context>& context, TNode<Object> left, TNode<Object> right,
+ TNode<UintPtrT> slot, const LazyNode<HeapObject>& maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode, bool /* unused */) {
TVARIABLE(Smi, feedback);
TNode<Object> result = Generate_BitwiseBinaryOpWithFeedback(
Operation::kBitwiseAnd, left, right, context, &feedback);
- UpdateFeedback(feedback.value(), maybe_feedback_vector, slot);
+ UpdateFeedback(feedback.value(), maybe_feedback_vector(), slot,
+ update_feedback_mode);
return result;
}
TNode<Object> Generate_ShiftLeftWithFeedback(
- TNode<Context> context, TNode<Object> left, TNode<Object> right,
- TNode<UintPtrT> slot, TNode<HeapObject> maybe_feedback_vector,
- bool /* unused */) {
+ const LazyNode<Context>& context, TNode<Object> left, TNode<Object> right,
+ TNode<UintPtrT> slot, const LazyNode<HeapObject>& maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode, bool /* unused */) {
TVARIABLE(Smi, feedback);
TNode<Object> result = Generate_BitwiseBinaryOpWithFeedback(
Operation::kShiftLeft, left, right, context, &feedback);
- UpdateFeedback(feedback.value(), maybe_feedback_vector, slot);
+ UpdateFeedback(feedback.value(), maybe_feedback_vector(), slot,
+ update_feedback_mode);
return result;
}
TNode<Object> Generate_ShiftRightWithFeedback(
- TNode<Context> context, TNode<Object> left, TNode<Object> right,
- TNode<UintPtrT> slot, TNode<HeapObject> maybe_feedback_vector,
- bool /* unused */) {
+ const LazyNode<Context>& context, TNode<Object> left, TNode<Object> right,
+ TNode<UintPtrT> slot, const LazyNode<HeapObject>& maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode, bool /* unused */) {
TVARIABLE(Smi, feedback);
TNode<Object> result = Generate_BitwiseBinaryOpWithFeedback(
Operation::kShiftRight, left, right, context, &feedback);
- UpdateFeedback(feedback.value(), maybe_feedback_vector, slot);
+ UpdateFeedback(feedback.value(), maybe_feedback_vector(), slot,
+ update_feedback_mode);
return result;
}
TNode<Object> Generate_ShiftRightLogicalWithFeedback(
- TNode<Context> context, TNode<Object> left, TNode<Object> right,
- TNode<UintPtrT> slot, TNode<HeapObject> maybe_feedback_vector,
- bool /* unused */) {
+ const LazyNode<Context>& context, TNode<Object> left, TNode<Object> right,
+ TNode<UintPtrT> slot, const LazyNode<HeapObject>& maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode, bool /* unused */) {
TVARIABLE(Smi, feedback);
TNode<Object> result = Generate_BitwiseBinaryOpWithFeedback(
Operation::kShiftRightLogical, left, right, context, &feedback);
- UpdateFeedback(feedback.value(), maybe_feedback_vector, slot);
+ UpdateFeedback(feedback.value(), maybe_feedback_vector(), slot,
+ update_feedback_mode);
return result;
}
- TNode<Object> Generate_BitwiseBinaryOpWithFeedback(Operation bitwise_op,
- TNode<Object> left,
- TNode<Object> right,
- TNode<Context> context,
- TVariable<Smi>* feedback) {
+ TNode<Object> Generate_BitwiseBinaryOpWithFeedback(
+ Operation bitwise_op, TNode<Object> left, TNode<Object> right,
+ const LazyNode<Context>& context, TVariable<Smi>* feedback) {
return Generate_BitwiseBinaryOpWithOptionalFeedback(bitwise_op, left, right,
context, feedback);
}
@@ -129,8 +136,8 @@ class BinaryOpAssembler : public CodeStubAssembler {
TNode<Object> left,
TNode<Object> right,
TNode<Context> context) {
- return Generate_BitwiseBinaryOpWithOptionalFeedback(bitwise_op, left, right,
- context, nullptr);
+ return Generate_BitwiseBinaryOpWithOptionalFeedback(
+ bitwise_op, left, right, [&] { return context; }, nullptr);
}
private:
@@ -140,14 +147,15 @@ class BinaryOpAssembler : public CodeStubAssembler {
std::function<TNode<Float64T>(TNode<Float64T>, TNode<Float64T>)>;
TNode<Object> Generate_BinaryOperationWithFeedback(
- TNode<Context> context, TNode<Object> left, TNode<Object> right,
- TNode<UintPtrT> slot, TNode<HeapObject> maybe_feedback_vector,
+ const LazyNode<Context>& context, TNode<Object> left, TNode<Object> right,
+ TNode<UintPtrT> slot, const LazyNode<HeapObject>& maybe_feedback_vector,
const SmiOperation& smiOperation, const FloatOperation& floatOperation,
- Operation op, bool rhs_known_smi);
+ Operation op, UpdateFeedbackMode update_feedback_mode,
+ bool rhs_known_smi);
TNode<Object> Generate_BitwiseBinaryOpWithOptionalFeedback(
Operation bitwise_op, TNode<Object> left, TNode<Object> right,
- TNode<Context> context, TVariable<Smi>* feedback);
+ const LazyNode<Context>& context, TVariable<Smi>* feedback);
};
} // namespace internal
diff --git a/deps/v8/src/ic/call-optimization.cc b/deps/v8/src/ic/call-optimization.cc
index 72f43743d2..8a6374a431 100644
--- a/deps/v8/src/ic/call-optimization.cc
+++ b/deps/v8/src/ic/call-optimization.cc
@@ -60,19 +60,10 @@ Handle<JSObject> CallOptimization::LookupHolderOfExpectedType(
return Handle<JSObject>::null();
}
-bool CallOptimization::IsCompatibleReceiver(Handle<Object> receiver,
- Handle<JSObject> holder) const {
+bool CallOptimization::IsCompatibleReceiverMap(
+ Handle<JSObject> api_holder, Handle<JSObject> holder,
+ HolderLookup holder_lookup) const {
DCHECK(is_simple_api_call());
- if (!receiver->IsHeapObject()) return false;
- Handle<Map> map(HeapObject::cast(*receiver).map(), holder->GetIsolate());
- return IsCompatibleReceiverMap(map, holder);
-}
-
-
-bool CallOptimization::IsCompatibleReceiverMap(Handle<Map> map,
- Handle<JSObject> holder) const {
- HolderLookup holder_lookup;
- Handle<JSObject> api_holder = LookupHolderOfExpectedType(map, &holder_lookup);
switch (holder_lookup) {
case kHolderNotFound:
return false;
diff --git a/deps/v8/src/ic/call-optimization.h b/deps/v8/src/ic/call-optimization.h
index c8c7f25d5a..b6d49a1bf9 100644
--- a/deps/v8/src/ic/call-optimization.h
+++ b/deps/v8/src/ic/call-optimization.h
@@ -42,13 +42,8 @@ class CallOptimization {
Handle<JSObject> LookupHolderOfExpectedType(
Handle<Map> receiver_map, HolderLookup* holder_lookup) const;
- // Check if the api holder is between the receiver and the holder.
- bool IsCompatibleReceiver(Handle<Object> receiver,
- Handle<JSObject> holder) const;
-
- // Check if the api holder is between the receiver and the holder.
- bool IsCompatibleReceiverMap(Handle<Map> receiver_map,
- Handle<JSObject> holder) const;
+ bool IsCompatibleReceiverMap(Handle<JSObject> api_holder,
+ Handle<JSObject> holder, HolderLookup) const;
private:
void Initialize(Isolate* isolate, Handle<JSFunction> function);
diff --git a/deps/v8/src/ic/ic.cc b/deps/v8/src/ic/ic.cc
index d13d1bdab5..2614e27440 100644
--- a/deps/v8/src/ic/ic.cc
+++ b/deps/v8/src/ic/ic.cc
@@ -432,7 +432,7 @@ MaybeHandle<Object> LoadIC::Load(Handle<Object> object, Handle<Name> name,
LookupForRead(&it, IsAnyHas());
if (name->IsPrivate()) {
- if (name->IsPrivateName() && !it.IsFound()) {
+ if (!IsAnyHas() && name->IsPrivateName() && !it.IsFound()) {
Handle<String> name_string(
String::cast(Symbol::cast(*name).description()), isolate());
if (name->IsPrivateBrand()) {
@@ -862,13 +862,14 @@ Handle<Object> LoadIC::ComputeHandler(LookupIterator* lookup) {
Handle<Object> accessors = lookup->GetAccessors();
if (accessors->IsAccessorPair()) {
- if (lookup->TryLookupCachedProperty()) {
+ Handle<AccessorPair> accessor_pair =
+ Handle<AccessorPair>::cast(accessors);
+ if (lookup->TryLookupCachedProperty(accessor_pair)) {
DCHECK_EQ(LookupIterator::DATA, lookup->state());
return ComputeHandler(lookup);
}
- Handle<Object> getter(AccessorPair::cast(*accessors).getter(),
- isolate());
+ Handle<Object> getter(accessor_pair->getter(), isolate());
if (!getter->IsJSFunction() && !getter->IsFunctionTemplateInfo()) {
TRACE_HANDLER_STATS(isolate(), LoadIC_SlowStub);
return LoadHandler::LoadSlow(isolate());
@@ -887,15 +888,17 @@ Handle<Object> LoadIC::ComputeHandler(LookupIterator* lookup) {
CallOptimization call_optimization(isolate(), getter);
if (call_optimization.is_simple_api_call()) {
- if (!call_optimization.IsCompatibleReceiverMap(map, holder) ||
+ CallOptimization::HolderLookup holder_lookup;
+ Handle<JSObject> api_holder =
+ call_optimization.LookupHolderOfExpectedType(map, &holder_lookup);
+
+ if (!call_optimization.IsCompatibleReceiverMap(api_holder, holder,
+ holder_lookup) ||
!holder->HasFastProperties()) {
TRACE_HANDLER_STATS(isolate(), LoadIC_SlowStub);
return LoadHandler::LoadSlow(isolate());
}
- CallOptimization::HolderLookup holder_lookup;
- call_optimization.LookupHolderOfExpectedType(map, &holder_lookup);
-
smi_handler = LoadHandler::LoadApiGetter(
isolate(), holder_lookup == CallOptimization::kHolderIsReceiver);
@@ -993,7 +996,8 @@ Handle<Object> LoadIC::ComputeHandler(LookupIterator* lookup) {
}
if (lookup->constness() == PropertyConstness::kConst &&
!holder_is_lookup_start_object) {
- DCHECK(!lookup->is_dictionary_holder());
+ DCHECK_IMPLIES(!V8_DICT_PROPERTY_CONST_TRACKING_BOOL,
+ !lookup->is_dictionary_holder());
Handle<Object> value = lookup->GetDataValue();
@@ -1745,11 +1749,12 @@ MaybeObjectHandle StoreIC::ComputeHandler(LookupIterator* lookup) {
CallOptimization call_optimization(isolate(), setter);
if (call_optimization.is_simple_api_call()) {
- if (call_optimization.IsCompatibleReceiver(receiver, holder)) {
- CallOptimization::HolderLookup holder_lookup;
- call_optimization.LookupHolderOfExpectedType(
- lookup_start_object_map(), &holder_lookup);
-
+ CallOptimization::HolderLookup holder_lookup;
+ Handle<JSObject> api_holder =
+ call_optimization.LookupHolderOfExpectedType(
+ lookup_start_object_map(), &holder_lookup);
+ if (call_optimization.IsCompatibleReceiverMap(api_holder, holder,
+ holder_lookup)) {
Handle<Smi> smi_handler = StoreHandler::StoreApiSetter(
isolate(),
holder_lookup == CallOptimization::kHolderIsReceiver);
@@ -1803,6 +1808,8 @@ MaybeObjectHandle StoreIC::ComputeHandler(LookupIterator* lookup) {
}
TRACE_HANDLER_STATS(isolate(), StoreIC_StoreNormalDH);
DCHECK(holder.is_identical_to(receiver));
+ DCHECK_IMPLIES(!V8_DICT_PROPERTY_CONST_TRACKING_BOOL,
+ lookup->constness() == PropertyConstness::kMutable);
// TODO(v8:11167) don't create slow hanlder once OrderedNameDictionary
// supported.
Handle<Smi> handler = V8_DICT_MODE_PROTOTYPES_BOOL
@@ -2766,9 +2773,7 @@ static Handle<Map> FastCloneObjectMap(Isolate* isolate, Handle<Map> source_map,
int slack = 0;
Handle<DescriptorArray> descriptors = DescriptorArray::CopyForFastObjectClone(
isolate, source_descriptors, size, slack);
- Handle<LayoutDescriptor> layout =
- LayoutDescriptor::New(isolate, map, descriptors, size);
- map->InitializeDescriptors(isolate, *descriptors, *layout);
+ map->InitializeDescriptors(isolate, *descriptors);
map->CopyUnusedPropertyFieldsAdjustedForInstanceSize(*source_map);
// Update bitfields
diff --git a/deps/v8/src/ic/keyed-store-generic.cc b/deps/v8/src/ic/keyed-store-generic.cc
index b2d33938b4..c741298d2c 100644
--- a/deps/v8/src/ic/keyed-store-generic.cc
+++ b/deps/v8/src/ic/keyed-store-generic.cc
@@ -842,10 +842,10 @@ void KeyedStoreGenericAssembler::EmitGenericPropertyStore(
&var_name_index, &not_found);
BIND(&dictionary_found);
{
- Label overwrite(this);
+ Label check_const(this), overwrite(this), done(this);
TNode<Uint32T> details =
LoadDetailsByKeyIndex(properties, var_name_index.value());
- JumpIfDataProperty(details, &overwrite,
+ JumpIfDataProperty(details, &check_const,
ShouldReconfigureExisting() ? nullptr : &readonly);
if (ShouldCallSetter()) {
@@ -860,13 +860,30 @@ void KeyedStoreGenericAssembler::EmitGenericPropertyStore(
Goto(slow);
}
+ BIND(&check_const);
+ {
+ if (V8_DICT_PROPERTY_CONST_TRACKING_BOOL) {
+ GotoIfNot(IsPropertyDetailsConst(details), &overwrite);
+ TNode<Object> prev_value =
+ LoadValueByKeyIndex(properties, var_name_index.value());
+
+ BranchIfSameValue(prev_value, p->value(), &done, slow,
+ SameValueMode::kNumbersOnly);
+ } else {
+ Goto(&overwrite);
+ }
+ }
+
BIND(&overwrite);
{
CheckForAssociatedProtector(name, slow);
StoreValueByKeyIndex<NameDictionary>(properties, var_name_index.value(),
p->value());
- exit_point->Return(p->value());
+ Goto(&done);
}
+
+ BIND(&done);
+ exit_point->Return(p->value());
}
BIND(&not_found);
diff --git a/deps/v8/src/ic/unary-op-assembler.cc b/deps/v8/src/ic/unary-op-assembler.cc
index 6580601a1f..4308f561a7 100644
--- a/deps/v8/src/ic/unary-op-assembler.cc
+++ b/deps/v8/src/ic/unary-op-assembler.cc
@@ -18,7 +18,8 @@ class UnaryOpAssemblerImpl final : public CodeStubAssembler {
TNode<Object> BitwiseNot(TNode<Context> context, TNode<Object> value,
TNode<UintPtrT> slot,
- TNode<HeapObject> maybe_feedback_vector) {
+ TNode<HeapObject> maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode) {
// TODO(jgruber): Make this implementation more consistent with other unary
// ops (i.e. have them all use UnaryOpWithFeedback or some other common
// mechanism).
@@ -38,13 +39,13 @@ class UnaryOpAssemblerImpl final : public CodeStubAssembler {
TaggedIsSmi(var_result.value()), BinaryOperationFeedback::kSignedSmall,
BinaryOperationFeedback::kNumber);
UpdateFeedback(SmiOr(result_type, var_feedback.value()),
- maybe_feedback_vector, slot);
+ maybe_feedback_vector, slot, update_feedback_mode);
Goto(&out);
// BigInt case.
BIND(&if_bigint);
UpdateFeedback(SmiConstant(BinaryOperationFeedback::kBigInt),
- maybe_feedback_vector, slot);
+ maybe_feedback_vector, slot, update_feedback_mode);
var_result =
CallRuntime(Runtime::kBigIntUnaryOp, context, var_bigint.value(),
SmiConstant(Operation::kBitwiseNot));
@@ -56,21 +57,24 @@ class UnaryOpAssemblerImpl final : public CodeStubAssembler {
TNode<Object> Decrement(TNode<Context> context, TNode<Object> value,
TNode<UintPtrT> slot,
- TNode<HeapObject> maybe_feedback_vector) {
- return IncrementOrDecrement<Operation::kDecrement>(context, value, slot,
- maybe_feedback_vector);
+ TNode<HeapObject> maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode) {
+ return IncrementOrDecrement<Operation::kDecrement>(
+ context, value, slot, maybe_feedback_vector, update_feedback_mode);
}
TNode<Object> Increment(TNode<Context> context, TNode<Object> value,
TNode<UintPtrT> slot,
- TNode<HeapObject> maybe_feedback_vector) {
- return IncrementOrDecrement<Operation::kIncrement>(context, value, slot,
- maybe_feedback_vector);
+ TNode<HeapObject> maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode) {
+ return IncrementOrDecrement<Operation::kIncrement>(
+ context, value, slot, maybe_feedback_vector, update_feedback_mode);
}
TNode<Object> Negate(TNode<Context> context, TNode<Object> value,
TNode<UintPtrT> slot,
- TNode<HeapObject> maybe_feedback_vector) {
+ TNode<HeapObject> maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode) {
SmiOperation smi_op = [=](TNode<Smi> smi_value,
TVariable<Smi>* var_feedback, Label* do_float_op,
TVariable<Float64T>* var_float) {
@@ -108,7 +112,8 @@ class UnaryOpAssemblerImpl final : public CodeStubAssembler {
SmiConstant(Operation::kNegate)));
};
return UnaryOpWithFeedback(context, value, slot, maybe_feedback_vector,
- smi_op, float_op, bigint_op);
+ smi_op, float_op, bigint_op,
+ update_feedback_mode);
}
private:
@@ -125,7 +130,8 @@ class UnaryOpAssemblerImpl final : public CodeStubAssembler {
TNode<HeapObject> maybe_feedback_vector,
const SmiOperation& smi_op,
const FloatOperation& float_op,
- const BigIntOperation& bigint_op) {
+ const BigIntOperation& bigint_op,
+ UpdateFeedbackMode update_feedback_mode) {
TVARIABLE(Object, var_value, value);
TVARIABLE(Object, var_result);
TVARIABLE(Float64T, var_float_value);
@@ -207,14 +213,16 @@ class UnaryOpAssemblerImpl final : public CodeStubAssembler {
}
BIND(&end);
- UpdateFeedback(var_feedback.value(), maybe_feedback_vector, slot);
+ UpdateFeedback(var_feedback.value(), maybe_feedback_vector, slot,
+ update_feedback_mode);
return var_result.value();
}
template <Operation kOperation>
TNode<Object> IncrementOrDecrement(TNode<Context> context,
TNode<Object> value, TNode<UintPtrT> slot,
- TNode<HeapObject> maybe_feedback_vector) {
+ TNode<HeapObject> maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode) {
STATIC_ASSERT(kOperation == Operation::kIncrement ||
kOperation == Operation::kDecrement);
static constexpr int kAddValue =
@@ -245,7 +253,8 @@ class UnaryOpAssemblerImpl final : public CodeStubAssembler {
SmiConstant(kOperation)));
};
return UnaryOpWithFeedback(context, value, slot, maybe_feedback_vector,
- smi_op, float_op, bigint_op);
+ smi_op, float_op, bigint_op,
+ update_feedback_mode);
}
};
@@ -253,30 +262,38 @@ class UnaryOpAssemblerImpl final : public CodeStubAssembler {
TNode<Object> UnaryOpAssembler::Generate_BitwiseNotWithFeedback(
TNode<Context> context, TNode<Object> value, TNode<UintPtrT> slot,
- TNode<HeapObject> maybe_feedback_vector) {
+ TNode<HeapObject> maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode) {
UnaryOpAssemblerImpl a(state_);
- return a.BitwiseNot(context, value, slot, maybe_feedback_vector);
+ return a.BitwiseNot(context, value, slot, maybe_feedback_vector,
+ update_feedback_mode);
}
TNode<Object> UnaryOpAssembler::Generate_DecrementWithFeedback(
TNode<Context> context, TNode<Object> value, TNode<UintPtrT> slot,
- TNode<HeapObject> maybe_feedback_vector) {
+ TNode<HeapObject> maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode) {
UnaryOpAssemblerImpl a(state_);
- return a.Decrement(context, value, slot, maybe_feedback_vector);
+ return a.Decrement(context, value, slot, maybe_feedback_vector,
+ update_feedback_mode);
}
TNode<Object> UnaryOpAssembler::Generate_IncrementWithFeedback(
TNode<Context> context, TNode<Object> value, TNode<UintPtrT> slot,
- TNode<HeapObject> maybe_feedback_vector) {
+ TNode<HeapObject> maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode) {
UnaryOpAssemblerImpl a(state_);
- return a.Increment(context, value, slot, maybe_feedback_vector);
+ return a.Increment(context, value, slot, maybe_feedback_vector,
+ update_feedback_mode);
}
TNode<Object> UnaryOpAssembler::Generate_NegateWithFeedback(
TNode<Context> context, TNode<Object> value, TNode<UintPtrT> slot,
- TNode<HeapObject> maybe_feedback_vector) {
+ TNode<HeapObject> maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode) {
UnaryOpAssemblerImpl a(state_);
- return a.Negate(context, value, slot, maybe_feedback_vector);
+ return a.Negate(context, value, slot, maybe_feedback_vector,
+ update_feedback_mode);
}
} // namespace internal
diff --git a/deps/v8/src/ic/unary-op-assembler.h b/deps/v8/src/ic/unary-op-assembler.h
index 447806722d..7dc6079fc4 100644
--- a/deps/v8/src/ic/unary-op-assembler.h
+++ b/deps/v8/src/ic/unary-op-assembler.h
@@ -21,19 +21,23 @@ class UnaryOpAssembler final {
TNode<Object> Generate_BitwiseNotWithFeedback(
TNode<Context> context, TNode<Object> value, TNode<UintPtrT> slot,
- TNode<HeapObject> maybe_feedback_vector);
+ TNode<HeapObject> maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode);
TNode<Object> Generate_DecrementWithFeedback(
TNode<Context> context, TNode<Object> value, TNode<UintPtrT> slot,
- TNode<HeapObject> maybe_feedback_vector);
+ TNode<HeapObject> maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode);
TNode<Object> Generate_IncrementWithFeedback(
TNode<Context> context, TNode<Object> value, TNode<UintPtrT> slot,
- TNode<HeapObject> maybe_feedback_vector);
+ TNode<HeapObject> maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode);
TNode<Object> Generate_NegateWithFeedback(
TNode<Context> context, TNode<Object> value, TNode<UintPtrT> slot,
- TNode<HeapObject> maybe_feedback_vector);
+ TNode<HeapObject> maybe_feedback_vector,
+ UpdateFeedbackMode update_feedback_mode);
private:
compiler::CodeAssemblerState* const state_;