Skip to content

Commit

Permalink
rt: Start using constants at end of instruction stream
Browse files Browse the repository at this point in the history
  • Loading branch information
dinfuehr committed Jan 1, 2025
1 parent 5819b19 commit 94903da
Show file tree
Hide file tree
Showing 3 changed files with 105 additions and 15 deletions.
69 changes: 69 additions & 0 deletions dora-asm/src/x64.rs
Original file line number Diff line number Diff line change
Expand Up @@ -769,6 +769,19 @@ impl AssemblerX64 {
}
}

pub fn movq_rl(&mut self, dest: Register, label: Label) {
self.emit_rex(true, dest.needs_rex(), false, false);
self.emit_u8(0x8B);
self.emit_modrm(0b00, dest.low_bits(), 0b101);

self.unresolved_jumps.push(ForwardJump {
offset: self.position().try_into().unwrap(),
label,
distance: JumpDistance::Far,
});
self.emit_u32(0);
}

pub fn movq_rr(&mut self, dest: Register, src: Register) {
self.emit_rex64_modrm(src, dest);
self.emit_u8(0x89);
Expand Down Expand Up @@ -1688,6 +1701,29 @@ impl AssemblerX64 {
self.emit_address(dest.low_bits(), src);
}

pub fn vmovsd_rl(&mut self, dest: XmmRegister, label: Label) {
debug_assert!(self.has_avx2);
self.emit_vex(
dest.needs_rex(),
false,
false,
VEX_MMMMM_0F,
VEX_W0,
VEX_VVVV_UNUSED,
VEX_L_SCALAR_128,
VEX_PP_F2,
);
self.emit_u8(0x10);
self.emit_modrm(0b00, dest.low_bits(), 0b101);

self.unresolved_jumps.push(ForwardJump {
offset: self.position().try_into().unwrap(),
label,
distance: JumpDistance::Far,
});
self.emit_u32(0);
}

pub fn vmovsd_rr(&mut self, dest: XmmRegister, lhs: XmmRegister, rhs: XmmRegister) {
debug_assert!(self.has_avx2);
self.emit_vex(
Expand Down Expand Up @@ -1736,6 +1772,29 @@ impl AssemblerX64 {
self.emit_address(dest.low_bits(), src);
}

pub fn vmovss_rl(&mut self, dest: XmmRegister, label: Label) {
debug_assert!(self.has_avx2);
self.emit_vex(
dest.needs_rex(),
false,
false,
VEX_MMMMM_0F,
VEX_W0,
VEX_VVVV_UNUSED,
VEX_L_SCALAR_128,
VEX_PP_F3,
);
self.emit_u8(0x10);
self.emit_modrm(0b00, dest.low_bits(), 0b101);

self.unresolved_jumps.push(ForwardJump {
offset: self.position().try_into().unwrap(),
label,
distance: JumpDistance::Far,
});
self.emit_u32(0);
}

pub fn vmovss_rr(&mut self, dest: XmmRegister, lhs: XmmRegister, rhs: XmmRegister) {
debug_assert!(self.has_avx2);
self.emit_vex(
Expand Down Expand Up @@ -4031,4 +4090,14 @@ mod tests {
fn test_vmovapd_rr() {
assert_emit!(0xc5, 0xf9, 0x28, 0xc1; vmovapd_rr(XMM0, XMM1); avx2);
}

#[test]
fn test_movq_rl() {
let mut buf = AssemblerX64::new(false);
let lbl = buf.create_label();
buf.movq_rl(RAX, lbl);
buf.bind_label(lbl);

assert_asm_bytes(vec![0x48, 0x8b, 0x05, 0, 0, 0, 0], buf.finalize(1).code());
}
}
31 changes: 28 additions & 3 deletions dora-runtime/src/masm.rs
Original file line number Diff line number Diff line change
Expand Up @@ -11,9 +11,9 @@ use crate::mem;
use crate::mirror::Header;
use crate::mode::MachineMode;
use crate::vm::{
CodeDescriptor, CommentTable, ConstPool, GcPoint, GcPointTable, InlinedLocation,
LazyCompilationData, LazyCompilationSite, LocationTable, RelocationKind, RelocationTable, Trap,
CODE_ALIGNMENT,
CodeDescriptor, CommentTable, ConstPool, ConstPoolValue, GcPoint, GcPointTable,
InlinedLocation, LazyCompilationData, LazyCompilationSite, LocationTable, RelocationKind,
RelocationTable, Trap, CODE_ALIGNMENT,
};
pub use dora_asm::Label;
use dora_bytecode::Location;
Expand Down Expand Up @@ -96,6 +96,7 @@ pub struct MacroAssembler {
lazy_compilation: LazyCompilationData,
constpool: ConstPool,
new_constpool: NewConstPool,
epilog_constants: Vec<(Label, ConstPoolValue)>,
gcpoints: GcPointTable,
comments: CommentTable,
positions: LocationTable,
Expand All @@ -111,6 +112,7 @@ impl MacroAssembler {
lazy_compilation: LazyCompilationData::new(),
constpool: ConstPool::new(),
new_constpool: NewConstPool::new(),
epilog_constants: Vec::new(),
gcpoints: GcPointTable::new(),
comments: CommentTable::new(),
positions: LocationTable::new(),
Expand All @@ -121,11 +123,13 @@ impl MacroAssembler {

pub fn data(mut self) -> Vec<u8> {
self.emit_bailouts();
self.emit_epilog_constants();
self.asm.finalize(1).code()
}

pub fn code(mut self) -> CodeDescriptor {
self.emit_bailouts();
self.emit_epilog_constants();

// Align data such that code start is properly aligned.
let cp_size = self.constpool.align(CODE_ALIGNMENT as i32);
Expand Down Expand Up @@ -178,6 +182,27 @@ impl MacroAssembler {
}
}

fn emit_epilog_constants(&mut self) {
for (label, value) in &self.epilog_constants {
self.asm.bind_label(*label);
match value {
ConstPoolValue::Ptr(value) => {
self.asm.emit_u64(value.to_usize() as u64);
}

ConstPoolValue::Float32(value) => {
self.asm.emit_u32(unsafe { std::mem::transmute(*value) });
}

ConstPoolValue::Float64(value) => {
self.asm.emit_u64(unsafe { std::mem::transmute(*value) });
}

_ => unreachable!(),
}
}
}

pub fn add_const_addr(&mut self, ptr: Address) -> i32 {
let result = self.constpool.add_addr(ptr);
assert_eq!(result, self.new_constpool.add_addr(ptr) as i32);
Expand Down
20 changes: 8 additions & 12 deletions dora-runtime/src/masm/x64.rs
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ use crate::mirror::{offset_of_array_data, offset_of_array_length, Header, REMEMB
use crate::mode::MachineMode;
use crate::shape::Shape;
use crate::threads::ThreadLocalData;
use crate::vm::{get_vm, LazyCompilationSite, Trap};
use crate::vm::{get_vm, ConstPoolValue, LazyCompilationSite, Trap};
pub use dora_asm::x64::AssemblerX64 as Assembler;
use dora_asm::x64::Register as AsmRegister;
use dora_asm::x64::{Address as AsmAddress, Condition, Immediate, ScaleFactor, XmmRegister};
Expand Down Expand Up @@ -1273,29 +1273,25 @@ impl MacroAssembler {
}

if has_avx2() {
let const_offset = match mode {
MachineMode::Float32 => self.add_const_f32(imm as f32),
MachineMode::Float64 => self.add_const_f64(imm),
let const_value = match mode {
MachineMode::Float32 => ConstPoolValue::Float32(imm as f32),
MachineMode::Float64 => ConstPoolValue::Float64(imm),
_ => unreachable!(),
};
let label = self.asm.create_label();
self.epilog_constants.push((label, const_value));

match mode {
MachineMode::Float32 => {
self.asm.vmovss_ra(dest.into(), AsmAddress::rip(0));
self.asm.vmovss_rl(dest.into(), label);
}

MachineMode::Float64 => {
self.asm.vmovsd_ra(dest.into(), AsmAddress::rip(0));
self.asm.vmovsd_rl(dest.into(), label);
}

_ => unreachable!(),
}

let inst_end = self.pos() as i32;
let disp = -(const_offset + inst_end);
self.asm.set_position(self.pos() - 4);
self.asm.emit_u32(disp as u32);
self.asm.set_position_end();
} else {
let pos = self.pos() as i32;
let inst_size = 8 + if dest.msb() != 0 { 1 } else { 0 };
Expand Down

0 comments on commit 94903da

Please sign in to comment.