diff options
author | Nicolas Geoffray <ngeoffray@google.com> | 2014-09-30 22:40:23 +0100 |
---|---|---|
committer | Nicolas Geoffray <ngeoffray@google.com> | 2014-10-06 16:36:49 +0100 |
commit | 9ae0daa60c568f98ef0020e52366856ff314615f (patch) | |
tree | e74b9ee49af0b1b202444fdaaca4b39620d962dd /compiler/optimizing | |
parent | 2d4e89e97812aeca16ff058d7286f29b7549c43a (diff) | |
download | art-9ae0daa60c568f98ef0020e52366856ff314615f.zip art-9ae0daa60c568f98ef0020e52366856ff314615f.tar.gz art-9ae0daa60c568f98ef0020e52366856ff314615f.tar.bz2 |
Add support for inputs dying at entry of instructions.
- Start using it in places where it makes sense.
- Also improve suspend check on arm to use subs directly.
Change-Id: I09ac0589f5ccb9b850ee757c76dcbcf35ee8cd01
Diffstat (limited to 'compiler/optimizing')
-rw-r--r-- | compiler/optimizing/code_generator_arm.cc | 53 | ||||
-rw-r--r-- | compiler/optimizing/code_generator_x86.cc | 38 | ||||
-rw-r--r-- | compiler/optimizing/code_generator_x86_64.cc | 40 | ||||
-rw-r--r-- | compiler/optimizing/live_ranges_test.cc | 2 | ||||
-rw-r--r-- | compiler/optimizing/locations.cc | 3 | ||||
-rw-r--r-- | compiler/optimizing/locations.h | 10 |
6 files changed, 87 insertions, 59 deletions
diff --git a/compiler/optimizing/code_generator_arm.cc b/compiler/optimizing/code_generator_arm.cc index 1876cb9..2aa04d4 100644 --- a/compiler/optimizing/code_generator_arm.cc +++ b/compiler/optimizing/code_generator_arm.cc @@ -611,7 +611,7 @@ void LocationsBuilderARM::VisitIf(HIf* if_instr) { DCHECK(cond->IsCondition()); HCondition* condition = cond->AsCondition(); if (condition->NeedsMaterialization()) { - locations->SetInAt(0, Location::RequiresRegister()); + locations->SetInAt(0, Location::RequiresRegister(), Location::kDiesAtEntry); } } @@ -657,8 +657,8 @@ void InstructionCodeGeneratorARM::VisitIf(HIf* if_instr) { void LocationsBuilderARM::VisitCondition(HCondition* comp) { LocationSummary* locations = new (GetGraph()->GetArena()) LocationSummary(comp, LocationSummary::kNoCall); - locations->SetInAt(0, Location::RequiresRegister()); - locations->SetInAt(1, Location::RegisterOrConstant(comp->InputAt(1))); + locations->SetInAt(0, Location::RequiresRegister(), Location::kDiesAtEntry); + locations->SetInAt(1, Location::RegisterOrConstant(comp->InputAt(1)), Location::kDiesAtEntry); if (comp->NeedsMaterialization()) { locations->SetOut(Location::RequiresRegister()); } @@ -960,8 +960,9 @@ void LocationsBuilderARM::VisitAdd(HAdd* add) { switch (add->GetResultType()) { case Primitive::kPrimInt: case Primitive::kPrimLong: { - locations->SetInAt(0, Location::RequiresRegister()); - locations->SetInAt(1, Location::RegisterOrConstant(add->InputAt(1))); + bool dies_at_entry = add->GetResultType() != Primitive::kPrimLong; + locations->SetInAt(0, Location::RequiresRegister(), dies_at_entry); + locations->SetInAt(1, Location::RegisterOrConstant(add->InputAt(1)), dies_at_entry); locations->SetOut(Location::RequiresRegister()); break; } @@ -1020,8 +1021,9 @@ void LocationsBuilderARM::VisitSub(HSub* sub) { switch (sub->GetResultType()) { case Primitive::kPrimInt: case Primitive::kPrimLong: { - locations->SetInAt(0, Location::RequiresRegister()); - locations->SetInAt(1, Location::RegisterOrConstant(sub->InputAt(1))); + bool dies_at_entry = sub->GetResultType() != Primitive::kPrimLong; + locations->SetInAt(0, Location::RequiresRegister(), dies_at_entry); + locations->SetInAt(1, Location::RegisterOrConstant(sub->InputAt(1)), dies_at_entry); locations->SetOut(Location::RequiresRegister()); break; } @@ -1116,7 +1118,7 @@ void InstructionCodeGeneratorARM::VisitParameterValue(HParameterValue* instructi void LocationsBuilderARM::VisitNot(HNot* instruction) { LocationSummary* locations = new (GetGraph()->GetArena()) LocationSummary(instruction, LocationSummary::kNoCall); - locations->SetInAt(0, Location::RequiresRegister()); + locations->SetInAt(0, Location::RequiresRegister(), Location::kDiesAtEntry); locations->SetOut(Location::RequiresRegister()); } @@ -1129,8 +1131,8 @@ void InstructionCodeGeneratorARM::VisitNot(HNot* instruction) { void LocationsBuilderARM::VisitCompare(HCompare* compare) { LocationSummary* locations = new (GetGraph()->GetArena()) LocationSummary(compare, LocationSummary::kNoCall); - locations->SetInAt(0, Location::RequiresRegister()); - locations->SetInAt(1, Location::RequiresRegister()); + locations->SetInAt(0, Location::RequiresRegister(), Location::kDiesAtEntry); + locations->SetInAt(1, Location::RequiresRegister(), Location::kDiesAtEntry); locations->SetOut(Location::RequiresRegister()); } @@ -1186,10 +1188,12 @@ void InstructionCodeGeneratorARM::VisitPhi(HPhi* instruction) { void LocationsBuilderARM::VisitInstanceFieldSet(HInstanceFieldSet* instruction) { LocationSummary* locations = new (GetGraph()->GetArena()) LocationSummary(instruction, LocationSummary::kNoCall); - locations->SetInAt(0, Location::RequiresRegister()); - locations->SetInAt(1, Location::RequiresRegister()); + bool is_object_type = instruction->GetFieldType() == Primitive::kPrimNot; + bool dies_at_entry = !is_object_type; + locations->SetInAt(0, Location::RequiresRegister(), dies_at_entry); + locations->SetInAt(1, Location::RequiresRegister(), dies_at_entry); // Temporary registers for the write barrier. - if (instruction->GetFieldType() == Primitive::kPrimNot) { + if (is_object_type) { locations->AddTemp(Location::RequiresRegister()); locations->AddTemp(Location::RequiresRegister()); } @@ -1246,7 +1250,7 @@ void InstructionCodeGeneratorARM::VisitInstanceFieldSet(HInstanceFieldSet* instr void LocationsBuilderARM::VisitInstanceFieldGet(HInstanceFieldGet* instruction) { LocationSummary* locations = new (GetGraph()->GetArena()) LocationSummary(instruction, LocationSummary::kNoCall); - locations->SetInAt(0, Location::RequiresRegister()); + locations->SetInAt(0, Location::RequiresRegister(), Location::kDiesAtEntry); locations->SetOut(Location::RequiresRegister()); } @@ -1328,8 +1332,9 @@ void InstructionCodeGeneratorARM::VisitNullCheck(HNullCheck* instruction) { void LocationsBuilderARM::VisitArrayGet(HArrayGet* instruction) { LocationSummary* locations = new (GetGraph()->GetArena()) LocationSummary(instruction, LocationSummary::kNoCall); - locations->SetInAt(0, Location::RequiresRegister()); - locations->SetInAt(1, Location::RegisterOrConstant(instruction->InputAt(1))); + locations->SetInAt(0, Location::RequiresRegister(), Location::kDiesAtEntry); + locations->SetInAt( + 1, Location::RegisterOrConstant(instruction->InputAt(1)), Location::kDiesAtEntry); locations->SetOut(Location::RequiresRegister()); } @@ -1439,9 +1444,10 @@ void LocationsBuilderARM::VisitArraySet(HArraySet* instruction) { locations->SetInAt(1, ArmCoreLocation(calling_convention.GetRegisterAt(1))); locations->SetInAt(2, ArmCoreLocation(calling_convention.GetRegisterAt(2))); } else { - locations->SetInAt(0, Location::RequiresRegister()); - locations->SetInAt(1, Location::RegisterOrConstant(instruction->InputAt(1))); - locations->SetInAt(2, Location::RequiresRegister()); + locations->SetInAt(0, Location::RequiresRegister(), Location::kDiesAtEntry); + locations->SetInAt( + 1, Location::RegisterOrConstant(instruction->InputAt(1)), Location::kDiesAtEntry); + locations->SetInAt(2, Location::RequiresRegister(), Location::kDiesAtEntry); } } @@ -1527,7 +1533,7 @@ void InstructionCodeGeneratorARM::VisitArraySet(HArraySet* instruction) { void LocationsBuilderARM::VisitArrayLength(HArrayLength* instruction) { LocationSummary* locations = new (GetGraph()->GetArena()) LocationSummary(instruction, LocationSummary::kNoCall); - locations->SetInAt(0, Location::RequiresRegister()); + locations->SetInAt(0, Location::RequiresRegister(), Location::kDiesAtEntry); locations->SetOut(Location::RequiresRegister()); } @@ -1610,13 +1616,12 @@ void InstructionCodeGeneratorARM::GenerateSuspendCheck(HSuspendCheck* instructio new (GetGraph()->GetArena()) SuspendCheckSlowPathARM(instruction, successor); codegen_->AddSlowPath(slow_path); - __ AddConstant(R4, R4, -1); - __ cmp(R4, ShifterOperand(0)); + __ subs(R4, R4, ShifterOperand(1)); if (successor == nullptr) { - __ b(slow_path->GetEntryLabel(), LE); + __ b(slow_path->GetEntryLabel(), EQ); __ Bind(slow_path->GetReturnLabel()); } else { - __ b(codegen_->GetLabelOf(successor), GT); + __ b(codegen_->GetLabelOf(successor), NE); __ b(slow_path->GetEntryLabel()); } } diff --git a/compiler/optimizing/code_generator_x86.cc b/compiler/optimizing/code_generator_x86.cc index ea67dfd..6791003 100644 --- a/compiler/optimizing/code_generator_x86.cc +++ b/compiler/optimizing/code_generator_x86.cc @@ -563,7 +563,7 @@ void LocationsBuilderX86::VisitIf(HIf* if_instr) { DCHECK(cond->IsCondition()); HCondition* condition = cond->AsCondition(); if (condition->NeedsMaterialization()) { - locations->SetInAt(0, Location::Any()); + locations->SetInAt(0, Location::Any(), Location::kDiesAtEntry); } } @@ -650,8 +650,8 @@ void InstructionCodeGeneratorX86::VisitStoreLocal(HStoreLocal* store) { void LocationsBuilderX86::VisitCondition(HCondition* comp) { LocationSummary* locations = new (GetGraph()->GetArena()) LocationSummary(comp, LocationSummary::kNoCall); - locations->SetInAt(0, Location::RequiresRegister()); - locations->SetInAt(1, Location::Any()); + locations->SetInAt(0, Location::RequiresRegister(), Location::kDiesAtEntry); + locations->SetInAt(1, Location::Any(), Location::kDiesAtEntry); if (comp->NeedsMaterialization()) { locations->SetOut(Location::RequiresRegister()); } @@ -1094,8 +1094,8 @@ void InstructionCodeGeneratorX86::VisitNot(HNot* instruction) { void LocationsBuilderX86::VisitCompare(HCompare* compare) { LocationSummary* locations = new (GetGraph()->GetArena()) LocationSummary(compare, LocationSummary::kNoCall); - locations->SetInAt(0, Location::RequiresRegister()); - locations->SetInAt(1, Location::Any()); + locations->SetInAt(0, Location::RequiresRegister(), Location::kDiesAtEntry); + locations->SetInAt(1, Location::Any(), Location::kDiesAtEntry); locations->SetOut(Location::RequiresRegister()); } @@ -1159,14 +1159,16 @@ void LocationsBuilderX86::VisitInstanceFieldSet(HInstanceFieldSet* instruction) new (GetGraph()->GetArena()) LocationSummary(instruction, LocationSummary::kNoCall); locations->SetInAt(0, Location::RequiresRegister()); Primitive::Type field_type = instruction->GetFieldType(); + bool is_object_type = field_type == Primitive::kPrimNot; + bool dies_at_entry = !is_object_type; if (field_type == Primitive::kPrimBoolean || field_type == Primitive::kPrimByte) { // Ensure the value is in a byte register. - locations->SetInAt(1, X86CpuLocation(EAX)); + locations->SetInAt(1, X86CpuLocation(EAX), dies_at_entry); } else { - locations->SetInAt(1, Location::RequiresRegister()); + locations->SetInAt(1, Location::RequiresRegister(), dies_at_entry); } // Temporary registers for the write barrier. - if (field_type == Primitive::kPrimNot) { + if (is_object_type) { locations->AddTemp(Location::RequiresRegister()); // Ensure the card is in a byte register. locations->AddTemp(X86CpuLocation(ECX)); @@ -1238,7 +1240,7 @@ void CodeGeneratorX86::MarkGCCard(Register temp, Register card, Register object, void LocationsBuilderX86::VisitInstanceFieldGet(HInstanceFieldGet* instruction) { LocationSummary* locations = new (GetGraph()->GetArena()) LocationSummary(instruction, LocationSummary::kNoCall); - locations->SetInAt(0, Location::RequiresRegister()); + locations->SetInAt(0, Location::RequiresRegister(), Location::kDiesAtEntry); locations->SetOut(Location::RequiresRegister()); } @@ -1324,8 +1326,9 @@ void InstructionCodeGeneratorX86::VisitNullCheck(HNullCheck* instruction) { void LocationsBuilderX86::VisitArrayGet(HArrayGet* instruction) { LocationSummary* locations = new (GetGraph()->GetArena()) LocationSummary(instruction, LocationSummary::kNoCall); - locations->SetInAt(0, Location::RequiresRegister()); - locations->SetInAt(1, Location::RegisterOrConstant(instruction->InputAt(1))); + locations->SetInAt(0, Location::RequiresRegister(), Location::kDiesAtEntry); + locations->SetInAt( + 1, Location::RegisterOrConstant(instruction->InputAt(1)), Location::kDiesAtEntry); locations->SetOut(Location::RequiresRegister()); } @@ -1433,13 +1436,16 @@ void LocationsBuilderX86::VisitArraySet(HArraySet* instruction) { locations->SetInAt(1, X86CpuLocation(calling_convention.GetRegisterAt(1))); locations->SetInAt(2, X86CpuLocation(calling_convention.GetRegisterAt(2))); } else { - locations->SetInAt(0, Location::RequiresRegister()); - locations->SetInAt(1, Location::RegisterOrConstant(instruction->InputAt(1))); + // We need the inputs to be different than the output in case of long operation. + bool dies_at_entry = value_type != Primitive::kPrimLong; + locations->SetInAt(0, Location::RequiresRegister(), dies_at_entry); + locations->SetInAt( + 1, Location::RegisterOrConstant(instruction->InputAt(1)), dies_at_entry); if (value_type == Primitive::kPrimBoolean || value_type == Primitive::kPrimByte) { // Ensure the value is in a byte register. - locations->SetInAt(2, X86CpuLocation(EAX)); + locations->SetInAt(2, X86CpuLocation(EAX), dies_at_entry); } else { - locations->SetInAt(2, Location::RequiresRegister()); + locations->SetInAt(2, Location::RequiresRegister(), dies_at_entry); } } } @@ -1523,7 +1529,7 @@ void InstructionCodeGeneratorX86::VisitArraySet(HArraySet* instruction) { void LocationsBuilderX86::VisitArrayLength(HArrayLength* instruction) { LocationSummary* locations = new (GetGraph()->GetArena()) LocationSummary(instruction); - locations->SetInAt(0, Location::RequiresRegister()); + locations->SetInAt(0, Location::RequiresRegister(), Location::kDiesAtEntry); locations->SetOut(Location::RequiresRegister()); instruction->SetLocations(locations); } diff --git a/compiler/optimizing/code_generator_x86_64.cc b/compiler/optimizing/code_generator_x86_64.cc index 78c7d9d..e0e0c79 100644 --- a/compiler/optimizing/code_generator_x86_64.cc +++ b/compiler/optimizing/code_generator_x86_64.cc @@ -446,7 +446,7 @@ void LocationsBuilderX86_64::VisitIf(HIf* if_instr) { DCHECK(cond->IsCondition()); HCondition* condition = cond->AsCondition(); if (condition->NeedsMaterialization()) { - locations->SetInAt(0, Location::Any()); + locations->SetInAt(0, Location::Any(), Location::kDiesAtEntry); } } @@ -530,8 +530,8 @@ void InstructionCodeGeneratorX86_64::VisitStoreLocal(HStoreLocal* store) { void LocationsBuilderX86_64::VisitCondition(HCondition* comp) { LocationSummary* locations = new (GetGraph()->GetArena()) LocationSummary(comp, LocationSummary::kNoCall); - locations->SetInAt(0, Location::RequiresRegister()); - locations->SetInAt(1, Location::Any()); + locations->SetInAt(0, Location::RequiresRegister(), Location::kDiesAtEntry); + locations->SetInAt(1, Location::Any(), Location::kDiesAtEntry); if (comp->NeedsMaterialization()) { locations->SetOut(Location::RequiresRegister()); } @@ -608,8 +608,8 @@ void InstructionCodeGeneratorX86_64::VisitGreaterThanOrEqual(HGreaterThanOrEqual void LocationsBuilderX86_64::VisitCompare(HCompare* compare) { LocationSummary* locations = new (GetGraph()->GetArena()) LocationSummary(compare, LocationSummary::kNoCall); - locations->SetInAt(0, Location::RequiresRegister()); - locations->SetInAt(1, Location::RequiresRegister()); + locations->SetInAt(0, Location::RequiresRegister(), Location::kDiesAtEntry); + locations->SetInAt(1, Location::RequiresRegister(), Location::kDiesAtEntry); locations->SetOut(Location::RequiresRegister()); } @@ -970,6 +970,9 @@ void InstructionCodeGeneratorX86_64::VisitSub(HSub* sub) { void LocationsBuilderX86_64::VisitNewInstance(HNewInstance* instruction) { LocationSummary* locations = new (GetGraph()->GetArena()) LocationSummary(instruction, LocationSummary::kCall); + InvokeRuntimeCallingConvention calling_convention; + locations->AddTemp(X86_64CpuLocation(calling_convention.GetRegisterAt(0))); + locations->AddTemp(X86_64CpuLocation(calling_convention.GetRegisterAt(1))); locations->SetOut(X86_64CpuLocation(RAX)); } @@ -1031,10 +1034,13 @@ void InstructionCodeGeneratorX86_64::VisitPhi(HPhi* instruction) { void LocationsBuilderX86_64::VisitInstanceFieldSet(HInstanceFieldSet* instruction) { LocationSummary* locations = new (GetGraph()->GetArena()) LocationSummary(instruction, LocationSummary::kNoCall); - locations->SetInAt(0, Location::RequiresRegister()); - locations->SetInAt(1, Location::RequiresRegister()); - // Temporary registers for the write barrier. - if (instruction->GetFieldType() == Primitive::kPrimNot) { + Primitive::Type field_type = instruction->GetFieldType(); + bool is_object_type = field_type == Primitive::kPrimNot; + bool dies_at_entry = !is_object_type; + locations->SetInAt(0, Location::RequiresRegister(), dies_at_entry); + locations->SetInAt(1, Location::RequiresRegister(), dies_at_entry); + if (is_object_type) { + // Temporary registers for the write barrier. locations->AddTemp(Location::RequiresRegister()); locations->AddTemp(Location::RequiresRegister()); } @@ -1088,7 +1094,7 @@ void InstructionCodeGeneratorX86_64::VisitInstanceFieldSet(HInstanceFieldSet* in void LocationsBuilderX86_64::VisitInstanceFieldGet(HInstanceFieldGet* instruction) { LocationSummary* locations = new (GetGraph()->GetArena()) LocationSummary(instruction, LocationSummary::kNoCall); - locations->SetInAt(0, Location::RequiresRegister()); + locations->SetInAt(0, Location::RequiresRegister(), Location::kDiesAtEntry); locations->SetOut(Location::RequiresRegister()); } @@ -1167,8 +1173,9 @@ void InstructionCodeGeneratorX86_64::VisitNullCheck(HNullCheck* instruction) { void LocationsBuilderX86_64::VisitArrayGet(HArrayGet* instruction) { LocationSummary* locations = new (GetGraph()->GetArena()) LocationSummary(instruction, LocationSummary::kNoCall); - locations->SetInAt(0, Location::RequiresRegister()); - locations->SetInAt(1, Location::RegisterOrConstant(instruction->InputAt(1))); + locations->SetInAt(0, Location::RequiresRegister(), Location::kDiesAtEntry); + locations->SetInAt( + 1, Location::RegisterOrConstant(instruction->InputAt(1)), Location::kDiesAtEntry); locations->SetOut(Location::RequiresRegister()); } @@ -1272,9 +1279,10 @@ void LocationsBuilderX86_64::VisitArraySet(HArraySet* instruction) { locations->SetInAt(1, X86_64CpuLocation(calling_convention.GetRegisterAt(1))); locations->SetInAt(2, X86_64CpuLocation(calling_convention.GetRegisterAt(2))); } else { - locations->SetInAt(0, Location::RequiresRegister()); - locations->SetInAt(1, Location::RegisterOrConstant(instruction->InputAt(1))); - locations->SetInAt(2, Location::RequiresRegister()); + locations->SetInAt(0, Location::RequiresRegister(), Location::kDiesAtEntry); + locations->SetInAt( + 1, Location::RegisterOrConstant(instruction->InputAt(1)), Location::kDiesAtEntry); + locations->SetInAt(2, Location::RequiresRegister(), Location::kDiesAtEntry); } } @@ -1354,7 +1362,7 @@ void InstructionCodeGeneratorX86_64::VisitArraySet(HArraySet* instruction) { void LocationsBuilderX86_64::VisitArrayLength(HArrayLength* instruction) { LocationSummary* locations = new (GetGraph()->GetArena()) LocationSummary(instruction, LocationSummary::kNoCall); - locations->SetInAt(0, Location::RequiresRegister()); + locations->SetInAt(0, Location::RequiresRegister(), Location::kDiesAtEntry); locations->SetOut(Location::RequiresRegister()); } diff --git a/compiler/optimizing/live_ranges_test.cc b/compiler/optimizing/live_ranges_test.cc index 03f8625..8be4746 100644 --- a/compiler/optimizing/live_ranges_test.cc +++ b/compiler/optimizing/live_ranges_test.cc @@ -268,7 +268,7 @@ TEST(LiveRangesTest, Loop1) { range = interval->GetFirstRange(); // Instruction is consumed by the if. ASSERT_EQ(14u, range->GetStart()); - ASSERT_EQ(17u, range->GetEnd()); + ASSERT_EQ(16u, range->GetEnd()); ASSERT_TRUE(range->GetNext() == nullptr); } diff --git a/compiler/optimizing/locations.cc b/compiler/optimizing/locations.cc index 1c36cdf..114d69c 100644 --- a/compiler/optimizing/locations.cc +++ b/compiler/optimizing/locations.cc @@ -25,13 +25,16 @@ LocationSummary::LocationSummary(HInstruction* instruction, CallKind call_kind) temps_(instruction->GetBlock()->GetGraph()->GetArena(), 0), environment_(instruction->GetBlock()->GetGraph()->GetArena(), instruction->EnvironmentSize()), + dies_at_entry_(instruction->GetBlock()->GetGraph()->GetArena(), instruction->InputCount()), call_kind_(call_kind), stack_mask_(nullptr), register_mask_(0), live_registers_() { inputs_.SetSize(instruction->InputCount()); + dies_at_entry_.SetSize(instruction->InputCount()); for (size_t i = 0; i < instruction->InputCount(); ++i) { inputs_.Put(i, Location()); + dies_at_entry_.Put(i, false); } environment_.SetSize(instruction->EnvironmentSize()); for (size_t i = 0; i < instruction->EnvironmentSize(); ++i) { diff --git a/compiler/optimizing/locations.h b/compiler/optimizing/locations.h index f358e05..8d0715a 100644 --- a/compiler/optimizing/locations.h +++ b/compiler/optimizing/locations.h @@ -34,6 +34,8 @@ class HInstruction; */ class Location : public ValueObject { public: + static constexpr bool kDiesAtEntry = true; + enum Kind { kInvalid = 0, kConstant = 1, @@ -312,7 +314,8 @@ class LocationSummary : public ArenaObject { LocationSummary(HInstruction* instruction, CallKind call_kind = kNoCall); - void SetInAt(uint32_t at, Location location) { + void SetInAt(uint32_t at, Location location, bool dies_at_entry = false) { + dies_at_entry_.Put(at, dies_at_entry); inputs_.Put(at, location); } @@ -390,10 +393,12 @@ class LocationSummary : public ArenaObject { bool InputOverlapsWithOutputOrTemp(uint32_t input, bool is_environment) const { if (is_environment) return true; Location location = Out(); - // TODO: Add more policies. if (input == 0 && location.IsUnallocated() && location.GetPolicy() == Location::kSameAsFirstInput) { return false; } + if (dies_at_entry_.Get(input)) { + return false; + } return true; } @@ -401,6 +406,7 @@ class LocationSummary : public ArenaObject { GrowableArray<Location> inputs_; GrowableArray<Location> temps_; GrowableArray<Location> environment_; + GrowableArray<bool> dies_at_entry_; Location output_; const CallKind call_kind_; |