mirror of
https://github.com/roc-lang/roc.git
synced 2025-09-29 06:44:46 +00:00
Replace some helper functions with Parse trait instances
This commit is contained in:
parent
8114ec60c1
commit
66c78ceed5
3 changed files with 35 additions and 54 deletions
|
@ -2,7 +2,7 @@ use bumpalo::collections::vec::Vec;
|
|||
use bumpalo::Bump;
|
||||
|
||||
use super::opcodes::OpCode;
|
||||
use super::parse::{parse_u32_or_panic, SkipBytes};
|
||||
use super::parse::{Parse, SkipBytes};
|
||||
use super::serialize::{SerialBuffer, Serialize};
|
||||
use super::CodeBuilder;
|
||||
|
||||
|
@ -92,13 +92,13 @@ pub fn parse_preloads_call_graph<'a>(
|
|||
call_graph.code_offsets.push(cursor as u32);
|
||||
call_graph.calls_offsets.push(call_graph.calls.len() as u32);
|
||||
|
||||
let func_size = parse_u32_or_panic(code_section_body, &mut cursor);
|
||||
let func_size = u32::parse((), code_section_body, &mut cursor).unwrap();
|
||||
let func_end = cursor + func_size as usize;
|
||||
|
||||
// Skip over local variable declarations
|
||||
let local_groups_count = parse_u32_or_panic(code_section_body, &mut cursor);
|
||||
let local_groups_count = u32::parse((), code_section_body, &mut cursor).unwrap();
|
||||
for _ in 0..local_groups_count {
|
||||
parse_u32_or_panic(code_section_body, &mut cursor);
|
||||
u32::parse((), code_section_body, &mut cursor).unwrap();
|
||||
cursor += 1; // ValueType
|
||||
}
|
||||
|
||||
|
@ -107,12 +107,12 @@ pub fn parse_preloads_call_graph<'a>(
|
|||
let opcode_byte: u8 = code_section_body[cursor];
|
||||
if opcode_byte == OpCode::CALL as u8 {
|
||||
cursor += 1;
|
||||
let call_index = parse_u32_or_panic(code_section_body, &mut cursor);
|
||||
let call_index = u32::parse((), code_section_body, &mut cursor).unwrap();
|
||||
call_graph.calls.push(call_index as u32);
|
||||
} else if opcode_byte == OpCode::CALLINDIRECT as u8 {
|
||||
cursor += 1;
|
||||
// Insert all indirect callees with a matching type signature
|
||||
let sig = parse_u32_or_panic(code_section_body, &mut cursor);
|
||||
let sig = u32::parse((), code_section_body, &mut cursor).unwrap();
|
||||
call_graph.calls.extend(
|
||||
indirect_callees
|
||||
.iter()
|
||||
|
|
|
@ -1,7 +1,5 @@
|
|||
use super::serialize::MAX_SIZE_ENCODED_U32;
|
||||
use bumpalo::collections::vec::Vec;
|
||||
use bumpalo::Bump;
|
||||
use roc_error_macros::internal_error;
|
||||
|
||||
/// Parse serialized bytes into a data structure
|
||||
/// Specific parsers may need contextual data from other parts of the .wasm file
|
||||
|
@ -41,32 +39,16 @@ impl Parse<()> for u32 {
|
|||
}
|
||||
}
|
||||
|
||||
// Parse a vector of bytes (used for strings, but we don't bother with utf8 validation)
|
||||
impl<'a> Parse<&'a Bump> for Vec<'a, u8> {
|
||||
// Parse string bytes without utf8 validation
|
||||
impl<'a> Parse<&'a Bump> for &'a [u8] {
|
||||
fn parse(arena: &'a Bump, bytes: &[u8], cursor: &mut usize) -> Result<Self, String> {
|
||||
let len = parse_u32_or_panic(bytes, cursor);
|
||||
let end = *cursor + len as usize;
|
||||
let bytes: &[u8] = &bytes[*cursor..end];
|
||||
let mut copy = Vec::with_capacity_in(bytes.len(), arena);
|
||||
copy.extend_from_slice(bytes);
|
||||
*cursor = end;
|
||||
Ok(copy)
|
||||
}
|
||||
}
|
||||
|
||||
pub fn parse_u32_or_panic(bytes: &[u8], cursor: &mut usize) -> u32 {
|
||||
let (value, len) = decode_u32(&bytes[*cursor..]).unwrap_or_else(|e| internal_error!("{}", e));
|
||||
*cursor += len;
|
||||
value
|
||||
}
|
||||
|
||||
pub fn parse_string_bytes<'a>(arena: &'a Bump, bytes: &[u8], cursor: &mut usize) -> &'a [u8] {
|
||||
let len = parse_u32_or_panic(bytes, cursor);
|
||||
let len = u32::parse((), bytes, cursor)?;
|
||||
let end = *cursor + len as usize;
|
||||
let bytes: &[u8] = &bytes[*cursor..end];
|
||||
let copy = arena.alloc_slice_copy(bytes);
|
||||
*cursor = end;
|
||||
copy
|
||||
Ok(copy)
|
||||
}
|
||||
}
|
||||
|
||||
impl SkipBytes for u32 {
|
||||
|
@ -105,7 +87,7 @@ impl SkipBytes for u8 {
|
|||
/// Note: This is just for skipping over Wasm bytes. We don't actually care about String vs str!
|
||||
impl SkipBytes for String {
|
||||
fn skip_bytes(bytes: &[u8], cursor: &mut usize) -> Result<(), String> {
|
||||
let len = parse_u32_or_panic(bytes, cursor);
|
||||
let len = u32::parse((), bytes, cursor)?;
|
||||
|
||||
if false {
|
||||
let str_bytes = &bytes[*cursor..(*cursor + len as usize)];
|
||||
|
@ -123,7 +105,7 @@ impl SkipBytes for String {
|
|||
#[cfg(test)]
|
||||
mod tests {
|
||||
use super::*;
|
||||
use crate::wasm_module::parse::{decode_u32, parse_u32_or_panic};
|
||||
use crate::wasm_module::parse::decode_u32;
|
||||
|
||||
#[test]
|
||||
fn test_decode_u32() {
|
||||
|
@ -148,13 +130,13 @@ mod tests {
|
|||
let expected = [0, 128, u32::MAX];
|
||||
let mut cursor = 0;
|
||||
|
||||
assert_eq!(parse_u32_or_panic(bytes, &mut cursor), expected[0]);
|
||||
assert_eq!(u32::parse((), bytes, &mut cursor).unwrap(), expected[0]);
|
||||
assert_eq!(cursor, 1);
|
||||
|
||||
assert_eq!(parse_u32_or_panic(bytes, &mut cursor), expected[1]);
|
||||
assert_eq!(u32::parse((), bytes, &mut cursor).unwrap(), expected[1]);
|
||||
assert_eq!(cursor, 3);
|
||||
|
||||
assert_eq!(parse_u32_or_panic(bytes, &mut cursor), expected[2]);
|
||||
assert_eq!(u32::parse((), bytes, &mut cursor).unwrap(), expected[2]);
|
||||
assert_eq!(cursor, 8);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -11,7 +11,7 @@ use super::dead_code::{
|
|||
};
|
||||
use super::linking::RelocationEntry;
|
||||
use super::opcodes::OpCode;
|
||||
use super::parse::{parse_string_bytes, parse_u32_or_panic, Parse, SkipBytes};
|
||||
use super::parse::{Parse, SkipBytes};
|
||||
use super::serialize::{SerialBuffer, Serialize, MAX_SIZE_ENCODED_U32};
|
||||
use super::{CodeBuilder, ValueType};
|
||||
|
||||
|
@ -118,9 +118,9 @@ fn parse_section<'a>(id: SectionId, module_bytes: &'a [u8], cursor: &mut usize)
|
|||
}
|
||||
*cursor += 1;
|
||||
|
||||
let section_size = parse_u32_or_panic(module_bytes, cursor);
|
||||
let section_size = u32::parse((), module_bytes, cursor).unwrap();
|
||||
let count_start = *cursor;
|
||||
let count = parse_u32_or_panic(module_bytes, cursor);
|
||||
let count = u32::parse((), module_bytes, cursor).unwrap();
|
||||
let body_start = *cursor;
|
||||
|
||||
let next_section_start = count_start + section_size as usize;
|
||||
|
@ -237,7 +237,7 @@ impl<'a> TypeSection<'a> {
|
|||
debug_assert!(self.bytes[i] == Signature::SEPARATOR);
|
||||
i += 1;
|
||||
|
||||
let n_params = parse_u32_or_panic(&self.bytes, &mut i);
|
||||
let n_params = u32::parse((), &self.bytes, &mut i).unwrap();
|
||||
i += n_params as usize; // skip over one byte per param type
|
||||
|
||||
let n_return_values = self.bytes[i];
|
||||
|
@ -421,7 +421,7 @@ impl<'a> FunctionSection<'a> {
|
|||
let mut signatures = Vec::with_capacity_in(count, arena);
|
||||
let mut cursor = 0;
|
||||
for _ in 0..count {
|
||||
signatures.push(parse_u32_or_panic(&self.bytes, &mut cursor));
|
||||
signatures.push(u32::parse((), &self.bytes, &mut cursor).unwrap());
|
||||
}
|
||||
signatures
|
||||
}
|
||||
|
@ -579,9 +579,9 @@ impl Limits {
|
|||
let variant_id = bytes[*cursor];
|
||||
*cursor += 1;
|
||||
|
||||
let min = parse_u32_or_panic(bytes, cursor);
|
||||
let min = u32::parse((), bytes, cursor).unwrap();
|
||||
if variant_id == LimitsId::MinMax as u8 {
|
||||
let max = parse_u32_or_panic(bytes, cursor);
|
||||
let max = u32::parse((), bytes, cursor).unwrap();
|
||||
Limits::MinMax(min, max)
|
||||
} else {
|
||||
Limits::Min(min)
|
||||
|
@ -663,7 +663,7 @@ impl ConstExpr {
|
|||
}
|
||||
*cursor += 1;
|
||||
|
||||
let value = parse_u32_or_panic(bytes, cursor);
|
||||
let value = u32::parse((), bytes, cursor).unwrap();
|
||||
|
||||
if bytes[*cursor] != OpCode::END as u8 {
|
||||
return err;
|
||||
|
@ -791,12 +791,12 @@ pub struct Export<'a> {
|
|||
|
||||
impl<'a> Export<'a> {
|
||||
fn parse(arena: &'a Bump, bytes: &[u8], cursor: &mut usize) -> Self {
|
||||
let name = parse_string_bytes(arena, bytes, cursor);
|
||||
let name = <&'a [u8]>::parse(arena, bytes, cursor).unwrap();
|
||||
|
||||
let ty = ExportType::from(bytes[*cursor]);
|
||||
*cursor += 1;
|
||||
|
||||
let index = parse_u32_or_panic(bytes, cursor);
|
||||
let index = u32::parse((), bytes, cursor).unwrap();
|
||||
|
||||
Export { name, ty, index }
|
||||
}
|
||||
|
@ -895,14 +895,14 @@ impl<'a> ElementSegment<'a> {
|
|||
let const_expr_opcode = bytes[*cursor];
|
||||
debug_assert!(const_expr_opcode == OpCode::I32CONST as u8);
|
||||
*cursor += 1;
|
||||
let offset = parse_u32_or_panic(bytes, cursor);
|
||||
let offset = u32::parse((), bytes, cursor).unwrap();
|
||||
debug_assert!(bytes[*cursor] == OpCode::END as u8);
|
||||
*cursor += 1;
|
||||
|
||||
let num_elems = parse_u32_or_panic(bytes, cursor);
|
||||
let num_elems = u32::parse((), bytes, cursor).unwrap();
|
||||
let mut fn_indices = Vec::with_capacity_in(num_elems as usize, arena);
|
||||
for _ in 0..num_elems {
|
||||
let fn_idx = parse_u32_or_panic(bytes, cursor);
|
||||
let fn_idx = u32::parse((), bytes, cursor).unwrap();
|
||||
|
||||
fn_indices.push(fn_idx);
|
||||
}
|
||||
|
@ -1219,7 +1219,7 @@ impl<'a> OpaqueSection<'a> {
|
|||
} else {
|
||||
let section_start = *cursor;
|
||||
*cursor += 1;
|
||||
let section_size = parse_u32_or_panic(module_bytes, cursor);
|
||||
let section_size = u32::parse((), module_bytes, cursor).unwrap();
|
||||
let next_section_start = *cursor + section_size as usize;
|
||||
bytes = &module_bytes[section_start..next_section_start];
|
||||
*cursor = next_section_start;
|
||||
|
@ -1293,7 +1293,7 @@ impl<'a> NameSection<'a> {
|
|||
*cursor += 1;
|
||||
|
||||
// Section size
|
||||
let section_size = parse_u32_or_panic(module_bytes, cursor) as usize;
|
||||
let section_size = u32::parse((), module_bytes, cursor).unwrap() as usize;
|
||||
let section_end = *cursor + section_size;
|
||||
|
||||
let mut section = NameSection {
|
||||
|
@ -1312,7 +1312,7 @@ impl<'a> NameSection<'a> {
|
|||
cursor: &mut usize,
|
||||
section_end: usize,
|
||||
) {
|
||||
let section_name = parse_string_bytes(arena, module_bytes, cursor);
|
||||
let section_name = <&'a [u8]>::parse(arena, module_bytes, cursor).unwrap();
|
||||
if section_name != Self::NAME.as_bytes() {
|
||||
internal_error!(
|
||||
"Expected Custom section {:?}, found {:?}",
|
||||
|
@ -1326,7 +1326,7 @@ impl<'a> NameSection<'a> {
|
|||
for _possible_subsection_id in 0..2 {
|
||||
let subsection_id = module_bytes[*cursor];
|
||||
*cursor += 1;
|
||||
let subsection_size = parse_u32_or_panic(module_bytes, cursor);
|
||||
let subsection_size = u32::parse((), module_bytes, cursor).unwrap();
|
||||
if subsection_id == NameSubSections::FunctionNames as u8 {
|
||||
found_function_names = true;
|
||||
break;
|
||||
|
@ -1341,12 +1341,11 @@ impl<'a> NameSection<'a> {
|
|||
}
|
||||
|
||||
// Function names
|
||||
let num_entries = parse_u32_or_panic(module_bytes, cursor) as usize;
|
||||
let num_entries = u32::parse((), module_bytes, cursor).unwrap() as usize;
|
||||
let fn_names_start = *cursor;
|
||||
for _ in 0..num_entries {
|
||||
let fn_index = parse_u32_or_panic(module_bytes, cursor);
|
||||
let name_bytes = parse_string_bytes(arena, module_bytes, cursor);
|
||||
|
||||
let fn_index = u32::parse((), module_bytes, cursor).unwrap();
|
||||
let name_bytes = <&'a [u8]>::parse(arena, module_bytes, cursor).unwrap();
|
||||
self.functions
|
||||
.insert(arena.alloc_slice_copy(name_bytes), fn_index);
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue