mirror of
https://repo.dactyloidae.xyz/Dactyloidae/UXP.git
synced 2026-09-08 00:38:39 +09:00
Issue #3049 - Stabilize loongarch64 Ion patching and wasm loads
This commit is contained in:
parent
f796b3f7f1
commit
85c6fcc68e
3 changed files with 164 additions and 65 deletions
|
|
@ -22,20 +22,13 @@ void js::jit::PatchJump(CodeLocationJump& jump_, CodeLocationLabel label,
|
|||
ReprotectCode reprotect) {
|
||||
Instruction* inst = reinterpret_cast<Instruction*>(jump_.raw());
|
||||
|
||||
// jumpWithPatch() reserves four instructions:
|
||||
// beq zero, zero, 0
|
||||
// INVALID_OFFSET
|
||||
// nop
|
||||
// nop
|
||||
// Patch that block into the long-jump form used elsewhere in the backend:
|
||||
// load64 scratch, target
|
||||
// jirl zero, scratch, 0
|
||||
MaybeAutoWritableJitCode awjc(inst, 4 * sizeof(uint32_t), reprotect);
|
||||
Assembler::WriteLoad64Instructions(inst, ScratchRegister,
|
||||
uintptr_t(label.raw()));
|
||||
inst[3] = InstImm(op_jirl, BOffImm16(0), ScratchRegister, zero);
|
||||
// jumpWithPatch() emits a long-jump template up front so patching only
|
||||
// updates the embedded target pointer and never mutates live control-flow
|
||||
// opcodes in place.
|
||||
MaybeAutoWritableJitCode awjc(inst, 3 * sizeof(uint32_t), reprotect);
|
||||
Assembler::UpdateLoad64Value(inst, uintptr_t(label.raw()));
|
||||
|
||||
AutoFlushICache::flush(uintptr_t(inst), 4 * sizeof(uint32_t));
|
||||
AutoFlushICache::flush(uintptr_t(inst), 3 * sizeof(uint32_t));
|
||||
}
|
||||
|
||||
// Note this is used for inter-wasm calls and may pass arguments and results
|
||||
|
|
@ -2337,7 +2330,12 @@ void Assembler::bind(RepatchLabel* label) {
|
|||
if (label->used() && !oom()) {
|
||||
BufferOffset branch(label->offset());
|
||||
InstImm* inst = reinterpret_cast<InstImm*>(editSrc(branch));
|
||||
bind(inst, branch.getOffset(), dest.getOffset());
|
||||
if ((inst[0].extractBitField(31, 25)) ==
|
||||
((uint32_t)op_lu12i_w >> 25)) {
|
||||
addLongJump(branch, dest);
|
||||
} else {
|
||||
bind(inst, branch.getOffset(), dest.getOffset());
|
||||
}
|
||||
}
|
||||
label->bind(dest.getOffset());
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1547,6 +1547,145 @@ void MacroAssemblerLOONGARCH64::ma_store(Imm32 imm, const BaseIndex& dest,
|
|||
asMasm().ma_store(scratch, Address(scratch2, 0), size, extension);
|
||||
}
|
||||
|
||||
void MacroAssemblerLOONGARCH64::ma_load_unaligned(
|
||||
const wasm::MemoryAccessDesc& access, Register dest, const BaseIndex& src,
|
||||
Register temp, LoadStoreSize size, LoadStoreExtension extension) {
|
||||
MOZ_ASSERT(dest != temp);
|
||||
|
||||
asMasm().computeEffectiveAddress(src, temp);
|
||||
|
||||
BufferOffset load = as_ld_bu(dest, temp, 0);
|
||||
if (size != SizeByte) {
|
||||
ScratchRegisterScope scratch(asMasm());
|
||||
const size_t byteSize = size / 8;
|
||||
for (size_t i = 1; i < byteSize; i++) {
|
||||
as_ld_bu(scratch, temp, i);
|
||||
as_slli_d(scratch, scratch, 8 * i);
|
||||
as_or(dest, dest, scratch);
|
||||
}
|
||||
}
|
||||
|
||||
switch (size) {
|
||||
case SizeByte:
|
||||
if (extension == SignExtend) {
|
||||
as_ext_w_b(dest, dest);
|
||||
}
|
||||
break;
|
||||
case SizeHalfWord:
|
||||
if (extension == SignExtend) {
|
||||
as_ext_w_h(dest, dest);
|
||||
}
|
||||
break;
|
||||
case SizeWord:
|
||||
if (extension == SignExtend) {
|
||||
as_addi_w(dest, dest, 0);
|
||||
}
|
||||
break;
|
||||
case SizeDouble:
|
||||
break;
|
||||
default:
|
||||
MOZ_CRASH("Invalid argument for ma_load_unaligned");
|
||||
}
|
||||
|
||||
append(access, load.getOffset(), asMasm().framePushed());
|
||||
}
|
||||
|
||||
void MacroAssemblerLOONGARCH64::ma_store_unaligned(
|
||||
const wasm::MemoryAccessDesc& access, Register data, const BaseIndex& dest,
|
||||
Register temp, LoadStoreSize size, LoadStoreExtension extension) {
|
||||
(void)extension;
|
||||
|
||||
MOZ_ASSERT(data != temp);
|
||||
|
||||
asMasm().computeEffectiveAddress(dest, temp);
|
||||
|
||||
BufferOffset store = as_st_b(data, temp, 0);
|
||||
if (size != SizeByte) {
|
||||
ScratchRegisterScope scratch(asMasm());
|
||||
const size_t byteSize = size / 8;
|
||||
for (size_t i = 1; i < byteSize; i++) {
|
||||
as_srli_d(scratch, data, 8 * i);
|
||||
as_st_b(scratch, temp, i);
|
||||
}
|
||||
}
|
||||
|
||||
append(access, store.getOffset(), asMasm().framePushed());
|
||||
}
|
||||
|
||||
void MacroAssemblerLOONGARCH64::loadUnalignedDouble(
|
||||
const wasm::MemoryAccessDesc& access, const BaseIndex& src, Register temp,
|
||||
FloatRegister dest) {
|
||||
asMasm().computeEffectiveAddress(src, temp);
|
||||
|
||||
ScratchRegisterScope scratch(asMasm());
|
||||
SecondScratchRegisterScope scratch2(asMasm());
|
||||
|
||||
BufferOffset load = as_ld_bu(scratch, temp, 0);
|
||||
for (size_t i = 1; i < sizeof(double); i++) {
|
||||
as_ld_bu(scratch2, temp, i);
|
||||
as_slli_d(scratch2, scratch2, 8 * i);
|
||||
as_or(scratch, scratch, scratch2);
|
||||
}
|
||||
|
||||
append(access, load.getOffset(), asMasm().framePushed());
|
||||
moveToDouble(scratch, dest);
|
||||
}
|
||||
|
||||
void MacroAssemblerLOONGARCH64::loadUnalignedFloat32(
|
||||
const wasm::MemoryAccessDesc& access, const BaseIndex& src, Register temp,
|
||||
FloatRegister dest) {
|
||||
asMasm().computeEffectiveAddress(src, temp);
|
||||
|
||||
ScratchRegisterScope scratch(asMasm());
|
||||
SecondScratchRegisterScope scratch2(asMasm());
|
||||
|
||||
BufferOffset load = as_ld_bu(scratch, temp, 0);
|
||||
for (size_t i = 1; i < sizeof(float); i++) {
|
||||
as_ld_bu(scratch2, temp, i);
|
||||
as_slli_d(scratch2, scratch2, 8 * i);
|
||||
as_or(scratch, scratch, scratch2);
|
||||
}
|
||||
|
||||
append(access, load.getOffset(), asMasm().framePushed());
|
||||
moveToFloat32(scratch, dest);
|
||||
}
|
||||
|
||||
void MacroAssemblerLOONGARCH64::storeUnalignedDouble(
|
||||
const wasm::MemoryAccessDesc& access, FloatRegister src, Register temp,
|
||||
const BaseIndex& dest) {
|
||||
asMasm().computeEffectiveAddress(dest, temp);
|
||||
|
||||
ScratchRegisterScope scratch(asMasm());
|
||||
SecondScratchRegisterScope scratch2(asMasm());
|
||||
moveFromDouble(src, scratch);
|
||||
|
||||
BufferOffset store = as_st_b(scratch, temp, 0);
|
||||
for (size_t i = 1; i < sizeof(double); i++) {
|
||||
as_srli_d(scratch2, scratch, 8 * i);
|
||||
as_st_b(scratch2, temp, i);
|
||||
}
|
||||
|
||||
append(access, store.getOffset(), asMasm().framePushed());
|
||||
}
|
||||
|
||||
void MacroAssemblerLOONGARCH64::storeUnalignedFloat32(
|
||||
const wasm::MemoryAccessDesc& access, FloatRegister src, Register temp,
|
||||
const BaseIndex& dest) {
|
||||
asMasm().computeEffectiveAddress(dest, temp);
|
||||
|
||||
ScratchRegisterScope scratch(asMasm());
|
||||
SecondScratchRegisterScope scratch2(asMasm());
|
||||
moveFromFloat32(src, scratch);
|
||||
|
||||
BufferOffset store = as_st_b(scratch, temp, 0);
|
||||
for (size_t i = 1; i < sizeof(float); i++) {
|
||||
as_srli_d(scratch2, scratch, 8 * i);
|
||||
as_st_b(scratch2, temp, i);
|
||||
}
|
||||
|
||||
append(access, store.getOffset(), asMasm().framePushed());
|
||||
}
|
||||
|
||||
// Branches when done from within loongarch-specific code.
|
||||
// TODO(loongarch64) Optimize ma_b
|
||||
void MacroAssemblerLOONGARCH64::ma_b(Register lhs, Register rhs, Label* label,
|
||||
|
|
@ -2512,16 +2651,18 @@ CodeOffsetJump MacroAssemblerLOONGARCH64Compat::backedgeJump(
|
|||
|
||||
CodeOffsetJump MacroAssemblerLOONGARCH64Compat::jumpWithPatch(
|
||||
RepatchLabel* label, Label* documentation) {
|
||||
(void)documentation;
|
||||
MOZ_ASSERT(!label->used());
|
||||
|
||||
BufferOffset bo = nextOffset();
|
||||
label->use(bo.getOffset());
|
||||
|
||||
m_buffer.ensureSpace(4 * sizeof(uint32_t));
|
||||
writeInst(InstImm(op_beq, BOffImm16(0), zero, zero).encode());
|
||||
writeInst(LabelBase::INVALID_OFFSET);
|
||||
as_nop();
|
||||
as_nop();
|
||||
if (label->bound()) {
|
||||
addLongJump(bo, BufferOffset(label->offset()));
|
||||
}
|
||||
ma_liPatchable(ScratchRegister, ImmWord(LabelBase::INVALID_OFFSET));
|
||||
as_jirl(zero, ScratchRegister, BOffImm16(0));
|
||||
return CodeOffsetJump(bo.getOffset());
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -559,62 +559,22 @@ class MacroAssemblerLOONGARCH64 : public Assembler {
|
|||
}
|
||||
void ma_load_unaligned(const wasm::MemoryAccessDesc& access, Register dest,
|
||||
const BaseIndex& src, Register temp,
|
||||
LoadStoreSize size, LoadStoreExtension extension) {
|
||||
(void)access;
|
||||
(void)dest;
|
||||
(void)src;
|
||||
(void)temp;
|
||||
(void)size;
|
||||
(void)extension;
|
||||
MOZ_CRASH("wasm unaligned integer loads are not supported on loongarch64 yet");
|
||||
}
|
||||
LoadStoreSize size, LoadStoreExtension extension);
|
||||
void ma_store_unaligned(const wasm::MemoryAccessDesc& access, Register data,
|
||||
const BaseIndex& dest, Register temp,
|
||||
LoadStoreSize size, LoadStoreExtension extension) {
|
||||
(void)access;
|
||||
(void)data;
|
||||
(void)dest;
|
||||
(void)temp;
|
||||
(void)size;
|
||||
(void)extension;
|
||||
MOZ_CRASH("wasm unaligned integer stores are not supported on loongarch64 yet");
|
||||
}
|
||||
LoadStoreSize size, LoadStoreExtension extension);
|
||||
void loadUnalignedDouble(const wasm::MemoryAccessDesc& access,
|
||||
const BaseIndex& src, Register temp,
|
||||
FloatRegister dest) {
|
||||
(void)access;
|
||||
(void)src;
|
||||
(void)temp;
|
||||
(void)dest;
|
||||
MOZ_CRASH("wasm unaligned double loads are not supported on loongarch64 yet");
|
||||
}
|
||||
FloatRegister dest);
|
||||
void loadUnalignedFloat32(const wasm::MemoryAccessDesc& access,
|
||||
const BaseIndex& src, Register temp,
|
||||
FloatRegister dest) {
|
||||
(void)access;
|
||||
(void)src;
|
||||
(void)temp;
|
||||
(void)dest;
|
||||
MOZ_CRASH("wasm unaligned float loads are not supported on loongarch64 yet");
|
||||
}
|
||||
FloatRegister dest);
|
||||
void storeUnalignedDouble(const wasm::MemoryAccessDesc& access,
|
||||
FloatRegister src, Register temp,
|
||||
const BaseIndex& dest) {
|
||||
(void)access;
|
||||
(void)src;
|
||||
(void)temp;
|
||||
(void)dest;
|
||||
MOZ_CRASH("wasm unaligned double stores are not supported on loongarch64 yet");
|
||||
}
|
||||
const BaseIndex& dest);
|
||||
void storeUnalignedFloat32(const wasm::MemoryAccessDesc& access,
|
||||
FloatRegister src, Register temp,
|
||||
const BaseIndex& dest) {
|
||||
(void)access;
|
||||
(void)src;
|
||||
(void)temp;
|
||||
(void)dest;
|
||||
MOZ_CRASH("wasm unaligned float stores are not supported on loongarch64 yet");
|
||||
}
|
||||
const BaseIndex& dest);
|
||||
|
||||
void ma_cmp_set(Register dst, Register lhs, Register rhs, Condition c);
|
||||
void ma_cmp_set(Register dst, Register lhs, Imm32 imm, Condition c);
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue