Commit 06e8df41 authored by Jakob Linke's avatar Jakob Linke Committed by V8 LUCI CQ

[maglev] Conservatively mark nodes with builtins calls as

.. Throw|LazyDeopt. Whether a builtin can Throw|LazyDeopt depends
on the implementation, so to be safe all builtin calls should be
marked as such - UNLESS we know for certain that one or the other
doesn't happen.

Drive-by: For calls with two result registers, properly consider
the second register in a few spots.

Bug: v8:7700
Change-Id: Icbcffb51e9760761a2f4e32d79af33abccb8f1cb
Fixed: chromium:1361245
Fixed: chromium:1360800
Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/3879617Reviewed-by: 's avatarLeszek Swirski <leszeks@chromium.org>
Auto-Submit: Jakob Linke <jgruber@chromium.org>
Commit-Queue: Jakob Linke <jgruber@chromium.org>
Cr-Commit-Position: refs/heads/main@{#83152}
parent d4482c07
...@@ -222,7 +222,7 @@ class UseMarkingProcessor { ...@@ -222,7 +222,7 @@ class UseMarkingProcessor {
register_frame->ForEachValue( register_frame->ForEachValue(
deopt_info->unit, [&](ValueNode* node, interpreter::Register reg) { deopt_info->unit, [&](ValueNode* node, interpreter::Register reg) {
// Skip over the result location. // Skip over the result location.
if (reg == deopt_info->result_location) return; if (deopt_info->IsResultRegister(reg)) return;
MarkUse(node, use_id, &deopt_info->input_locations[index++], MarkUse(node, use_id, &deopt_info->input_locations[index++],
loop_used_nodes); loop_used_nodes);
}); });
......
...@@ -2008,7 +2008,8 @@ void MaglevGraphBuilder::VisitCallRuntimeForPair() { ...@@ -2008,7 +2008,8 @@ void MaglevGraphBuilder::VisitCallRuntimeForPair() {
for (int i = 0; i < args.register_count(); ++i) { for (int i = 0; i < args.register_count(); ++i) {
call_runtime->set_arg(i, GetTaggedValue(args[i])); call_runtime->set_arg(i, GetTaggedValue(args[i]));
} }
StoreRegisterPair(iterator_.GetRegisterOperand(3), call_runtime); auto result = iterator_.GetRegisterPairOperand(3);
StoreRegisterPair(result, call_runtime);
} }
void MaglevGraphBuilder::VisitInvokeIntrinsic() { void MaglevGraphBuilder::VisitInvokeIntrinsic() {
...@@ -2324,21 +2325,19 @@ void MaglevGraphBuilder::VisitCreateArrayLiteral() { ...@@ -2324,21 +2325,19 @@ void MaglevGraphBuilder::VisitCreateArrayLiteral() {
int bytecode_flags = GetFlag8Operand(2); int bytecode_flags = GetFlag8Operand(2);
int literal_flags = int literal_flags =
interpreter::CreateArrayLiteralFlags::FlagsBits::decode(bytecode_flags); interpreter::CreateArrayLiteralFlags::FlagsBits::decode(bytecode_flags);
ValueNode* result;
if (interpreter::CreateArrayLiteralFlags::FastCloneSupportedBit::decode( if (interpreter::CreateArrayLiteralFlags::FastCloneSupportedBit::decode(
bytecode_flags)) { bytecode_flags)) {
// TODO(victorgomes): CreateShallowArrayLiteral should not need the // TODO(victorgomes): CreateShallowArrayLiteral should not need the
// boilerplate descriptor. However the current builtin checks that the // boilerplate descriptor. However the current builtin checks that the
// feedback exists and fallsback to CreateArrayLiteral if it doesn't. // feedback exists and fallsback to CreateArrayLiteral if it doesn't.
result = AddNewNode<CreateShallowArrayLiteral>( SetAccumulator(AddNewNode<CreateShallowArrayLiteral>(
{}, constant_elements, compiler::FeedbackSource{feedback(), slot_index}, {}, constant_elements, compiler::FeedbackSource{feedback(), slot_index},
literal_flags); literal_flags));
} else { } else {
result = AddNewNode<CreateArrayLiteral>( SetAccumulator(AddNewNode<CreateArrayLiteral>(
{}, constant_elements, compiler::FeedbackSource{feedback(), slot_index}, {}, constant_elements, compiler::FeedbackSource{feedback(), slot_index},
literal_flags); literal_flags));
} }
SetAccumulator(result);
} }
void MaglevGraphBuilder::VisitCreateArrayFromIterable() { void MaglevGraphBuilder::VisitCreateArrayFromIterable() {
...@@ -2361,21 +2360,19 @@ void MaglevGraphBuilder::VisitCreateObjectLiteral() { ...@@ -2361,21 +2360,19 @@ void MaglevGraphBuilder::VisitCreateObjectLiteral() {
int bytecode_flags = GetFlag8Operand(2); int bytecode_flags = GetFlag8Operand(2);
int literal_flags = int literal_flags =
interpreter::CreateObjectLiteralFlags::FlagsBits::decode(bytecode_flags); interpreter::CreateObjectLiteralFlags::FlagsBits::decode(bytecode_flags);
ValueNode* result;
if (interpreter::CreateObjectLiteralFlags::FastCloneSupportedBit::decode( if (interpreter::CreateObjectLiteralFlags::FastCloneSupportedBit::decode(
bytecode_flags)) { bytecode_flags)) {
// TODO(victorgomes): CreateShallowObjectLiteral should not need the // TODO(victorgomes): CreateShallowObjectLiteral should not need the
// boilerplate descriptor. However the current builtin checks that the // boilerplate descriptor. However the current builtin checks that the
// feedback exists and fallsback to CreateObjectLiteral if it doesn't. // feedback exists and fallsback to CreateObjectLiteral if it doesn't.
result = AddNewNode<CreateShallowObjectLiteral>( SetAccumulator(AddNewNode<CreateShallowObjectLiteral>(
{}, boilerplate_desc, compiler::FeedbackSource{feedback(), slot_index}, {}, boilerplate_desc, compiler::FeedbackSource{feedback(), slot_index},
literal_flags); literal_flags));
} else { } else {
result = AddNewNode<CreateObjectLiteral>( SetAccumulator(AddNewNode<CreateObjectLiteral>(
{}, boilerplate_desc, compiler::FeedbackSource{feedback(), slot_index}, {}, boilerplate_desc, compiler::FeedbackSource{feedback(), slot_index},
literal_flags); literal_flags));
} }
SetAccumulator(result);
} }
void MaglevGraphBuilder::VisitCreateEmptyObjectLiteral() { void MaglevGraphBuilder::VisitCreateEmptyObjectLiteral() {
...@@ -2751,10 +2748,10 @@ void MaglevGraphBuilder::VisitForInPrepare() { ...@@ -2751,10 +2748,10 @@ void MaglevGraphBuilder::VisitForInPrepare() {
// |cache_info_triple + 2|, with the registers holding cache_type, // |cache_info_triple + 2|, with the registers holding cache_type,
// cache_array, and cache_length respectively. // cache_array, and cache_length respectively.
interpreter::Register first = iterator_.GetRegisterOperand(0); interpreter::Register first = iterator_.GetRegisterOperand(0);
interpreter::Register second(first.index() + 1); auto array_and_length =
interpreter::Register third(first.index() + 2); std::make_pair(interpreter::Register{first.index() + 1},
StoreRegister(second, result); interpreter::Register{first.index() + 2});
StoreRegister(third, GetSecondValue(result)); StoreRegisterPair(array_and_length, result);
} }
void MaglevGraphBuilder::VisitForInContinue() { void MaglevGraphBuilder::VisitForInContinue() {
......
...@@ -787,21 +787,27 @@ class MaglevGraphBuilder { ...@@ -787,21 +787,27 @@ class MaglevGraphBuilder {
if (!IsConstantNode(value->opcode())) { if (!IsConstantNode(value->opcode())) {
DCHECK_NE(0, new_nodes_.count(value)); DCHECK_NE(0, new_nodes_.count(value));
} }
MarkAsLazyDeoptResult(value, target); MarkAsLazyDeoptResult(value, target, 1);
current_interpreter_frame_.set(target, value); current_interpreter_frame_.set(target, value);
} }
void StoreRegisterPair(interpreter::Register target, CallRuntime* value) { template <typename NodeT>
void StoreRegisterPair(
std::pair<interpreter::Register, interpreter::Register> target,
NodeT* value) {
const interpreter::Register target0 = target.first;
const interpreter::Register target1 = target.second;
DCHECK_EQ(interpreter::Register(target0.index() + 1), target1);
DCHECK_EQ(value->ReturnCount(), 2); DCHECK_EQ(value->ReturnCount(), 2);
DCHECK_NE(0, new_nodes_.count(value)); DCHECK_NE(0, new_nodes_.count(value));
MarkAsLazyDeoptResult(value, target, value->ReturnCount()); MarkAsLazyDeoptResult(value, target0, value->ReturnCount());
current_interpreter_frame_.set(target, value); current_interpreter_frame_.set(target0, value);
ValueNode* second_value = GetSecondValue(value); ValueNode* second_value = GetSecondValue(value);
DCHECK_NE(0, new_nodes_.count(second_value)); DCHECK_NE(0, new_nodes_.count(second_value));
current_interpreter_frame_.set(interpreter::Register(target.index() + 1), current_interpreter_frame_.set(target1, second_value);
second_value);
} }
CheckpointedInterpreterState GetLatestCheckpointedState() { CheckpointedInterpreterState GetLatestCheckpointedState() {
...@@ -832,7 +838,7 @@ class MaglevGraphBuilder { ...@@ -832,7 +838,7 @@ class MaglevGraphBuilder {
template <typename NodeT> template <typename NodeT>
void MarkAsLazyDeoptResult(NodeT* value, void MarkAsLazyDeoptResult(NodeT* value,
interpreter::Register result_location, interpreter::Register result_location,
int result_size = 1) { int result_size) {
DCHECK_EQ(NodeT::kProperties.can_lazy_deopt(), DCHECK_EQ(NodeT::kProperties.can_lazy_deopt(),
value->properties().can_lazy_deopt()); value->properties().can_lazy_deopt());
if constexpr (NodeT::kProperties.can_lazy_deopt()) { if constexpr (NodeT::kProperties.can_lazy_deopt()) {
......
...@@ -430,7 +430,7 @@ void PrintLazyDeopt(std::ostream& os, std::vector<BasicBlock*> targets, ...@@ -430,7 +430,7 @@ void PrintLazyDeopt(std::ostream& os, std::vector<BasicBlock*> targets,
os << ", "; os << ", ";
} }
os << reg.ToString() << ":"; os << reg.ToString() << ":";
if (reg == deopt_info->result_location) { if (deopt_info->IsResultRegister(reg)) {
os << "<result>"; os << "<result>";
} else { } else {
os << PrintNodeLabel(graph_labeller, node) << ":" os << PrintNodeLabel(graph_labeller, node) << ":"
......
...@@ -379,6 +379,15 @@ DeoptInfo::DeoptInfo(Zone* zone, const MaglevCompilationUnit& compilation_unit, ...@@ -379,6 +379,15 @@ DeoptInfo::DeoptInfo(Zone* zone, const MaglevCompilationUnit& compilation_unit,
} }
} }
bool LazyDeoptInfo::IsResultRegister(interpreter::Register reg) const {
if (V8_LIKELY(result_size == 1)) {
return reg == result_location;
}
DCHECK_EQ(result_size, 2);
return reg == result_location ||
reg == interpreter::Register(result_location.index() + 1);
}
// --- // ---
// Nodes // Nodes
// --- // ---
...@@ -707,6 +716,7 @@ void ForInPrepare::GenerateCode(MaglevAssembler* masm, ...@@ -707,6 +716,7 @@ void ForInPrepare::GenerateCode(MaglevAssembler* masm,
TaggedIndex::FromIntptr(feedback().index())); TaggedIndex::FromIntptr(feedback().index()));
__ Move(D::GetRegisterParameter(D::kFeedbackVector), feedback().vector); __ Move(D::GetRegisterParameter(D::kFeedbackVector), feedback().vector);
__ CallBuiltin(Builtin::kForInPrepare); __ CallBuiltin(Builtin::kForInPrepare);
masm->DefineExceptionHandlerAndLazyDeoptPoint(this);
} }
void ForInNext::AllocateVreg(MaglevVregAllocationState* vreg_state) { void ForInNext::AllocateVreg(MaglevVregAllocationState* vreg_state) {
...@@ -752,6 +762,7 @@ void GetIterator::GenerateCode(MaglevAssembler* masm, ...@@ -752,6 +762,7 @@ void GetIterator::GenerateCode(MaglevAssembler* masm,
TaggedIndex::FromIntptr(call_slot())); TaggedIndex::FromIntptr(call_slot()));
__ Move(D::GetRegisterParameter(D::kMaybeFeedbackVector), feedback()); __ Move(D::GetRegisterParameter(D::kMaybeFeedbackVector), feedback());
__ CallBuiltin(Builtin::kGetIteratorWithFeedback); __ CallBuiltin(Builtin::kGetIteratorWithFeedback);
masm->DefineExceptionHandlerAndLazyDeoptPoint(this);
} }
void GetSecondReturnedValue::AllocateVreg( void GetSecondReturnedValue::AllocateVreg(
...@@ -905,6 +916,7 @@ void CreateEmptyArrayLiteral::GenerateCode(MaglevAssembler* masm, ...@@ -905,6 +916,7 @@ void CreateEmptyArrayLiteral::GenerateCode(MaglevAssembler* masm,
__ Move(D::GetRegisterParameter(D::kSlot), Smi::FromInt(feedback().index())); __ Move(D::GetRegisterParameter(D::kSlot), Smi::FromInt(feedback().index()));
__ Move(D::GetRegisterParameter(D::kFeedbackVector), feedback().vector); __ Move(D::GetRegisterParameter(D::kFeedbackVector), feedback().vector);
__ CallBuiltin(Builtin::kCreateEmptyArrayLiteral); __ CallBuiltin(Builtin::kCreateEmptyArrayLiteral);
masm->DefineExceptionHandlerAndLazyDeoptPoint(this);
} }
void CreateArrayLiteral::AllocateVreg(MaglevVregAllocationState* vreg_state) { void CreateArrayLiteral::AllocateVreg(MaglevVregAllocationState* vreg_state) {
...@@ -935,6 +947,7 @@ void CreateShallowArrayLiteral::GenerateCode(MaglevAssembler* masm, ...@@ -935,6 +947,7 @@ void CreateShallowArrayLiteral::GenerateCode(MaglevAssembler* masm,
constant_elements().object()); constant_elements().object());
__ Move(D::GetRegisterParameter(D::kFlags), Smi::FromInt(flags())); __ Move(D::GetRegisterParameter(D::kFlags), Smi::FromInt(flags()));
__ CallBuiltin(Builtin::kCreateShallowArrayLiteral); __ CallBuiltin(Builtin::kCreateShallowArrayLiteral);
masm->DefineExceptionHandlerAndLazyDeoptPoint(this);
} }
void CreateObjectLiteral::AllocateVreg(MaglevVregAllocationState* vreg_state) { void CreateObjectLiteral::AllocateVreg(MaglevVregAllocationState* vreg_state) {
...@@ -988,6 +1001,7 @@ void CreateShallowObjectLiteral::GenerateCode(MaglevAssembler* masm, ...@@ -988,6 +1001,7 @@ void CreateShallowObjectLiteral::GenerateCode(MaglevAssembler* masm,
__ Move(D::GetRegisterParameter(D::kDesc), boilerplate_descriptor().object()); __ Move(D::GetRegisterParameter(D::kDesc), boilerplate_descriptor().object());
__ Move(D::GetRegisterParameter(D::kFlags), Smi::FromInt(flags())); __ Move(D::GetRegisterParameter(D::kFlags), Smi::FromInt(flags()));
__ CallBuiltin(Builtin::kCreateShallowObjectLiteral); __ CallBuiltin(Builtin::kCreateShallowObjectLiteral);
masm->DefineExceptionHandlerAndLazyDeoptPoint(this);
} }
void CreateFunctionContext::AllocateVreg( void CreateFunctionContext::AllocateVreg(
...@@ -1028,6 +1042,7 @@ void CreateFunctionContext::GenerateCode(MaglevAssembler* masm, ...@@ -1028,6 +1042,7 @@ void CreateFunctionContext::GenerateCode(MaglevAssembler* masm,
__ Move(D::GetRegisterParameter(D::kSlots), Immediate(slot_count())); __ Move(D::GetRegisterParameter(D::kSlots), Immediate(slot_count()));
__ CallBuiltin(Builtin::kFastNewFunctionContextEval); __ CallBuiltin(Builtin::kFastNewFunctionContextEval);
} }
masm->DefineExceptionHandlerAndLazyDeoptPoint(this);
} }
void CreateFunctionContext::PrintParams( void CreateFunctionContext::PrintParams(
std::ostream& os, MaglevGraphLabeller* graph_labeller) const { std::ostream& os, MaglevGraphLabeller* graph_labeller) const {
...@@ -1049,6 +1064,7 @@ void FastCreateClosure::GenerateCode(MaglevAssembler* masm, ...@@ -1049,6 +1064,7 @@ void FastCreateClosure::GenerateCode(MaglevAssembler* masm,
shared_function_info().object()); shared_function_info().object());
__ Move(D::GetRegisterParameter(D::kFeedbackCell), feedback_cell().object()); __ Move(D::GetRegisterParameter(D::kFeedbackCell), feedback_cell().object());
__ CallBuiltin(Builtin::kFastNewClosure); __ CallBuiltin(Builtin::kFastNewClosure);
masm->DefineExceptionHandlerAndLazyDeoptPoint(this);
} }
void FastCreateClosure::PrintParams(std::ostream& os, void FastCreateClosure::PrintParams(std::ostream& os,
MaglevGraphLabeller* graph_labeller) const { MaglevGraphLabeller* graph_labeller) const {
...@@ -1107,6 +1123,7 @@ void GetTemplateObject::GenerateCode(MaglevAssembler* masm, ...@@ -1107,6 +1123,7 @@ void GetTemplateObject::GenerateCode(MaglevAssembler* masm,
__ Move(D::GetRegisterParameter(D::kSlot), feedback().slot.ToInt()); __ Move(D::GetRegisterParameter(D::kSlot), feedback().slot.ToInt());
__ Move(D::GetRegisterParameter(D::kShared), shared_function_info_.object()); __ Move(D::GetRegisterParameter(D::kShared), shared_function_info_.object());
__ CallBuiltin(Builtin::kGetTemplateObject); __ CallBuiltin(Builtin::kGetTemplateObject);
masm->DefineExceptionHandlerAndLazyDeoptPoint(this);
} }
void Abort::AllocateVreg(MaglevVregAllocationState* vreg_state) {} void Abort::AllocateVreg(MaglevVregAllocationState* vreg_state) {}
......
...@@ -525,6 +525,14 @@ class OpProperties { ...@@ -525,6 +525,14 @@ class OpProperties {
static constexpr OpProperties NeedsRegisterSnapshot() { static constexpr OpProperties NeedsRegisterSnapshot() {
return OpProperties(kNeedsRegisterSnapshotBit::encode(true)); return OpProperties(kNeedsRegisterSnapshotBit::encode(true));
} }
// Without auditing the call target, we must assume it can cause a lazy deopt
// and throw. Use this when codegen calls runtime or a builtin, unless
// certain that the target either doesn't throw or cannot deopt.
// TODO(jgruber): Go through all nodes marked with this property and decide
// whether to keep it (or remove either the lazy-deopt or throw flag).
static constexpr OpProperties GenericRuntimeOrBuiltinCall() {
return Call() | NonMemorySideEffects() | LazyDeopt() | Throw();
}
static constexpr OpProperties JSCall() { static constexpr OpProperties JSCall() {
return Call() | NonMemorySideEffects() | LazyDeopt() | Throw(); return Call() | NonMemorySideEffects() | LazyDeopt() | Throw();
} }
...@@ -680,6 +688,8 @@ class LazyDeoptInfo : public DeoptInfo { ...@@ -680,6 +688,8 @@ class LazyDeoptInfo : public DeoptInfo {
CheckpointedInterpreterState checkpoint) CheckpointedInterpreterState checkpoint)
: DeoptInfo(zone, compilation_unit, checkpoint) {} : DeoptInfo(zone, compilation_unit, checkpoint) {}
bool IsResultRegister(interpreter::Register reg) const;
int deopting_call_return_pc = -1; int deopting_call_return_pc = -1;
interpreter::Register result_location = interpreter::Register result_location =
interpreter::Register::invalid_value(); interpreter::Register::invalid_value();
...@@ -1983,13 +1993,16 @@ class ForInPrepare : public FixedInputValueNodeT<2, ForInPrepare> { ...@@ -1983,13 +1993,16 @@ class ForInPrepare : public FixedInputValueNodeT<2, ForInPrepare> {
explicit ForInPrepare(uint64_t bitfield, compiler::FeedbackSource& feedback) explicit ForInPrepare(uint64_t bitfield, compiler::FeedbackSource& feedback)
: Base(bitfield), feedback_(feedback) {} : Base(bitfield), feedback_(feedback) {}
static constexpr OpProperties kProperties = OpProperties::Call(); static constexpr OpProperties kProperties =
OpProperties::GenericRuntimeOrBuiltinCall();
compiler::FeedbackSource feedback() const { return feedback_; } compiler::FeedbackSource feedback() const { return feedback_; }
Input& context() { return Node::input(0); } Input& context() { return Node::input(0); }
Input& enumerator() { return Node::input(1); } Input& enumerator() { return Node::input(1); }
int ReturnCount() const { return 2; }
DECL_NODE_INTERFACE_WITH_EMPTY_PRINT_PARAMS() DECL_NODE_INTERFACE_WITH_EMPTY_PRINT_PARAMS()
private: private:
...@@ -2221,7 +2234,8 @@ class CreateEmptyArrayLiteral ...@@ -2221,7 +2234,8 @@ class CreateEmptyArrayLiteral
compiler::FeedbackSource feedback() const { return feedback_; } compiler::FeedbackSource feedback() const { return feedback_; }
// The implementation currently calls runtime. // The implementation currently calls runtime.
static constexpr OpProperties kProperties = OpProperties::Call(); static constexpr OpProperties kProperties =
OpProperties::GenericRuntimeOrBuiltinCall();
DECL_NODE_INTERFACE_WITH_EMPTY_PRINT_PARAMS() DECL_NODE_INTERFACE_WITH_EMPTY_PRINT_PARAMS()
...@@ -2275,7 +2289,8 @@ class CreateShallowArrayLiteral ...@@ -2275,7 +2289,8 @@ class CreateShallowArrayLiteral
int flags() const { return flags_; } int flags() const { return flags_; }
// The implementation currently calls runtime. // The implementation currently calls runtime.
static constexpr OpProperties kProperties = OpProperties::Call(); static constexpr OpProperties kProperties =
OpProperties::GenericRuntimeOrBuiltinCall();
DECL_NODE_INTERFACE_WITH_EMPTY_PRINT_PARAMS() DECL_NODE_INTERFACE_WITH_EMPTY_PRINT_PARAMS()
...@@ -2357,7 +2372,8 @@ class CreateShallowObjectLiteral ...@@ -2357,7 +2372,8 @@ class CreateShallowObjectLiteral
int flags() const { return flags_; } int flags() const { return flags_; }
// The implementation currently calls runtime. // The implementation currently calls runtime.
static constexpr OpProperties kProperties = OpProperties::Call(); static constexpr OpProperties kProperties =
OpProperties::GenericRuntimeOrBuiltinCall();
DECL_NODE_INTERFACE_WITH_EMPTY_PRINT_PARAMS() DECL_NODE_INTERFACE_WITH_EMPTY_PRINT_PARAMS()
...@@ -2387,7 +2403,8 @@ class CreateFunctionContext ...@@ -2387,7 +2403,8 @@ class CreateFunctionContext
Input& context() { return input(0); } Input& context() { return input(0); }
// The implementation currently calls runtime. // The implementation currently calls runtime.
static constexpr OpProperties kProperties = OpProperties::Call(); static constexpr OpProperties kProperties =
OpProperties::GenericRuntimeOrBuiltinCall();
DECL_NODE_INTERFACE() DECL_NODE_INTERFACE()
...@@ -2416,7 +2433,8 @@ class FastCreateClosure : public FixedInputValueNodeT<1, FastCreateClosure> { ...@@ -2416,7 +2433,8 @@ class FastCreateClosure : public FixedInputValueNodeT<1, FastCreateClosure> {
Input& context() { return input(0); } Input& context() { return input(0); }
// The implementation currently calls runtime. // The implementation currently calls runtime.
static constexpr OpProperties kProperties = OpProperties::Call(); static constexpr OpProperties kProperties =
OpProperties::GenericRuntimeOrBuiltinCall();
DECL_NODE_INTERFACE() DECL_NODE_INTERFACE()
...@@ -2682,7 +2700,8 @@ class GetTemplateObject : public FixedInputValueNodeT<1, GetTemplateObject> { ...@@ -2682,7 +2700,8 @@ class GetTemplateObject : public FixedInputValueNodeT<1, GetTemplateObject> {
feedback_(feedback) {} feedback_(feedback) {}
// The implementation currently calls runtime. // The implementation currently calls runtime.
static constexpr OpProperties kProperties = OpProperties::Call(); static constexpr OpProperties kProperties =
OpProperties::GenericRuntimeOrBuiltinCall();
Input& description() { return input(0); } Input& description() { return input(0); }
...@@ -3328,7 +3347,7 @@ class CallRuntime : public ValueNodeT<CallRuntime> { ...@@ -3328,7 +3347,7 @@ class CallRuntime : public ValueNodeT<CallRuntime> {
set_input(i + kFixedInputCount, node); set_input(i + kFixedInputCount, node);
} }
int ReturnCount() { int ReturnCount() const {
return Runtime::FunctionForId(function_id())->result_size; return Runtime::FunctionForId(function_id())->result_size;
} }
......
...@@ -521,8 +521,9 @@ void StraightForwardRegisterAllocator::UpdateUse( ...@@ -521,8 +521,9 @@ void StraightForwardRegisterAllocator::UpdateUse(
// See also: UpdateUse(EagerDeoptInfo&). // See also: UpdateUse(EagerDeoptInfo&).
checkpoint_state->ForEachValue( checkpoint_state->ForEachValue(
deopt_info.unit, [&](ValueNode* node, interpreter::Register reg) { deopt_info.unit, [&](ValueNode* node, interpreter::Register reg) {
// Skip over the result location. // Skip over the result location since it is irrelevant for lazy deopts
if (reg == deopt_info.result_location) return; // (unoptimized code will recreate the result).
if (deopt_info.IsResultRegister(reg)) return;
if (FLAG_trace_maglev_regalloc) { if (FLAG_trace_maglev_regalloc) {
printing_visitor_->os() printing_visitor_->os()
<< "- using " << PrintNodeLabel(graph_labeller(), node) << "\n"; << "- using " << PrintNodeLabel(graph_labeller(), node) << "\n";
......
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