Skip to content

Commit

Permalink
Merge pull request #27 from oli-obk/travis
Browse files Browse the repository at this point in the history
create a miri-pass test that allows us to run miri for arbitrary targets
  • Loading branch information
solson authored Jun 16, 2016
2 parents bac37e6 + 60f2bb9 commit 8db0bc0
Show file tree
Hide file tree
Showing 5 changed files with 83 additions and 32 deletions.
5 changes: 1 addition & 4 deletions .travis.yml
Original file line number Diff line number Diff line change
@@ -1,16 +1,13 @@
language: rust
rust:
- nightly
matrix:
allow_failures:
- rust: nightly
before_script:
- |
pip install 'travis-cargo<0.2' --user &&
export PATH=$HOME/.local/bin:$PATH
script:
- |
travis-cargo build &&
env RUST_SYSROOT=$HOME/rust travis-cargo build &&
env RUST_SYSROOT=$HOME/rust travis-cargo test
notifications:
email:
Expand Down
10 changes: 8 additions & 2 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -21,4 +21,4 @@ log = "0.3.6"
log_settings = "0.1.1"

[dev-dependencies]
compiletest_rs = "0.1.1"
compiletest_rs = "0.2"
4 changes: 3 additions & 1 deletion src/bin/miri.rs
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ use miri::{
Frame,
};
use rustc::session::Session;
use rustc_driver::{driver, CompilerCalls};
use rustc_driver::{driver, CompilerCalls, Compilation};
use rustc::ty::{TyCtxt, subst};
use rustc::hir::def_id::DefId;

Expand All @@ -31,6 +31,7 @@ impl<'a> CompilerCalls<'a> for MiriCompilerCalls {
) -> driver::CompileController<'a> {
let mut control = driver::CompileController::basic();

control.after_analysis.stop = Compilation::Stop;
control.after_analysis.callback = Box::new(|state| {
state.session.abort_if_errors();

Expand Down Expand Up @@ -70,6 +71,7 @@ impl<'a> CompilerCalls<'a> for MiriCompilerCalls {
}
}
}
state.session.abort_if_errors();
});

control
Expand Down
94 changes: 70 additions & 24 deletions tests/compiletest.rs
Original file line number Diff line number Diff line change
@@ -1,43 +1,89 @@
extern crate compiletest_rs as compiletest;

use std::path::PathBuf;
use std::path::{PathBuf, Path};
use std::io::Write;

fn run_mode(mode: &'static str) {
fn run_mode(dir: &'static str, mode: &'static str, sysroot: &str) {
// Disable rustc's new error fomatting. It breaks these tests.
std::env::remove_var("RUST_NEW_ERROR_FORMAT");

// Taken from https://github.com/Manishearth/rust-clippy/pull/911.
let home = option_env!("RUSTUP_HOME").or(option_env!("MULTIRUST_HOME"));
let toolchain = option_env!("RUSTUP_TOOLCHAIN").or(option_env!("MULTIRUST_TOOLCHAIN"));
let sysroot = match (home, toolchain) {
(Some(home), Some(toolchain)) => format!("{}/toolchains/{}", home, toolchain),
_ => option_env!("RUST_SYSROOT")
.expect("need to specify RUST_SYSROOT env var or use rustup or multirust")
.to_owned(),
};
let flags = format!("--sysroot {} -Dwarnings", sysroot);

// FIXME: read directories in sysroot/lib/rustlib and generate the test targets from that
let targets = &["x86_64-unknown-linux-gnu", "i686-unknown-linux-gnu"];

for &target in targets {
use std::io::Write;
let stderr = std::io::stderr();
write!(stderr.lock(), "running tests for target {}", target).unwrap();
for_all_targets(sysroot, |target| {
let mut config = compiletest::default_config();
config.host_rustcflags = Some(flags.clone());
config.mode = mode.parse().expect("Invalid mode");
config.run_lib_path = format!("{}/lib/rustlib/{}/lib", sysroot, target);
config.run_lib_path = Path::new(sysroot).join("lib").join("rustlib").join(&target).join("lib");
config.rustc_path = "target/debug/miri".into();
config.src_base = PathBuf::from(format!("tests/{}", mode));
config.src_base = PathBuf::from(format!("tests/{}", dir));
config.target = target.to_owned();
config.target_rustcflags = Some(flags.clone());
compiletest::run_tests(&config);
});
}

fn for_all_targets<F: FnMut(String)>(sysroot: &str, mut f: F) {
for target in std::fs::read_dir(format!("{}/lib/rustlib/", sysroot)).unwrap() {
let target = target.unwrap();
if !target.metadata().unwrap().is_dir() {
continue;
}
let target = target.file_name().into_string().unwrap();
if target == "etc" {
continue;
}
let stderr = std::io::stderr();
writeln!(stderr.lock(), "running tests for target {}", target).unwrap();
f(target);
}
}

#[test]
fn compile_test() {
run_mode("compile-fail");
run_mode("run-pass");
let mut failed = false;
// Taken from https://github.com/Manishearth/rust-clippy/pull/911.
let home = option_env!("RUSTUP_HOME").or(option_env!("MULTIRUST_HOME"));
let toolchain = option_env!("RUSTUP_TOOLCHAIN").or(option_env!("MULTIRUST_TOOLCHAIN"));
let sysroot = match (home, toolchain) {
(Some(home), Some(toolchain)) => format!("{}/toolchains/{}", home, toolchain),
_ => option_env!("RUST_SYSROOT")
.expect("need to specify RUST_SYSROOT env var or use rustup or multirust")
.to_owned(),
};
run_mode("compile-fail", "compile-fail", &sysroot);
for_all_targets(&sysroot, |target| {
for file in std::fs::read_dir("tests/run-pass").unwrap() {
let file = file.unwrap();
if !file.metadata().unwrap().is_file() {
continue;
}
let file = file.path();
let stderr = std::io::stderr();
write!(stderr.lock(), "test [miri-pass] {} ", file.to_str().unwrap()).unwrap();
let mut cmd = std::process::Command::new("target/debug/miri");
cmd.arg(file);
cmd.arg("-Dwarnings");
cmd.arg(format!("--target={}", target));
let libs = Path::new(&sysroot).join("lib");
let sysroot = libs.join("rustlib").join(&target).join("lib");
let paths = std::env::join_paths(&[libs, sysroot]).unwrap();
cmd.env(compiletest::procsrv::dylib_env_var(), paths);
match cmd.output() {
Ok(ref output) if output.status.success() => writeln!(stderr.lock(), "ok").unwrap(),
Ok(output) => {
failed = true;
writeln!(stderr.lock(), "FAILED with exit code {}", output.status.code().unwrap_or(0)).unwrap();
writeln!(stderr.lock(), "stdout: \n {}", std::str::from_utf8(&output.stdout).unwrap()).unwrap();
writeln!(stderr.lock(), "stderr: \n {}", std::str::from_utf8(&output.stderr).unwrap()).unwrap();
}
Err(e) => {
failed = true;
writeln!(stderr.lock(), "FAILED: {}", e).unwrap();
},
}
}
let stderr = std::io::stderr();
writeln!(stderr.lock(), "").unwrap();
});
if failed {
panic!("some tests failed");
}
}

0 comments on commit 8db0bc0

Please sign in to comment.