diff --git a/lib/clif-backend/src/libcalls.rs b/lib/clif-backend/src/libcalls.rs index 012adb3c2..661d74d40 100644 --- a/lib/clif-backend/src/libcalls.rs +++ b/lib/clif-backend/src/libcalls.rs @@ -26,7 +26,7 @@ pub extern "C" fn nearbyintf32(x: f32) -> f32 { } if x.is_nan() { - x + f32::from_bits(x.to_bits() | (1 << 22)) } else { let k = f32::EPSILON.recip(); let a = x.abs(); @@ -64,7 +64,7 @@ pub extern "C" fn nearbyintf64(x: f64) -> f64 { } if x.is_nan() { - x + f64::from_bits(x.to_bits() | (1 << 51)) } else { let k = f64::EPSILON.recip(); let a = x.abs(); diff --git a/lib/runtime/examples/test.rs b/lib/runtime/examples/test.rs index 20ad160d7..dd3ce56b7 100644 --- a/lib/runtime/examples/test.rs +++ b/lib/runtime/examples/test.rs @@ -11,51 +11,8 @@ fn main() { fn create_module_1() -> Box { let module_str = "(module - (type (;0;) (func)) - (type (;1;) (func)) - (type (;2;) (func (param i64 i64 f64 i64 f64 i64 f32 i32))) - (type (;3;) (func (param f64 i64 f64 i64 f64 i64 f32 i32))) - (func (;0;) (type 0)) - (func (;1;) (type 3) (param f64 i64 f64 i64 f64 i64 f32 i32)) - (func (;2;) (type 0)) - (func (;3;) (type 3) (param f64 i64 f64 i64 f64 i64 f32 i32)) - (func (;4;) (type 3) (param f64 i64 f64 i64 f64 i64 f32 i32)) - (func (;5;) (type 2) (param i64 i64 f64 i64 f64 i64 f32 i32)) - (func (;6;) (type 2) (param i64 i64 f64 i64 f64 i64 f32 i32)) - (func (;7;) (type 0) - f64.const 0x0p+0 (;=0;) - i64.const 0 - f64.const 0x0p+0 (;=0;) - i64.const 0 - f64.const 0x0p+0 (;=0;) - i64.const 0 - f32.const 0x0p+0 (;=0;) - i32.const 0 - i32.const 0 - call_indirect (type 3) - f64.const 0x0p+0 (;=0;) - i64.const 0 - f64.const 0x0p+0 (;=0;) - i64.const 0 - f64.const 0x0p+0 (;=0;) - i64.const 0 - f32.const 0x0p+0 (;=0;) - i32.const 0 - i32.const 2 - call_indirect (type 3) - f64.const 0x0p+0 (;=0;) - i64.const 0 - f64.const 0x0p+0 (;=0;) - i64.const 0 - f64.const 0x0p+0 (;=0;) - i64.const 0 - f32.const 0x0p+0 (;=0;) - i32.const 0 - i32.const 3 - call_indirect (type 3)) - (table (;0;) 7 7 anyfunc) - (export \"signature-implicit-reused\" (func 7)) - (elem (;0;) (i32.const 0) 4 2 1 4 0 5 6)) + (import \"spectest\" \"memory\" (memory (;0;) 0)) + (data (;0;) (i32.const 0) \"\")) "; let wasm_binary = wat2wasm(module_str.as_bytes()).expect("WAST not valid or malformed"); let module = wasmer_runtime::compile(&wasm_binary[..], &CraneliftCompiler::new()).expect("WASM can't be compiled"); diff --git a/lib/runtime/src/backing.rs b/lib/runtime/src/backing.rs index 6a5e95fe8..270de479a 100644 --- a/lib/runtime/src/backing.rs +++ b/lib/runtime/src/backing.rs @@ -179,94 +179,104 @@ impl ImportBacking { "imported tables not yet supported" ); - let mut functions = Vec::with_capacity(module.imported_functions.len()); - for ( - index, + Ok(ImportBacking { + functions: import_functions(module, imports)?, + memories: vec![].into_boxed_slice(), + tables: vec![].into_boxed_slice(), + globals: import_globals(module, imports)?, + }) + } +} + +// fn import_memories(module: &Module, imports: &dyn ImportResolver) -> Result, String> { + +// } + +fn import_functions(module: &Module, imports: &dyn ImportResolver) -> Result, String> { + let mut functions = Vec::with_capacity(module.imported_functions.len()); + for ( + index, + ImportName { + module: mod_name, + name: item_name, + }, + ) in &module.imported_functions + { + let sig_index = module.func_assoc[index]; + let expected_sig = module.sig_registry.lookup_func_sig(sig_index); + let import = imports.get(mod_name, item_name); + match import { + Some(&Import::Func(ref func, ref signature)) => { + if expected_sig == signature { + functions.push(vm::ImportedFunc { + func: func.inner(), + // vmctx: ptr::null_mut(), + }); + } else { + return Err(format!( + "unexpected signature for {:?}:{:?}", + mod_name, item_name + )); + } + } + Some(_) => { + return Err(format!( + "incorrect import type for {}:{}", + mod_name, item_name + )); + } + None => { + return Err(format!("import not found: {}:{}", mod_name, item_name)); + } + } + } + Ok(functions.into_boxed_slice()) +} + +fn import_globals(module: &Module, imports: &dyn ImportResolver) -> Result, String> { + let mut globals = Vec::with_capacity(module.imported_globals.len()); + for ( + _, + ( ImportName { module: mod_name, name: item_name, }, - ) in &module.imported_functions - { - let sig_index = module.func_assoc[index]; - let expected_sig = module.sig_registry.lookup_func_sig(sig_index); - let import = imports.get(mod_name, item_name); - match import { - Some(&Import::Func(ref func, ref signature)) => { - if expected_sig == signature { - functions.push(vm::ImportedFunc { - func: func.inner(), - // vmctx: ptr::null_mut(), - }); - } else { - return Err(format!( - "unexpected signature for {:?}:{:?}", - mod_name, item_name - )); - } - } - Some(_) => { - return Err(format!( - "incorrect import type for {}:{}", - mod_name, item_name - )); - } - None => { - return Err(format!("import not found: {}:{}", mod_name, item_name)); - } - } - } - - let mut globals = Vec::with_capacity(module.imported_globals.len()); - for ( - _, - ( - ImportName { - module: mod_name, - name: item_name, - }, - global_desc, - ), - ) in &module.imported_globals - { - let import = imports.get(mod_name, item_name); - match import { - Some(Import::Global(val)) => { - if val.ty() == global_desc.ty { - globals.push(vm::ImportedGlobal { - global: vm::LocalGlobal { - data: match val { - Value::I32(n) => *n as u64, - Value::I64(n) => *n as u64, - Value::F32(n) => (*n).to_bits() as u64, - Value::F64(n) => (*n).to_bits(), - }, + global_desc, + ), + ) in &module.imported_globals + { + let import = imports.get(mod_name, item_name); + match import { + Some(Import::Global(val)) => { + if val.ty() == global_desc.ty { + globals.push(vm::ImportedGlobal { + global: vm::LocalGlobal { + data: match val { + Value::I32(n) => *n as u64, + Value::I64(n) => *n as u64, + Value::F32(n) => (*n).to_bits() as u64, + Value::F64(n) => (*n).to_bits(), }, - }); - } else { - return Err(format!( - "unexpected global type for {:?}:{:?}", - mod_name, item_name - )); - } - } - Some(_) => { + }, + }); + } else { return Err(format!( - "incorrect import type for {}:{}", + "unexpected global type for {:?}:{:?}", mod_name, item_name )); } - None => { - return Err(format!("import not found: {}:{}", mod_name, item_name)); - } + } + Some(_) => { + return Err(format!( + "incorrect import type for {}:{}", + mod_name, item_name + )); + } + None => { + return Err(format!("import not found: {}:{}", mod_name, item_name)); } } - - Ok(ImportBacking { - functions: functions.into_boxed_slice(), - memories: vec![].into_boxed_slice(), - tables: vec![].into_boxed_slice(), - globals: globals.into_boxed_slice(), - }) } + Ok(globals.into_boxed_slice()) } diff --git a/lib/runtime/tests/spectests/_common.rs b/lib/runtime/tests/spectests/_common.rs index 0703dd191..d02acafc7 100644 --- a/lib/runtime/tests/spectests/_common.rs +++ b/lib/runtime/tests/spectests/_common.rs @@ -95,7 +95,7 @@ impl NaNCheck for f32 { impl NaNCheck for f64 { /// The MSB of the mantissa must be set for a NaN to be a quiet NaN. fn is_quiet_nan(&self) -> bool { - let bit_mask = 0b1 << 51; // Used to check if 51st bit is set, which is MSB of the mantissa + let bit_mask = 0b1 << 51; // Used to check if 52st bit is set, which is MSB of the mantissa self.is_nan() && (self.to_bits() & bit_mask) == bit_mask }