X64 Crankshaft: Add LTemplatedInstruction and some derived classes to lithium-x64.cc.
authorwhesse@chromium.org <whesse@chromium.org@ce2b1a6d-e550-0410-aec6-3dcde31c8c00>
Tue, 11 Jan 2011 11:33:52 +0000 (11:33 +0000)
committerwhesse@chromium.org <whesse@chromium.org@ce2b1a6d-e550-0410-aec6-3dcde31c8c00>
Tue, 11 Jan 2011 11:33:52 +0000 (11:33 +0000)
Review URL: http://codereview.chromium.org/6128008

git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@6257 ce2b1a6d-e550-0410-aec6-3dcde31c8c00

src/ia32/lithium-ia32.h
src/x64/lithium-x64.cc
src/x64/lithium-x64.h

index e79214b82282413af26c2261612d1ecca6c14f97..4940b2c5bdc512d175a5398bf5efb52da4c679c2 100644 (file)
@@ -85,10 +85,12 @@ class Translation;
 //     LConstantT
 //   LDeoptimize
 //   LFunctionLiteral
+//   LGap
+//     LLabel
 //   LGlobalObject
 //   LGlobalReceiver
-//   LLabel
-//   LLayzBailout
+//   LGoto
+//   LLazyBailout
 //   LLoadGlobal
 //   LMaterializedLiteral
 //     LArrayLiteral
index 3e0cfdd75335f589062c27964273edbdc797925e..7957381238a157f1cc5a60eb26ab60c462191589 100644 (file)
 namespace v8 {
 namespace internal {
 
+LOsrEntry::LOsrEntry() {
+  for (int i = 0; i < Register::kNumAllocatableRegisters; ++i) {
+    register_spills_[i] = NULL;
+  }
+  for (int i = 0; i < DoubleRegister::kNumAllocatableRegisters; ++i) {
+    double_register_spills_[i] = NULL;
+  }
+}
+
+
+void LOsrEntry::MarkSpilledRegister(int allocation_index,
+                                    LOperand* spill_operand) {
+  ASSERT(spill_operand->IsStackSlot());
+  ASSERT(register_spills_[allocation_index] == NULL);
+  register_spills_[allocation_index] = spill_operand;
+}
+
+
+void LOsrEntry::MarkSpilledDoubleRegister(int allocation_index,
+                                          LOperand* spill_operand) {
+  ASSERT(spill_operand->IsDoubleStackSlot());
+  ASSERT(double_register_spills_[allocation_index] == NULL);
+  double_register_spills_[allocation_index] = spill_operand;
+}
+
+
+void LOsrEntry::CompileToNative(LCodeGen* generator) {
+  UNIMPLEMENTED();
+  // Implement in lithium-codegen-x64.cc.
+}
+
+
+void LInstruction::PrintTo(StringStream* stream) {
+  stream->Add("%s ", this->Mnemonic());
+  if (HasResult()) {
+    LTemplateInstruction<1>::cast(this)->result()->PrintTo(stream);
+    stream->Add(" ");
+  }
+  PrintDataTo(stream);
+
+  if (HasEnvironment()) {
+    stream->Add(" ");
+    // environment()->PrintTo(stream);
+  }
+
+  if (HasPointerMap()) {
+    stream->Add(" ");
+    //pointer_map()->PrintTo(stream);
+  }
+}
+
+
+void LLabel::PrintDataTo(StringStream* stream) {
+  LGap::PrintDataTo(stream);
+  LLabel* rep = replacement();
+  if (rep != NULL) {
+    stream->Add(" Dead block replaced with B%d", rep->block_id());
+  }
+}
+
+
 bool LGap::IsRedundant() const {
   for (int i = 0; i < 4; i++) {
     if (parallel_moves_[i] != NULL && !parallel_moves_[i]->IsRedundant()) {
@@ -42,7 +103,7 @@ bool LGap::IsRedundant() const {
 }
 
 
-void LGap::PrintDataTo(StringStream* stream) const {
+void LGap::PrintDataTo(StringStream* stream) {
   for (int i = 0; i < 4; i++) {
     stream->Add("(");
     if (parallel_moves_[i] != NULL) {
@@ -53,6 +114,11 @@ void LGap::PrintDataTo(StringStream* stream) const {
 }
 
 
+void LGoto::PrintDataTo(StringStream* stream) {
+  stream->Add("B%d", block_id());
+}
+
+
 LChunk* LChunkBuilder::Build() {
   ASSERT(is_unused());
   chunk_ = new LChunk(graph());
index 24577cba1ebe5da2bf6d7be8117869a82fd78f99..7d9a4af3d11c5069ece71d0528c3ad8b3e7d3efd 100644 (file)
@@ -45,13 +45,23 @@ class Translation;
 // Type hierarchy:
 //
 // LInstruction
+//   LDeoptimize
 //   LGap
+//     LLabel
+//   LGoto
+//   LLazyBailout
+//   LOsrEntry
 
 #define LITHIUM_ALL_INSTRUCTION_LIST(V)         \
   LITHIUM_CONCRETE_INSTRUCTION_LIST(V)
 
 #define LITHIUM_CONCRETE_INSTRUCTION_LIST(V)    \
-  V(Gap)
+  V(Deoptimize)                                 \
+  V(Gap)                                        \
+  V(Goto)                                       \
+  V(Label)                                      \
+  V(LazyBailout)                                \
+  V(OsrEntry)
 
 
 #define DECLARE_INSTRUCTION(type)                \
@@ -80,20 +90,10 @@ class LInstruction: public ZoneObject {
       : hydrogen_value_(NULL) { }
   virtual ~LInstruction() { }
 
-  // Predicates should be generated by macro as in lithium-ia32.h.
-  virtual bool IsLabel() const {
-    UNIMPLEMENTED();
-    return false;
-  }
-  virtual bool IsOsrEntry() const {
-    UNIMPLEMENTED();
-    return false;
-  }
-
   virtual void CompileToNative(LCodeGen* generator) = 0;
   virtual const char* Mnemonic() const = 0;
-  virtual void PrintTo(StringStream* stream) const;
-  virtual void PrintDataTo(StringStream* stream) const { }
+  virtual void PrintTo(StringStream* stream);
+  virtual void PrintDataTo(StringStream* stream) { }
 
   // Declare virtual type testers.
 #define DECLARE_DO(type) virtual bool Is##type() const { return false; }
@@ -109,9 +109,7 @@ class LInstruction: public ZoneObject {
   LPointerMap* pointer_map() const { return pointer_map_.get(); }
   bool HasPointerMap() const { return pointer_map_.is_set(); }
 
-  void set_result(LOperand* operand) { result_.set(operand); }
-  LOperand* result() const { return result_.get(); }
-  bool HasResult() const { return result_.is_set(); }
+  virtual bool HasResult() const = 0;
 
   void set_hydrogen_value(HValue* value) { hydrogen_value_ = value; }
   HValue* hydrogen_value() const { return hydrogen_value_; }
@@ -129,13 +127,37 @@ class LInstruction: public ZoneObject {
  private:
   SetOncePointer<LEnvironment> environment_;
   SetOncePointer<LPointerMap> pointer_map_;
-  SetOncePointer<LOperand> result_;
   HValue* hydrogen_value_;
   SetOncePointer<LEnvironment> deoptimization_environment_;
 };
 
 
-class LGap: public LInstruction {
+template <int Result>
+class LTemplateInstruction: public LInstruction { };
+
+
+template<>
+class LTemplateInstruction<0>: public LInstruction {
+  virtual bool HasResult() const { return false; }
+};
+
+
+template<>
+class LTemplateInstruction<1>: public LInstruction {
+ public:
+  static LTemplateInstruction<1>* cast(LInstruction* instr)  {
+    ASSERT(instr->HasResult());
+    return reinterpret_cast<LTemplateInstruction<1>*>(instr);
+  }
+  void set_result(LOperand* operand) { result_.set(operand); }
+  LOperand* result() const { return result_.get(); }
+  virtual bool HasResult() const { return result_.is_set(); }
+ private:
+  SetOncePointer<LOperand> result_;
+};
+
+
+class LGap: public LTemplateInstruction<0> {
  public:
   explicit LGap(HBasicBlock* block)
       : block_(block) {
@@ -146,7 +168,7 @@ class LGap: public LInstruction {
   }
 
   DECLARE_CONCRETE_INSTRUCTION(Gap, "gap")
-  virtual void PrintDataTo(StringStream* stream) const;
+  virtual void PrintDataTo(StringStream* stream);
 
   bool IsRedundant() const;
 
@@ -176,9 +198,61 @@ class LGap: public LInstruction {
 };
 
 
+class LGoto: public LTemplateInstruction<0> {
+ public:
+  LGoto(int block_id, bool include_stack_check = false)
+    : block_id_(block_id), include_stack_check_(include_stack_check) { }
+
+  DECLARE_CONCRETE_INSTRUCTION(Goto, "goto")
+  virtual void PrintDataTo(StringStream* stream);
+  virtual bool IsControl() const { return true; }
+
+  int block_id() const { return block_id_; }
+  bool include_stack_check() const { return include_stack_check_; }
+
+ private:
+  int block_id_;
+  bool include_stack_check_;
+};
+
+
+class LLazyBailout: public LTemplateInstruction<0> {
+ public:
+  LLazyBailout() : gap_instructions_size_(0) { }
+
+  DECLARE_CONCRETE_INSTRUCTION(LazyBailout, "lazy-bailout")
+
+  void set_gap_instructions_size(int gap_instructions_size) {
+    gap_instructions_size_ = gap_instructions_size;
+  }
+  int gap_instructions_size() { return gap_instructions_size_; }
+
+ private:
+  int gap_instructions_size_;
+};
+
+
+class LDeoptimize: public LTemplateInstruction<0> {
+ public:
+  DECLARE_CONCRETE_INSTRUCTION(Deoptimize, "deoptimize")
+};
+
+
 class LLabel: public LGap {
  public:
-  explicit LLabel(HBasicBlock* block) : LGap(block) { }
+  explicit LLabel(HBasicBlock* block)
+      : LGap(block), replacement_(NULL) { }
+
+  DECLARE_CONCRETE_INSTRUCTION(Label, "label")
+
+  virtual void PrintDataTo(StringStream* stream);
+
+  int block_id() const { return block()->block_id(); }
+  bool is_loop_header() const { return block()->IsLoopHeader(); }
+  Label* label() { return &label_; }
+  LLabel* replacement() const { return replacement_; }
+  void set_replacement(LLabel* label) { replacement_ = label; }
+  bool HasReplacement() const { return replacement_ != NULL; }
 
  private:
   Label label_;
@@ -186,30 +260,18 @@ class LLabel: public LGap {
 };
 
 
-class LOsrEntry: public LInstruction {
+class LOsrEntry: public LTemplateInstruction<0> {
  public:
-  // Function could be generated by a macro as in lithium-ia32.h.
-  static LOsrEntry* cast(LInstruction* instr) {
-    UNIMPLEMENTED();
-    return NULL;
-  }
+  LOsrEntry();
 
-  LOperand** SpilledRegisterArray() {
-    UNIMPLEMENTED();
-    return NULL;
-  }
-  LOperand** SpilledDoubleRegisterArray() {
-    UNIMPLEMENTED();
-    return NULL;
-  }
+  DECLARE_CONCRETE_INSTRUCTION(OsrEntry, "osr-entry")
 
-  void MarkSpilledRegister(int allocation_index, LOperand* spill_operand) {
-    UNIMPLEMENTED();
-  }
+  LOperand** SpilledRegisterArray() { return register_spills_; }
+  LOperand** SpilledDoubleRegisterArray() { return double_register_spills_; }
+
+  void MarkSpilledRegister(int allocation_index, LOperand* spill_operand);
   void MarkSpilledDoubleRegister(int allocation_index,
-                                 LOperand* spill_operand) {
-    UNIMPLEMENTED();
-  }
+                                 LOperand* spill_operand);
 
  private:
   // Arrays of spill slot operands for registers with an assigned spill