Add func_addr encodings for Intel.

This commit is contained in:
Jakob Stoklund Olesen
2017-09-19 16:33:38 -07:00
parent d92686d1cd
commit fb827a2d4b
5 changed files with 52 additions and 7 deletions

View File

@@ -336,10 +336,15 @@ ebb0:
; asm: call foo
call fn0() ; bin: e8 PCRel4(fn0) 00000000
; asm: movl $-1, %ecx
[-,%rcx] v400 = func_addr.i32 fn0 ; bin: b9 Abs4(fn0) ffffffff
; asm: movl $-1, %esi
[-,%rsi] v401 = func_addr.i32 fn0 ; bin: be Abs4(fn0) ffffffff
; asm: call *%ecx
call_indirect sig0, v1() ; bin: ff d1
call_indirect sig0, v400() ; bin: ff d1
; asm: call *%esi
call_indirect sig0, v2() ; bin: ff d6
call_indirect sig0, v401() ; bin: ff d6
; asm: testl %ecx, %ecx
; asm: je ebb1

View File

@@ -421,12 +421,19 @@ ebb0:
; asm: call foo
call fn0() ; bin: e8 PCRel4(fn0) 00000000
; asm: movabsq $-1, %rcx
[-,%rcx] v400 = func_addr.i64 fn0 ; bin: 48 b9 Abs8(fn0) ffffffffffffffff
; asm: movabsq $-1, %rsi
[-,%rsi] v401 = func_addr.i64 fn0 ; bin: 48 be Abs8(fn0) ffffffffffffffff
; asm: movabsq $-1, %r10
[-,%r10] v402 = func_addr.i64 fn0 ; bin: 49 ba Abs8(fn0) ffffffffffffffff
; asm: call *%rcx
call_indirect sig0, v1() ; bin: 40 ff d1
call_indirect sig0, v400() ; bin: 40 ff d1
; asm: call *%rsi
call_indirect sig0, v2() ; bin: 40 ff d6
call_indirect sig0, v401() ; bin: 40 ff d6
; asm: call *%r10
call_indirect sig0, v3() ; bin: 41 ff d2
call_indirect sig0, v402() ; bin: 41 ff d2
; asm: testq %rcx, %rcx
; asm: je ebb1

View File

@@ -243,6 +243,13 @@ enc_flt(base.store.f64.any, r.fst, 0x66, 0x0f, 0xd6)
enc_flt(base.store.f64.any, r.fstDisp8, 0x66, 0x0f, 0xd6)
enc_flt(base.store.f64.any, r.fstDisp32, 0x66, 0x0f, 0xd6)
#
# Function addresses.
#
I32.enc(base.func_addr.i32, *r.fnaddr4(0xb8))
I64.enc(base.func_addr.i64, *r.fnaddr8.rex(0xb8, w=1))
#
# Call/return
#

View File

@@ -7,7 +7,7 @@ from cdsl.predicates import IsSignedInt, IsEqual
from base.formats import Unary, UnaryImm, Binary, BinaryImm, MultiAry
from base.formats import Nullary, Call, IndirectCall, Store, Load
from base.formats import IntCompare
from base.formats import RegMove, Ternary, Jump, Branch
from base.formats import RegMove, Ternary, Jump, Branch, FuncAddr
from .registers import GPR, ABCD, FPR
try:
@@ -351,6 +351,26 @@ puiq = TailRecipe(
sink.put8(imm as u64);
''')
# XX+rd id with Abs4 function relocation.
fnaddr4 = TailRecipe(
'fnaddr4', FuncAddr, size=4, ins=(), outs=GPR,
emit='''
PUT_OP(bits | (out_reg0 & 7), rex1(out_reg0), sink);
sink.reloc_func(RelocKind::Abs4.into(), func_ref);
// Write the immediate as `!0` for the benefit of BaldrMonkey.
sink.put4(!0);
''')
# XX+rd iq with Abs8 function relocation.
fnaddr8 = TailRecipe(
'fnaddr8', FuncAddr, size=8, ins=(), outs=GPR,
emit='''
PUT_OP(bits | (out_reg0 & 7), rex1(out_reg0), sink);
sink.reloc_func(RelocKind::Abs8.into(), func_ref);
// Write the immediate as `!0` for the benefit of BaldrMonkey.
sink.put8(!0);
''')
#
# Store recipes.
#

View File

@@ -11,9 +11,15 @@ include!(concat!(env!("OUT_DIR"), "/binemit-intel.rs"));
pub enum RelocKind {
/// A 4-byte relative function reference. Based from relocation + 4 bytes.
PCRel4,
/// A 4-byte absolute function reference.
Abs4,
/// An 8-byte absolute function reference.
Abs8,
}
pub static RELOC_NAMES: [&'static str; 1] = ["PCRel4"];
pub static RELOC_NAMES: [&'static str; 3] = ["PCRel4", "Abs4", "Abs8"];
impl Into<Reloc> for RelocKind {
fn into(self) -> Reloc {