Rework arm64 register codes and fix Arm64ManagedRegister tests.
Change-Id: I81ce3bc8a212c9c35be3a41b182ada87b32391ec
diff --git a/runtime/arch/arm64/context_arm64.cc b/runtime/arch/arm64/context_arm64.cc
index 3eb92c8..0614f1a 100644
--- a/runtime/arch/arm64/context_arm64.cc
+++ b/runtime/arch/arm64/context_arm64.cc
@@ -75,6 +75,7 @@
bool Arm64Context::SetGPR(uint32_t reg, uintptr_t value) {
DCHECK_LT(reg, static_cast<uint32_t>(kNumberOfCoreRegisters));
+ DCHECK_NE(reg, static_cast<uint32_t>(XZR));
DCHECK_NE(gprs_[reg], &gZero); // Can't overwrite this static value since they are never reset.
if (gprs_[reg] != nullptr) {
*gprs_[reg] = value;
@@ -146,11 +147,13 @@
extern "C" void art_quick_do_long_jump(uint64_t*, uint64_t*);
void Arm64Context::DoLongJump() {
- uint64_t gprs[32];
+ uint64_t gprs[kNumberOfCoreRegisters];
uint64_t fprs[kNumberOfDRegisters];
- // Do not use kNumberOfCoreRegisters, as this is with the distinction of SP and XZR
- for (size_t i = 0; i < 32; ++i) {
+ // The long jump routine called below expects to find the value for SP at index 31.
+ DCHECK_EQ(SP, 31);
+
+ for (size_t i = 0; i < kNumberOfCoreRegisters; ++i) {
gprs[i] = gprs_[i] != nullptr ? *gprs_[i] : Arm64Context::kBadGprBase + i;
}
for (size_t i = 0; i < kNumberOfDRegisters; ++i) {
diff --git a/runtime/arch/arm64/registers_arm64.cc b/runtime/arch/arm64/registers_arm64.cc
index 87901e3..3ed6eff 100644
--- a/runtime/arch/arm64/registers_arm64.cc
+++ b/runtime/arch/arm64/registers_arm64.cc
@@ -32,11 +32,11 @@
"w0", "w1", "w2", "w3", "w4", "w5", "w6", "w7", "w8", "w9",
"w10", "w11", "w12", "w13", "w14", "w15", "w16", "w17", "w18", "w19",
"w20", "w21", "w22", "w23", "w24", "w25", "w26", "w27", "w28", "w29",
- "w30", "wsp", "wxr"
+ "w30", "wsp", "wzr"
};
std::ostream& operator<<(std::ostream& os, const Register& rhs) {
- if (rhs >= X0 && rhs <= XZR) {
+ if (rhs >= X0 && rhs < kNumberOfCoreRegisters) {
os << kRegisterNames[rhs];
} else {
os << "XRegister[" << static_cast<int>(rhs) << "]";
@@ -45,7 +45,7 @@
}
std::ostream& operator<<(std::ostream& os, const WRegister& rhs) {
- if (rhs >= W0 && rhs <= WZR) {
+ if (rhs >= W0 && rhs < kNumberOfWRegisters) {
os << kWRegisterNames[rhs];
} else {
os << "WRegister[" << static_cast<int>(rhs) << "]";
diff --git a/runtime/arch/arm64/registers_arm64.h b/runtime/arch/arm64/registers_arm64.h
index 9ccab70..5bf8242 100644
--- a/runtime/arch/arm64/registers_arm64.h
+++ b/runtime/arch/arm64/registers_arm64.h
@@ -55,17 +55,17 @@
X28 = 28,
X29 = 29,
X30 = 30,
- X31 = 31,
- TR = 18, // ART Thread Register - Managed Runtime (Caller Saved Reg)
- ETR = 21, // ART Thread Register - External Calls (Callee Saved Reg)
- IP0 = 16, // Used as scratch by VIXL.
- IP1 = 17, // Used as scratch by ART JNI Assembler.
- FP = 29,
- LR = 30,
- SP = 31, // SP is X31 and overlaps with XRZ but we encode it as a
- // special register, due to the different instruction semantics.
- XZR = 32,
+ SP = 31, // SP and XZR are encoded in instructions using the register
+ XZR = 32, // code `31`, the context deciding which is used. We use a
+ // different enum value to distinguish between the two.
kNumberOfCoreRegisters = 33,
+ // Aliases.
+ TR = X18, // ART Thread Register - Managed Runtime (Caller Saved Reg)
+ ETR = X21, // ART Thread Register - External Calls (Callee Saved Reg)
+ IP0 = X16, // Used as scratch by VIXL.
+ IP1 = X17, // Used as scratch by ART JNI Assembler.
+ FP = X29,
+ LR = X30,
kNoRegister = -1,
};
std::ostream& operator<<(std::ostream& os, const Register& rhs);
@@ -103,9 +103,9 @@
W28 = 28,
W29 = 29,
W30 = 30,
- W31 = 31,
- WZR = 31,
- kNumberOfWRegisters = 32,
+ WSP = 31,
+ WZR = 32,
+ kNumberOfWRegisters = 33,
kNoWRegister = -1,
};
std::ostream& operator<<(std::ostream& os, const WRegister& rhs);