From 265a9fa6c92805b5190ae56f7c89c212e3283463 Mon Sep 17 00:00:00 2001 From: BiancaIalangi Date: Fri, 20 Sep 2024 23:14:11 +0300 Subject: [PATCH] wasm-extractor - fix report parameters --- contracts/examples/empty/src/empty.rs | 4 +- framework/meta-lib/src/code_report_json.rs | 2 +- .../meta-lib/src/tools/report_creator.rs | 24 +++++++++-- .../meta-lib/src/tools/wasm_extractor.rs | 40 ++++++++++++------- 4 files changed, 50 insertions(+), 20 deletions(-) diff --git a/contracts/examples/empty/src/empty.rs b/contracts/examples/empty/src/empty.rs index 81353a08d9..e7495881d3 100644 --- a/contracts/examples/empty/src/empty.rs +++ b/contracts/examples/empty/src/empty.rs @@ -7,7 +7,9 @@ use multiversx_sc::imports::*; #[multiversx_sc::contract] pub trait EmptyContract { #[init] - fn init(&self) {} + fn init(&self) -> u32 { + 64 + } #[upgrade] fn upgrade(&self) {} diff --git a/framework/meta-lib/src/code_report_json.rs b/framework/meta-lib/src/code_report_json.rs index a0b997bb6e..b1ec390436 100644 --- a/framework/meta-lib/src/code_report_json.rs +++ b/framework/meta-lib/src/code_report_json.rs @@ -24,7 +24,7 @@ impl CodeReportJson { path: report.path.clone(), size, has_allocator: report.has_allocator, - has_panic: report.has_panic.clone(), + has_panic: report.has_panic.to_string(), } } } diff --git a/framework/meta-lib/src/tools/report_creator.rs b/framework/meta-lib/src/tools/report_creator.rs index 37af10fa4e..93cc44e14c 100644 --- a/framework/meta-lib/src/tools/report_creator.rs +++ b/framework/meta-lib/src/tools/report_creator.rs @@ -1,10 +1,28 @@ -pub const WITH_MESSAGE: &str = "with message"; -pub const WITHOUT_MESSAGE: &str = "without message"; +use std::fmt::Display; + +#[derive(Default)] +pub enum PanicMessage { + #[default] + None, + WithoutMessage, + WithMessage, +} + +impl Display for PanicMessage { + fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { + let panic_status = match self { + PanicMessage::None => "None", + PanicMessage::WithoutMessage => "without message", + PanicMessage::WithMessage => "with message", + }; + write!(f, "{}", panic_status) + } +} pub struct ReportCreator { pub path: String, pub has_allocator: bool, - pub has_panic: String, + pub has_panic: PanicMessage, } impl ReportCreator {} diff --git a/framework/meta-lib/src/tools/wasm_extractor.rs b/framework/meta-lib/src/tools/wasm_extractor.rs index 50d5b78aff..e2e7d8ddd6 100644 --- a/framework/meta-lib/src/tools/wasm_extractor.rs +++ b/framework/meta-lib/src/tools/wasm_extractor.rs @@ -1,17 +1,17 @@ use colored::Colorize; use std::fs; use wasmparser::{ - BinaryReaderError, DataSectionReader, FunctionBody, ImportSectionReader, Parser, Payload, + BinaryReaderError, DataSectionReader, FunctionBody, ImportSectionReader, Operator, Parser, + Payload, }; use crate::ei::EIVersion; -use super::report_creator::{ReportCreator, WITHOUT_MESSAGE, WITH_MESSAGE}; +use super::report_creator::{PanicMessage, ReportCreator}; const PANIC_WITH_MESSAGE: &[u8; 16] = b"panic occurred: "; const PANIC_WITHOUT_MESSAGE: &[u8; 14] = b"panic occurred"; const ERROR_FAIL_ALLOCATOR: &[u8; 27] = b"memory allocation forbidden"; -const MEMORY_GROW_OPCODE: u8 = 0x40; pub struct WasmInfo { pub imports: Vec, @@ -49,25 +49,35 @@ fn populate_wasm_info( let mut allocator_trigger = false; let mut ei_check = false; let mut memory_grow_flag = false; - let mut has_panic = "none"; + let mut has_panic: PanicMessage = PanicMessage::default(); let parser = Parser::new(0); for payload in parser.parse_all(&wasm_data) { match payload? { Payload::ImportSection(import_section) => { imports = extract_imports(import_section, extract_imports_enabled); - ei_check = is_ei_valid(imports.clone(), check_ei); + ei_check |= is_ei_valid(imports.clone(), check_ei); }, Payload::DataSection(data_section) => { - allocator_trigger = is_fail_allocator_triggered(data_section.clone()); - if is_panic_with_message_triggered(data_section.clone()) { - has_panic = WITH_MESSAGE; - } else if is_panic_without_message_triggered(data_section) { - has_panic = WITHOUT_MESSAGE; + allocator_trigger |= is_fail_allocator_triggered(data_section.clone()); + match has_panic { + PanicMessage::None => { + if is_panic_with_message_triggered(data_section.clone()) { + has_panic = PanicMessage::WithMessage; + } else if is_panic_without_message_triggered(data_section) { + has_panic = PanicMessage::WithoutMessage; + } + }, + PanicMessage::WithoutMessage => { + if is_panic_with_message_triggered(data_section.clone()) { + has_panic = PanicMessage::WithMessage; + } + }, + PanicMessage::WithMessage => continue, } }, Payload::CodeSectionEntry(code_section) => { - memory_grow_flag = is_mem_grow(code_section); + memory_grow_flag |= is_mem_grow(code_section); }, _ => (), } @@ -76,7 +86,7 @@ fn populate_wasm_info( let report = ReportCreator { path, has_allocator: allocator_trigger, - has_panic: has_panic.to_string(), + has_panic, }; Ok(WasmInfo { @@ -173,9 +183,9 @@ fn is_ei_valid(imports: Vec, check_ei: &Option) -> bool { } fn is_mem_grow(code_section: FunctionBody) -> bool { - let mut code = code_section.get_binary_reader(); - while code.bytes_remaining() > 0 { - if code.read_u8().unwrap() == MEMORY_GROW_OPCODE { + for op_reader in code_section.get_operators_reader().iter_mut() { + let op = op_reader.read().unwrap(); + if let Operator::MemoryGrow { mem: _ } = op { return true; } }