Commit 63516a8c authored by epertoso's avatar epertoso Committed by Commit bot

[interpreter] Collect type feedback in Add, Mul, Div and Mod.

Introduces code stubs to collect type feedback for the Add, Mul, Div and Mod operations in the interpreter, and modifies the BytecodeGraphBuilder to make use of it.

BUG=v8:5273
LOG=N

Review-Url: https://codereview.chromium.org/2224343002
Cr-Commit-Position: refs/heads/master@{#38543}
parent 27a60a38
...@@ -3217,6 +3217,37 @@ compiler::Node* CodeStubAssembler::LoadTypeFeedbackVectorForStub() { ...@@ -3217,6 +3217,37 @@ compiler::Node* CodeStubAssembler::LoadTypeFeedbackVectorForStub() {
return LoadObjectField(literals, LiteralsArray::kFeedbackVectorOffset); return LoadObjectField(literals, LiteralsArray::kFeedbackVectorOffset);
} }
void CodeStubAssembler::UpdateFeedback(compiler::Node* feedback,
compiler::Node* type_feedback_vector,
compiler::Node* slot_id) {
Label combine_feedback(this), record_feedback(this), end(this);
Node* previous_feedback =
LoadFixedArrayElement(type_feedback_vector, slot_id);
Node* is_uninitialized = WordEqual(
previous_feedback,
HeapConstant(TypeFeedbackVector::UninitializedSentinel(isolate())));
BranchIf(is_uninitialized, &record_feedback, &combine_feedback);
Bind(&record_feedback);
{
StoreFixedArrayElement(type_feedback_vector, slot_id, SmiTag(feedback),
SKIP_WRITE_BARRIER);
Goto(&end);
}
Bind(&combine_feedback);
{
Node* untagged_previous_feedback = SmiUntag(previous_feedback);
Node* combined_feedback = Word32Or(untagged_previous_feedback, feedback);
StoreFixedArrayElement(type_feedback_vector, slot_id,
SmiTag(combined_feedback), SKIP_WRITE_BARRIER);
Goto(&end);
}
Bind(&end);
}
compiler::Node* CodeStubAssembler::LoadReceiverMap(compiler::Node* receiver) { compiler::Node* CodeStubAssembler::LoadReceiverMap(compiler::Node* receiver) {
Variable var_receiver_map(this, MachineRepresentation::kTagged); Variable var_receiver_map(this, MachineRepresentation::kTagged);
// TODO(ishell): defer blocks when it works. // TODO(ishell): defer blocks when it works.
......
...@@ -497,6 +497,11 @@ class CodeStubAssembler : public compiler::CodeAssembler { ...@@ -497,6 +497,11 @@ class CodeStubAssembler : public compiler::CodeAssembler {
// Load type feedback vector from the stub caller's frame. // Load type feedback vector from the stub caller's frame.
compiler::Node* LoadTypeFeedbackVectorForStub(); compiler::Node* LoadTypeFeedbackVectorForStub();
// Update the type feedback vector.
void UpdateFeedback(compiler::Node* feedback,
compiler::Node* type_feedback_vector,
compiler::Node* slot_id);
compiler::Node* LoadReceiverMap(compiler::Node* receiver); compiler::Node* LoadReceiverMap(compiler::Node* receiver);
// Checks monomorphic case. Returns {feedback} entry of the vector. // Checks monomorphic case. Returns {feedback} entry of the vector.
......
This diff is collapsed.
...@@ -121,11 +121,15 @@ namespace internal { ...@@ -121,11 +121,15 @@ namespace internal {
V(CreateWeakCell) \ V(CreateWeakCell) \
V(StringLength) \ V(StringLength) \
V(Add) \ V(Add) \
V(AddWithFeedback) \
V(Subtract) \ V(Subtract) \
V(SubtractWithFeedback) \ V(SubtractWithFeedback) \
V(Multiply) \ V(Multiply) \
V(MultiplyWithFeedback) \
V(Divide) \ V(Divide) \
V(DivideWithFeedback) \
V(Modulus) \ V(Modulus) \
V(ModulusWithFeedback) \
V(ShiftRight) \ V(ShiftRight) \
V(ShiftRightLogical) \ V(ShiftRightLogical) \
V(ShiftLeft) \ V(ShiftLeft) \
...@@ -756,6 +760,15 @@ class AddStub final : public TurboFanCodeStub { ...@@ -756,6 +760,15 @@ class AddStub final : public TurboFanCodeStub {
DEFINE_TURBOFAN_BINARY_OP_CODE_STUB(Add, TurboFanCodeStub); DEFINE_TURBOFAN_BINARY_OP_CODE_STUB(Add, TurboFanCodeStub);
}; };
class AddWithFeedbackStub final : public TurboFanCodeStub {
public:
explicit AddWithFeedbackStub(Isolate* isolate) : TurboFanCodeStub(isolate) {}
DEFINE_CALL_INTERFACE_DESCRIPTOR(BinaryOp);
DEFINE_TURBOFAN_BINARY_OP_CODE_STUB_WITH_FEEDBACK(AddWithFeedback,
TurboFanCodeStub);
};
class SubtractStub final : public TurboFanCodeStub { class SubtractStub final : public TurboFanCodeStub {
public: public:
explicit SubtractStub(Isolate* isolate) : TurboFanCodeStub(isolate) {} explicit SubtractStub(Isolate* isolate) : TurboFanCodeStub(isolate) {}
...@@ -782,6 +795,16 @@ class MultiplyStub final : public TurboFanCodeStub { ...@@ -782,6 +795,16 @@ class MultiplyStub final : public TurboFanCodeStub {
DEFINE_TURBOFAN_BINARY_OP_CODE_STUB(Multiply, TurboFanCodeStub); DEFINE_TURBOFAN_BINARY_OP_CODE_STUB(Multiply, TurboFanCodeStub);
}; };
class MultiplyWithFeedbackStub final : public TurboFanCodeStub {
public:
explicit MultiplyWithFeedbackStub(Isolate* isolate)
: TurboFanCodeStub(isolate) {}
DEFINE_CALL_INTERFACE_DESCRIPTOR(BinaryOp);
DEFINE_TURBOFAN_BINARY_OP_CODE_STUB_WITH_FEEDBACK(MultiplyWithFeedback,
TurboFanCodeStub);
};
class DivideStub final : public TurboFanCodeStub { class DivideStub final : public TurboFanCodeStub {
public: public:
explicit DivideStub(Isolate* isolate) : TurboFanCodeStub(isolate) {} explicit DivideStub(Isolate* isolate) : TurboFanCodeStub(isolate) {}
...@@ -790,6 +813,16 @@ class DivideStub final : public TurboFanCodeStub { ...@@ -790,6 +813,16 @@ class DivideStub final : public TurboFanCodeStub {
DEFINE_TURBOFAN_BINARY_OP_CODE_STUB(Divide, TurboFanCodeStub); DEFINE_TURBOFAN_BINARY_OP_CODE_STUB(Divide, TurboFanCodeStub);
}; };
class DivideWithFeedbackStub final : public TurboFanCodeStub {
public:
explicit DivideWithFeedbackStub(Isolate* isolate)
: TurboFanCodeStub(isolate) {}
DEFINE_CALL_INTERFACE_DESCRIPTOR(BinaryOp);
DEFINE_TURBOFAN_BINARY_OP_CODE_STUB_WITH_FEEDBACK(DivideWithFeedback,
TurboFanCodeStub);
};
class ModulusStub final : public TurboFanCodeStub { class ModulusStub final : public TurboFanCodeStub {
public: public:
explicit ModulusStub(Isolate* isolate) : TurboFanCodeStub(isolate) {} explicit ModulusStub(Isolate* isolate) : TurboFanCodeStub(isolate) {}
...@@ -798,6 +831,16 @@ class ModulusStub final : public TurboFanCodeStub { ...@@ -798,6 +831,16 @@ class ModulusStub final : public TurboFanCodeStub {
DEFINE_TURBOFAN_BINARY_OP_CODE_STUB(Modulus, TurboFanCodeStub); DEFINE_TURBOFAN_BINARY_OP_CODE_STUB(Modulus, TurboFanCodeStub);
}; };
class ModulusWithFeedbackStub final : public TurboFanCodeStub {
public:
explicit ModulusWithFeedbackStub(Isolate* isolate)
: TurboFanCodeStub(isolate) {}
DEFINE_CALL_INTERFACE_DESCRIPTOR(BinaryOp);
DEFINE_TURBOFAN_BINARY_OP_CODE_STUB_WITH_FEEDBACK(ModulusWithFeedback,
TurboFanCodeStub);
};
class ShiftRightStub final : public TurboFanCodeStub { class ShiftRightStub final : public TurboFanCodeStub {
public: public:
explicit ShiftRightStub(Isolate* isolate) : TurboFanCodeStub(isolate) {} explicit ShiftRightStub(Isolate* isolate) : TurboFanCodeStub(isolate) {}
......
...@@ -1150,7 +1150,7 @@ inline uint32_t ObjectHash(Address address) { ...@@ -1150,7 +1150,7 @@ inline uint32_t ObjectHash(Address address) {
kPointerSizeLog2); kPointerSizeLog2);
} }
// Type feedbac is encoded in such a way that, we can combine the feedback // Type feedback is encoded in such a way that, we can combine the feedback
// at different points by performing an 'OR' operation. Type feedback moves // at different points by performing an 'OR' operation. Type feedback moves
// to a more generic type when we combine feedback. // to a more generic type when we combine feedback.
// kSignedSmall -> kNumber -> kAny // kSignedSmall -> kNumber -> kAny
......
...@@ -780,7 +780,7 @@ void Interpreter::DoBinaryOpWithFeedback(InterpreterAssembler* assembler) { ...@@ -780,7 +780,7 @@ void Interpreter::DoBinaryOpWithFeedback(InterpreterAssembler* assembler) {
// //
// Add register <src> to accumulator. // Add register <src> to accumulator.
void Interpreter::DoAdd(InterpreterAssembler* assembler) { void Interpreter::DoAdd(InterpreterAssembler* assembler) {
DoBinaryOp<AddStub>(assembler); DoBinaryOpWithFeedback<AddWithFeedbackStub>(assembler);
} }
// Sub <src> // Sub <src>
...@@ -794,21 +794,21 @@ void Interpreter::DoSub(InterpreterAssembler* assembler) { ...@@ -794,21 +794,21 @@ void Interpreter::DoSub(InterpreterAssembler* assembler) {
// //
// Multiply accumulator by register <src>. // Multiply accumulator by register <src>.
void Interpreter::DoMul(InterpreterAssembler* assembler) { void Interpreter::DoMul(InterpreterAssembler* assembler) {
DoBinaryOp<MultiplyStub>(assembler); DoBinaryOpWithFeedback<MultiplyWithFeedbackStub>(assembler);
} }
// Div <src> // Div <src>
// //
// Divide register <src> by accumulator. // Divide register <src> by accumulator.
void Interpreter::DoDiv(InterpreterAssembler* assembler) { void Interpreter::DoDiv(InterpreterAssembler* assembler) {
DoBinaryOp<DivideStub>(assembler); DoBinaryOpWithFeedback<DivideWithFeedbackStub>(assembler);
} }
// Mod <src> // Mod <src>
// //
// Modulo register <src> by accumulator. // Modulo register <src> by accumulator.
void Interpreter::DoMod(InterpreterAssembler* assembler) { void Interpreter::DoMod(InterpreterAssembler* assembler) {
DoBinaryOp<ModulusStub>(assembler); DoBinaryOpWithFeedback<ModulusWithFeedbackStub>(assembler);
} }
// BitwiseOr <src> // BitwiseOr <src>
......
...@@ -501,7 +501,7 @@ TEST(InterpreterParameter8) { ...@@ -501,7 +501,7 @@ TEST(InterpreterParameter8) {
.Return(); .Return();
Handle<BytecodeArray> bytecode_array = builder.ToBytecodeArray(); Handle<BytecodeArray> bytecode_array = builder.ToBytecodeArray();
InterpreterTester tester(handles.main_isolate(), bytecode_array); InterpreterTester tester(handles.main_isolate(), bytecode_array, vector);
typedef Handle<Object> H; typedef Handle<Object> H;
auto callable = tester.GetCallable<H, H, H, H, H, H, H, H>(); auto callable = tester.GetCallable<H, H, H, H, H, H, H, H>();
......
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