Reviewers: jarin,

https://codereview.chromium.org/748773002/diff/1/src/compiler/graph-visualizer.cc
File src/compiler/graph-visualizer.cc (right):

https://codereview.chromium.org/748773002/diff/1/src/compiler/graph-visualizer.cc#newcode726
src/compiler/graph-visualizer.cc:726: int index = -1;
On 2014/11/21 10:55:39, jarin wrote:
How about DCHECK((range->TopLevel()->GetSpillRange() != nullptr) ==
FLAG_turbo_reuse_spill_slots)?

benedikt saw a crash here, so i was fixing it - nothing to do with this
cl

https://codereview.chromium.org/748773002/diff/1/src/compiler/register-allocator.cc
File src/compiler/register-allocator.cc (right):

https://codereview.chromium.org/748773002/diff/1/src/compiler/register-allocator.cc#newcode549
src/compiler/register-allocator.cc:549:
use_spill_ranges_(FLAG_turbo_reuse_spill_slots) {
On 2014/11/21 10:55:39, jarin wrote:
Why is there this extra indirection? Can't we use the naked flag?
(That will
simplify the removal once we are done.)

ok

https://codereview.chromium.org/748773002/diff/1/src/flag-definitions.h
File src/flag-definitions.h (right):

https://codereview.chromium.org/748773002/diff/1/src/flag-definitions.h#newcode391
src/flag-definitions.h:391: DEFINE_BOOL(turbo_reuse_spill_slots, false,
"reuse spill slots in TurboFan")
On 2014/11/21 10:55:39, jarin wrote:
Please, add a TODO explaining that this is just temporary for
experimentation.

okay

Description:
[turbofan] put spill slot reuse behind a flag

BUG=

Please review this at https://codereview.chromium.org/748773002/

Base URL: https://chromium.googlesource.com/v8/v8.git@master

Affected files (+60, -3 lines):
  M src/compiler/graph-visualizer.cc
  M src/compiler/pipeline.cc
  M src/compiler/register-allocator.h
  M src/compiler/register-allocator.cc
  M src/flag-definitions.h


Index: src/compiler/graph-visualizer.cc
diff --git a/src/compiler/graph-visualizer.cc b/src/compiler/graph-visualizer.cc index 40b182a34c881352cef2b3242db5b1860e83e6a6..c9be0ac5ac2450f0f2bb2cde4a442aa0a264c11f 100644
--- a/src/compiler/graph-visualizer.cc
+++ b/src/compiler/graph-visualizer.cc
@@ -724,7 +724,8 @@ void GraphC1Visualizer::PrintLiveRange(LiveRange* range, const char* type) {
       }
     } else if (range->IsSpilled()) {
       int index = -1;
-      if (range->TopLevel()->GetSpillRange()->id() != -1) {
+      if (range->TopLevel()->GetSpillRange() != nullptr &&
+          range->TopLevel()->GetSpillRange()->id() != -1) {
         index = range->TopLevel()->GetSpillRange()->id();
       } else {
         index = range->TopLevel()->GetSpillOperand()->index();
Index: src/compiler/pipeline.cc
diff --git a/src/compiler/pipeline.cc b/src/compiler/pipeline.cc
index 10bbe7c1bc6d38e5b962b0646d6465b4b0e811cf..e5460d1fad6b0ad18221e1defa19d23b52e33fc1 100644
--- a/src/compiler/pipeline.cc
+++ b/src/compiler/pipeline.cc
@@ -944,7 +944,9 @@ void Pipeline::AllocateRegisters(const RegisterConfiguration* config,
     data->set_compilation_failed();
     return;
   }
-  Run<ReuseSpillSlotsPhase>();
+  if (FLAG_turbo_reuse_spill_slots) {
+    Run<ReuseSpillSlotsPhase>();
+  }
   Run<PopulatePointerMapsPhase>();
   Run<ConnectRangesPhase>();
   Run<ResolveControlFlowPhase>();
Index: src/compiler/register-allocator.cc
diff --git a/src/compiler/register-allocator.cc b/src/compiler/register-allocator.cc index 59d80c6f7c6fbfadda50fde5fac33da698b22892..283603a44e1728e6a9c8ae82b79fa053415a5c73 100644
--- a/src/compiler/register-allocator.cc
+++ b/src/compiler/register-allocator.cc
@@ -881,6 +881,8 @@ void SpillRange::MergeDisjointIntervals(UseInterval* other, Zone* zone) {


 void RegisterAllocator::ReuseSpillSlots() {
+  DCHECK(FLAG_turbo_reuse_spill_slots);
+
   // Merge disjoint spill ranges
   for (int i = 0; i < spill_ranges_.length(); i++) {
     SpillRange* range = spill_ranges_.at(i);
@@ -915,6 +917,7 @@ void RegisterAllocator::ReuseSpillSlots() {


SpillRange* RegisterAllocator::AssignSpillRangeToLiveRange(LiveRange* range) {
+  DCHECK(FLAG_turbo_reuse_spill_slots);
   int spill_id = spill_ranges_.length();
   SpillRange* spill_range =
       new (local_zone()) SpillRange(range, spill_id, local_zone());
@@ -1932,10 +1935,40 @@ bool RegisterAllocator::UnhandledIsSorted() {
 }


+void RegisterAllocator::FreeSpillSlot(LiveRange* range) {
+  DCHECK(!FLAG_turbo_reuse_spill_slots);
+  // Check that we are the last range.
+  if (range->next() != NULL) return;
+
+  if (!range->TopLevel()->HasAllocatedSpillOperand()) return;
+
+  InstructionOperand* spill_operand = range->TopLevel()->GetSpillOperand();
+  if (spill_operand->IsConstant()) return;
+  if (spill_operand->index() >= 0) {
+    reusable_slots_.Add(range, local_zone());
+  }
+}
+
+
+InstructionOperand* RegisterAllocator::TryReuseSpillSlot(LiveRange* range) {
+  DCHECK(!FLAG_turbo_reuse_spill_slots);
+  if (reusable_slots_.is_empty()) return NULL;
+  if (reusable_slots_.first()->End().Value() >
+      range->TopLevel()->Start().Value()) {
+    return NULL;
+  }
+  InstructionOperand* result =
+      reusable_slots_.first()->TopLevel()->GetSpillOperand();
+  reusable_slots_.Remove(0);
+  return result;
+}
+
+
 void RegisterAllocator::ActiveToHandled(LiveRange* range) {
   DCHECK(active_live_ranges_.Contains(range));
   active_live_ranges_.RemoveElement(range);
   TraceAlloc("Moving live range %d from active to handled\n", range->id());
+  if (!FLAG_turbo_reuse_spill_slots) FreeSpillSlot(range);
 }


@@ -1951,6 +1984,7 @@ void RegisterAllocator::InactiveToHandled(LiveRange* range) {
   DCHECK(inactive_live_ranges_.Contains(range));
   inactive_live_ranges_.RemoveElement(range);
TraceAlloc("Moving live range %d from inactive to handled\n", range->id());
+  if (!FLAG_turbo_reuse_spill_slots) FreeSpillSlot(range);
 }


@@ -2335,7 +2369,23 @@ void RegisterAllocator::Spill(LiveRange* range) {
   LiveRange* first = range->TopLevel();

   if (!first->HasAllocatedSpillOperand()) {
-    AssignSpillRangeToLiveRange(first);
+    if (FLAG_turbo_reuse_spill_slots) {
+      AssignSpillRangeToLiveRange(first);
+    } else {
+      InstructionOperand* op = TryReuseSpillSlot(range);
+      if (op == NULL) {
+        // Allocate a new operand referring to the spill slot.
+        RegisterKind kind = range->Kind();
+        int index = frame()->AllocateSpillSlot(kind == DOUBLE_REGISTERS);
+        if (kind == DOUBLE_REGISTERS) {
+          op = DoubleStackSlotOperand::Create(index, local_zone());
+        } else {
+          DCHECK(kind == GENERAL_REGISTERS);
+          op = StackSlotOperand::Create(index, local_zone());
+        }
+      }
+      first->SetSpillOperand(op);
+    }
   }
   range->MakeSpilled(code_zone());
 }
Index: src/compiler/register-allocator.h
diff --git a/src/compiler/register-allocator.h b/src/compiler/register-allocator.h index 5fbb821ccfbcb90a252caff1a5770342a538511f..8499a7981a510193bfd28e2b569b3b3bea37552a 100644
--- a/src/compiler/register-allocator.h
+++ b/src/compiler/register-allocator.h
@@ -457,6 +457,8 @@ class RegisterAllocator FINAL : public ZoneObject {
   bool TryAllocateFreeReg(LiveRange* range);
   void AllocateBlockedReg(LiveRange* range);
   SpillRange* AssignSpillRangeToLiveRange(LiveRange* range);
+  void FreeSpillSlot(LiveRange* range);
+  InstructionOperand* TryReuseSpillSlot(LiveRange* range);

   // Live range splitting helpers.

Index: src/flag-definitions.h
diff --git a/src/flag-definitions.h b/src/flag-definitions.h
index 0d7363e8f52828e32617ba7f382325771226df7e..adc730fc44f116d4412b88e666088e9ee22ca054 100644
--- a/src/flag-definitions.h
+++ b/src/flag-definitions.h
@@ -388,6 +388,8 @@ DEFINE_BOOL(loop_assignment_analysis, true, "perform loop assignment analysis")
 DEFINE_IMPLICATION(turbo_inlining_intrinsics, turbo_inlining)
 DEFINE_IMPLICATION(turbo_inlining, turbo_types)
 DEFINE_BOOL(turbo_profiling, false, "enable profiling in TurboFan")
+// TODO(dcarney): this is just for experimentation, remove when default.
+DEFINE_BOOL(turbo_reuse_spill_slots, false, "reuse spill slots in TurboFan")

 DEFINE_INT(typed_array_max_size_in_heap, 64,
            "threshold for in-heap typed array")


--
--
v8-dev mailing list
[email protected]
http://groups.google.com/group/v8-dev
--- You received this message because you are subscribed to the Google Groups "v8-dev" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to [email protected].
For more options, visit https://groups.google.com/d/optout.

Reply via email to