pub struct BinaryReader<'a> { /* private fields */ }
Expand description
A binary reader of the WebAssembly structures and types.
Implementations§
source§impl<'a> BinaryReader<'a>
impl<'a> BinaryReader<'a>
sourcepub fn new(
data: &[u8],
original_offset: usize,
features: WasmFeatures,
) -> BinaryReader<'_>
pub fn new( data: &[u8], original_offset: usize, features: WasmFeatures, ) -> BinaryReader<'_>
Creates a new binary reader which will parse the data
provided.
The original_offset
provided is used for byte offsets in errors that
are generated. That offset is added to the current position in data
.
This can be helpful when data
is just a window of a view into a larger
wasm binary perhaps not even entirely stored locally.
The features
argument provided controls which WebAssembly features are
active when parsing this data. Wasm features typically don’t affect
parsing too too much and are generally more applicable during
validation, but features and proposals will often reinterpret
previously-invalid constructs as now-valid things meaning something
slightly different. This means that invalid bytes before a feature may
now be interpreted differently after a feature is implemented. This
means that the set of activated features can affect what errors are
generated and when they are generated.
In general it’s safe to pass WasmFeatures::all()
here. There’s no
downside to enabling all features while parsing and only enabling a
subset of features during validation.
Note that the activated set of features does not guarantee that
BinaryReader
will return an error for disabled features. For example
if SIMD is disabled then SIMD instructions will still be parsed via
BinaryReader::visit_operator
. Validation must still be performed to
provide a strict guarantee that if a feature is disabled that a binary
doesn’t leverage the feature. The activated set of features here instead
only affects locations where preexisting bytes are reinterpreted in
different ways with future proposals, such as the memarg
moving from a
32-bit offset to a 64-bit offset with the memory64
proposal.
sourcepub fn original_position(&self) -> usize
pub fn original_position(&self) -> usize
Gets the original position of the binary reader.
sourcepub fn features(&self) -> WasmFeatures
pub fn features(&self) -> WasmFeatures
Returns the currently active set of wasm features that this reader is using while parsing.
For more information see BinaryReader::new
.
sourcepub fn set_features(&mut self, features: WasmFeatures)
pub fn set_features(&mut self, features: WasmFeatures)
Sets the wasm features active while parsing to the features
specified.
For more information see BinaryReader::new
.
sourcepub fn range(&self) -> Range<usize>
pub fn range(&self) -> Range<usize>
Returns a range from the starting offset to the end of the buffer.
sourcepub fn read<T>(&mut self) -> Result<T, BinaryReaderError>where
T: FromReader<'a>,
pub fn read<T>(&mut self) -> Result<T, BinaryReaderError>where
T: FromReader<'a>,
Reads a value of type T
from this binary reader, advancing the
internal position in this reader forward as data is read.
sourcepub fn read_size(
&mut self,
limit: usize,
desc: &str,
) -> Result<usize, BinaryReaderError>
pub fn read_size( &mut self, limit: usize, desc: &str, ) -> Result<usize, BinaryReaderError>
Reads a variable-length 32-bit size from the byte stream while checking against a limit.
sourcepub fn read_iter<'me, T>(
&'me mut self,
limit: usize,
desc: &str,
) -> Result<BinaryReaderIter<'a, 'me, T>, BinaryReaderError>where
T: FromReader<'a>,
pub fn read_iter<'me, T>(
&'me mut self,
limit: usize,
desc: &str,
) -> Result<BinaryReaderIter<'a, 'me, T>, BinaryReaderError>where
T: FromReader<'a>,
Reads a variable-length 32-bit size from the byte stream while checking against a limit.
Then reads that many values of type T
and returns them as an iterator.
Note that regardless of how many items are read from the returned iterator the items will still be parsed from this reader.
sourcepub fn current_position(&self) -> usize
pub fn current_position(&self) -> usize
Returns the BinaryReader
’s current position.
sourcepub fn bytes_remaining(&self) -> usize
pub fn bytes_remaining(&self) -> usize
Returns the number of bytes remaining in the BinaryReader
.
sourcepub fn read_bytes(&mut self, size: usize) -> Result<&'a [u8], BinaryReaderError>
pub fn read_bytes(&mut self, size: usize) -> Result<&'a [u8], BinaryReaderError>
Advances the BinaryReader
size
bytes, and returns a slice from the
current position of size
length.
§Errors
If size
exceeds the remaining length in BinaryReader
.
sourcepub fn read_reader(
&mut self,
err: &str,
) -> Result<BinaryReader<'a>, BinaryReaderError>
pub fn read_reader( &mut self, err: &str, ) -> Result<BinaryReader<'a>, BinaryReaderError>
Reads a length-prefixed list of bytes from this reader and returns a
new BinaryReader
to read that list of bytes.
Advances the position of this reader by the number of bytes read.
sourcepub fn read_u32(&mut self) -> Result<u32, BinaryReaderError>
pub fn read_u32(&mut self) -> Result<u32, BinaryReaderError>
Advances the BinaryReader
four bytes and returns a u32
.
§Errors
If BinaryReader
has less than four bytes remaining.
sourcepub fn read_u64(&mut self) -> Result<u64, BinaryReaderError>
pub fn read_u64(&mut self) -> Result<u64, BinaryReaderError>
Advances the BinaryReader
eight bytes and returns a u64
.
§Errors
If BinaryReader
has less than eight bytes remaining.
sourcepub fn read_u8(&mut self) -> Result<u8, BinaryReaderError>
pub fn read_u8(&mut self) -> Result<u8, BinaryReaderError>
sourcepub fn read_var_u32(&mut self) -> Result<u32, BinaryReaderError>
pub fn read_var_u32(&mut self) -> Result<u32, BinaryReaderError>
Advances the BinaryReader
up to four bytes to parse a variable
length integer as a u32
.
§Errors
If BinaryReader
has less than one or up to four bytes remaining, or
the integer is larger than 32 bits.
sourcepub fn read_var_u64(&mut self) -> Result<u64, BinaryReaderError>
pub fn read_var_u64(&mut self) -> Result<u64, BinaryReaderError>
Advances the BinaryReader
up to four bytes to parse a variable
length integer as a u64
.
§Errors
If BinaryReader
has less than one or up to eight bytes remaining, or
the integer is larger than 64 bits.
sourcepub fn skip(
&mut self,
f: impl FnOnce(&mut BinaryReader<'a>) -> Result<(), BinaryReaderError>,
) -> Result<BinaryReader<'a>, BinaryReaderError>
pub fn skip( &mut self, f: impl FnOnce(&mut BinaryReader<'a>) -> Result<(), BinaryReaderError>, ) -> Result<BinaryReader<'a>, BinaryReaderError>
Executes f
to skip some data in this binary reader and then returns a
reader which will read the skipped data.
sourcepub fn skip_string(&mut self) -> Result<(), BinaryReaderError>
pub fn skip_string(&mut self) -> Result<(), BinaryReaderError>
Advances the BinaryReader
past a WebAssembly string. This method does
not perform any utf-8 validation.
§Errors
If BinaryReader
has less than four bytes, the string’s length exceeds
the remaining bytes, or the string length
exceeds limits::MAX_WASM_STRING_SIZE
.
sourcepub fn read_var_i32(&mut self) -> Result<i32, BinaryReaderError>
pub fn read_var_i32(&mut self) -> Result<i32, BinaryReaderError>
Advances the BinaryReader
up to four bytes to parse a variable
length integer as a i32
.
§Errors
If BinaryReader
has less than one or up to four bytes remaining, or
the integer is larger than 32 bits.
sourcepub fn read_var_s33(&mut self) -> Result<i64, BinaryReaderError>
pub fn read_var_s33(&mut self) -> Result<i64, BinaryReaderError>
Advances the BinaryReader
up to four bytes to parse a variable
length integer as a signed 33 bit integer, returned as a i64
.
§Errors
If BinaryReader
has less than one or up to five bytes remaining, or
the integer is larger than 33 bits.
sourcepub fn read_var_i64(&mut self) -> Result<i64, BinaryReaderError>
pub fn read_var_i64(&mut self) -> Result<i64, BinaryReaderError>
Advances the BinaryReader
up to eight bytes to parse a variable
length integer as a 64 bit integer, returned as a i64
.
§Errors
If BinaryReader
has less than one or up to eight bytes remaining, or
the integer is larger than 64 bits.
sourcepub fn read_f32(&mut self) -> Result<Ieee32, BinaryReaderError>
pub fn read_f32(&mut self) -> Result<Ieee32, BinaryReaderError>
Advances the BinaryReader
up to four bytes to parse a variable
length integer as a 32 bit floating point integer, returned as Ieee32
.
§Errors
If BinaryReader
has less than one or up to four bytes remaining, or
the integer is larger than 32 bits.
sourcepub fn read_f64(&mut self) -> Result<Ieee64, BinaryReaderError>
pub fn read_f64(&mut self) -> Result<Ieee64, BinaryReaderError>
Advances the BinaryReader
up to four bytes to parse a variable
length integer as a 32 bit floating point integer, returned as Ieee32
.
§Errors
If BinaryReader
has less than one or up to four bytes remaining, or
the integer is larger than 32 bits.
sourcepub fn read_string(&mut self) -> Result<&'a str, BinaryReaderError>
pub fn read_string(&mut self) -> Result<&'a str, BinaryReaderError>
Reads a WebAssembly string from the module.
§Errors
If BinaryReader
has less than up to four bytes remaining, the string’s
length exceeds the remaining bytes, the string’s length exceeds
limits::MAX_WASM_STRING_SIZE
, or the string contains invalid utf-8.
sourcepub fn visit_operator<T>(
&mut self,
visitor: &mut T,
) -> Result<<T as VisitOperator<'a>>::Output, BinaryReaderError>where
T: VisitOperator<'a>,
pub fn visit_operator<T>(
&mut self,
visitor: &mut T,
) -> Result<<T as VisitOperator<'a>>::Output, BinaryReaderError>where
T: VisitOperator<'a>,
Visit the next available operator with the specified VisitOperator
instance.
Note that this does not implicitly propagate any additional information such as instruction offsets. In order to do so, consider storing such data within the visitor before visiting.
§Errors
If BinaryReader
has less bytes remaining than required to parse the Operator
.
§Examples
Store an offset for use in diagnostics or any other purposes:
pub fn dump(mut reader: BinaryReader) -> Result<()> {
let mut visitor = Dumper { offset: 0 };
while !reader.eof() {
visitor.offset = reader.original_position();
reader.visit_operator(&mut visitor)?;
}
Ok(())
}
struct Dumper {
offset: usize
}
macro_rules! define_visit_operator {
($(@$proposal:ident $op:ident $({ $($arg:ident: $argty:ty),* })? => $visit:ident)*) => {
$(
fn $visit(&mut self $($(,$arg: $argty)*)?) -> Self::Output {
println!("{}: {}", self.offset, stringify!($visit));
}
)*
}
}
impl<'a> VisitOperator<'a> for Dumper {
type Output = ();
for_each_operator!(define_visit_operator);
}
sourcepub fn read_operator(&mut self) -> Result<Operator<'a>, BinaryReaderError>
pub fn read_operator(&mut self) -> Result<Operator<'a>, BinaryReaderError>
Reads the next available Operator
.
§Errors
If BinaryReader
has less bytes remaining than required to parse
the Operator
.
sourcepub fn is_end_then_eof(&self) -> bool
pub fn is_end_then_eof(&self) -> bool
Returns whether there is an end
opcode followed by eof remaining in
this reader.
Trait Implementations§
source§impl<'a> Clone for BinaryReader<'a>
impl<'a> Clone for BinaryReader<'a>
source§fn clone(&self) -> BinaryReader<'a>
fn clone(&self) -> BinaryReader<'a>
1.0.0 · source§fn clone_from(&mut self, source: &Self)
fn clone_from(&mut self, source: &Self)
source
. Read moresource§impl<'a> Debug for BinaryReader<'a>
impl<'a> Debug for BinaryReader<'a>
source§impl<'a> Hash for BinaryReader<'a>
impl<'a> Hash for BinaryReader<'a>
Auto Trait Implementations§
impl<'a> Freeze for BinaryReader<'a>
impl<'a> RefUnwindSafe for BinaryReader<'a>
impl<'a> Send for BinaryReader<'a>
impl<'a> Sync for BinaryReader<'a>
impl<'a> Unpin for BinaryReader<'a>
impl<'a> UnwindSafe for BinaryReader<'a>
Blanket Implementations§
source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
source§impl<T> CloneToUninit for Twhere
T: Clone,
impl<T> CloneToUninit for Twhere
T: Clone,
source§unsafe fn clone_to_uninit(&self, dst: *mut T)
unsafe fn clone_to_uninit(&self, dst: *mut T)
clone_to_uninit
)source§impl<T> IntoEither for T
impl<T> IntoEither for T
source§fn into_either(self, into_left: bool) -> Either<Self, Self>
fn into_either(self, into_left: bool) -> Either<Self, Self>
self
into a Left
variant of Either<Self, Self>
if into_left
is true
.
Converts self
into a Right
variant of Either<Self, Self>
otherwise. Read moresource§fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
self
into a Left
variant of Either<Self, Self>
if into_left(&self)
returns true
.
Converts self
into a Right
variant of Either<Self, Self>
otherwise. Read more