Skip to content

Commit

Permalink
Fix cranelift tests
Browse files Browse the repository at this point in the history
  • Loading branch information
alexcrichton committed Jul 22, 2020
1 parent b9789d0 commit 66b956e
Show file tree
Hide file tree
Showing 5 changed files with 70 additions and 83 deletions.
12 changes: 11 additions & 1 deletion cranelift/wasm/src/environ/dummy.rs
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ use cranelift_frontend::FunctionBuilder;
use std::boxed::Box;
use std::string::String;
use std::vec::Vec;
use wasmparser::{FuncValidator, FunctionBody, ValidatorResources};
use wasmparser::{FuncValidator, FunctionBody, ValidatorResources, WasmFeatures};

/// Compute a `ir::ExternalName` for a given wasm function index.
fn get_func_name(func_index: FuncIndex) -> ir::ExternalName {
Expand Down Expand Up @@ -747,4 +747,14 @@ impl<'data> ModuleEnvironment<'data> for DummyEnvironment {
self.function_names[func_index] = String::from(name);
Ok(())
}

fn wasm_features(&self) -> WasmFeatures {
WasmFeatures {
multi_value: true,
simd: true,
reference_types: true,
bulk_memory: true,
..WasmFeatures::default()
}
}
}
124 changes: 55 additions & 69 deletions cranelift/wasm/src/func_translator.rs
Original file line number Diff line number Diff line change
Expand Up @@ -280,26 +280,27 @@ fn cur_srcloc(reader: &BinaryReader) -> ir::SourceLoc {
mod tests {
use super::{FuncTranslator, ReturnMode};
use crate::environ::DummyEnvironment;
use crate::ModuleTranslationState;
use cranelift_codegen::ir::types::I32;
use cranelift_codegen::{ir, isa, settings, Context};
use log::debug;
use target_lexicon::PointerWidth;
use wasmparser::{
FuncValidator, FunctionBody, Parser, ValidPayload, Validator, ValidatorResources,
};

#[test]
fn small1() {
// Implicit return.
//
// (func $small1 (param i32) (result i32)
// (i32.add (get_local 0) (i32.const 1))
// )
const BODY: [u8; 7] = [
0x00, // local decl count
0x20, 0x00, // get_local 0
0x41, 0x01, // i32.const 1
0x6a, // i32.add
0x0b, // end
];
let wasm = wat::parse_str(
"
(module
(func $small2 (param i32) (result i32)
(i32.add (get_local 0) (i32.const 1))
)
)
",
)
.unwrap();

let mut trans = FuncTranslator::new();
let flags = settings::Flags::new(settings::builder());
Expand All @@ -312,21 +313,15 @@ mod tests {
false,
);

let module_translation_state = ModuleTranslationState::new();
let mut ctx = Context::new();

ctx.func.name = ir::ExternalName::testcase("small1");
ctx.func.signature.params.push(ir::AbiParam::new(I32));
ctx.func.signature.returns.push(ir::AbiParam::new(I32));

let (body, mut validator) = extract_func(&wasm);
trans
.translate(
&module_translation_state,
&BODY,
0,
&mut ctx.func,
&mut runtime.func_env(),
)
.translate_body(&mut validator, body, &mut ctx.func, &mut runtime.func_env())
.unwrap();
debug!("{}", ctx.func.display(None));
ctx.verify(&flags).unwrap();
Expand All @@ -335,18 +330,16 @@ mod tests {
#[test]
fn small2() {
// Same as above, but with an explicit return instruction.
//
// (func $small2 (param i32) (result i32)
// (return (i32.add (get_local 0) (i32.const 1)))
// )
const BODY: [u8; 8] = [
0x00, // local decl count
0x20, 0x00, // get_local 0
0x41, 0x01, // i32.const 1
0x6a, // i32.add
0x0f, // return
0x0b, // end
];
let wasm = wat::parse_str(
"
(module
(func $small2 (param i32) (result i32)
(return (i32.add (get_local 0) (i32.const 1)))
)
)
",
)
.unwrap();

let mut trans = FuncTranslator::new();
let flags = settings::Flags::new(settings::builder());
Expand All @@ -359,21 +352,15 @@ mod tests {
false,
);

let module_translation_state = ModuleTranslationState::new();
let mut ctx = Context::new();

ctx.func.name = ir::ExternalName::testcase("small2");
ctx.func.signature.params.push(ir::AbiParam::new(I32));
ctx.func.signature.returns.push(ir::AbiParam::new(I32));

let (body, mut validator) = extract_func(&wasm);
trans
.translate(
&module_translation_state,
&BODY,
0,
&mut ctx.func,
&mut runtime.func_env(),
)
.translate_body(&mut validator, body, &mut ctx.func, &mut runtime.func_env())
.unwrap();
debug!("{}", ctx.func.display(None));
ctx.verify(&flags).unwrap();
Expand All @@ -382,27 +369,21 @@ mod tests {
#[test]
fn infloop() {
// An infinite loop, no return instructions.
//
// (func $infloop (result i32)
// (local i32)
// (loop (result i32)
// (i32.add (get_local 0) (i32.const 1))
// (set_local 0)
// (br 0)
// )
// )
const BODY: [u8; 16] = [
0x01, // 1 local decl.
0x01, 0x7f, // 1 i32 local.
0x03, 0x7f, // loop i32
0x20, 0x00, // get_local 0
0x41, 0x01, // i32.const 0
0x6a, // i32.add
0x21, 0x00, // set_local 0
0x0c, 0x00, // br 0
0x0b, // end
0x0b, // end
];
let wasm = wat::parse_str(
"
(module
(func $infloop (result i32)
(local i32)
(loop (result i32)
(i32.add (get_local 0) (i32.const 1))
(set_local 0)
(br 0)
)
)
)
",
)
.unwrap();

let mut trans = FuncTranslator::new();
let flags = settings::Flags::new(settings::builder());
Expand All @@ -415,22 +396,27 @@ mod tests {
false,
);

let module_translation_state = ModuleTranslationState::new();
let mut ctx = Context::new();

ctx.func.name = ir::ExternalName::testcase("infloop");
ctx.func.signature.returns.push(ir::AbiParam::new(I32));

let (body, mut validator) = extract_func(&wasm);
trans
.translate(
&module_translation_state,
&BODY,
0,
&mut ctx.func,
&mut runtime.func_env(),
)
.translate_body(&mut validator, body, &mut ctx.func, &mut runtime.func_env())
.unwrap();
debug!("{}", ctx.func.display(None));
ctx.verify(&flags).unwrap();
}

fn extract_func(wat: &[u8]) -> (FunctionBody<'_>, FuncValidator<ValidatorResources>) {
let mut validator = Validator::new();
for payload in Parser::new(0).parse_all(wat) {
match validator.payload(&payload.unwrap()).unwrap() {
ValidPayload::Func(validator, body) => return (body, validator),
_ => {}
}
}
panic!("failed to find function");
}
}
12 changes: 1 addition & 11 deletions cranelift/wasm/tests/wasm_testsuite.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,6 @@ use cranelift_codegen::settings::{self, Flags};
use cranelift_codegen::verifier;
use cranelift_wasm::{translate_module, DummyEnvironment, FuncIndex, ReturnMode};
use std::fs;
use std::fs::File;
use std::io;
use std::io::prelude::*;
use std::path::Path;
use std::str::FromStr;
use target_lexicon::triple;
Expand Down Expand Up @@ -69,20 +66,13 @@ fn use_name_section() {
);
}

fn read_file(path: &Path) -> io::Result<Vec<u8>> {
let mut buf: Vec<u8> = Vec::new();
let mut file = File::open(path)?;
file.read_to_end(&mut buf)?;
Ok(buf)
}

fn read_module(path: &Path) -> Vec<u8> {
match path.extension() {
None => {
panic!("the file extension is not wasm or wat");
}
Some(ext) => match ext.to_str() {
Some("wasm") => read_file(path).expect("error reading wasm file"),
Some("wasm") => std::fs::read(path).expect("error reading wasm file"),
Some("wat") => wat::parse_file(path)
.map_err(|e| e.to_string())
.expect("failed to parse wat"),
Expand Down
1 change: 1 addition & 0 deletions cranelift/wasmtests/passive-data.wat
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
(module
(data $passive "this is a passive data segment")
(memory 0)

(func (export "init") (param i32 i32 i32)
local.get 0 ;; dst
Expand Down
4 changes: 2 additions & 2 deletions cranelift/wasmtests/ref-func-0.wat
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
global.get 2
global.get 3)

(global (export "externref-imported") externref (ref.func $imported))
(global (export "externref-local") externref (ref.func $local))
(global (export "externref-imported") externref (ref.null extern))
(global (export "externref-local") externref (ref.null extern))
(global (export "funcref-imported") funcref (ref.func $imported))
(global (export "funcref-local") funcref (ref.func $local)))

0 comments on commit 66b956e

Please sign in to comment.