diff options
| author | Fabian Freyer <fabian.freyer@physik.tu-berlin.de> | 2022-02-10 23:09:38 +0100 |
|---|---|---|
| committer | Kyle Martin <krm504@nyu.edu> | 2022-02-14 15:28:25 -0500 |
| commit | 692088fac1a880263491b105ceb4b242402a6d6b (patch) | |
| tree | f43f71cc11b24d6a86d4be536e0bdf86ec52bfe0 /rust/src/binaryreader.rs | |
| parent | ee4ac3bb46f83f80b7f9b5b38dca0e2a49dc07e2 (diff) | |
rust: Add BinaryReader and BinaryWriter
Diffstat (limited to 'rust/src/binaryreader.rs')
| -rw-r--r-- | rust/src/binaryreader.rs | 85 |
1 files changed, 85 insertions, 0 deletions
diff --git a/rust/src/binaryreader.rs b/rust/src/binaryreader.rs new file mode 100644 index 00000000..c92b9e50 --- /dev/null +++ b/rust/src/binaryreader.rs @@ -0,0 +1,85 @@ +use binaryninjacore_sys::*; + +use crate::binaryview::BinaryView; +use crate::Endianness; + +use std::io::{Read, Seek, SeekFrom}; + +pub struct BinaryReader { + handle: *mut BNBinaryReader, +} + +impl BinaryReader { + pub fn new(view: &BinaryView, endian: Endianness) -> Self { + let handle = unsafe { BNCreateBinaryReader(view.handle) }; + unsafe { + BNSetBinaryReaderEndianness(handle, endian); + } + Self { handle } + } + + pub fn endian(&self) -> Endianness { + unsafe { BNGetBinaryReaderEndianness(self.handle) } + } + + pub fn set_endian(&self, endian: Endianness) { + unsafe { BNSetBinaryReaderEndianness(self.handle, endian) } + } + + pub fn offset(&self) -> u64 { + unsafe { BNGetReaderPosition(self.handle) } + } + + pub fn eof(&self) -> bool { + unsafe { BNIsEndOfFile(self.handle) } + } +} + +impl Seek for BinaryReader { + /// Seek to the specified position. + /// + /// # Errors + /// Seeking relative to [SeekFrom::End] is unsupported and will return an error. + fn seek(&mut self, pos: SeekFrom) -> std::io::Result<u64> { + unsafe { + match pos { + SeekFrom::Current(offset) => BNSeekBinaryReaderRelative(self.handle, offset), + SeekFrom::Start(offset) => BNSeekBinaryReader(self.handle, offset), + _ => { + return Err(std::io::Error::new( + std::io::ErrorKind::Unsupported, + "Cannot seek end of BinaryReader", + )) + } + }; + } + + Ok(self.offset()) + } +} + +impl Read for BinaryReader { + fn read(&mut self, buf: &mut [u8]) -> std::io::Result<usize> { + let len = buf.len(); + + let result = unsafe { BNReadData(self.handle, buf.as_mut_ptr() as *mut _, len) }; + + if !result { + Err(std::io::Error::new( + std::io::ErrorKind::Other, + "Read out of bounds", + )) + } else { + Ok(len) + } + } +} + +impl Drop for BinaryReader { + fn drop(&mut self) { + unsafe { BNFreeBinaryReader(self.handle) } + } +} + +unsafe impl Sync for BinaryReader {} +unsafe impl Send for BinaryReader {} |
