Add support for emitting code with a single return at the end. (#153)

This also enables testing of the wasmtests tests.

This also updates for wabt updating to the official "wat" filename
extension, as opposed to "wast".
This commit is contained in:
Dan Gohman
2017-09-12 13:27:36 -07:00
committed by GitHub
parent 2e046d68ce
commit 1ab207b93c
15 changed files with 154 additions and 38 deletions

View File

@@ -1,5 +1,4 @@
//! CLI tool to use the functions provided by crates [wasm2cretonne](../wasm2cretonne/index.html)
//! and [wasmstandalone](../wasmstandalone/index.html).
//! CLI tool to use the functions provided by the [cretonne-wasm](../cton_wasm/index.html) crate.
//!
//! Reads Wasm binary files (one Wasm module per file), translates the functions' code to Cretonne
//! IL. Can also executes the `start` function of the module by laying out the memories, globals
@@ -13,6 +12,7 @@ use cretonne::dominator_tree::DominatorTree;
use cretonne::Context;
use cretonne::result::CtonError;
use cretonne::verifier;
use cretonne::settings::{self, Configurable};
use std::fs::File;
use std::error::Error;
use std::io;
@@ -54,7 +54,16 @@ pub fn run(
flag_verbose: bool,
flag_optimize: bool,
flag_check: bool,
flag_enable: Vec<String>,
) -> Result<(), String> {
let mut flag_builder = settings::builder();
for enable in flag_enable {
flag_builder.enable(&enable).map_err(|_| {
format!("unrecognized flag: {}", enable)
})?;
}
let flags = settings::Flags::new(&flag_builder);
for filename in files {
let path = Path::new(&filename);
let name = String::from(path.as_os_str().to_string_lossy());
@@ -64,6 +73,7 @@ pub fn run(
flag_check,
path.to_path_buf(),
name,
&flags,
) {
Ok(()) => {}
Err(message) => return Err(message),
@@ -78,6 +88,7 @@ fn handle_module(
flag_check: bool,
path: PathBuf,
name: String,
flags: &settings::Flags,
) -> Result<(), String> {
let mut terminal = term::stdout().unwrap();
terminal.fg(term::color::YELLOW).unwrap();
@@ -89,7 +100,7 @@ fn handle_module(
terminal.reset().unwrap();
let data = match path.extension() {
None => {
return Err(String::from("the file extension is not wasm or wast"));
return Err(String::from("the file extension is not wasm or wat"));
}
Some(ext) => {
match ext.to_str() {
@@ -101,17 +112,17 @@ fn handle_module(
}
}
}
Some("wast") => {
let tmp_dir = TempDir::new("wasm2cretonne").unwrap();
Some("wat") => {
let tmp_dir = TempDir::new("cretonne-wasm").unwrap();
let file_path = tmp_dir.path().join("module.wasm");
File::create(file_path.clone()).unwrap();
Command::new("wast2wasm")
Command::new("wat2wasm")
.arg(path.clone())
.arg("-o")
.arg(file_path.to_str().unwrap())
.output()
.or_else(|e| if let io::ErrorKind::NotFound = e.kind() {
return Err(String::from("wast2wasm not found"));
return Err(String::from("wat2wasm not found"));
} else {
return Err(String::from(e.description()));
})
@@ -124,12 +135,12 @@ fn handle_module(
}
}
None | Some(&_) => {
return Err(String::from("the file extension is not wasm or wast"));
return Err(String::from("the file extension is not wasm or wat"));
}
}
}
};
let mut dummy_runtime = DummyRuntime::new();
let mut dummy_runtime = DummyRuntime::with_flags(flags.clone());
let translation = {
let runtime: &mut WasmRuntime = &mut dummy_runtime;
match translate_module(&data, runtime) {