Index: src/mips/lithium-codegen-mips.cc |
diff --git a/src/mips/lithium-codegen-mips.cc b/src/mips/lithium-codegen-mips.cc |
index e6f52d84b707ef82d3385eddea892525039b744d..a60829d5e8e726e0706a726969e0697a0f62818d 100644 |
--- a/src/mips/lithium-codegen-mips.cc |
+++ b/src/mips/lithium-codegen-mips.cc |
@@ -5792,13 +5792,61 @@ void LCodeGen::DoCheckMapValue(LCheckMapValue* instr) { |
} |
+void LCodeGen::DoDeferredLoadMutableDouble(LLoadFieldByIndex* instr, |
+ Register result, |
+ Register object, |
+ Register index) { |
+ PushSafepointRegistersScope scope(this, Safepoint::kWithRegisters); |
+ __ Push(object); |
+ __ Push(index); |
Paul Lind
2014/03/31 22:39:59
You should combine the two Pushes, to save an inst
|
+ __ mov(cp, zero_reg); |
+ __ CallRuntimeSaveDoubles(Runtime::kLoadMutableDouble); |
+ RecordSafepointWithRegisters( |
+ instr->pointer_map(), 2, Safepoint::kNoLazyDeopt); |
+ __ StoreToSafepointRegisterSlot(v0, result); |
+} |
+ |
+ |
void LCodeGen::DoLoadFieldByIndex(LLoadFieldByIndex* instr) { |
+ class DeferredLoadMutableDouble V8_FINAL : public LDeferredCode { |
+ public: |
+ DeferredLoadMutableDouble(LCodeGen* codegen, |
+ LLoadFieldByIndex* instr, |
+ Register result, |
+ Register object, |
+ Register index) |
+ : LDeferredCode(codegen), |
+ instr_(instr), |
+ result_(result), |
+ object_(object), |
+ index_(index) { |
+ } |
+ virtual void Generate() V8_OVERRIDE { |
+ codegen()->DoDeferredLoadMutableDouble(instr_, result_, object_, index_); |
+ } |
+ virtual LInstruction* instr() V8_OVERRIDE { return instr_; } |
+ private: |
+ LLoadFieldByIndex* instr_; |
+ Register result_; |
+ Register object_; |
+ Register index_; |
+ }; |
+ |
Register object = ToRegister(instr->object()); |
Register index = ToRegister(instr->index()); |
Register result = ToRegister(instr->result()); |
Register scratch = scratch0(); |
+ DeferredLoadMutableDouble* deferred; |
+ deferred = new(zone()) DeferredLoadMutableDouble( |
+ this, instr, result, object, index); |
+ |
Label out_of_object, done; |
+ |
+ __ And(scratch, index, Operand(Smi::FromInt(1))); |
+ __ Branch(deferred->entry(), ne, scratch, Operand(zero_reg)); |
+ __ sra(index, index, 1); |
+ |
__ Branch(USE_DELAY_SLOT, &out_of_object, lt, index, Operand(zero_reg)); |
__ sll(scratch, index, kPointerSizeLog2 - kSmiTagSize); // In delay slot. |
@@ -5814,6 +5862,7 @@ void LCodeGen::DoLoadFieldByIndex(LLoadFieldByIndex* instr) { |
__ Subu(scratch, result, scratch); |
__ lw(result, FieldMemOperand(scratch, |
FixedArray::kHeaderSize - kPointerSize)); |
+ __ bind(deferred->exit()); |
__ bind(&done); |
} |