Use capstone to validate precise-output tests (#5780)

Use the capstone library to disassemble precise-output tests, in addition to pretty-printing their vcode.
This commit is contained in:
Trevor Elliott
2023-02-15 16:35:10 -08:00
committed by GitHub
parent eabd43a178
commit f04decc4a1
277 changed files with 39340 additions and 98 deletions

View File

@@ -90,7 +90,7 @@ impl TargetIsa for AArch64Backend {
Ok(CompiledCodeStencil {
buffer,
frame_size,
disasm: emit_result.disasm,
vcode: emit_result.disasm,
value_labels_ranges,
sized_stackslot_offsets,
dynamic_stackslot_offsets,
@@ -195,6 +195,22 @@ impl TargetIsa for AArch64Backend {
// 4-byte alignment.
32
}
#[cfg(feature = "disas")]
fn to_capstone(&self) -> Result<capstone::Capstone, capstone::Error> {
use capstone::prelude::*;
let mut cs = Capstone::new()
.arm64()
.mode(arch::arm64::ArchMode::Arm)
.build()?;
// AArch64 uses inline constants rather than a separate constant pool right now.
// Without this option, Capstone will stop disassembling as soon as it sees
// an inline constant that is not also a valid instruction. With this option,
// Capstone will print a `.byte` directive with the bytes of the inline constant
// and continue to the next instruction.
cs.set_skipdata(true)?;
Ok(cs)
}
}
impl fmt::Display for AArch64Backend {

View File

@@ -307,6 +307,12 @@ pub trait TargetIsa: fmt::Display + Send + Sync {
{
Arc::new(self)
}
/// Generate a `Capstone` context for disassembling bytecode for this architecture.
#[cfg(feature = "disas")]
fn to_capstone(&self) -> Result<capstone::Capstone, capstone::Error> {
Err(capstone::Error::UnsupportedArch)
}
}
/// Methods implemented for free for target ISA!

View File

@@ -91,7 +91,7 @@ impl TargetIsa for Riscv64Backend {
Ok(CompiledCodeStencil {
buffer,
frame_size,
disasm: emit_result.disasm,
vcode: emit_result.disasm,
value_labels_ranges,
sized_stackslot_offsets,
dynamic_stackslot_offsets,
@@ -169,6 +169,20 @@ impl TargetIsa for Riscv64Backend {
fn function_alignment(&self) -> u32 {
4
}
#[cfg(feature = "disas")]
fn to_capstone(&self) -> Result<capstone::Capstone, capstone::Error> {
use capstone::prelude::*;
let mut cs = Capstone::new()
.riscv()
.mode(arch::riscv::ArchMode::RiscV64)
.build()?;
// Similar to AArch64, RISC-V uses inline constants rather than a separate
// constant pool. We want to skip dissasembly over inline constants instead
// of stopping on invalid bytes.
cs.set_skipdata(true)?;
Ok(cs)
}
}
impl fmt::Display for Riscv64Backend {

View File

@@ -87,7 +87,7 @@ impl TargetIsa for S390xBackend {
Ok(CompiledCodeStencil {
buffer,
frame_size,
disasm: emit_result.disasm,
vcode: emit_result.disasm,
value_labels_ranges,
sized_stackslot_offsets,
dynamic_stackslot_offsets,
@@ -170,6 +170,19 @@ impl TargetIsa for S390xBackend {
fn function_alignment(&self) -> u32 {
4
}
#[cfg(feature = "disas")]
fn to_capstone(&self) -> Result<capstone::Capstone, capstone::Error> {
use capstone::prelude::*;
let mut cs = Capstone::new()
.sysz()
.mode(arch::sysz::ArchMode::Default)
.build()?;
cs.set_skipdata(true)?;
Ok(cs)
}
}
impl fmt::Display for S390xBackend {

View File

@@ -84,7 +84,7 @@ impl TargetIsa for X64Backend {
Ok(CompiledCodeStencil {
buffer,
frame_size,
disasm: emit_result.disasm,
vcode: emit_result.disasm,
value_labels_ranges,
sized_stackslot_offsets,
dynamic_stackslot_offsets,
@@ -171,6 +171,16 @@ impl TargetIsa for X64Backend {
fn function_alignment(&self) -> u32 {
16
}
#[cfg(feature = "disas")]
fn to_capstone(&self) -> Result<capstone::Capstone, capstone::Error> {
use capstone::prelude::*;
Capstone::new()
.x86()
.mode(arch::x86::ArchMode::Mode64)
.syntax(arch::x86::ArchSyntax::Att)
.build()
}
}
impl fmt::Display for X64Backend {