dcb/dcb-exe/src/exe/inst/iter.rs
Filipe Rodrigues 29643a72db Removed custom implementation of DataType.
Removed `DataType::AsciiChar` and added `DataType::AsciiStr`.
`inst::Inst::decode` now takes a data and func table.
2021-01-12 15:19:07 +00:00

64 lines
1.2 KiB
Rust

//! Parsing iterator
// Imports
use super::{Inst, InstSize};
use crate::{
exe::{DataTable, FuncTable},
Pos,
};
/// Parsing iterator.
///
/// Parses instructions from a byte slice, `[u8]` along with it's position.
#[derive(PartialEq, Eq, Clone, Debug)]
pub struct ParseIter<'a> {
/// Remaining bytes
bytes: &'a [u8],
/// Starting position of bytes
cur_pos: Pos,
/// Data table
data_table: &'a DataTable,
/// Func table
func_table: &'a FuncTable,
}
impl<'a> ParseIter<'a> {
/// Creates a new parsing iterator
#[must_use]
pub const fn new(bytes: &'a [u8], data_table: &'a DataTable, func_table: &'a FuncTable, start_pos: Pos) -> Self {
Self {
bytes,
cur_pos: start_pos,
data_table,
func_table,
}
}
/// Returns the current position of the iterator
#[must_use]
pub const fn cur_pos(&self) -> Pos {
self.cur_pos
}
}
impl<'a> Iterator for ParseIter<'a> {
type Item = (Pos, Inst<'a>);
fn next(&mut self) -> Option<Self::Item> {
// Try to read an instruction
let inst = Inst::decode(self.cur_pos, self.bytes, self.data_table, self.func_table)?;
let pos = self.cur_pos;
// Then skip it in our bytes
let len = inst.size();
self.cur_pos += len;
self.bytes = &self.bytes[len..];
// And return it
Some((pos, inst))
}
}