YJIT: Merge x86_merge into x86_split (#7487)

This commit is contained in:
Takashi Kokubun 2023-03-09 11:58:40 -08:00 коммит произвёл GitHub
Родитель 1347d707ca
Коммит 487142928a
Не найден ключ, соответствующий данной подписи
Идентификатор ключа GPG: 4AEE18F83AFDEB23
1 изменённых файлов: 12 добавлений и 31 удалений

Просмотреть файл

@ -105,36 +105,6 @@ impl Assembler
// These are the callee-saved registers in the x86-64 SysV ABI
// RBX, RSP, RBP, and R12–R15
/// Merge IR instructions for the x86 platform. As of x86_split, all `out` operands
/// are Opnd::Out, but you sometimes want to use Opnd::Reg for example to shorten the
/// generated code, which is what this pass does.
fn x86_merge(mut self) -> Assembler {
let live_ranges: Vec<usize> = take(&mut self.live_ranges);
let mut asm = Assembler::new_with_label_names(take(&mut self.label_names));
let mut iterator = self.into_draining_iter();
while let Some((index, mut insn)) = iterator.next_unmapped() {
match (&insn, iterator.peek()) {
// Merge `lea` and `mov` into a single `lea` when possible
(Insn::Lea { opnd, out }, Some(Insn::Mov { dest: Opnd::Reg(reg), src }))
if matches!(out, Opnd::InsnOut { .. }) && out == src && live_ranges[index] == index + 1 => {
asm.push_insn(Insn::Lea { opnd: *opnd, out: Opnd::Reg(*reg) });
iterator.map_insn_index(&mut asm);
iterator.next_unmapped(); // Pop merged Insn::Mov
}
_ => {
let mut opnd_iter = insn.opnd_iter_mut();
while let Some(opnd) = opnd_iter.next() {
*opnd = iterator.map_opnd(*opnd);
}
asm.push_insn(insn);
}
}
iterator.map_insn_index(&mut asm);
}
asm
}
/// Split IR instructions for the x86 platform
fn x86_split(mut self) -> Assembler
{
@ -363,6 +333,18 @@ impl Assembler
// just performs the call.
asm.ccall(*fptr, vec![]);
},
Insn::Lea { .. } => {
// Merge `lea` and `mov` into a single `lea` when possible
match (&insn, iterator.peek()) {
(Insn::Lea { opnd, out }, Some(Insn::Mov { dest: Opnd::Reg(reg), src }))
if matches!(out, Opnd::InsnOut { .. }) && out == src && live_ranges[index] == index + 1 => {
asm.push_insn(Insn::Lea { opnd: *opnd, out: Opnd::Reg(*reg) });
iterator.map_insn_index(&mut asm);
iterator.next_unmapped(); // Pop merged Insn::Mov
}
_ => asm.push_insn(insn),
}
},
_ => {
if insn.out_opnd().is_some() {
let out_num_bits = Opnd::match_num_bits_iter(insn.opnd_iter());
@ -749,7 +731,6 @@ impl Assembler
{
let asm = self.lower_stack();
let asm = asm.x86_split();
let asm = asm.x86_merge();
let mut asm = asm.alloc_regs(regs);
// Create label instances in the code block