Commit f57ba6b9 authored by Sigurd Schneider's avatar Sigurd Schneider Committed by Commit Bot

[turbofan] Add feedback to CheckNumber

Bug: v8:7127, v8:7204
Change-Id: I923658dd9142d658f1155015f5ee02526d280e2a
Reviewed-on: https://chromium-review.googlesource.com/824171
Commit-Queue: Sigurd Schneider <sigurds@chromium.org>
Reviewed-by: 's avatarBenedikt Meurer <bmeurer@chromium.org>
Cr-Commit-Position: refs/heads/master@{#50101}
parent 2f3f5301
...@@ -1433,6 +1433,7 @@ Node* EffectControlLinearizer::LowerCompareMaps(Node* node) { ...@@ -1433,6 +1433,7 @@ Node* EffectControlLinearizer::LowerCompareMaps(Node* node) {
Node* EffectControlLinearizer::LowerCheckNumber(Node* node, Node* frame_state) { Node* EffectControlLinearizer::LowerCheckNumber(Node* node, Node* frame_state) {
Node* value = node->InputAt(0); Node* value = node->InputAt(0);
const CheckParameters& params = CheckParametersOf(node->op());
auto if_not_smi = __ MakeDeferredLabel(); auto if_not_smi = __ MakeDeferredLabel();
auto done = __ MakeLabel(); auto done = __ MakeLabel();
...@@ -1444,7 +1445,7 @@ Node* EffectControlLinearizer::LowerCheckNumber(Node* node, Node* frame_state) { ...@@ -1444,7 +1445,7 @@ Node* EffectControlLinearizer::LowerCheckNumber(Node* node, Node* frame_state) {
__ Bind(&if_not_smi); __ Bind(&if_not_smi);
Node* value_map = __ LoadField(AccessBuilder::ForMap(), value); Node* value_map = __ LoadField(AccessBuilder::ForMap(), value);
Node* check1 = __ WordEqual(value_map, __ HeapNumberMapConstant()); Node* check1 = __ WordEqual(value_map, __ HeapNumberMapConstant());
__ DeoptimizeIfNot(DeoptimizeReason::kNotAHeapNumber, VectorSlotPair(), __ DeoptimizeIfNot(DeoptimizeReason::kNotAHeapNumber, params.feedback(),
check1, frame_state); check1, frame_state);
__ Goto(&done); __ Goto(&done);
......
...@@ -1045,8 +1045,9 @@ Reduction JSBuiltinReducer::ReduceArrayPush(Node* node) { ...@@ -1045,8 +1045,9 @@ Reduction JSBuiltinReducer::ReduceArrayPush(Node* node) {
value = effect = value = effect =
graph()->NewNode(simplified()->CheckSmi(), value, effect, control); graph()->NewNode(simplified()->CheckSmi(), value, effect, control);
} else if (IsDoubleElementsKind(receiver_map->elements_kind())) { } else if (IsDoubleElementsKind(receiver_map->elements_kind())) {
value = effect = graph()->NewNode(simplified()->CheckNumber(), value, value = effect =
effect, control); graph()->NewNode(simplified()->CheckNumber(VectorSlotPair()), value,
effect, control);
// Make sure we do not store signaling NaNs into double arrays. // Make sure we do not store signaling NaNs into double arrays.
value = graph()->NewNode(simplified()->NumberSilenceNaN(), value); value = graph()->NewNode(simplified()->NumberSilenceNaN(), value);
} }
......
...@@ -624,8 +624,9 @@ Reduction JSCreateLowering::ReduceNewArray(Node* node, ...@@ -624,8 +624,9 @@ Reduction JSCreateLowering::ReduceNewArray(Node* node,
} else if (IsDoubleElementsKind(elements_kind)) { } else if (IsDoubleElementsKind(elements_kind)) {
for (auto& value : values) { for (auto& value : values) {
if (!NodeProperties::GetType(value)->Is(Type::Number())) { if (!NodeProperties::GetType(value)->Is(Type::Number())) {
value = effect = graph()->NewNode(simplified()->CheckNumber(), value, value = effect =
effect, control); graph()->NewNode(simplified()->CheckNumber(VectorSlotPair()), value,
effect, control);
} }
// Make sure we do not store signaling NaNs into double arrays. // Make sure we do not store signaling NaNs into double arrays.
value = graph()->NewNode(simplified()->NumberSilenceNaN(), value); value = graph()->NewNode(simplified()->NumberSilenceNaN(), value);
......
...@@ -1808,8 +1808,9 @@ JSNativeContextSpecialization::BuildPropertyStore( ...@@ -1808,8 +1808,9 @@ JSNativeContextSpecialization::BuildPropertyStore(
access_mode == AccessMode::kStoreInLiteral); access_mode == AccessMode::kStoreInLiteral);
switch (field_representation) { switch (field_representation) {
case MachineRepresentation::kFloat64: { case MachineRepresentation::kFloat64: {
value = effect = graph()->NewNode(simplified()->CheckNumber(), value, value = effect =
effect, control); graph()->NewNode(simplified()->CheckNumber(VectorSlotPair()), value,
effect, control);
if (!field_index.is_inobject() || field_index.is_hidden_field() || if (!field_index.is_inobject() || field_index.is_hidden_field() ||
!FLAG_unbox_double_fields) { !FLAG_unbox_double_fields) {
if (access_info.HasTransitionMap()) { if (access_info.HasTransitionMap()) {
...@@ -2398,8 +2399,9 @@ JSNativeContextSpecialization::BuildElementAccess( ...@@ -2398,8 +2399,9 @@ JSNativeContextSpecialization::BuildElementAccess(
value = effect = value = effect =
graph()->NewNode(simplified()->CheckSmi(), value, effect, control); graph()->NewNode(simplified()->CheckSmi(), value, effect, control);
} else if (IsDoubleElementsKind(elements_kind)) { } else if (IsDoubleElementsKind(elements_kind)) {
value = effect = graph()->NewNode(simplified()->CheckNumber(), value, value = effect =
effect, control); graph()->NewNode(simplified()->CheckNumber(VectorSlotPair()), value,
effect, control);
// Make sure we do not store signalling NaNs into double arrays. // Make sure we do not store signalling NaNs into double arrays.
value = graph()->NewNode(simplified()->NumberSilenceNaN(), value); value = graph()->NewNode(simplified()->NumberSilenceNaN(), value);
} }
......
...@@ -82,8 +82,9 @@ bool PropertyAccessBuilder::TryBuildNumberCheck(MapHandles const& maps, ...@@ -82,8 +82,9 @@ bool PropertyAccessBuilder::TryBuildNumberCheck(MapHandles const& maps,
Node* control) { Node* control) {
if (HasOnlyNumberMaps(maps)) { if (HasOnlyNumberMaps(maps)) {
// Monomorphic number access (we also deal with Smis here). // Monomorphic number access (we also deal with Smis here).
*receiver = *effect = graph()->NewNode(simplified()->CheckNumber(), *receiver = *effect =
*receiver, *effect, control); graph()->NewNode(simplified()->CheckNumber(VectorSlotPair()), *receiver,
*effect, control);
return true; return true;
} }
return false; return false;
......
...@@ -132,6 +132,9 @@ bool IsCompatibleCheck(Node const* a, Node const* b) { ...@@ -132,6 +132,9 @@ bool IsCompatibleCheck(Node const* a, Node const* b) {
} else if (a->opcode() == IrOpcode::kCheckBounds && } else if (a->opcode() == IrOpcode::kCheckBounds &&
b->opcode() == IrOpcode::kCheckBounds) { b->opcode() == IrOpcode::kCheckBounds) {
// CheckBounds are compatible independent of associated feedback. // CheckBounds are compatible independent of associated feedback.
} else if (a->opcode() == IrOpcode::kCheckNumber &&
b->opcode() == IrOpcode::kCheckNumber) {
// CheckNumbers are compatible independent of associated feedback.
} else { } else {
return false; return false;
} }
......
...@@ -139,7 +139,8 @@ std::ostream& operator<<(std::ostream& os, CheckParameters const& p) { ...@@ -139,7 +139,8 @@ std::ostream& operator<<(std::ostream& os, CheckParameters const& p) {
} }
CheckParameters const& CheckParametersOf(Operator const* op) { CheckParameters const& CheckParametersOf(Operator const* op) {
CHECK_EQ(IrOpcode::kCheckBounds, op->opcode()); CHECK(op->opcode() == IrOpcode::kCheckBounds ||
op->opcode() == IrOpcode::kCheckNumber);
return OpParameter<CheckParameters>(op); return OpParameter<CheckParameters>(op);
} }
...@@ -665,7 +666,6 @@ DeoptimizeReason DeoptimizeReasonOf(const Operator* op) { ...@@ -665,7 +666,6 @@ DeoptimizeReason DeoptimizeReasonOf(const Operator* op) {
#define CHECKED_OP_LIST(V) \ #define CHECKED_OP_LIST(V) \
V(CheckHeapObject, 1, 1) \ V(CheckHeapObject, 1, 1) \
V(CheckInternalizedString, 1, 1) \ V(CheckInternalizedString, 1, 1) \
V(CheckNumber, 1, 1) \
V(CheckReceiver, 1, 1) \ V(CheckReceiver, 1, 1) \
V(CheckSmi, 1, 1) \ V(CheckSmi, 1, 1) \
V(CheckString, 1, 1) \ V(CheckString, 1, 1) \
...@@ -687,7 +687,9 @@ DeoptimizeReason DeoptimizeReasonOf(const Operator* op) { ...@@ -687,7 +687,9 @@ DeoptimizeReason DeoptimizeReasonOf(const Operator* op) {
V(CheckedTaggedToTaggedSigned, 1, 1) \ V(CheckedTaggedToTaggedSigned, 1, 1) \
V(CheckedTaggedToTaggedPointer, 1, 1) V(CheckedTaggedToTaggedPointer, 1, 1)
#define CHECKED_WITH_FEEDBACK_OP_LIST(V) V(CheckBounds, 2, 1) #define CHECKED_WITH_FEEDBACK_OP_LIST(V) \
V(CheckBounds, 2, 1) \
V(CheckNumber, 1, 1)
struct SimplifiedOperatorGlobalCache final { struct SimplifiedOperatorGlobalCache final {
#define PURE(Name, properties, value_input_count, control_input_count) \ #define PURE(Name, properties, value_input_count, control_input_count) \
......
...@@ -473,7 +473,7 @@ class V8_EXPORT_PRIVATE SimplifiedOperatorBuilder final ...@@ -473,7 +473,7 @@ class V8_EXPORT_PRIVATE SimplifiedOperatorBuilder final
const Operator* CheckHeapObject(); const Operator* CheckHeapObject();
const Operator* CheckInternalizedString(); const Operator* CheckInternalizedString();
const Operator* CheckNumber(); const Operator* CheckNumber(const VectorSlotPair& feedback);
const Operator* CheckSmi(); const Operator* CheckSmi();
const Operator* CheckString(); const Operator* CheckString();
const Operator* CheckSeqString(); const Operator* CheckSeqString();
......
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