x86 decoders implemented as part of the yaxpeax project.
yaxpeax-x86
implements traits provided by yaxpeax-arch
, which are likely how you want to use this library from Rust. included in the ffi/
directory is a repackaging of yaxpeax-x86
suitable for use by non-Rust callers, such as C or C++.
#[no_std]
#[no_std]
the decoders provided by yaxpeax-x86
are designed to be usable in a no_std
setting, and does so by default. to build yaxpeax_x86
decoders in no_std
you'll want to set default-features = false
as with many other no_std
Rust crates. serde currently (though it doesn't seem necessarily?) relies on std
, as well as the colors
feature to render instructions with default (eg terminal-friendly) syntax highlighting.
yaxpeax-x86
decoders provide the option to specify what instruction set extensions are eligible when decoding, to support decoding x86 instructions as understood by a particular microarchitecture. the default yaxpeax_x86::InstDecoder
takes an optimistsic approach to decoding and assumes all feature sets are available, as well as accepting both intel-specific and amd-specific quirks around undefined encodings.
by the in-repo benchmark, yaxpeax_x86::long_mode
decodes x86_64
instructions at anywhere between 60 million instructions per second to just shy of 100 million instructions per second, depending on hardware and distribution of instructions being decoded. when hooked up to disasm-bench
, yaxpeax_x86::long_mode
has shown roughly 150mb/s decode throughput.
yaxpeax_x86::long_mode
is expected to be around 20kb of code and data. currently a stripped static build of ffi/
takes a bit more space - around 130kb. instruction rendering is currently non-optional, and is a significant amount of .text
size. data tables are larger than anticipated, and it's currently an open question if they can be reduced down, or the size target of yaxpeax_x86::long_mode
should be raised.
this, however, does not by any means make this library the smallest x86_64
decoder; zydis
handily beats yaxpeax-x86
out, taking only 10kb in an -O3 build for benchmarking.
the canonical copy of yaxpeax-x86
is at https://git.iximeow.net/yaxpeax-x86/.
yaxpeax-x86
is also mirrored on GitHub at https://www.github.com/iximeow/yaxpeax-x86.
yaxpeax-x86
likely has many corners where it does not reject instructions it should. particularly likely is accepting a register operand where the corresponding instruction specifically only allows memory encodings - lea
is a good example of this. user beware!yaxpeax-x86
will, but does not yet, have decoders for protected-mode and real-mode x86
. currently, yaxpeax-x86
assumes that it is decoding long mode x86_64
instructions. it is strongly recommended to use <yaxpeax_x86::x86_64 as Arch>::Instruction
and similar type aliases, rather than using struct and operand types directly. user beware!yaxpeax_x86
is instances of unsafe { unreachable_unchecked(); }
. while these are, currently, all unreachable, this code should default to a fail-safe assertion fail, with unreachable_unchecked
being an opt-in feature. user beware!a changelog across crate versions is maintained in the CHANGELOG
file located in the repo, as well as online.
iced
looks to be another very good x86_64
decoder, with an in-progress translation to rust
disas-bench
, a handy benchmark of several x86_64
decoders, easily extended to compare with yaxpeax-x86
as well.