about summary refs log tree commit diff
path: root/compiler/rustc_codegen_cranelift/scripts
diff options
context:
space:
mode:
Diffstat (limited to 'compiler/rustc_codegen_cranelift/scripts')
-rw-r--r--compiler/rustc_codegen_cranelift/scripts/Readme.md2
-rw-r--r--compiler/rustc_codegen_cranelift/scripts/cargo.rs78
-rw-r--r--compiler/rustc_codegen_cranelift/scripts/config.sh6
-rw-r--r--compiler/rustc_codegen_cranelift/scripts/ext_config.sh32
-rwxr-xr-xcompiler/rustc_codegen_cranelift/scripts/filter_profile.rs126
-rwxr-xr-xcompiler/rustc_codegen_cranelift/scripts/rustup.sh58
-rw-r--r--compiler/rustc_codegen_cranelift/scripts/setup_rust_fork.sh57
-rwxr-xr-xcompiler/rustc_codegen_cranelift/scripts/test_bootstrap.sh15
-rwxr-xr-xcompiler/rustc_codegen_cranelift/scripts/test_rustc_tests.sh93
-rwxr-xr-xcompiler/rustc_codegen_cranelift/scripts/tests.sh163
10 files changed, 630 insertions, 0 deletions
diff --git a/compiler/rustc_codegen_cranelift/scripts/Readme.md b/compiler/rustc_codegen_cranelift/scripts/Readme.md
new file mode 100644
index 00000000000..83cec9c6f36
--- /dev/null
+++ b/compiler/rustc_codegen_cranelift/scripts/Readme.md
@@ -0,0 +1,2 @@
+This directory is for scripts that are either never directly invoked or are not used very often.
+Scripts that are frequently used should be kept at the project root.
diff --git a/compiler/rustc_codegen_cranelift/scripts/cargo.rs b/compiler/rustc_codegen_cranelift/scripts/cargo.rs
new file mode 100644
index 00000000000..89ec8da77d3
--- /dev/null
+++ b/compiler/rustc_codegen_cranelift/scripts/cargo.rs
@@ -0,0 +1,78 @@
+use std::env;
+#[cfg(unix)]
+use std::os::unix::process::CommandExt;
+use std::path::PathBuf;
+use std::process::Command;
+
+fn main() {
+    if env::var("RUSTC_WRAPPER").map_or(false, |wrapper| wrapper.contains("sccache")) {
+        eprintln!(
+            "\x1b[1;93m=== Warning: Unsetting RUSTC_WRAPPER to prevent interference with sccache ===\x1b[0m"
+        );
+        env::remove_var("RUSTC_WRAPPER");
+    }
+
+    let sysroot = PathBuf::from(env::current_exe().unwrap().parent().unwrap());
+
+    env::set_var("RUSTC", sysroot.join("bin/cg_clif".to_string() + env::consts::EXE_SUFFIX));
+
+    let mut rustdoc_flags = env::var("RUSTDOCFLAGS").unwrap_or(String::new());
+    rustdoc_flags.push_str(" -Cpanic=abort -Zpanic-abort-tests -Zcodegen-backend=");
+    rustdoc_flags.push_str(
+        sysroot
+            .join(if cfg!(windows) { "bin" } else { "lib" })
+            .join(
+                env::consts::DLL_PREFIX.to_string()
+                    + "rustc_codegen_cranelift"
+                    + env::consts::DLL_SUFFIX,
+            )
+            .to_str()
+            .unwrap(),
+    );
+    rustdoc_flags.push_str(" --sysroot ");
+    rustdoc_flags.push_str(sysroot.to_str().unwrap());
+    env::set_var("RUSTDOCFLAGS", rustdoc_flags);
+
+    // Ensure that the right toolchain is used
+    env::set_var("RUSTUP_TOOLCHAIN", env!("RUSTUP_TOOLCHAIN"));
+
+    let args: Vec<_> = match env::args().nth(1).as_deref() {
+        Some("jit") => {
+            env::set_var(
+                "RUSTFLAGS",
+                env::var("RUSTFLAGS").unwrap_or(String::new()) + " -Cprefer-dynamic",
+            );
+            std::array::IntoIter::new(["rustc".to_string()])
+                .chain(env::args().skip(2))
+                .chain([
+                    "--".to_string(),
+                    "-Zunstable-features".to_string(),
+                    "-Cllvm-args=mode=jit".to_string(),
+                ])
+                .collect()
+        }
+        Some("lazy-jit") => {
+            env::set_var(
+                "RUSTFLAGS",
+                env::var("RUSTFLAGS").unwrap_or(String::new()) + " -Cprefer-dynamic",
+            );
+            std::array::IntoIter::new(["rustc".to_string()])
+                .chain(env::args().skip(2))
+                .chain([
+                    "--".to_string(),
+                    "-Zunstable-features".to_string(),
+                    "-Cllvm-args=mode=jit-lazy".to_string(),
+                ])
+                .collect()
+        }
+        _ => env::args().skip(1).collect(),
+    };
+
+    #[cfg(unix)]
+    Command::new("cargo").args(args).exec();
+
+    #[cfg(not(unix))]
+    std::process::exit(
+        Command::new("cargo").args(args).spawn().unwrap().wait().unwrap().code().unwrap_or(1),
+    );
+}
diff --git a/compiler/rustc_codegen_cranelift/scripts/config.sh b/compiler/rustc_codegen_cranelift/scripts/config.sh
new file mode 100644
index 00000000000..53ada369b08
--- /dev/null
+++ b/compiler/rustc_codegen_cranelift/scripts/config.sh
@@ -0,0 +1,6 @@
+# Note to people running shellcheck: this file should only be sourced, not executed directly.
+
+set -e
+
+export LD_LIBRARY_PATH="$(rustc --print sysroot)/lib:$LD_LIBRARY_PATH"
+export DYLD_LIBRARY_PATH="$(rustc --print sysroot)/lib:$DYLD_LIBRARY_PATH"
diff --git a/compiler/rustc_codegen_cranelift/scripts/ext_config.sh b/compiler/rustc_codegen_cranelift/scripts/ext_config.sh
new file mode 100644
index 00000000000..11d6c4c8318
--- /dev/null
+++ b/compiler/rustc_codegen_cranelift/scripts/ext_config.sh
@@ -0,0 +1,32 @@
+# Note to people running shellcheck: this file should only be sourced, not executed directly.
+
+# Various env vars that should only be set for the build system
+
+set -e
+
+export CG_CLIF_DISPLAY_CG_TIME=1
+export CG_CLIF_DISABLE_INCR_CACHE=1
+
+export HOST_TRIPLE=$(rustc -vV | grep host | cut -d: -f2 | tr -d " ")
+export TARGET_TRIPLE=${TARGET_TRIPLE:-$HOST_TRIPLE}
+
+export RUN_WRAPPER=''
+export JIT_SUPPORTED=1
+if [[ "$HOST_TRIPLE" != "$TARGET_TRIPLE" ]]; then
+   export JIT_SUPPORTED=0
+   if [[ "$TARGET_TRIPLE" == "aarch64-unknown-linux-gnu" ]]; then
+      # We are cross-compiling for aarch64. Use the correct linker and run tests in qemu.
+      export RUSTFLAGS='-Clinker=aarch64-linux-gnu-gcc '$RUSTFLAGS
+      export RUN_WRAPPER='qemu-aarch64 -L /usr/aarch64-linux-gnu'
+   elif [[ "$TARGET_TRIPLE" == "x86_64-pc-windows-gnu" ]]; then
+      # We are cross-compiling for Windows. Run tests in wine.
+      export RUN_WRAPPER='wine'
+   else
+      echo "Unknown non-native platform"
+   fi
+fi
+
+# FIXME fix `#[linkage = "extern_weak"]` without this
+if [[ "$(uname)" == 'Darwin' ]]; then
+   export RUSTFLAGS="$RUSTFLAGS -Clink-arg=-undefined -Clink-arg=dynamic_lookup"
+fi
diff --git a/compiler/rustc_codegen_cranelift/scripts/filter_profile.rs b/compiler/rustc_codegen_cranelift/scripts/filter_profile.rs
new file mode 100755
index 00000000000..c4801a0a87b
--- /dev/null
+++ b/compiler/rustc_codegen_cranelift/scripts/filter_profile.rs
@@ -0,0 +1,126 @@
+#!/bin/bash
+#![forbid(unsafe_code)]/* This line is ignored by bash
+# This block is ignored by rustc
+pushd $(dirname "$0")/../
+source scripts/config.sh
+RUSTC="$(pwd)/build/bin/cg_clif"
+popd
+PROFILE=$1 OUTPUT=$2 exec $RUSTC -Zunstable-options -Cllvm-args=mode=jit -Cprefer-dynamic $0
+#*/
+
+//! This program filters away uninteresting samples and trims uninteresting frames for stackcollapse
+//! profiles.
+//!
+//! Usage: ./filter_profile.rs <profile in stackcollapse format> <output file>
+//!
+//! This file is specially crafted to be both a valid bash script and valid rust source file. If
+//! executed as bash script this will run the rust source using cg_clif in JIT mode.
+
+use std::io::Write;
+
+fn main() -> Result<(), Box<dyn std::error::Error>> {
+    let profile_name = std::env::var("PROFILE").unwrap();
+    let output_name = std::env::var("OUTPUT").unwrap();
+    if profile_name.is_empty() || output_name.is_empty() {
+        println!("Usage: ./filter_profile.rs <profile in stackcollapse format> <output file>");
+        std::process::exit(1);
+    }
+    let profile = std::fs::read_to_string(profile_name)
+        .map_err(|err| format!("Failed to read profile {}", err))?;
+    let mut output = std::fs::OpenOptions::new()
+        .create(true)
+        .write(true)
+        .truncate(true)
+        .open(output_name)?;
+
+    for line in profile.lines() {
+        let mut stack = &line[..line.rfind(" ").unwrap()];
+        let count = &line[line.rfind(" ").unwrap() + 1..];
+
+        // Filter away uninteresting samples
+        if !stack.contains("rustc_codegen_cranelift") {
+            continue;
+        }
+
+        if stack.contains("rustc_mir::monomorphize::partitioning::collect_and_partition_mono_items")
+            || stack.contains("rustc_incremental::assert_dep_graph::assert_dep_graph")
+            || stack.contains("rustc_symbol_mangling::test::report_symbol_names")
+        {
+            continue;
+        }
+
+        // Trim start
+        if let Some(index) = stack.find("rustc_interface::passes::configure_and_expand") {
+            stack = &stack[index..];
+        } else if let Some(index) = stack.find("rustc_interface::passes::analysis") {
+            stack = &stack[index..];
+        } else if let Some(index) = stack.find("rustc_interface::passes::start_codegen") {
+            stack = &stack[index..];
+        } else if let Some(index) = stack.find("rustc_interface::queries::Linker::link") {
+            stack = &stack[index..];
+        }
+
+        if let Some(index) = stack.find("rustc_codegen_cranelift::driver::aot::module_codegen") {
+            stack = &stack[index..];
+        }
+
+        // Trim end
+        const MALLOC: &str = "malloc";
+        if let Some(index) = stack.find(MALLOC) {
+            stack = &stack[..index + MALLOC.len()];
+        }
+
+        const FREE: &str = "free";
+        if let Some(index) = stack.find(FREE) {
+            stack = &stack[..index + FREE.len()];
+        }
+
+        const TYPECK_ITEM_BODIES: &str = "rustc_typeck::check::typeck_item_bodies";
+        if let Some(index) = stack.find(TYPECK_ITEM_BODIES) {
+            stack = &stack[..index + TYPECK_ITEM_BODIES.len()];
+        }
+
+        const COLLECT_AND_PARTITION_MONO_ITEMS: &str =
+            "rustc_mir::monomorphize::partitioning::collect_and_partition_mono_items";
+        if let Some(index) = stack.find(COLLECT_AND_PARTITION_MONO_ITEMS) {
+            stack = &stack[..index + COLLECT_AND_PARTITION_MONO_ITEMS.len()];
+        }
+
+        const ASSERT_DEP_GRAPH: &str = "rustc_incremental::assert_dep_graph::assert_dep_graph";
+        if let Some(index) = stack.find(ASSERT_DEP_GRAPH) {
+            stack = &stack[..index + ASSERT_DEP_GRAPH.len()];
+        }
+
+        const REPORT_SYMBOL_NAMES: &str = "rustc_symbol_mangling::test::report_symbol_names";
+        if let Some(index) = stack.find(REPORT_SYMBOL_NAMES) {
+            stack = &stack[..index + REPORT_SYMBOL_NAMES.len()];
+        }
+
+        const ENCODE_METADATA: &str = "rustc_middle::ty::context::TyCtxt::encode_metadata";
+        if let Some(index) = stack.find(ENCODE_METADATA) {
+            stack = &stack[..index + ENCODE_METADATA.len()];
+        }
+
+        const SUBST_AND_NORMALIZE_ERASING_REGIONS: &str = "rustc_middle::ty::normalize_erasing_regions::<impl rustc_middle::ty::context::TyCtxt>::subst_and_normalize_erasing_regions";
+        if let Some(index) = stack.find(SUBST_AND_NORMALIZE_ERASING_REGIONS) {
+            stack = &stack[..index + SUBST_AND_NORMALIZE_ERASING_REGIONS.len()];
+        }
+
+        const NORMALIZE_ERASING_LATE_BOUND_REGIONS: &str = "rustc_middle::ty::normalize_erasing_regions::<impl rustc_middle::ty::context::TyCtxt>::normalize_erasing_late_bound_regions";
+        if let Some(index) = stack.find(NORMALIZE_ERASING_LATE_BOUND_REGIONS) {
+            stack = &stack[..index + NORMALIZE_ERASING_LATE_BOUND_REGIONS.len()];
+        }
+
+        const INST_BUILD: &str = "<cranelift_frontend::frontend::FuncInstBuilder as cranelift_codegen::ir::builder::InstBuilderBase>::build";
+        if let Some(index) = stack.find(INST_BUILD) {
+            stack = &stack[..index + INST_BUILD.len()];
+        }
+
+        output.write_all(stack.as_bytes())?;
+        output.write_all(&*b" ")?;
+        output.write_all(count.as_bytes())?;
+        output.write_all(&*b"\n")?;
+    }
+
+    Ok(())
+}
diff --git a/compiler/rustc_codegen_cranelift/scripts/rustup.sh b/compiler/rustc_codegen_cranelift/scripts/rustup.sh
new file mode 100755
index 00000000000..cc34c080886
--- /dev/null
+++ b/compiler/rustc_codegen_cranelift/scripts/rustup.sh
@@ -0,0 +1,58 @@
+#!/usr/bin/env bash
+
+set -e
+
+case $1 in
+    "prepare")
+        TOOLCHAIN=$(date +%Y-%m-%d)
+
+        echo "=> Installing new nightly"
+        rustup toolchain install --profile minimal "nightly-${TOOLCHAIN}" # Sanity check to see if the nightly exists
+        sed -i "s/\"nightly-.*\"/\"nightly-${TOOLCHAIN}\"/" rust-toolchain
+        rustup component add rustfmt || true
+
+        echo "=> Uninstalling all old nighlies"
+        for nightly in $(rustup toolchain list | grep nightly | grep -v "$TOOLCHAIN" | grep -v nightly-x86_64); do
+            rustup toolchain uninstall "$nightly"
+        done
+
+        ./clean_all.sh
+        ./y.rs prepare
+
+        (cd build_sysroot && cargo update)
+
+        ;;
+    "commit")
+        git add rust-toolchain build_sysroot/Cargo.lock
+        git commit -m "Rustup to $(rustc -V)"
+        ;;
+    "push")
+        cg_clif=$(pwd)
+        pushd ../rust
+        git pull origin master
+        branch=sync_cg_clif-$(date +%Y-%m-%d)
+        git checkout -b "$branch"
+        git subtree pull --prefix=compiler/rustc_codegen_cranelift/ https://github.com/bjorn3/rustc_codegen_cranelift.git master
+        git push -u my "$branch"
+
+        # immediately merge the merge commit into cg_clif to prevent merge conflicts when syncing
+        # from rust-lang/rust later
+        git subtree push --prefix=compiler/rustc_codegen_cranelift/ "$cg_clif" sync_from_rust
+        popd
+        git merge sync_from_rust
+	;;
+    "pull")
+        cg_clif=$(pwd)
+        pushd ../rust
+        git pull origin master
+        rust_vers="$(git rev-parse HEAD)"
+        git subtree push --prefix=compiler/rustc_codegen_cranelift/ "$cg_clif" sync_from_rust
+        popd
+        git merge sync_from_rust -m "Sync from rust $rust_vers"
+        git branch -d sync_from_rust
+        ;;
+    *)
+        echo "Unknown command '$1'"
+        echo "Usage: ./rustup.sh prepare|commit"
+        ;;
+esac
diff --git a/compiler/rustc_codegen_cranelift/scripts/setup_rust_fork.sh b/compiler/rustc_codegen_cranelift/scripts/setup_rust_fork.sh
new file mode 100644
index 00000000000..ca83e7096b8
--- /dev/null
+++ b/compiler/rustc_codegen_cranelift/scripts/setup_rust_fork.sh
@@ -0,0 +1,57 @@
+#!/bin/bash
+set -e
+
+./y.rs build
+source scripts/config.sh
+
+echo "[SETUP] Rust fork"
+git clone https://github.com/rust-lang/rust.git || true
+pushd rust
+git fetch
+git checkout -- .
+git checkout "$(rustc -V | cut -d' ' -f3 | tr -d '(')"
+
+git apply - <<EOF
+diff --git a/Cargo.toml b/Cargo.toml
+index 5bd1147cad5..10d68a2ff14 100644
+--- a/Cargo.toml
++++ b/Cargo.toml
+@@ -111,5 +111,7 @@ rustc-std-workspace-std = { path = 'library/rustc-std-workspace-std' }
+ rustc-std-workspace-alloc = { path = 'library/rustc-std-workspace-alloc' }
+ rustc-std-workspace-std = { path = 'library/rustc-std-workspace-std' }
+
++compiler_builtins = { path = "../build_sysroot/compiler-builtins" }
++
+ [patch."https://github.com/rust-lang/rust-clippy"]
+ clippy_lints = { path = "src/tools/clippy/clippy_lints" }
+diff --git a/library/alloc/Cargo.toml b/library/alloc/Cargo.toml
+index d95b5b7f17f..00b6f0e3635 100644
+--- a/library/alloc/Cargo.toml
++++ b/library/alloc/Cargo.toml
+@@ -8,7 +8,7 @@ edition = "2018"
+
+ [dependencies]
+ core = { path = "../core" }
+-compiler_builtins = { version = "0.1.40", features = ['rustc-dep-of-std'] }
++compiler_builtins = { version = "0.1.46", features = ['rustc-dep-of-std', 'no-asm'] }
+
+ [dev-dependencies]
+ rand = "0.7"
+ rand_xorshift = "0.2"
+EOF
+
+cat > config.toml <<EOF
+[llvm]
+ninja = false
+
+[build]
+rustc = "$(pwd)/../build/bin/cg_clif"
+cargo = "$(rustup which cargo)"
+full-bootstrap = true
+local-rebuild = true
+
+[rust]
+codegen-backends = ["cranelift"]
+deny-warnings = false
+EOF
+popd
diff --git a/compiler/rustc_codegen_cranelift/scripts/test_bootstrap.sh b/compiler/rustc_codegen_cranelift/scripts/test_bootstrap.sh
new file mode 100755
index 00000000000..791d457993d
--- /dev/null
+++ b/compiler/rustc_codegen_cranelift/scripts/test_bootstrap.sh
@@ -0,0 +1,15 @@
+#!/usr/bin/env bash
+set -e
+
+cd "$(dirname "$0")/../"
+
+source ./scripts/setup_rust_fork.sh
+
+echo "[TEST] Bootstrap of rustc"
+pushd rust
+rm -r compiler/rustc_codegen_cranelift/{Cargo.*,src}
+cp ../Cargo.* compiler/rustc_codegen_cranelift/
+cp -r ../src compiler/rustc_codegen_cranelift/src
+
+./x.py build --stage 1 library/std
+popd
diff --git a/compiler/rustc_codegen_cranelift/scripts/test_rustc_tests.sh b/compiler/rustc_codegen_cranelift/scripts/test_rustc_tests.sh
new file mode 100755
index 00000000000..0ac49dd3574
--- /dev/null
+++ b/compiler/rustc_codegen_cranelift/scripts/test_rustc_tests.sh
@@ -0,0 +1,93 @@
+#!/bin/bash
+set -e
+
+cd $(dirname "$0")/../
+
+source ./scripts/setup_rust_fork.sh
+
+echo "[TEST] Test suite of rustc"
+pushd rust
+
+cargo install ripgrep
+
+rm -r src/test/ui/{extern/,panics/,unsized-locals/,thinlto/,simd*,*lto*.rs,linkage*,unwind-*.rs} || true
+for test in $(rg --files-with-matches "asm!|catch_unwind|should_panic|lto" src/test/ui); do
+  rm $test
+done
+
+for test in $(rg -i --files-with-matches "//(\[\w+\])?~|// error-pattern:|// build-fail|// run-fail|-Cllvm-args" src/test/ui); do
+  rm $test
+done
+
+git checkout -- src/test/ui/issues/auxiliary/issue-3136-a.rs # contains //~ERROR, but shouldn't be removed
+
+# these all depend on unwinding support
+rm src/test/ui/backtrace.rs
+rm src/test/ui/array-slice-vec/box-of-array-of-drop-*.rs
+rm src/test/ui/array-slice-vec/slice-panic-*.rs
+rm src/test/ui/array-slice-vec/nested-vec-3.rs
+rm src/test/ui/cleanup-rvalue-temp-during-incomplete-alloc.rs
+rm src/test/ui/issues/issue-26655.rs
+rm src/test/ui/issues/issue-29485.rs
+rm src/test/ui/issues/issue-30018-panic.rs
+rm src/test/ui/multi-panic.rs
+rm src/test/ui/sepcomp/sepcomp-unwind.rs
+rm src/test/ui/structs-enums/unit-like-struct-drop-run.rs
+rm src/test/ui/terminate-in-initializer.rs
+rm src/test/ui/threads-sendsync/task-stderr.rs
+rm src/test/ui/numbers-arithmetic/int-abs-overflow.rs
+rm src/test/ui/drop/drop-trait-enum.rs
+rm src/test/ui/numbers-arithmetic/issue-8460.rs
+rm src/test/ui/rt-explody-panic-payloads.rs
+rm src/test/incremental/change_crate_dep_kind.rs
+
+rm src/test/ui/issues/issue-28950.rs # depends on stack size optimizations
+rm src/test/ui/init-large-type.rs # same
+rm src/test/ui/sse2.rs # cpuid not supported, so sse2 not detected
+rm src/test/ui/issues/issue-33992.rs # unsupported linkages
+rm src/test/ui/issues/issue-51947.rs # same
+rm src/test/ui/numbers-arithmetic/saturating-float-casts.rs # intrinsic gives different but valid result
+rm src/test/ui/mir/mir_misc_casts.rs # depends on deduplication of constants
+rm src/test/ui/mir/mir_raw_fat_ptr.rs # same
+rm src/test/ui/consts/issue-33537.rs # same
+rm src/test/ui/async-await/async-fn-size-moved-locals.rs # -Cpanic=abort shrinks some generator by one byte
+rm src/test/ui/async-await/async-fn-size-uninit-locals.rs # same
+rm src/test/ui/generator/size-moved-locals.rs # same
+rm src/test/ui/fn/dyn-fn-alignment.rs # wants a 256 byte alignment
+rm src/test/ui/test-attrs/test-fn-signature-verification-for-explicit-return-type.rs # "Cannot run dynamic test fn out-of-process"
+rm src/test/ui/intrinsics/intrinsic-nearby.rs # unimplemented nearbyintf32 and nearbyintf64 intrinsics
+
+rm src/test/incremental/hashes/inline_asm.rs # inline asm
+rm src/test/incremental/issue-72386.rs # same
+rm src/test/incremental/issue-49482.rs # same
+rm src/test/incremental/issue-54059.rs # same
+rm src/test/incremental/lto.rs # requires lto
+
+rm -r src/test/run-make/emit-shared-files # requires the rustdoc executable in build/bin/
+rm -r src/test/run-make/unstable-flag-required # same
+rm -r src/test/run-make/emit-named-files # requires full --emit support
+
+rm src/test/pretty/asm.rs # inline asm
+rm src/test/pretty/raw-str-nonexpr.rs # same
+
+rm -r src/test/run-pass-valgrind/unsized-locals
+
+rm src/test/ui/json-bom-plus-crlf-multifile.rs # differing warning
+rm src/test/ui/json-bom-plus-crlf.rs # same
+rm src/test/ui/match/issue-82392.rs # differing error
+rm src/test/ui/type-alias-impl-trait/cross_crate_ice*.rs # requires removed aux dep
+
+rm src/test/ui/allocator/no_std-alloc-error-handler-default.rs # missing rust_oom definition
+rm src/test/ui/cfg/cfg-panic.rs
+rm -r src/test/ui/hygiene/
+
+rm -r src/test/ui/polymorphization/ # polymorphization not yet supported
+rm src/test/codegen-units/polymorphization/unused_type_parameters.rs # same
+
+rm -r src/test/run-make/fmt-write-bloat/ # tests an optimization
+rm src/test/ui/abi/mir/mir_codegen_calls_variadic.rs # requires float varargs
+rm src/test/ui/abi/variadic-ffi.rs # requires callee side vararg support
+
+echo "[TEST] rustc test suite"
+RUST_TEST_NOCAPTURE=1 COMPILETEST_FORCE_STAGE0=1 ./x.py test --stage 0 src/test/{codegen-units,run-make,run-pass-valgrind,ui}
+popd
diff --git a/compiler/rustc_codegen_cranelift/scripts/tests.sh b/compiler/rustc_codegen_cranelift/scripts/tests.sh
new file mode 100755
index 00000000000..0eef710239b
--- /dev/null
+++ b/compiler/rustc_codegen_cranelift/scripts/tests.sh
@@ -0,0 +1,163 @@
+#!/usr/bin/env bash
+
+set -e
+
+source scripts/config.sh
+source scripts/ext_config.sh
+export RUSTC=false # ensure that cg_llvm isn't accidentally used
+MY_RUSTC="$(pwd)/build/bin/cg_clif $RUSTFLAGS -L crate=target/out --out-dir target/out -Cdebuginfo=2"
+
+function no_sysroot_tests() {
+    echo "[BUILD] mini_core"
+    $MY_RUSTC example/mini_core.rs --crate-name mini_core --crate-type lib,dylib --target "$TARGET_TRIPLE"
+
+    echo "[BUILD] example"
+    $MY_RUSTC example/example.rs --crate-type lib --target "$TARGET_TRIPLE"
+
+    if [[ "$JIT_SUPPORTED" = "1" ]]; then
+        echo "[JIT] mini_core_hello_world"
+        CG_CLIF_JIT_ARGS="abc bcd" $MY_RUSTC -Zunstable-options -Cllvm-args=mode=jit -Cprefer-dynamic example/mini_core_hello_world.rs --cfg jit --target "$HOST_TRIPLE"
+
+        echo "[JIT-lazy] mini_core_hello_world"
+        CG_CLIF_JIT_ARGS="abc bcd" $MY_RUSTC -Zunstable-options -Cllvm-args=mode=jit-lazy -Cprefer-dynamic example/mini_core_hello_world.rs --cfg jit --target "$HOST_TRIPLE"
+    else
+        echo "[JIT] mini_core_hello_world (skipped)"
+    fi
+
+    echo "[AOT] mini_core_hello_world"
+    $MY_RUSTC example/mini_core_hello_world.rs --crate-name mini_core_hello_world --crate-type bin -g --target "$TARGET_TRIPLE"
+    $RUN_WRAPPER ./target/out/mini_core_hello_world abc bcd
+    # (echo "break set -n main"; echo "run"; sleep 1; echo "si -c 10"; sleep 1; echo "frame variable") | lldb -- ./target/out/mini_core_hello_world abc bcd
+}
+
+function base_sysroot_tests() {
+    echo "[AOT] arbitrary_self_types_pointers_and_wrappers"
+    $MY_RUSTC example/arbitrary_self_types_pointers_and_wrappers.rs --crate-name arbitrary_self_types_pointers_and_wrappers --crate-type bin --target "$TARGET_TRIPLE"
+    $RUN_WRAPPER ./target/out/arbitrary_self_types_pointers_and_wrappers
+
+    echo "[AOT] alloc_system"
+    $MY_RUSTC example/alloc_system.rs --crate-type lib --target "$TARGET_TRIPLE"
+
+    echo "[AOT] alloc_example"
+    $MY_RUSTC example/alloc_example.rs --crate-type bin --target "$TARGET_TRIPLE"
+    $RUN_WRAPPER ./target/out/alloc_example
+
+    if [[ "$JIT_SUPPORTED" = "1" ]]; then
+        echo "[JIT] std_example"
+        $MY_RUSTC -Zunstable-options -Cllvm-args=mode=jit -Cprefer-dynamic example/std_example.rs --target "$HOST_TRIPLE"
+
+        echo "[JIT-lazy] std_example"
+        $MY_RUSTC -Zunstable-options -Cllvm-args=mode=jit-lazy -Cprefer-dynamic example/std_example.rs --target "$HOST_TRIPLE"
+    else
+        echo "[JIT] std_example (skipped)"
+    fi
+
+    echo "[AOT] dst_field_align"
+    # FIXME Re-add -Zmir-opt-level=2 once rust-lang/rust#67529 is fixed.
+    $MY_RUSTC example/dst-field-align.rs --crate-name dst_field_align --crate-type bin --target "$TARGET_TRIPLE"
+    $RUN_WRAPPER ./target/out/dst_field_align || (echo $?; false)
+
+    echo "[AOT] std_example"
+    $MY_RUSTC example/std_example.rs --crate-type bin --target "$TARGET_TRIPLE"
+    $RUN_WRAPPER ./target/out/std_example arg
+
+    echo "[AOT] subslice-patterns-const-eval"
+    $MY_RUSTC example/subslice-patterns-const-eval.rs --crate-type bin -Cpanic=abort --target "$TARGET_TRIPLE"
+    $RUN_WRAPPER ./target/out/subslice-patterns-const-eval
+
+    echo "[AOT] track-caller-attribute"
+    $MY_RUSTC example/track-caller-attribute.rs --crate-type bin -Cpanic=abort --target "$TARGET_TRIPLE"
+    $RUN_WRAPPER ./target/out/track-caller-attribute
+
+    echo "[AOT] mod_bench"
+    $MY_RUSTC example/mod_bench.rs --crate-type bin --target "$TARGET_TRIPLE"
+    $RUN_WRAPPER ./target/out/mod_bench
+}
+
+function extended_sysroot_tests() {
+    pushd rand
+    ../build/cargo clean
+    if [[ "$HOST_TRIPLE" = "$TARGET_TRIPLE" ]]; then
+        echo "[TEST] rust-random/rand"
+        ../build/cargo test --workspace
+    else
+        echo "[AOT] rust-random/rand"
+        ../build/cargo build --workspace --target $TARGET_TRIPLE --tests
+    fi
+    popd
+
+    pushd simple-raytracer
+    if [[ "$HOST_TRIPLE" = "$TARGET_TRIPLE" ]]; then
+        echo "[BENCH COMPILE] ebobby/simple-raytracer"
+        hyperfine --runs "${RUN_RUNS:-10}" --warmup 1 --prepare "../build/cargo clean" \
+        "RUSTC=rustc RUSTFLAGS='' cargo build" \
+        "../build/cargo build"
+
+        echo "[BENCH RUN] ebobby/simple-raytracer"
+        cp ./target/debug/main ./raytracer_cg_clif
+        hyperfine --runs "${RUN_RUNS:-10}" ./raytracer_cg_llvm ./raytracer_cg_clif
+    else
+        ../build/cargo clean
+        echo "[BENCH COMPILE] ebobby/simple-raytracer (skipped)"
+        echo "[COMPILE] ebobby/simple-raytracer"
+        ../build/cargo build --target $TARGET_TRIPLE
+        echo "[BENCH RUN] ebobby/simple-raytracer (skipped)"
+    fi
+    popd
+
+    pushd build_sysroot/sysroot_src/library/core/tests
+    echo "[TEST] libcore"
+    ../../../../../build/cargo clean
+    if [[ "$HOST_TRIPLE" = "$TARGET_TRIPLE" ]]; then
+        ../../../../../build/cargo test
+    else
+        ../../../../../build/cargo build --target $TARGET_TRIPLE --tests
+    fi
+    popd
+
+    pushd regex
+    echo "[TEST] rust-lang/regex example shootout-regex-dna"
+    ../build/cargo clean
+    export RUSTFLAGS="$RUSTFLAGS --cap-lints warn" # newer aho_corasick versions throw a deprecation warning
+    # Make sure `[codegen mono items] start` doesn't poison the diff
+    ../build/cargo build --example shootout-regex-dna --target $TARGET_TRIPLE
+    if [[ "$HOST_TRIPLE" = "$TARGET_TRIPLE" ]]; then
+        cat examples/regexdna-input.txt \
+            | ../build/cargo run --example shootout-regex-dna --target $TARGET_TRIPLE \
+            | grep -v "Spawned thread" > res.txt
+        diff -u res.txt examples/regexdna-output.txt
+    fi
+
+    if [[ "$HOST_TRIPLE" = "$TARGET_TRIPLE" ]]; then
+        echo "[TEST] rust-lang/regex tests"
+        ../build/cargo test --tests -- --exclude-should-panic --test-threads 1 -Zunstable-options -q
+    else
+        echo "[AOT] rust-lang/regex tests"
+        ../build/cargo build --tests --target $TARGET_TRIPLE
+    fi
+    popd
+
+    pushd stdsimd
+    echo "[TEST] rust-lang/stdsimd"
+    ../build/cargo clean
+    ../build/cargo build --all-targets --target $TARGET_TRIPLE
+    if [[ "$HOST_TRIPLE" = "$TARGET_TRIPLE" ]]; then
+        ../build/cargo test -q
+    fi
+    popd
+}
+
+case "$1" in
+    "no_sysroot")
+        no_sysroot_tests
+        ;;
+    "base_sysroot")
+        base_sysroot_tests
+        ;;
+    "extended_sysroot")
+        extended_sysroot_tests
+        ;;
+    *)
+        echo "unknown test suite"
+        ;;
+esac