Commit 5ea59597 authored by Clemens Hammacher's avatar Clemens Hammacher Committed by Commit Bot

[Liftoff] Remove all computation of "half indexes"

Instead, always pass an index and an enum pointing to either half.

R=titzer@chromium.org

Bug: v8:6600, v8:8562
Change-Id: I7e73bd97bfc7ebf644b242980aa0a73cd5f18949
Reviewed-on: https://chromium-review.googlesource.com/c/1392189
Commit-Queue: Clemens Hammacher <clemensh@chromium.org>
Reviewed-by: 's avatarAndreas Haas <ahaas@chromium.org>
Cr-Commit-Position: refs/heads/master@{#58516}
parent fa844bdb
...@@ -54,18 +54,14 @@ inline MemOperand GetStackSlot(uint32_t index) { ...@@ -54,18 +54,14 @@ inline MemOperand GetStackSlot(uint32_t index) {
return MemOperand(fp, -offset); return MemOperand(fp, -offset);
} }
inline MemOperand GetHalfStackSlot(uint32_t half_index) { inline MemOperand GetHalfStackSlot(uint32_t index, RegPairHalf half) {
int32_t half_offset =
half == kLowWord ? 0 : LiftoffAssembler::kStackSlotSize / 2;
int32_t offset = kFirstStackSlotOffset + int32_t offset = kFirstStackSlotOffset +
half_index * (LiftoffAssembler::kStackSlotSize / 2); index * LiftoffAssembler::kStackSlotSize - half_offset;
return MemOperand(fp, -offset); return MemOperand(fp, -offset);
} }
inline MemOperand GetHalfStackSlot(uint32_t index, RegPairHalf half) {
STATIC_ASSERT(kLowWord == 0);
STATIC_ASSERT(kHighWord == 1);
return GetHalfStackSlot(2 * index - half);
}
inline MemOperand GetInstanceOperand() { inline MemOperand GetInstanceOperand() {
return MemOperand(fp, -kInstanceOffset); return MemOperand(fp, -kInstanceOffset);
} }
...@@ -601,8 +597,9 @@ void LiftoffAssembler::Fill(LiftoffRegister reg, uint32_t index, ...@@ -601,8 +597,9 @@ void LiftoffAssembler::Fill(LiftoffRegister reg, uint32_t index,
} }
} }
void LiftoffAssembler::FillI64Half(Register reg, uint32_t half_index) { void LiftoffAssembler::FillI64Half(Register reg, uint32_t index,
ldr(reg, liftoff::GetHalfStackSlot(half_index)); RegPairHalf half) {
ldr(reg, liftoff::GetHalfStackSlot(index, half));
} }
#define I32_BINOP(name, instruction) \ #define I32_BINOP(name, instruction) \
......
...@@ -363,7 +363,7 @@ void LiftoffAssembler::Fill(LiftoffRegister reg, uint32_t index, ...@@ -363,7 +363,7 @@ void LiftoffAssembler::Fill(LiftoffRegister reg, uint32_t index,
Ldr(liftoff::GetRegFromType(reg, type), src); Ldr(liftoff::GetRegFromType(reg, type), src);
} }
void LiftoffAssembler::FillI64Half(Register, uint32_t half_index) { void LiftoffAssembler::FillI64Half(Register, uint32_t index, RegPairHalf) {
UNREACHABLE(); UNREACHABLE();
} }
......
...@@ -34,15 +34,11 @@ inline Operand GetStackSlot(uint32_t index) { ...@@ -34,15 +34,11 @@ inline Operand GetStackSlot(uint32_t index) {
return Operand(ebp, -kFirstStackSlotOffset - offset); return Operand(ebp, -kFirstStackSlotOffset - offset);
} }
inline Operand GetHalfStackSlot(uint32_t half_index) {
int32_t offset = half_index * (LiftoffAssembler::kStackSlotSize / 2);
return Operand(ebp, -kFirstStackSlotOffset - offset);
}
inline MemOperand GetHalfStackSlot(uint32_t index, RegPairHalf half) { inline MemOperand GetHalfStackSlot(uint32_t index, RegPairHalf half) {
STATIC_ASSERT(kLowWord == 0); int32_t half_offset =
STATIC_ASSERT(kHighWord == 1); half == kLowWord ? 0 : LiftoffAssembler::kStackSlotSize / 2;
return GetHalfStackSlot(2 * index - half); int32_t offset = index * LiftoffAssembler::kStackSlotSize - half_offset;
return Operand(ebp, -kFirstStackSlotOffset - offset);
} }
// TODO(clemensh): Make this a constexpr variable once Operand is constexpr. // TODO(clemensh): Make this a constexpr variable once Operand is constexpr.
...@@ -498,8 +494,9 @@ void LiftoffAssembler::Fill(LiftoffRegister reg, uint32_t index, ...@@ -498,8 +494,9 @@ void LiftoffAssembler::Fill(LiftoffRegister reg, uint32_t index,
} }
} }
void LiftoffAssembler::FillI64Half(Register reg, uint32_t half_index) { void LiftoffAssembler::FillI64Half(Register reg, uint32_t index,
mov(reg, liftoff::GetHalfStackSlot(half_index)); RegPairHalf half) {
mov(reg, liftoff::GetHalfStackSlot(index, half));
} }
void LiftoffAssembler::emit_i32_add(Register dst, Register lhs, Register rhs) { void LiftoffAssembler::emit_i32_add(Register dst, Register lhs, Register rhs) {
......
...@@ -40,9 +40,10 @@ class StackTransferRecipe { ...@@ -40,9 +40,10 @@ class StackTransferRecipe {
}; };
struct RegisterLoad { struct RegisterLoad {
enum LoadKind : uint8_t { enum LoadKind : uint8_t {
kConstant, // load a constant value into a register. kConstant, // load a constant value into a register.
kStack, // fill a register from a stack slot. kStack, // fill a register from a stack slot.
kHalfStack // fill one half of a register pair from half a stack slot. kLowHalfStack, // fill a register from the low half of a stack slot.
kHighHalfStack // fill a register from the high half of a stack slot.
}; };
LiftoffRegister dst; LiftoffRegister dst;
...@@ -63,9 +64,10 @@ class StackTransferRecipe { ...@@ -63,9 +64,10 @@ class StackTransferRecipe {
ValueType type) { ValueType type) {
return {dst, kStack, type, stack_index}; return {dst, kStack, type, stack_index};
} }
static RegisterLoad HalfStack(LiftoffRegister dst, static RegisterLoad HalfStack(LiftoffRegister dst, int32_t stack_index,
int32_t half_stack_index) { RegPairHalf half) {
return {dst, kHalfStack, kWasmI32, half_stack_index}; return {dst, half == kLowWord ? kLowHalfStack : kHighHalfStack, kWasmI32,
stack_index};
} }
private: private:
...@@ -142,9 +144,12 @@ class StackTransferRecipe { ...@@ -142,9 +144,12 @@ class StackTransferRecipe {
case RegisterLoad::kStack: case RegisterLoad::kStack:
asm_->Fill(rl.dst, rl.value, rl.type); asm_->Fill(rl.dst, rl.value, rl.type);
break; break;
case RegisterLoad::kHalfStack: case RegisterLoad::kLowHalfStack:
// As half of a register pair, {rl.dst} must be a gp register. case RegisterLoad::kHighHalfStack:
asm_->FillI64Half(rl.dst.gp(), rl.value); // Half of a register pair, {rl.dst} must be a gp register.
auto half =
rl.kind == RegisterLoad::kLowHalfStack ? kLowWord : kHighWord;
asm_->FillI64Half(rl.dst.gp(), rl.value, half);
break; break;
} }
} }
...@@ -208,7 +213,7 @@ class StackTransferRecipe { ...@@ -208,7 +213,7 @@ class StackTransferRecipe {
DCHECK_EQ(kWasmI64, src.type()); DCHECK_EQ(kWasmI64, src.type());
switch (src.loc()) { switch (src.loc()) {
case VarState::kStack: case VarState::kStack:
LoadI64HalfStackSlot(dst, 2 * index - (half == kLowWord ? 0 : 1)); LoadI64HalfStackSlot(dst, index, half);
break; break;
case VarState::kRegister: { case VarState::kRegister: {
LiftoffRegister src_half = LiftoffRegister src_half =
...@@ -251,9 +256,10 @@ class StackTransferRecipe { ...@@ -251,9 +256,10 @@ class StackTransferRecipe {
register_loads_.emplace_back(RegisterLoad::Stack(dst, stack_index, type)); register_loads_.emplace_back(RegisterLoad::Stack(dst, stack_index, type));
} }
void LoadI64HalfStackSlot(LiftoffRegister dst, uint32_t half_stack_index) { void LoadI64HalfStackSlot(LiftoffRegister dst, uint32_t stack_index,
RegPairHalf half) {
register_loads_.emplace_back( register_loads_.emplace_back(
RegisterLoad::HalfStack(dst, half_stack_index)); RegisterLoad::HalfStack(dst, stack_index, half));
} }
private: private:
......
...@@ -384,9 +384,8 @@ class LiftoffAssembler : public TurboAssembler { ...@@ -384,9 +384,8 @@ class LiftoffAssembler : public TurboAssembler {
inline void Spill(uint32_t index, WasmValue); inline void Spill(uint32_t index, WasmValue);
inline void Fill(LiftoffRegister, uint32_t index, ValueType); inline void Fill(LiftoffRegister, uint32_t index, ValueType);
// Only used on 32-bit systems: Fill a register from a "half stack slot", i.e. // Only used on 32-bit systems: Fill a register from a "half stack slot", i.e.
// 4 bytes on the stack holding half of a 64-bit value. The two half_indexes // 4 bytes on the stack holding half of a 64-bit value.
// corresponding to slot {index} are {2*index} and {2*index-1}. inline void FillI64Half(Register, uint32_t index, RegPairHalf);
inline void FillI64Half(Register, uint32_t half_index);
// i32 binops. // i32 binops.
inline void emit_i32_add(Register dst, Register lhs, Register rhs); inline void emit_i32_add(Register dst, Register lhs, Register rhs);
......
...@@ -34,8 +34,10 @@ inline MemOperand GetStackSlot(uint32_t index) { ...@@ -34,8 +34,10 @@ inline MemOperand GetStackSlot(uint32_t index) {
return MemOperand(fp, -kFirstStackSlotOffset - offset); return MemOperand(fp, -kFirstStackSlotOffset - offset);
} }
inline MemOperand GetHalfStackSlot(uint32_t half_index) { inline MemOperand GetHalfStackSlot(uint32_t index, RegPairHalf half) {
int32_t offset = half_index * (LiftoffAssembler::kStackSlotSize / 2); int32_t half_offset =
half == kLowWord ? 0 : LiftoffAssembler::kStackSlotSize / 2;
int32_t offset = index * LiftoffAssembler::kStackSlotSize + half_offset;
return MemOperand(fp, -kFirstStackSlotOffset - offset); return MemOperand(fp, -kFirstStackSlotOffset - offset);
} }
...@@ -584,8 +586,9 @@ void LiftoffAssembler::Fill(LiftoffRegister reg, uint32_t index, ...@@ -584,8 +586,9 @@ void LiftoffAssembler::Fill(LiftoffRegister reg, uint32_t index,
} }
} }
void LiftoffAssembler::FillI64Half(Register reg, uint32_t half_index) { void LiftoffAssembler::FillI64Half(Register reg, uint32_t index,
lw(reg, liftoff::GetHalfStackSlot(half_index)); RegPairHalf half) {
lw(reg, liftoff::GetHalfStackSlot(index, half));
} }
void LiftoffAssembler::emit_i32_mul(Register dst, Register lhs, Register rhs) { void LiftoffAssembler::emit_i32_mul(Register dst, Register lhs, Register rhs) {
......
...@@ -496,7 +496,7 @@ void LiftoffAssembler::Fill(LiftoffRegister reg, uint32_t index, ...@@ -496,7 +496,7 @@ void LiftoffAssembler::Fill(LiftoffRegister reg, uint32_t index,
} }
} }
void LiftoffAssembler::FillI64Half(Register, uint32_t half_index) { void LiftoffAssembler::FillI64Half(Register, uint32_t index, RegPairHalf) {
UNREACHABLE(); UNREACHABLE();
} }
......
...@@ -105,7 +105,7 @@ void LiftoffAssembler::Fill(LiftoffRegister reg, uint32_t index, ...@@ -105,7 +105,7 @@ void LiftoffAssembler::Fill(LiftoffRegister reg, uint32_t index,
BAILOUT("Fill"); BAILOUT("Fill");
} }
void LiftoffAssembler::FillI64Half(Register, uint32_t half_index) { void LiftoffAssembler::FillI64Half(Register, uint32_t index, RegPairHalf) {
BAILOUT("FillI64Half"); BAILOUT("FillI64Half");
} }
......
...@@ -105,7 +105,7 @@ void LiftoffAssembler::Fill(LiftoffRegister reg, uint32_t index, ...@@ -105,7 +105,7 @@ void LiftoffAssembler::Fill(LiftoffRegister reg, uint32_t index,
BAILOUT("Fill"); BAILOUT("Fill");
} }
void LiftoffAssembler::FillI64Half(Register, uint32_t half_index) { void LiftoffAssembler::FillI64Half(Register, uint32_t index, RegPairHalf) {
BAILOUT("FillI64Half"); BAILOUT("FillI64Half");
} }
......
...@@ -418,7 +418,7 @@ void LiftoffAssembler::Fill(LiftoffRegister reg, uint32_t index, ...@@ -418,7 +418,7 @@ void LiftoffAssembler::Fill(LiftoffRegister reg, uint32_t index,
} }
} }
void LiftoffAssembler::FillI64Half(Register, uint32_t half_index) { void LiftoffAssembler::FillI64Half(Register, uint32_t index, RegPairHalf) {
UNREACHABLE(); UNREACHABLE();
} }
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment