Commit 33d956e7 authored by Milad Fa's avatar Milad Fa Committed by V8 LUCI CQ

S390[liftoff]: Implement simd load and extend ops

Change-Id: I86f34d698bf34590359a980282fa60d6501a6da9
Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/3469628Reviewed-by: 's avatarJunliang Yan <junyan@redhat.com>
Commit-Queue: Milad Farazmand <mfarazma@redhat.com>
Cr-Commit-Position: refs/heads/main@{#79157}
parent 1025bf26
......@@ -6054,16 +6054,16 @@ void TurboAssembler::I16x8Q15MulRSatS(Simd128Register dst, Simd128Register src1,
V(16x8, vlbrrep, LoadU16LE, 1) \
V(8x16, vlrep, LoadU8, 0)
#define LOAD_SPLAT(name, vector_instr, scalar_instr, condition) \
void TurboAssembler::LoadAndSplat##name##LE(Simd128Register dst, \
const MemOperand& mem) { \
if (CAN_LOAD_STORE_REVERSE && is_uint12(mem.offset())) { \
vector_instr(dst, mem, Condition(condition)); \
return; \
} \
scalar_instr(r1, mem); \
vlvg(dst, r1, MemOperand(r0, 0), Condition(condition)); \
vrep(dst, dst, Operand(0), Condition(condition)); \
#define LOAD_SPLAT(name, vector_instr, scalar_instr, condition) \
void TurboAssembler::LoadAndSplat##name##LE( \
Simd128Register dst, const MemOperand& mem, Register scratch) { \
if (CAN_LOAD_STORE_REVERSE && is_uint12(mem.offset())) { \
vector_instr(dst, mem, Condition(condition)); \
return; \
} \
scalar_instr(scratch, mem); \
vlvg(dst, scratch, MemOperand(r0, 0), Condition(condition)); \
vrep(dst, dst, Operand(0), Condition(condition)); \
}
LOAD_SPLAT_LIST(LOAD_SPLAT)
#undef LOAD_SPLAT
......@@ -6077,40 +6077,41 @@ LOAD_SPLAT_LIST(LOAD_SPLAT)
V(8x8U, vuplh, 0) \
V(8x8S, vuph, 0)
#define LOAD_EXTEND(name, unpack_instr, condition) \
void TurboAssembler::LoadAndExtend##name##LE(Simd128Register dst, \
const MemOperand& mem) { \
if (CAN_LOAD_STORE_REVERSE && is_uint12(mem.offset())) { \
vlebrg(kScratchDoubleReg, mem, Condition(0)); \
} else { \
LoadU64LE(r1, mem); \
vlvg(kScratchDoubleReg, r1, MemOperand(r0, 0), Condition(3)); \
} \
unpack_instr(dst, kScratchDoubleReg, Condition(0), Condition(0), \
Condition(condition)); \
#define LOAD_EXTEND(name, unpack_instr, condition) \
void TurboAssembler::LoadAndExtend##name##LE( \
Simd128Register dst, const MemOperand& mem, Register scratch) { \
if (CAN_LOAD_STORE_REVERSE && is_uint12(mem.offset())) { \
vlebrg(dst, mem, Condition(0)); \
} else { \
LoadU64LE(scratch, mem); \
vlvg(dst, scratch, MemOperand(r0, 0), Condition(3)); \
} \
unpack_instr(dst, dst, Condition(0), Condition(0), Condition(condition)); \
}
LOAD_EXTEND_LIST(LOAD_EXTEND)
#undef LOAD_EXTEND
#undef LOAD_EXTEND
void TurboAssembler::LoadV32ZeroLE(Simd128Register dst, const MemOperand& mem) {
void TurboAssembler::LoadV32ZeroLE(Simd128Register dst, const MemOperand& mem,
Register scratch) {
vx(dst, dst, dst, Condition(0), Condition(0), Condition(0));
if (CAN_LOAD_STORE_REVERSE && is_uint12(mem.offset())) {
vlebrf(dst, mem, Condition(3));
return;
}
LoadU32LE(r1, mem);
vlvg(dst, r1, MemOperand(r0, 3), Condition(2));
LoadU32LE(scratch, mem);
vlvg(dst, scratch, MemOperand(r0, 3), Condition(2));
}
void TurboAssembler::LoadV64ZeroLE(Simd128Register dst, const MemOperand& mem) {
void TurboAssembler::LoadV64ZeroLE(Simd128Register dst, const MemOperand& mem,
Register scratch) {
vx(dst, dst, dst, Condition(0), Condition(0), Condition(0));
if (CAN_LOAD_STORE_REVERSE && is_uint12(mem.offset())) {
vlebrg(dst, mem, Condition(1));
return;
}
LoadU64LE(r1, mem);
vlvg(dst, r1, MemOperand(r0, 1), Condition(3));
LoadU64LE(scratch, mem);
vlvg(dst, scratch, MemOperand(r0, 1), Condition(3));
}
#define LOAD_LANE_LIST(V) \
......
......@@ -399,18 +399,30 @@ class V8_EXPORT_PRIVATE TurboAssembler : public TurboAssemblerBase {
void LoadF64LE(DoubleRegister dst, const MemOperand& opnd, Register scratch);
void LoadF32LE(DoubleRegister dst, const MemOperand& opnd, Register scratch);
// Vector LE Load and Transform instructions.
void LoadAndSplat64x2LE(Simd128Register dst, const MemOperand& mem);
void LoadAndSplat32x4LE(Simd128Register dst, const MemOperand& mem);
void LoadAndSplat16x8LE(Simd128Register dst, const MemOperand& mem);
void LoadAndSplat8x16LE(Simd128Register dst, const MemOperand& mem);
void LoadAndExtend8x8ULE(Simd128Register dst, const MemOperand& mem);
void LoadAndExtend8x8SLE(Simd128Register dst, const MemOperand& mem);
void LoadAndExtend16x4ULE(Simd128Register dst, const MemOperand& mem);
void LoadAndExtend16x4SLE(Simd128Register dst, const MemOperand& mem);
void LoadAndExtend32x2ULE(Simd128Register dst, const MemOperand& mem);
void LoadAndExtend32x2SLE(Simd128Register dst, const MemOperand& mem);
void LoadV32ZeroLE(Simd128Register dst, const MemOperand& mem);
void LoadV64ZeroLE(Simd128Register dst, const MemOperand& mem);
void LoadAndSplat64x2LE(Simd128Register dst, const MemOperand& mem,
Register scratch);
void LoadAndSplat32x4LE(Simd128Register dst, const MemOperand& mem,
Register scratch);
void LoadAndSplat16x8LE(Simd128Register dst, const MemOperand& me,
Register scratch);
void LoadAndSplat8x16LE(Simd128Register dst, const MemOperand& mem,
Register scratch);
void LoadAndExtend8x8ULE(Simd128Register dst, const MemOperand& mem,
Register scratch);
void LoadAndExtend8x8SLE(Simd128Register dst, const MemOperand& mem,
Register scratch);
void LoadAndExtend16x4ULE(Simd128Register dst, const MemOperand& mem,
Register scratch);
void LoadAndExtend16x4SLE(Simd128Register dst, const MemOperand& mem,
Register scratch);
void LoadAndExtend32x2ULE(Simd128Register dst, const MemOperand& mem,
Register scratch);
void LoadAndExtend32x2SLE(Simd128Register dst, const MemOperand& mem,
Register scratch);
void LoadV32ZeroLE(Simd128Register dst, const MemOperand& mem,
Register scratch);
void LoadV64ZeroLE(Simd128Register dst, const MemOperand& mem,
Register scratch);
void LoadLane8LE(Simd128Register dst, const MemOperand& mem, int lane,
Register scratch);
void LoadLane16LE(Simd128Register dst, const MemOperand& mem, int lane,
......
......@@ -3022,7 +3022,7 @@ CodeGenerator::CodeGenResult CodeGenerator::AssembleArchInstruction(
AddressingMode mode = kMode_None; \
MemOperand operand = i.MemoryOperand(&mode); \
Simd128Register dst = i.OutputSimd128Register(); \
__ LoadAndSplat##type##LE(dst, operand);
__ LoadAndSplat##type##LE(dst, operand, kScratchReg);
case kS390_S128Load64Splat: {
LOAD_SPLAT(64x2);
break;
......@@ -3044,7 +3044,7 @@ CodeGenerator::CodeGenResult CodeGenerator::AssembleArchInstruction(
AddressingMode mode = kMode_None; \
MemOperand operand = i.MemoryOperand(&mode); \
Simd128Register dst = i.OutputSimd128Register(); \
__ LoadAndExtend##type##LE(dst, operand);
__ LoadAndExtend##type##LE(dst, operand, kScratchReg);
case kS390_S128Load32x2U: {
LOAD_EXTEND(32x2U);
break;
......@@ -3074,7 +3074,7 @@ CodeGenerator::CodeGenResult CodeGenerator::AssembleArchInstruction(
AddressingMode mode = kMode_None; \
MemOperand operand = i.MemoryOperand(&mode); \
Simd128Register dst = i.OutputSimd128Register(); \
__ LoadV##type##ZeroLE(dst, operand);
__ LoadV##type##ZeroLE(dst, operand, kScratchReg);
case kS390_S128Load32Zero: {
LOAD_AND_ZERO(32);
break;
......
......@@ -2572,7 +2572,51 @@ void LiftoffAssembler::LoadTransform(LiftoffRegister dst, Register src_addr,
LoadType type,
LoadTransformationKind transform,
uint32_t* protected_load_pc) {
bailout(kSimd, "Load transform unimplemented");
if (!is_int20(offset_imm)) {
mov(ip, Operand(offset_imm));
if (offset_reg != no_reg) {
AddS64(ip, offset_reg);
}
offset_reg = ip;
offset_imm = 0;
}
MemOperand src_op =
MemOperand(src_addr, offset_reg == no_reg ? r0 : offset_reg, offset_imm);
*protected_load_pc = pc_offset();
MachineType memtype = type.mem_type();
if (transform == LoadTransformationKind::kExtend) {
if (memtype == MachineType::Int8()) {
LoadAndExtend8x8SLE(dst.fp(), src_op, r1);
} else if (memtype == MachineType::Uint8()) {
LoadAndExtend8x8ULE(dst.fp(), src_op, r1);
} else if (memtype == MachineType::Int16()) {
LoadAndExtend16x4SLE(dst.fp(), src_op, r1);
} else if (memtype == MachineType::Uint16()) {
LoadAndExtend16x4ULE(dst.fp(), src_op, r1);
} else if (memtype == MachineType::Int32()) {
LoadAndExtend32x2SLE(dst.fp(), src_op, r1);
} else if (memtype == MachineType::Uint32()) {
LoadAndExtend32x2ULE(dst.fp(), src_op, r1);
}
} else if (transform == LoadTransformationKind::kZeroExtend) {
if (memtype == MachineType::Int32()) {
LoadV32ZeroLE(dst.fp(), src_op, r1);
} else {
DCHECK_EQ(MachineType::Int64(), memtype);
LoadV64ZeroLE(dst.fp(), src_op, r1);
}
} else {
DCHECK_EQ(LoadTransformationKind::kSplat, transform);
if (memtype == MachineType::Int8()) {
LoadAndSplat8x16LE(dst.fp(), src_op, r1);
} else if (memtype == MachineType::Int16()) {
LoadAndSplat16x8LE(dst.fp(), src_op, r1);
} else if (memtype == MachineType::Int32()) {
LoadAndSplat32x4LE(dst.fp(), src_op, r1);
} else if (memtype == MachineType::Int64()) {
LoadAndSplat64x2LE(dst.fp(), src_op, r1);
}
}
}
void LiftoffAssembler::LoadLane(LiftoffRegister dst, LiftoffRegister src,
......
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