Quick compiler: reference cleanup
For 32-bit targets, object references are 32 bits wide both in
Dalvik virtual registers and in core physical registers. Because of
this, object references and non-floating point values were both
handled as if they had the same register class (kCoreReg).
However, for 64-bit systems, references are 32 bits in Dalvik vregs, but
64 bits in physical registers. Although the same underlying physical
core registers will still be used for object reference and non-float
values, different register class views will be used to represent them.
For example, an object reference in arm64 might be held in x3 at some
point, while the same underlying physical register, w3, would be used
to hold a 32-bit int.
This CL breaks apart the handling of object reference and non-float values
to allow the proper register class (or register view) to be used. A
new register class, kRefReg, is introduced which will map to a 32-bit
core register on 32-bit targets, and 64-bit core registers on 64-bit
targets. From this point on, object references should be allocated
registers in the kRefReg class rather than kCoreReg.
Change-Id: I6166827daa8a0ea3af326940d56a6a14874f5810
diff --git a/compiler/dex/quick/mir_to_lir.h b/compiler/dex/quick/mir_to_lir.h
index 8d572ca..1281d45 100644
--- a/compiler/dex/quick/mir_to_lir.h
+++ b/compiler/dex/quick/mir_to_lir.h
@@ -456,6 +456,8 @@
int next_sp_reg_;
GrowableArray<RegisterInfo*> dp_regs_; // Double precision float.
int next_dp_reg_;
+ GrowableArray<RegisterInfo*>* ref_regs_; // Points to core_regs_ or core64_regs_
+ int* next_ref_reg_;
private:
Mir2Lir* const m2l_;
@@ -550,8 +552,12 @@
* just use our knowledge of type to select the most appropriate register class?
*/
RegisterClass RegClassBySize(OpSize size) {
- return (size == kUnsignedHalf || size == kSignedHalf || size == kUnsignedByte ||
- size == kSignedByte) ? kCoreReg : kAnyReg;
+ if (size == kReference) {
+ return kRefReg;
+ } else {
+ return (size == kUnsignedHalf || size == kSignedHalf || size == kUnsignedByte ||
+ size == kSignedByte) ? kCoreReg : kAnyReg;
+ }
}
size_t CodeBufferSizeInBytes() {
@@ -612,6 +618,8 @@
return current_dalvik_offset_;
}
+ RegisterClass ShortyToRegClass(char shorty_type);
+ RegisterClass LocToRegClass(RegLocation loc);
int ComputeFrameSize();
virtual void Materialize();
virtual CompiledMethod* GetCompiledMethod();
@@ -699,7 +707,7 @@
virtual RegStorage AllocFreeTemp();
virtual RegStorage AllocTemp();
virtual RegStorage AllocTempWide();
- virtual RegStorage AllocTempWord();
+ virtual RegStorage AllocTempRef();
virtual RegStorage AllocTempSingle();
virtual RegStorage AllocTempDouble();
virtual RegStorage AllocTypedTemp(bool fp_hint, int reg_class);
@@ -719,7 +727,6 @@
void NullifyRange(RegStorage reg, int s_reg);
void MarkDef(RegLocation rl, LIR *start, LIR *finish);
void MarkDefWide(RegLocation rl, LIR *start, LIR *finish);
- virtual RegLocation WideToNarrow(RegLocation rl);
void ResetDefLoc(RegLocation rl);
void ResetDefLocWide(RegLocation rl);
void ResetDefTracking();
@@ -764,8 +771,8 @@
void DoPromotion();
int VRegOffset(int v_reg);
int SRegOffset(int s_reg);
- RegLocation GetReturnWide(bool is_double);
- RegLocation GetReturn(bool is_float);
+ RegLocation GetReturnWide(RegisterClass reg_class);
+ RegLocation GetReturn(RegisterClass reg_class);
RegisterInfo* GetRegInfo(RegStorage reg);
// Shared by all targets - implemented in gen_common.cc.
@@ -973,6 +980,8 @@
}
// Load Dalvik value with 32-bit memory storage. If compressed object reference, decompress.
virtual RegLocation LoadValue(RegLocation rl_src, RegisterClass op_kind);
+ // Same as above, but derive the target register class from the location record.
+ virtual RegLocation LoadValue(RegLocation rl_src);
// Load Dalvik value with 64-bit memory storage.
virtual RegLocation LoadValueWide(RegLocation rl_src, RegisterClass op_kind);
// Load Dalvik value with 32-bit memory storage. If compressed object reference, decompress.
@@ -1122,6 +1131,7 @@
virtual RegLocation GetReturnAlt() = 0;
virtual RegLocation GetReturnWideAlt() = 0;
virtual RegLocation LocCReturn() = 0;
+ virtual RegLocation LocCReturnRef() = 0;
virtual RegLocation LocCReturnDouble() = 0;
virtual RegLocation LocCReturnFloat() = 0;
virtual RegLocation LocCReturnWide() = 0;