From 5b32aa074762faa5d7132aa9d2943cf35a05d833 Mon Sep 17 00:00:00 2001 From: Maybe Waffle Date: Wed, 11 May 2022 17:52:00 +0400 Subject: [PATCH 01/98] Add pointer masking convenience functions This commit adds the following functions all of which have a signature `pointer, usize -> pointer`: - `<*mut T>::mask` - `<*const T>::mask` - `intrinsics::ptr_mask` These functions are equivalent to `.map_addr(|a| a & mask)` but they utilize `llvm.ptrmask` llvm intrinsic. *masks your pointers* --- src/intrinsics/mod.rs | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/src/intrinsics/mod.rs b/src/intrinsics/mod.rs index b2a83e1d4ebc9..65e964c786b52 100644 --- a/src/intrinsics/mod.rs +++ b/src/intrinsics/mod.rs @@ -540,6 +540,13 @@ fn codegen_regular_intrinsic_call<'tcx>( ret.write_cvalue(fx, CValue::by_val(res, base.layout())); } + sym::ptr_mask => { + intrinsic_args!(fx, args => (ptr, mask); intrinsic); + let ptr_val = ptr.load_scalar(fx); + + fx.bcx.ins().band(ptr_val, mask); + } + sym::transmute => { intrinsic_args!(fx, args => (from); intrinsic); From 63a137605f837eebe4af0074fc23c9684b12e97e Mon Sep 17 00:00:00 2001 From: Waffle Maybe Date: Wed, 11 May 2022 21:43:13 +0400 Subject: [PATCH 02/98] use shorter `ptr_mask` impl in cg cranelift Co-authored-by: bjorn3 --- src/intrinsics/mod.rs | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/src/intrinsics/mod.rs b/src/intrinsics/mod.rs index 65e964c786b52..35880bb3e22be 100644 --- a/src/intrinsics/mod.rs +++ b/src/intrinsics/mod.rs @@ -542,9 +542,7 @@ fn codegen_regular_intrinsic_call<'tcx>( sym::ptr_mask => { intrinsic_args!(fx, args => (ptr, mask); intrinsic); - let ptr_val = ptr.load_scalar(fx); - - fx.bcx.ins().band(ptr_val, mask); + fx.bcx.ins().band(ptr, mask); } sym::transmute => { From 5f357c2c51e5663f5c75b389c3fb3501753ac3be Mon Sep 17 00:00:00 2001 From: Waffle Maybe Date: Sun, 7 Aug 2022 22:32:26 +0400 Subject: [PATCH 03/98] fix cg cranelift Co-authored-by: bjorn3 <17426603+bjorn3@users.noreply.github.com> --- src/intrinsics/mod.rs | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/intrinsics/mod.rs b/src/intrinsics/mod.rs index 35880bb3e22be..9fe43157d508a 100644 --- a/src/intrinsics/mod.rs +++ b/src/intrinsics/mod.rs @@ -542,6 +542,8 @@ fn codegen_regular_intrinsic_call<'tcx>( sym::ptr_mask => { intrinsic_args!(fx, args => (ptr, mask); intrinsic); + let ptr = ptr.load_scalar(fx); + let mask = mask.load_scalar(fx); fx.bcx.ins().band(ptr, mask); } From cfef0a4f8df6085a81f130674e9c2f67b042fd02 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Wed, 24 Aug 2022 18:40:58 +0200 Subject: [PATCH 04/98] Merge commit 'e9d1a0a7b0b28dd422f1a790ccde532acafbf193' into sync_cg_clif-2022-08-24 --- .cirrus.yml | 2 +- .github/workflows/main.yml | 10 +- .gitignore | 3 + Cargo.lock | 147 +++-- Cargo.toml | 14 +- Readme.md | 4 +- build_sysroot/Cargo.lock | 20 +- build_system/abi_checker.rs | 60 ++ build_system/build_backend.rs | 4 +- build_system/build_sysroot.rs | 10 +- build_system/mod.rs | 58 +- build_system/prepare.rs | 11 +- build_system/rustc_info.rs | 9 + build_system/tests.rs | 618 ++++++++++++++++++ build_system/utils.rs | 29 +- clean_all.sh | 2 +- config.txt | 35 + example/mini_core.rs | 12 +- example/mini_core_hello_world.rs | 117 +++- ...01-abi-checker-Disable-failing-tests.patch | 36 + .../0023-sysroot-Ignore-failing-tests.patch | 12 + rust-toolchain | 2 +- scripts/tests.sh | 203 ------ src/abi/pass_mode.rs | 6 +- src/base.rs | 227 +++---- src/common.rs | 46 +- src/concurrency_limiter.rs | 168 +++++ src/debuginfo/emit.rs | 2 +- src/debuginfo/line_info.rs | 213 +++--- src/debuginfo/mod.rs | 282 ++------ src/discriminant.rs | 20 +- src/driver/aot.rs | 560 +++++++++------- src/driver/jit.rs | 49 +- src/global_asm.rs | 114 ++++ src/inline_asm.rs | 176 +++-- src/intrinsics/cpuid.rs | 2 +- src/intrinsics/llvm.rs | 1 + src/intrinsics/mod.rs | 47 +- src/intrinsics/simd.rs | 33 +- src/lib.rs | 55 +- src/optimize/mod.rs | 17 - src/pretty_clif.rs | 61 +- src/toolchain.rs | 6 +- src/trap.rs | 25 +- src/value_and_place.rs | 10 +- test.sh | 13 +- 46 files changed, 2292 insertions(+), 1259 deletions(-) create mode 100644 build_system/abi_checker.rs create mode 100644 build_system/tests.rs create mode 100644 patches/0001-abi-checker-Disable-failing-tests.patch delete mode 100755 scripts/tests.sh create mode 100644 src/concurrency_limiter.rs create mode 100644 src/global_asm.rs diff --git a/.cirrus.yml b/.cirrus.yml index 61da6a2491c52..732edd66196d7 100644 --- a/.cirrus.yml +++ b/.cirrus.yml @@ -22,4 +22,4 @@ task: - # Reduce amount of benchmark runs as they are slow - export COMPILE_RUNS=2 - export RUN_RUNS=2 - - ./test.sh + - ./y.rs test diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index aa556a21bf8c3..e8897e9ae8145 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -103,7 +103,7 @@ jobs: # Enable extra checks export CG_CLIF_ENABLE_VERIFIER=1 - ./test.sh + ./y.rs test - name: Package prebuilt cg_clif run: tar cvfJ cg_clif.tar.xz build @@ -162,14 +162,14 @@ jobs: #name: Test run: | # Enable backtraces for easier debugging - #export RUST_BACKTRACE=1 + #$Env:RUST_BACKTRACE=1 # Reduce amount of benchmark runs as they are slow - #export COMPILE_RUNS=2 - #export RUN_RUNS=2 + #$Env:COMPILE_RUNS=2 + #$Env:RUN_RUNS=2 # Enable extra checks - #export CG_CLIF_ENABLE_VERIFIER=1 + #$Env:CG_CLIF_ENABLE_VERIFIER=1 ./y.exe build diff --git a/.gitignore b/.gitignore index 5aeaf3a178804..6fd3e4443de5c 100644 --- a/.gitignore +++ b/.gitignore @@ -8,6 +8,8 @@ perf.data.old *.string* /y.bin /y.bin.dSYM +/y.exe +/y.pdb /build /build_sysroot/sysroot_src /build_sysroot/compiler-builtins @@ -17,3 +19,4 @@ perf.data.old /regex /simple-raytracer /portable-simd +/abi-checker diff --git a/Cargo.lock b/Cargo.lock index 402fbb16f97ee..edae7e471578a 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -50,18 +50,18 @@ checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd" [[package]] name = "cranelift-bforest" -version = "0.85.3" +version = "0.87.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "749d0d6022c9038dccf480bdde2a38d435937335bf2bb0f14e815d94517cdce8" +checksum = "93945adbccc8d731503d3038814a51e8317497c9e205411820348132fa01a358" dependencies = [ "cranelift-entity", ] [[package]] name = "cranelift-codegen" -version = "0.85.3" +version = "0.87.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e94370cc7b37bf652ccd8bb8f09bd900997f7ccf97520edfc75554bb5c4abbea" +checksum = "2b482acc9d0d0d1ad3288a90a8150ee648be3dce8dc8c8669ff026f72debdc31" dependencies = [ "cranelift-bforest", "cranelift-codegen-meta", @@ -77,30 +77,30 @@ dependencies = [ [[package]] name = "cranelift-codegen-meta" -version = "0.85.3" +version = "0.87.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e0a3cea8fdab90e44018c5b9a1dfd460d8ee265ac354337150222a354628bdb6" +checksum = "f9ec188d71e663192ef9048f204e410a7283b609942efc9fcc77da6d496edbb8" dependencies = [ "cranelift-codegen-shared", ] [[package]] name = "cranelift-codegen-shared" -version = "0.85.3" +version = "0.87.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5ac72f76f2698598951ab26d8c96eaa854810e693e7dd52523958b5909fde6b2" +checksum = "3ad794b1b1c2c7bd9f7b76cfe0f084eaf7753e55d56191c3f7d89e8fa4978b99" [[package]] name = "cranelift-entity" -version = "0.85.3" +version = "0.87.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "09eaeacfcd2356fe0e66b295e8f9d59fdd1ac3ace53ba50de14d628ec902f72d" +checksum = "342da0d5056f4119d3c311c4aab2460ceb6ee6e127bb395b76dd2279a09ea7a5" [[package]] name = "cranelift-frontend" -version = "0.85.3" +version = "0.87.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "dba69c9980d5ffd62c18a2bde927855fcd7c8dc92f29feaf8636052662cbd99c" +checksum = "dfff792f775b07d4d9cfe9f1c767ce755c6cbadda1bbd6db18a1c75ff9f7376a" dependencies = [ "cranelift-codegen", "log", @@ -110,15 +110,15 @@ dependencies = [ [[package]] name = "cranelift-isle" -version = "0.85.3" +version = "0.87.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d2920dc1e05cac40304456ed3301fde2c09bd6a9b0210bcfa2f101398d628d5b" +checksum = "8d51089478849f2ac8ef60a8a2d5346c8d4abfec0e45ac5b24530ef9f9499e1e" [[package]] name = "cranelift-jit" -version = "0.85.3" +version = "0.87.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1c3c5ed067f2c81577e431f3039148a9c187b33cc79e0d1731fede27d801ec56" +checksum = "095936e41720f86004b4c57ce88e6a13af28646bb3a6fb4afbebd5ae90c50029" dependencies = [ "anyhow", "cranelift-codegen", @@ -129,14 +129,14 @@ dependencies = [ "log", "region", "target-lexicon", - "winapi", + "windows-sys", ] [[package]] name = "cranelift-module" -version = "0.85.3" +version = "0.87.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "eee6784303bf9af235237a4885f7417e09a35df896d38ea969a0081064b3ede4" +checksum = "704a1aea4723d97eafe0fb7af110f6f6868b1ac95f5380bbc9adb2a3b8cf97e8" dependencies = [ "anyhow", "cranelift-codegen", @@ -144,9 +144,9 @@ dependencies = [ [[package]] name = "cranelift-native" -version = "0.85.3" +version = "0.87.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f04dfa45f9b2a6f587c564d6b63388e00cd6589d2df6ea2758cf79e1a13285e6" +checksum = "885debe62f2078638d6585f54c9f05f5c2008f22ce5a2a9100ada785fc065dbd" dependencies = [ "cranelift-codegen", "libc", @@ -155,9 +155,9 @@ dependencies = [ [[package]] name = "cranelift-object" -version = "0.85.3" +version = "0.87.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0bf38b2c505db749276793116c0cb30bd096206c7810e471677a453134881881" +checksum = "aac1310cf1081ae8eca916c92cd163b977c77cab6e831fa812273c26ff921816" dependencies = [ "anyhow", "cranelift-codegen", @@ -187,9 +187,9 @@ dependencies = [ [[package]] name = "getrandom" -version = "0.2.6" +version = "0.2.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9be70c98951c83b8d2f8f60d7065fa6d5146873094452a1008da8c2f1e4205ad" +checksum = "4eb1a864a501629691edf6c15a593b7a51eebaa1e8468e9ddc623de7c9b58ec6" dependencies = [ "cfg-if", "libc", @@ -198,28 +198,22 @@ dependencies = [ [[package]] name = "gimli" -version = "0.26.1" +version = "0.26.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "78cc372d058dcf6d5ecd98510e7fbc9e5aec4d21de70f65fea8fecebcd881bd4" +checksum = "22030e2c5a68ec659fde1e949a745124b48e6fa8b045b7ed5bd1fe4ccc5c4e5d" dependencies = [ "indexmap", ] [[package]] name = "hashbrown" -version = "0.11.2" +version = "0.12.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ab5ef0d4909ef3724cc8cce6ccc8572c5c817592e9285f5464f8e86f8bd3726e" +checksum = "8a9ee70c43aaf417c914396645a0fa852624801b24ebb7ae78fe8272889ac888" dependencies = [ "ahash", ] -[[package]] -name = "hashbrown" -version = "0.12.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8a9ee70c43aaf417c914396645a0fa852624801b24ebb7ae78fe8272889ac888" - [[package]] name = "indexmap" version = "1.9.1" @@ -227,14 +221,14 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "10a35a97730320ffe8e2d410b5d3b69279b98d2c14bdb8b70ea89ecf7888d41e" dependencies = [ "autocfg", - "hashbrown 0.12.3", + "hashbrown", ] [[package]] name = "libc" -version = "0.2.126" +version = "0.2.127" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "349d5a591cd28b49e1d1037471617a32ddcda5731b99419008085f72d5a53836" +checksum = "505e71a4706fa491e9b1b55f51b95d4037d0821ee40131190475f692b35b009b" [[package]] name = "libloading" @@ -248,9 +242,9 @@ dependencies = [ [[package]] name = "log" -version = "0.4.14" +version = "0.4.17" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "51b9bbe6c47d51fc3e1a9b945965946b4c44142ab8792c50835a980d362c2710" +checksum = "abb12e687cfb44aa40f41fc3978ef76448f9b6038cad6aef4259d3c095a2382e" dependencies = [ "cfg-if", ] @@ -266,33 +260,33 @@ dependencies = [ [[package]] name = "memchr" -version = "2.4.1" +version = "2.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "308cc39be01b73d0d18f82a0e7b2a3df85245f84af96fdddc5d202d27e47b86a" +checksum = "2dffe52ecf27772e601905b7522cb4ef790d2cc203488bbd0e2fe85fcb74566d" [[package]] name = "object" -version = "0.28.4" +version = "0.29.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e42c982f2d955fac81dd7e1d0e1426a7d702acd9c98d19ab01083a6a0328c424" +checksum = "21158b2c33aa6d4561f1c0a6ea283ca92bc54802a93b263e910746d679a7eb53" dependencies = [ "crc32fast", - "hashbrown 0.11.2", + "hashbrown", "indexmap", "memchr", ] [[package]] name = "once_cell" -version = "1.10.0" +version = "1.13.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "87f3e037eac156d1775da914196f0f37741a274155e34a0b7e427c35d2a2ecb9" +checksum = "18a6dbe30758c9f83eb00cbea4ac95966305f5a7772f3f42ebfc7fc7eddbd8e1" [[package]] name = "regalloc2" -version = "0.2.3" +version = "0.3.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4a8d23b35d7177df3b9d31ed8a9ab4bf625c668be77a319d4f5efd4a5257701c" +checksum = "d43a209257d978ef079f3d446331d0f1794f5e0fc19b306a199983857833a779" dependencies = [ "fxhash", "log", @@ -340,15 +334,15 @@ checksum = "03b634d87b960ab1a38c4fe143b508576f075e7c978bfad18217645ebfdfa2ec" [[package]] name = "smallvec" -version = "1.8.1" +version = "1.9.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cc88c725d61fc6c3132893370cac4a0200e3fedf5da8331c570664b1987f5ca2" +checksum = "2fd0db749597d91ff862fd1d55ea87f7855a744a8425a64695b6fca237d1dad1" [[package]] name = "target-lexicon" -version = "0.12.3" +version = "0.12.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d7fa7e55043acb85fca6b3c01485a2eeb6b69c5d21002e273c79e465f43b7ac1" +checksum = "c02424087780c9b71cc96799eaeddff35af2bc513278cda5c99fc1f5d026d3c1" [[package]] name = "version_check" @@ -358,9 +352,9 @@ checksum = "49874b5167b65d7193b8aba1567f5c7d93d001cafc34600cee003eda787e483f" [[package]] name = "wasi" -version = "0.10.2+wasi-snapshot-preview1" +version = "0.11.0+wasi-snapshot-preview1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fd6fbd9a79829dd1ad0cc20627bf1ed606756a7f77edff7b66b7064f9cb327c6" +checksum = "9c8d87e72b64a3b4db28d11ce29237c246188f4f51057d65a7eab63b7987e423" [[package]] name = "winapi" @@ -383,3 +377,46 @@ name = "winapi-x86_64-pc-windows-gnu" version = "0.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f" + +[[package]] +name = "windows-sys" +version = "0.36.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ea04155a16a59f9eab786fe12a4a450e75cdb175f9e0d80da1e17db09f55b8d2" +dependencies = [ + "windows_aarch64_msvc", + "windows_i686_gnu", + "windows_i686_msvc", + "windows_x86_64_gnu", + "windows_x86_64_msvc", +] + +[[package]] +name = "windows_aarch64_msvc" +version = "0.36.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9bb8c3fd39ade2d67e9874ac4f3db21f0d710bee00fe7cab16949ec184eeaa47" + +[[package]] +name = "windows_i686_gnu" +version = "0.36.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "180e6ccf01daf4c426b846dfc66db1fc518f074baa793aa7d9b9aaeffad6a3b6" + +[[package]] +name = "windows_i686_msvc" +version = "0.36.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e2e7917148b2812d1eeafaeb22a97e4813dfa60a3f8f78ebe204bcc88f12f024" + +[[package]] +name = "windows_x86_64_gnu" +version = "0.36.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4dcd171b8776c41b97521e5da127a2d86ad280114807d0b2ab1e462bc764d9e1" + +[[package]] +name = "windows_x86_64_msvc" +version = "0.36.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c811ca4a8c853ef420abd8592ba53ddbbac90410fab6903b3e79972a631f7680" diff --git a/Cargo.toml b/Cargo.toml index 61e977e3e69bf..e7c3427485480 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -8,15 +8,15 @@ crate-type = ["dylib"] [dependencies] # These have to be in sync with each other -cranelift-codegen = { version = "0.85.3", features = ["unwind", "all-arch"] } -cranelift-frontend = "0.85.3" -cranelift-module = "0.85.3" -cranelift-native = "0.85.3" -cranelift-jit = { version = "0.85.3", optional = true } -cranelift-object = "0.85.3" +cranelift-codegen = { version = "0.87.0", features = ["unwind", "all-arch"] } +cranelift-frontend = "0.87.0" +cranelift-module = "0.87.0" +cranelift-native = "0.87.0" +cranelift-jit = { version = "0.87.0", optional = true } +cranelift-object = "0.87.0" target-lexicon = "0.12.0" gimli = { version = "0.26.0", default-features = false, features = ["write"]} -object = { version = "0.28.0", default-features = false, features = ["std", "read_core", "write", "archive", "coff", "elf", "macho", "pe"] } +object = { version = "0.29.0", default-features = false, features = ["std", "read_core", "write", "archive", "coff", "elf", "macho", "pe"] } ar = { git = "https://github.com/bjorn3/rust-ar.git", branch = "do_not_remove_cg_clif_ranlib" } indexmap = "1.9.1" diff --git a/Readme.md b/Readme.md index 8a2db5a43ecbf..1e84c7fa3657b 100644 --- a/Readme.md +++ b/Readme.md @@ -52,9 +52,7 @@ configuration options. ## Not yet supported * Inline assembly ([no cranelift support](https://github.com/bytecodealliance/wasmtime/issues/1041)) - * On Linux there is support for invoking an external assembler for `global_asm!` and `asm!`. - `llvm_asm!` will remain unimplemented forever. `asm!` doesn't yet support reg classes. You - have to specify specific registers instead. + * On UNIX there is support for invoking an external assembler for `global_asm!` and `asm!`. * SIMD ([tracked here](https://github.com/bjorn3/rustc_codegen_cranelift/issues/171), some basic things work) ## License diff --git a/build_sysroot/Cargo.lock b/build_sysroot/Cargo.lock index 7b2cdd273366f..6c5043bb6f8e1 100644 --- a/build_sysroot/Cargo.lock +++ b/build_sysroot/Cargo.lock @@ -56,9 +56,9 @@ dependencies = [ [[package]] name = "compiler_builtins" -version = "0.1.75" +version = "0.1.79" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c6e3183e88f659a862835db8f4b67dbeed3d93e44dd4927eef78edb1c149d784" +checksum = "4f873ce2bd3550b0b565f878b3d04ea8253f4259dc3d20223af2e1ba86f5ecca" dependencies = [ "rustc-std-workspace-core", ] @@ -69,9 +69,9 @@ version = "0.0.0" [[package]] name = "dlmalloc" -version = "0.2.3" +version = "0.2.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a6fe28e0bf9357092740362502f5cc7955d8dc125ebda71dec72336c2e15c62e" +checksum = "203540e710bfadb90e5e29930baf5d10270cec1f43ab34f46f78b147b2de715a" dependencies = [ "compiler_builtins", "libc", @@ -80,9 +80,9 @@ dependencies = [ [[package]] name = "fortanix-sgx-abi" -version = "0.3.3" +version = "0.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c56c422ef86062869b2d57ae87270608dc5929969dd130a6e248979cf4fb6ca6" +checksum = "57cafc2274c10fab234f176b25903ce17e690fca7597090d50880e047a0389c5" dependencies = [ "compiler_builtins", "rustc-std-workspace-core", @@ -123,9 +123,9 @@ dependencies = [ [[package]] name = "hermit-abi" -version = "0.2.4" +version = "0.2.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7668753748e445859e4e373c3d41117235d9feed578392f5a3a73efdc751ca4a" +checksum = "897cd85af6387be149f55acf168e41be176a02de7872403aaab184afc2f327e6" dependencies = [ "compiler_builtins", "libc", @@ -135,9 +135,9 @@ dependencies = [ [[package]] name = "libc" -version = "0.2.126" +version = "0.2.132" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "349d5a591cd28b49e1d1037471617a32ddcda5731b99419008085f72d5a53836" +checksum = "8371e4e5341c3a96db127eb2465ac681ced4c433e01dd0e938adbef26ba93ba5" dependencies = [ "rustc-std-workspace-core", ] diff --git a/build_system/abi_checker.rs b/build_system/abi_checker.rs new file mode 100644 index 0000000000000..67dbd0a38a4fb --- /dev/null +++ b/build_system/abi_checker.rs @@ -0,0 +1,60 @@ +use super::build_sysroot; +use super::config; +use super::utils::spawn_and_wait; +use build_system::SysrootKind; +use std::env; +use std::path::Path; +use std::process::Command; + +pub(crate) fn run( + channel: &str, + sysroot_kind: SysrootKind, + target_dir: &Path, + cg_clif_build_dir: &Path, + host_triple: &str, + target_triple: &str, +) { + if !config::get_bool("testsuite.abi-checker") { + eprintln!("[SKIP] abi-checker"); + return; + } + + if host_triple != target_triple { + eprintln!("[SKIP] abi-checker (cross-compilation not supported)"); + return; + } + + eprintln!("Building sysroot for abi-checker"); + build_sysroot::build_sysroot( + channel, + sysroot_kind, + target_dir, + cg_clif_build_dir, + host_triple, + target_triple, + ); + + eprintln!("Running abi-checker"); + let mut abi_checker_path = env::current_dir().unwrap(); + abi_checker_path.push("abi-checker"); + env::set_current_dir(abi_checker_path.clone()).unwrap(); + + let build_dir = abi_checker_path.parent().unwrap().join("build"); + let cg_clif_dylib_path = build_dir.join(if cfg!(windows) { "bin" } else { "lib" }).join( + env::consts::DLL_PREFIX.to_string() + "rustc_codegen_cranelift" + env::consts::DLL_SUFFIX, + ); + + let pairs = ["rustc_calls_cgclif", "cgclif_calls_rustc", "cgclif_calls_cc", "cc_calls_cgclif"]; + + let mut cmd = Command::new("cargo"); + cmd.arg("run"); + cmd.arg("--target"); + cmd.arg(target_triple); + cmd.arg("--"); + cmd.arg("--pairs"); + cmd.args(pairs); + cmd.arg("--add-rustc-codegen-backend"); + cmd.arg(format!("cgclif:{}", cg_clif_dylib_path.display())); + + spawn_and_wait(cmd); +} diff --git a/build_system/build_backend.rs b/build_system/build_backend.rs index 48faec8bc4b94..9e59b8199b412 100644 --- a/build_system/build_backend.rs +++ b/build_system/build_backend.rs @@ -2,6 +2,8 @@ use std::env; use std::path::{Path, PathBuf}; use std::process::Command; +use super::utils::is_ci; + pub(crate) fn build_backend( channel: &str, host_triple: &str, @@ -14,7 +16,7 @@ pub(crate) fn build_backend( let mut rustflags = env::var("RUSTFLAGS").unwrap_or_default(); - if env::var("CI").as_ref().map(|val| &**val) == Ok("true") { + if is_ci() { // Deny warnings on CI rustflags += " -Dwarnings"; diff --git a/build_system/build_sysroot.rs b/build_system/build_sysroot.rs index 16cce83dd9c85..7e205b0fd0b3b 100644 --- a/build_system/build_sysroot.rs +++ b/build_system/build_sysroot.rs @@ -2,7 +2,7 @@ use std::fs; use std::path::{Path, PathBuf}; use std::process::{self, Command}; -use super::rustc_info::{get_file_name, get_rustc_version}; +use super::rustc_info::{get_file_name, get_rustc_version, get_wrapper_file_name}; use super::utils::{spawn_and_wait, try_hard_link}; use super::SysrootKind; @@ -10,10 +10,12 @@ pub(crate) fn build_sysroot( channel: &str, sysroot_kind: SysrootKind, target_dir: &Path, - cg_clif_build_dir: PathBuf, + cg_clif_build_dir: &Path, host_triple: &str, target_triple: &str, ) { + eprintln!("[BUILD] sysroot {:?}", sysroot_kind); + if target_dir.exists() { fs::remove_dir_all(target_dir).unwrap(); } @@ -35,11 +37,13 @@ pub(crate) fn build_sysroot( // Build and copy rustc and cargo wrappers for wrapper in ["rustc-clif", "cargo-clif"] { + let wrapper_name = get_wrapper_file_name(wrapper, "bin"); + let mut build_cargo_wrapper_cmd = Command::new("rustc"); build_cargo_wrapper_cmd .arg(PathBuf::from("scripts").join(format!("{wrapper}.rs"))) .arg("-o") - .arg(target_dir.join(wrapper)) + .arg(target_dir.join(wrapper_name)) .arg("-g"); spawn_and_wait(build_cargo_wrapper_cmd); } diff --git a/build_system/mod.rs b/build_system/mod.rs index b897b7fbacfcd..c3706dc6f8203 100644 --- a/build_system/mod.rs +++ b/build_system/mod.rs @@ -2,11 +2,15 @@ use std::env; use std::path::PathBuf; use std::process; +use self::utils::is_ci; + +mod abi_checker; mod build_backend; mod build_sysroot; mod config; mod prepare; mod rustc_info; +mod tests; mod utils; fn usage() { @@ -15,6 +19,9 @@ fn usage() { eprintln!( " ./y.rs build [--debug] [--sysroot none|clif|llvm] [--target-dir DIR] [--no-unstable-features]" ); + eprintln!( + " ./y.rs test [--debug] [--sysroot none|clif|llvm] [--target-dir DIR] [--no-unstable-features]" + ); } macro_rules! arg_error { @@ -25,11 +32,13 @@ macro_rules! arg_error { }}; } +#[derive(PartialEq, Debug)] enum Command { Build, + Test, } -#[derive(Copy, Clone)] +#[derive(Copy, Clone, Debug)] pub(crate) enum SysrootKind { None, Clif, @@ -42,16 +51,22 @@ pub fn main() { // The target dir is expected in the default location. Guard against the user changing it. env::set_var("CARGO_TARGET_DIR", "target"); + if is_ci() { + // Disabling incr comp reduces cache size and incr comp doesn't save as much on CI anyway + env::set_var("CARGO_BUILD_INCREMENTAL", "false"); + } + let mut args = env::args().skip(1); let command = match args.next().as_deref() { Some("prepare") => { if args.next().is_some() { - arg_error!("./x.rs prepare doesn't expect arguments"); + arg_error!("./y.rs prepare doesn't expect arguments"); } prepare::prepare(); process::exit(0); } Some("build") => Command::Build, + Some("test") => Command::Test, Some(flag) if flag.starts_with('-') => arg_error!("Expected command found flag {}", flag), Some(command) => arg_error!("Unknown command {}", command), None => { @@ -117,12 +132,35 @@ pub fn main() { let cg_clif_build_dir = build_backend::build_backend(channel, &host_triple, use_unstable_features); - build_sysroot::build_sysroot( - channel, - sysroot_kind, - &target_dir, - cg_clif_build_dir, - &host_triple, - &target_triple, - ); + match command { + Command::Test => { + tests::run_tests( + channel, + sysroot_kind, + &target_dir, + &cg_clif_build_dir, + &host_triple, + &target_triple, + ); + + abi_checker::run( + channel, + sysroot_kind, + &target_dir, + &cg_clif_build_dir, + &host_triple, + &target_triple, + ); + } + Command::Build => { + build_sysroot::build_sysroot( + channel, + sysroot_kind, + &target_dir, + &cg_clif_build_dir, + &host_triple, + &target_triple, + ); + } + } } diff --git a/build_system/prepare.rs b/build_system/prepare.rs index 8bb00352d3fe3..d23b7f00dcf16 100644 --- a/build_system/prepare.rs +++ b/build_system/prepare.rs @@ -14,6 +14,14 @@ pub(crate) fn prepare() { eprintln!("[INSTALL] hyperfine"); Command::new("cargo").arg("install").arg("hyperfine").spawn().unwrap().wait().unwrap(); + clone_repo_shallow_github( + "abi-checker", + "Gankra", + "abi-checker", + "a2232d45f202846f5c02203c9f27355360f9a2ff", + ); + apply_patches("abi-checker", Path::new("abi-checker")); + clone_repo_shallow_github( "rand", "rust-random", @@ -50,8 +58,7 @@ pub(crate) fn prepare() { spawn_and_wait(build_cmd); fs::copy( Path::new("simple-raytracer/target/debug").join(get_file_name("main", "bin")), - // FIXME use get_file_name here too once testing is migrated to rust - "simple-raytracer/raytracer_cg_llvm", + Path::new("simple-raytracer").join(get_file_name("raytracer_cg_llvm", "bin")), ) .unwrap(); } diff --git a/build_system/rustc_info.rs b/build_system/rustc_info.rs index 9206bb02bd3da..913b589afcc87 100644 --- a/build_system/rustc_info.rs +++ b/build_system/rustc_info.rs @@ -63,3 +63,12 @@ pub(crate) fn get_file_name(crate_name: &str, crate_type: &str) -> String { assert!(file_name.contains(crate_name)); file_name } + +/// Similar to `get_file_name`, but converts any dashes (`-`) in the `crate_name` to +/// underscores (`_`). This is specially made for the the rustc and cargo wrappers +/// which have a dash in the name, and that is not allowed in a crate name. +pub(crate) fn get_wrapper_file_name(crate_name: &str, crate_type: &str) -> String { + let crate_name = crate_name.replace('-', "_"); + let wrapper_name = get_file_name(&crate_name, crate_type); + wrapper_name.replace('_', "-") +} diff --git a/build_system/tests.rs b/build_system/tests.rs new file mode 100644 index 0000000000000..dc83b10958e01 --- /dev/null +++ b/build_system/tests.rs @@ -0,0 +1,618 @@ +use super::build_sysroot; +use super::config; +use super::rustc_info::get_wrapper_file_name; +use super::utils::{spawn_and_wait, spawn_and_wait_with_input}; +use build_system::SysrootKind; +use std::env; +use std::ffi::OsStr; +use std::fs; +use std::path::{Path, PathBuf}; +use std::process::Command; + +struct TestCase { + config: &'static str, + func: &'static dyn Fn(&TestRunner), +} + +impl TestCase { + const fn new(config: &'static str, func: &'static dyn Fn(&TestRunner)) -> Self { + Self { config, func } + } +} + +const NO_SYSROOT_SUITE: &[TestCase] = &[ + TestCase::new("build.mini_core", &|runner| { + runner.run_rustc([ + "example/mini_core.rs", + "--crate-name", + "mini_core", + "--crate-type", + "lib,dylib", + "--target", + &runner.target_triple, + ]); + }), + TestCase::new("build.example", &|runner| { + runner.run_rustc([ + "example/example.rs", + "--crate-type", + "lib", + "--target", + &runner.target_triple, + ]); + }), + TestCase::new("jit.mini_core_hello_world", &|runner| { + let mut jit_cmd = runner.rustc_command([ + "-Zunstable-options", + "-Cllvm-args=mode=jit", + "-Cprefer-dynamic", + "example/mini_core_hello_world.rs", + "--cfg", + "jit", + "--target", + &runner.host_triple, + ]); + jit_cmd.env("CG_CLIF_JIT_ARGS", "abc bcd"); + spawn_and_wait(jit_cmd); + + eprintln!("[JIT-lazy] mini_core_hello_world"); + let mut jit_cmd = runner.rustc_command([ + "-Zunstable-options", + "-Cllvm-args=mode=jit-lazy", + "-Cprefer-dynamic", + "example/mini_core_hello_world.rs", + "--cfg", + "jit", + "--target", + &runner.host_triple, + ]); + jit_cmd.env("CG_CLIF_JIT_ARGS", "abc bcd"); + spawn_and_wait(jit_cmd); + }), + TestCase::new("aot.mini_core_hello_world", &|runner| { + runner.run_rustc([ + "example/mini_core_hello_world.rs", + "--crate-name", + "mini_core_hello_world", + "--crate-type", + "bin", + "-g", + "--target", + &runner.target_triple, + ]); + runner.run_out_command("mini_core_hello_world", ["abc", "bcd"]); + }), +]; + +const BASE_SYSROOT_SUITE: &[TestCase] = &[ + TestCase::new("aot.arbitrary_self_types_pointers_and_wrappers", &|runner| { + runner.run_rustc([ + "example/arbitrary_self_types_pointers_and_wrappers.rs", + "--crate-name", + "arbitrary_self_types_pointers_and_wrappers", + "--crate-type", + "bin", + "--target", + &runner.target_triple, + ]); + runner.run_out_command("arbitrary_self_types_pointers_and_wrappers", []); + }), + TestCase::new("aot.issue_91827_extern_types", &|runner| { + runner.run_rustc([ + "example/issue-91827-extern-types.rs", + "--crate-name", + "issue_91827_extern_types", + "--crate-type", + "bin", + "--target", + &runner.target_triple, + ]); + runner.run_out_command("issue_91827_extern_types", []); + }), + TestCase::new("build.alloc_system", &|runner| { + runner.run_rustc([ + "example/alloc_system.rs", + "--crate-type", + "lib", + "--target", + &runner.target_triple, + ]); + }), + TestCase::new("aot.alloc_example", &|runner| { + runner.run_rustc([ + "example/alloc_example.rs", + "--crate-type", + "bin", + "--target", + &runner.target_triple, + ]); + runner.run_out_command("alloc_example", []); + }), + TestCase::new("jit.std_example", &|runner| { + runner.run_rustc([ + "-Zunstable-options", + "-Cllvm-args=mode=jit", + "-Cprefer-dynamic", + "example/std_example.rs", + "--target", + &runner.host_triple, + ]); + + eprintln!("[JIT-lazy] std_example"); + runner.run_rustc([ + "-Zunstable-options", + "-Cllvm-args=mode=jit-lazy", + "-Cprefer-dynamic", + "example/std_example.rs", + "--target", + &runner.host_triple, + ]); + }), + TestCase::new("aot.std_example", &|runner| { + runner.run_rustc([ + "example/std_example.rs", + "--crate-type", + "bin", + "--target", + &runner.target_triple, + ]); + runner.run_out_command("std_example", ["arg"]); + }), + TestCase::new("aot.dst_field_align", &|runner| { + runner.run_rustc([ + "example/dst-field-align.rs", + "--crate-name", + "dst_field_align", + "--crate-type", + "bin", + "--target", + &runner.target_triple, + ]); + runner.run_out_command("dst_field_align", []); + }), + TestCase::new("aot.subslice-patterns-const-eval", &|runner| { + runner.run_rustc([ + "example/subslice-patterns-const-eval.rs", + "--crate-type", + "bin", + "-Cpanic=abort", + "--target", + &runner.target_triple, + ]); + runner.run_out_command("subslice-patterns-const-eval", []); + }), + TestCase::new("aot.track-caller-attribute", &|runner| { + runner.run_rustc([ + "example/track-caller-attribute.rs", + "--crate-type", + "bin", + "-Cpanic=abort", + "--target", + &runner.target_triple, + ]); + runner.run_out_command("track-caller-attribute", []); + }), + TestCase::new("aot.float-minmax-pass", &|runner| { + runner.run_rustc([ + "example/float-minmax-pass.rs", + "--crate-type", + "bin", + "-Cpanic=abort", + "--target", + &runner.target_triple, + ]); + runner.run_out_command("float-minmax-pass", []); + }), + TestCase::new("aot.mod_bench", &|runner| { + runner.run_rustc([ + "example/mod_bench.rs", + "--crate-type", + "bin", + "--target", + &runner.target_triple, + ]); + runner.run_out_command("mod_bench", []); + }), +]; + +const EXTENDED_SYSROOT_SUITE: &[TestCase] = &[ + TestCase::new("test.rust-random/rand", &|runner| { + runner.in_dir(["rand"], |runner| { + runner.run_cargo(["clean"]); + + if runner.host_triple == runner.target_triple { + eprintln!("[TEST] rust-random/rand"); + runner.run_cargo(["test", "--workspace"]); + } else { + eprintln!("[AOT] rust-random/rand"); + runner.run_cargo([ + "build", + "--workspace", + "--target", + &runner.target_triple, + "--tests", + ]); + } + }); + }), + TestCase::new("bench.simple-raytracer", &|runner| { + runner.in_dir(["simple-raytracer"], |runner| { + let run_runs = env::var("RUN_RUNS").unwrap_or("10".to_string()); + + if runner.host_triple == runner.target_triple { + eprintln!("[BENCH COMPILE] ebobby/simple-raytracer"); + let mut bench_compile = Command::new("hyperfine"); + bench_compile.arg("--runs"); + bench_compile.arg(&run_runs); + bench_compile.arg("--warmup"); + bench_compile.arg("1"); + bench_compile.arg("--prepare"); + bench_compile.arg(format!("{:?}", runner.cargo_command(["clean"]))); + + if cfg!(windows) { + bench_compile.arg("cmd /C \"set RUSTFLAGS= && cargo build\""); + } else { + bench_compile.arg("RUSTFLAGS='' cargo build"); + } + + bench_compile.arg(format!("{:?}", runner.cargo_command(["build"]))); + spawn_and_wait(bench_compile); + + eprintln!("[BENCH RUN] ebobby/simple-raytracer"); + fs::copy(PathBuf::from("./target/debug/main"), PathBuf::from("raytracer_cg_clif")) + .unwrap(); + + let mut bench_run = Command::new("hyperfine"); + bench_run.arg("--runs"); + bench_run.arg(&run_runs); + bench_run.arg(PathBuf::from("./raytracer_cg_llvm")); + bench_run.arg(PathBuf::from("./raytracer_cg_clif")); + spawn_and_wait(bench_run); + } else { + runner.run_cargo(["clean"]); + eprintln!("[BENCH COMPILE] ebobby/simple-raytracer (skipped)"); + eprintln!("[COMPILE] ebobby/simple-raytracer"); + runner.run_cargo(["build", "--target", &runner.target_triple]); + eprintln!("[BENCH RUN] ebobby/simple-raytracer (skipped)"); + } + }); + }), + TestCase::new("test.libcore", &|runner| { + runner.in_dir(["build_sysroot", "sysroot_src", "library", "core", "tests"], |runner| { + runner.run_cargo(["clean"]); + + if runner.host_triple == runner.target_triple { + runner.run_cargo(["test"]); + } else { + eprintln!("Cross-Compiling: Not running tests"); + runner.run_cargo(["build", "--target", &runner.target_triple, "--tests"]); + } + }); + }), + TestCase::new("test.regex-shootout-regex-dna", &|runner| { + runner.in_dir(["regex"], |runner| { + runner.run_cargo(["clean"]); + + // newer aho_corasick versions throw a deprecation warning + let lint_rust_flags = format!("{} --cap-lints warn", runner.rust_flags); + + let mut build_cmd = runner.cargo_command([ + "build", + "--example", + "shootout-regex-dna", + "--target", + &runner.target_triple, + ]); + build_cmd.env("RUSTFLAGS", lint_rust_flags.clone()); + spawn_and_wait(build_cmd); + + if runner.host_triple == runner.target_triple { + let mut run_cmd = runner.cargo_command([ + "run", + "--example", + "shootout-regex-dna", + "--target", + &runner.target_triple, + ]); + run_cmd.env("RUSTFLAGS", lint_rust_flags); + + let input = + fs::read_to_string(PathBuf::from("examples/regexdna-input.txt")).unwrap(); + let expected_path = PathBuf::from("examples/regexdna-output.txt"); + let expected = fs::read_to_string(&expected_path).unwrap(); + + let output = spawn_and_wait_with_input(run_cmd, input); + // Make sure `[codegen mono items] start` doesn't poison the diff + let output = output + .lines() + .filter(|line| !line.contains("codegen mono items")) + .chain(Some("")) // This just adds the trailing newline + .collect::>() + .join("\r\n"); + + let output_matches = expected.lines().eq(output.lines()); + if !output_matches { + let res_path = PathBuf::from("res.txt"); + fs::write(&res_path, &output).unwrap(); + + if cfg!(windows) { + println!("Output files don't match!"); + println!("Expected Output:\n{}", expected); + println!("Actual Output:\n{}", output); + } else { + let mut diff = Command::new("diff"); + diff.arg("-u"); + diff.arg(res_path); + diff.arg(expected_path); + spawn_and_wait(diff); + } + + std::process::exit(1); + } + } + }); + }), + TestCase::new("test.regex", &|runner| { + runner.in_dir(["regex"], |runner| { + runner.run_cargo(["clean"]); + + // newer aho_corasick versions throw a deprecation warning + let lint_rust_flags = format!("{} --cap-lints warn", runner.rust_flags); + + if runner.host_triple == runner.target_triple { + let mut run_cmd = runner.cargo_command([ + "test", + "--tests", + "--", + "--exclude-should-panic", + "--test-threads", + "1", + "-Zunstable-options", + "-q", + ]); + run_cmd.env("RUSTFLAGS", lint_rust_flags); + spawn_and_wait(run_cmd); + } else { + eprintln!("Cross-Compiling: Not running tests"); + let mut build_cmd = + runner.cargo_command(["build", "--tests", "--target", &runner.target_triple]); + build_cmd.env("RUSTFLAGS", lint_rust_flags.clone()); + spawn_and_wait(build_cmd); + } + }); + }), + TestCase::new("test.portable-simd", &|runner| { + runner.in_dir(["portable-simd"], |runner| { + runner.run_cargo(["clean"]); + runner.run_cargo(["build", "--all-targets", "--target", &runner.target_triple]); + + if runner.host_triple == runner.target_triple { + runner.run_cargo(["test", "-q"]); + } + }); + }), +]; + +pub(crate) fn run_tests( + channel: &str, + sysroot_kind: SysrootKind, + target_dir: &Path, + cg_clif_build_dir: &Path, + host_triple: &str, + target_triple: &str, +) { + let runner = TestRunner::new(host_triple.to_string(), target_triple.to_string()); + + if config::get_bool("testsuite.no_sysroot") { + build_sysroot::build_sysroot( + channel, + SysrootKind::None, + &target_dir, + cg_clif_build_dir, + &host_triple, + &target_triple, + ); + + let _ = fs::remove_dir_all(Path::new("target").join("out")); + runner.run_testsuite(NO_SYSROOT_SUITE); + } else { + eprintln!("[SKIP] no_sysroot tests"); + } + + let run_base_sysroot = config::get_bool("testsuite.base_sysroot"); + let run_extended_sysroot = config::get_bool("testsuite.extended_sysroot"); + + if run_base_sysroot || run_extended_sysroot { + build_sysroot::build_sysroot( + channel, + sysroot_kind, + &target_dir, + cg_clif_build_dir, + &host_triple, + &target_triple, + ); + } + + if run_base_sysroot { + runner.run_testsuite(BASE_SYSROOT_SUITE); + } else { + eprintln!("[SKIP] base_sysroot tests"); + } + + if run_extended_sysroot { + runner.run_testsuite(EXTENDED_SYSROOT_SUITE); + } else { + eprintln!("[SKIP] extended_sysroot tests"); + } +} + +struct TestRunner { + root_dir: PathBuf, + out_dir: PathBuf, + jit_supported: bool, + rust_flags: String, + run_wrapper: Vec, + host_triple: String, + target_triple: String, +} + +impl TestRunner { + pub fn new(host_triple: String, target_triple: String) -> Self { + let root_dir = env::current_dir().unwrap(); + + let mut out_dir = root_dir.clone(); + out_dir.push("target"); + out_dir.push("out"); + + let is_native = host_triple == target_triple; + let jit_supported = target_triple.contains("x86_64") && is_native && !host_triple.contains("windows"); + + let mut rust_flags = env::var("RUSTFLAGS").ok().unwrap_or("".to_string()); + let mut run_wrapper = Vec::new(); + + if !is_native { + match target_triple.as_str() { + "aarch64-unknown-linux-gnu" => { + // We are cross-compiling for aarch64. Use the correct linker and run tests in qemu. + rust_flags = format!("-Clinker=aarch64-linux-gnu-gcc{}", rust_flags); + run_wrapper = vec!["qemu-aarch64", "-L", "/usr/aarch64-linux-gnu"]; + } + "x86_64-pc-windows-gnu" => { + // We are cross-compiling for Windows. Run tests in wine. + run_wrapper = vec!["wine"]; + } + _ => { + println!("Unknown non-native platform"); + } + } + } + + // FIXME fix `#[linkage = "extern_weak"]` without this + if host_triple.contains("darwin") { + rust_flags = format!("{} -Clink-arg=-undefined -Clink-arg=dynamic_lookup", rust_flags); + } + + Self { + root_dir, + out_dir, + jit_supported, + rust_flags, + run_wrapper: run_wrapper.iter().map(|s| s.to_string()).collect(), + host_triple, + target_triple, + } + } + + pub fn run_testsuite(&self, tests: &[TestCase]) { + for &TestCase { config, func } in tests { + let (tag, testname) = config.split_once('.').unwrap(); + let tag = tag.to_uppercase(); + let is_jit_test = tag == "JIT"; + + if !config::get_bool(config) || (is_jit_test && !self.jit_supported) { + eprintln!("[{tag}] {testname} (skipped)"); + continue; + } else { + eprintln!("[{tag}] {testname}"); + } + + func(self); + } + } + + fn in_dir<'a, I, F>(&self, dir: I, callback: F) + where + I: IntoIterator, + F: FnOnce(&TestRunner), + { + let current = env::current_dir().unwrap(); + let mut new = current.clone(); + for d in dir { + new.push(d); + } + + env::set_current_dir(new).unwrap(); + callback(self); + env::set_current_dir(current).unwrap(); + } + + fn rustc_command(&self, args: I) -> Command + where + I: IntoIterator, + S: AsRef, + { + let mut rustc_clif = self.root_dir.clone(); + rustc_clif.push("build"); + rustc_clif.push(get_wrapper_file_name("rustc-clif", "bin")); + + let mut cmd = Command::new(rustc_clif); + cmd.args(self.rust_flags.split_whitespace()); + cmd.arg("-L"); + cmd.arg(format!("crate={}", self.out_dir.display())); + cmd.arg("--out-dir"); + cmd.arg(format!("{}", self.out_dir.display())); + cmd.arg("-Cdebuginfo=2"); + cmd.args(args); + cmd + } + + fn run_rustc(&self, args: I) + where + I: IntoIterator, + S: AsRef, + { + spawn_and_wait(self.rustc_command(args)); + } + + fn run_out_command<'a, I>(&self, name: &str, args: I) + where + I: IntoIterator, + { + let mut full_cmd = vec![]; + + // Prepend the RUN_WRAPPER's + if !self.run_wrapper.is_empty() { + full_cmd.extend(self.run_wrapper.iter().cloned()); + } + + full_cmd.push({ + let mut out_path = self.out_dir.clone(); + out_path.push(name); + out_path.to_str().unwrap().to_string() + }); + + for arg in args.into_iter() { + full_cmd.push(arg.to_string()); + } + + let mut cmd_iter = full_cmd.into_iter(); + let first = cmd_iter.next().unwrap(); + + let mut cmd = Command::new(first); + cmd.args(cmd_iter); + + spawn_and_wait(cmd); + } + + fn cargo_command(&self, args: I) -> Command + where + I: IntoIterator, + S: AsRef, + { + let mut cargo_clif = self.root_dir.clone(); + cargo_clif.push("build"); + cargo_clif.push(get_wrapper_file_name("cargo-clif", "bin")); + + let mut cmd = Command::new(cargo_clif); + cmd.args(args); + cmd.env("RUSTFLAGS", &self.rust_flags); + cmd + } + + fn run_cargo<'a, I>(&self, args: I) + where + I: IntoIterator, + { + spawn_and_wait(self.cargo_command(args)); + } +} diff --git a/build_system/utils.rs b/build_system/utils.rs index 12b5d70fad853..bdf8f8ecd9970 100644 --- a/build_system/utils.rs +++ b/build_system/utils.rs @@ -1,6 +1,8 @@ +use std::env; use std::fs; +use std::io::Write; use std::path::Path; -use std::process::{self, Command}; +use std::process::{self, Command, Stdio}; #[track_caller] pub(crate) fn try_hard_link(src: impl AsRef, dst: impl AsRef) { @@ -18,6 +20,27 @@ pub(crate) fn spawn_and_wait(mut cmd: Command) { } } +#[track_caller] +pub(crate) fn spawn_and_wait_with_input(mut cmd: Command, input: String) -> String { + let mut child = cmd + .stdin(Stdio::piped()) + .stdout(Stdio::piped()) + .spawn() + .expect("Failed to spawn child process"); + + let mut stdin = child.stdin.take().expect("Failed to open stdin"); + std::thread::spawn(move || { + stdin.write_all(input.as_bytes()).expect("Failed to write to stdin"); + }); + + let output = child.wait_with_output().expect("Failed to read stdout"); + if !output.status.success() { + process::exit(1); + } + + String::from_utf8(output.stdout).unwrap() +} + pub(crate) fn copy_dir_recursively(from: &Path, to: &Path) { for entry in fs::read_dir(from).unwrap() { let entry = entry.unwrap(); @@ -33,3 +56,7 @@ pub(crate) fn copy_dir_recursively(from: &Path, to: &Path) { } } } + +pub(crate) fn is_ci() -> bool { + env::var("CI").as_ref().map(|val| &**val) == Ok("true") +} diff --git a/clean_all.sh b/clean_all.sh index ea1f8c1e8920a..62e52bd195800 100755 --- a/clean_all.sh +++ b/clean_all.sh @@ -3,4 +3,4 @@ set -e rm -rf build_sysroot/{sysroot_src/,target/,compiler-builtins/,rustc_version} rm -rf target/ build/ perf.data{,.old} y.bin -rm -rf rand/ regex/ simple-raytracer/ portable-simd/ +rm -rf rand/ regex/ simple-raytracer/ portable-simd/ abi-checker/ diff --git a/config.txt b/config.txt index b14db27d6206f..2264d301d5920 100644 --- a/config.txt +++ b/config.txt @@ -15,3 +15,38 @@ # This option can be changed while the build system is already running for as long as sysroot # building hasn't started yet. #keep_sysroot + + +# Testsuite +# +# Each test suite item has a corresponding key here. The default is to run all tests. +# Comment any of these lines to skip individual tests. + +testsuite.no_sysroot +build.mini_core +build.example +jit.mini_core_hello_world +aot.mini_core_hello_world + +testsuite.base_sysroot +aot.arbitrary_self_types_pointers_and_wrappers +aot.issue_91827_extern_types +build.alloc_system +aot.alloc_example +jit.std_example +aot.std_example +aot.dst_field_align +aot.subslice-patterns-const-eval +aot.track-caller-attribute +aot.float-minmax-pass +aot.mod_bench + +testsuite.extended_sysroot +test.rust-random/rand +bench.simple-raytracer +test.libcore +test.regex-shootout-regex-dna +test.regex +test.portable-simd + +testsuite.abi-checker diff --git a/example/mini_core.rs b/example/mini_core.rs index 8b6042a3d6638..42f8aa50ba1a9 100644 --- a/example/mini_core.rs +++ b/example/mini_core.rs @@ -535,7 +535,7 @@ unsafe fn allocate(size: usize, _align: usize) -> *mut u8 { } #[lang = "box_free"] -unsafe fn box_free(ptr: Unique, alloc: ()) { +unsafe fn box_free(ptr: Unique, _alloc: ()) { libc::free(ptr.pointer.0 as *mut u8); } @@ -575,11 +575,19 @@ pub mod intrinsics { } pub mod libc { + // With the new Universal CRT, msvc has switched to all the printf functions being inline wrapper + // functions. legacy_stdio_definitions.lib which provides the printf wrapper functions as normal + // symbols to link against. + #[cfg_attr(unix, link(name = "c"))] + #[cfg_attr(target_env="msvc", link(name="legacy_stdio_definitions"))] + extern "C" { + pub fn printf(format: *const i8, ...) -> i32; + } + #[cfg_attr(unix, link(name = "c"))] #[cfg_attr(target_env = "msvc", link(name = "msvcrt"))] extern "C" { pub fn puts(s: *const i8) -> i32; - pub fn printf(format: *const i8, ...) -> i32; pub fn malloc(size: usize) -> *mut u8; pub fn free(ptr: *mut u8); pub fn memcpy(dst: *mut u8, src: *const u8, size: usize); diff --git a/example/mini_core_hello_world.rs b/example/mini_core_hello_world.rs index aa1f239bae23e..e83be3a3df5c4 100644 --- a/example/mini_core_hello_world.rs +++ b/example/mini_core_hello_world.rs @@ -139,7 +139,7 @@ pub struct bool_11 { field10: bool, } -extern "C" fn bool_struct_in_11(arg0: bool_11) {} +extern "C" fn bool_struct_in_11(_arg0: bool_11) {} #[allow(unreachable_code)] // FIXME false positive fn main() { @@ -321,7 +321,7 @@ fn main() { #[cfg(not(any(jit, windows)))] test_tls(); - #[cfg(all(not(jit), target_arch = "x86_64", target_os = "linux"))] + #[cfg(all(not(jit), target_arch = "x86_64", any(target_os = "linux", target_os = "darwin")))] unsafe { global_asm_test(); } @@ -343,7 +343,7 @@ fn main() { } } -#[cfg(all(not(jit), target_arch = "x86_64", target_os = "linux"))] +#[cfg(all(not(jit), target_arch = "x86_64", any(target_os = "linux", target_os = "darwin")))] extern "C" { fn global_asm_test(); } @@ -358,6 +358,16 @@ global_asm! { " } +#[cfg(all(not(jit), target_arch = "x86_64", target_os = "darwin"))] +global_asm! { + " + .global _global_asm_test + _global_asm_test: + // comment that would normally be removed by LLVM + ret + " +} + #[repr(C)] enum c_void { _1, @@ -375,6 +385,7 @@ struct pthread_attr_t { } #[link(name = "pthread")] +#[cfg(unix)] extern "C" { fn pthread_attr_init(attr: *mut pthread_attr_t) -> c_int; @@ -391,6 +402,91 @@ extern "C" { ) -> c_int; } +type DWORD = u32; +type LPDWORD = *mut u32; + +type LPVOID = *mut c_void; +type HANDLE = *mut c_void; + +#[link(name = "msvcrt")] +#[cfg(windows)] +extern "C" { + fn WaitForSingleObject( + hHandle: LPVOID, + dwMilliseconds: DWORD + ) -> DWORD; + + fn CreateThread( + lpThreadAttributes: LPVOID, // Technically LPSECURITY_ATTRIBUTES, but we don't use it anyway + dwStackSize: usize, + lpStartAddress: extern "C" fn(_: *mut c_void) -> *mut c_void, + lpParameter: LPVOID, + dwCreationFlags: DWORD, + lpThreadId: LPDWORD + ) -> HANDLE; +} + +struct Thread { + #[cfg(windows)] + handle: HANDLE, + #[cfg(unix)] + handle: pthread_t, +} + +impl Thread { + unsafe fn create(f: extern "C" fn(_: *mut c_void) -> *mut c_void) -> Self { + #[cfg(unix)] + { + let mut attr: pthread_attr_t = zeroed(); + let mut thread: pthread_t = 0; + + if pthread_attr_init(&mut attr) != 0 { + assert!(false); + } + + if pthread_create(&mut thread, &attr, f, 0 as *mut c_void) != 0 { + assert!(false); + } + + Thread { + handle: thread, + } + } + + #[cfg(windows)] + { + let handle = CreateThread(0 as *mut c_void, 0, f, 0 as *mut c_void, 0, 0 as *mut u32); + + if (handle as u64) == 0 { + assert!(false); + } + + Thread { + handle, + } + } + } + + + unsafe fn join(self) { + #[cfg(unix)] + { + let mut res = 0 as *mut c_void; + pthread_join(self.handle, &mut res); + } + + #[cfg(windows)] + { + // The INFINITE macro is used to signal operations that do not timeout. + let infinite = 0xffffffff; + assert!(WaitForSingleObject(self.handle, infinite) == 0); + } + } +} + + + + #[thread_local] #[cfg(not(jit))] static mut TLS: u8 = 42; @@ -404,21 +500,10 @@ extern "C" fn mutate_tls(_: *mut c_void) -> *mut c_void { #[cfg(not(jit))] fn test_tls() { unsafe { - let mut attr: pthread_attr_t = zeroed(); - let mut thread: pthread_t = 0; - assert_eq!(TLS, 42); - if pthread_attr_init(&mut attr) != 0 { - assert!(false); - } - - if pthread_create(&mut thread, &attr, mutate_tls, 0 as *mut c_void) != 0 { - assert!(false); - } - - let mut res = 0 as *mut c_void; - pthread_join(thread, &mut res); + let thread = Thread::create(mutate_tls); + thread.join(); // TLS of main thread must not have been changed by the other thread. assert_eq!(TLS, 42); diff --git a/patches/0001-abi-checker-Disable-failing-tests.patch b/patches/0001-abi-checker-Disable-failing-tests.patch new file mode 100644 index 0000000000000..526366a759876 --- /dev/null +++ b/patches/0001-abi-checker-Disable-failing-tests.patch @@ -0,0 +1,36 @@ +From 1a315ba225577dbbd1f449d9609f16f984f68708 Mon Sep 17 00:00:00 2001 +From: Afonso Bordado +Date: Fri, 12 Aug 2022 22:51:58 +0000 +Subject: [PATCH] Disable abi-checker tests + +--- + src/report.rs | 14 ++++++++++++++ + 1 file changed, 14 insertions(+) + +diff --git a/src/report.rs b/src/report.rs +index 7346f5e..8347762 100644 +--- a/src/report.rs ++++ b/src/report.rs +@@ -45,6 +45,20 @@ pub fn get_test_rules(test: &TestKey, caller: &dyn AbiImpl, callee: &dyn AbiImpl + // + // THIS AREA RESERVED FOR VENDORS TO APPLY PATCHES + ++ // Currently MSVC has some broken ABI issues. Furthermore, they cause ++ // a STATUS_ACCESS_VIOLATION, so we can't even run them. Ensure that they compile and link. ++ if cfg!(windows) && (test.test_name == "bool" || test.test_name == "ui128") { ++ result.run = Link; ++ result.check = Pass(Link); ++ } ++ ++ // structs is broken in the current release of cranelift for aarch64. ++ // It has been fixed for cranelift 0.88: https://github.com/bytecodealliance/wasmtime/pull/4634 ++ if cfg!(target_arch = "aarch64") && test.test_name == "structs" { ++ result.run = Link; ++ result.check = Pass(Link); ++ } ++ + // END OF VENDOR RESERVED AREA + // + // +-- +2.34.1 diff --git a/patches/0023-sysroot-Ignore-failing-tests.patch b/patches/0023-sysroot-Ignore-failing-tests.patch index 50ef0bd9418c7..f3cd7ee77e26e 100644 --- a/patches/0023-sysroot-Ignore-failing-tests.patch +++ b/patches/0023-sysroot-Ignore-failing-tests.patch @@ -46,5 +46,17 @@ index 4bc44e9..8e3c7a4 100644 #[test] fn cell_allows_array_cycle() { +diff --git a/library/core/tests/atomic.rs b/library/core/tests/atomic.rs +index 13b12db..96fe4b9 100644 +--- a/library/core/tests/atomic.rs ++++ b/library/core/tests/atomic.rs +@@ -185,6 +185,7 @@ fn ptr_bitops() { + } + + #[test] ++#[cfg_attr(target_arch = "s390x", ignore)] // s390x backend doesn't support stack alignment >8 bytes + #[cfg(any(not(target_arch = "arm"), target_os = "linux"))] // Missing intrinsic in compiler-builtins + fn ptr_bitops_tagging() { + #[repr(align(16))] -- 2.21.0 (Apple Git-122) diff --git a/rust-toolchain b/rust-toolchain index 3ab395d89d50e..14f2746ecb19f 100644 --- a/rust-toolchain +++ b/rust-toolchain @@ -1,3 +1,3 @@ [toolchain] -channel = "nightly-2022-07-25" +channel = "nightly-2022-08-24" components = ["rust-src", "rustc-dev", "llvm-tools-preview"] diff --git a/scripts/tests.sh b/scripts/tests.sh deleted file mode 100755 index 9b5ffa4096049..0000000000000 --- a/scripts/tests.sh +++ /dev/null @@ -1,203 +0,0 @@ -#!/usr/bin/env bash - -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='' - -case "$TARGET_TRIPLE" in - x86_64*) - export JIT_SUPPORTED=1 - ;; - *) - export JIT_SUPPORTED=0 - ;; -esac - -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 - -MY_RUSTC="$(pwd)/build/rustc-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] issue_91827_extern_types" - $MY_RUSTC example/issue-91827-extern-types.rs --crate-name issue_91827_extern_types --crate-type bin --target "$TARGET_TRIPLE" - $RUN_WRAPPER ./target/out/issue_91827_extern_types - - echo "[BUILD] 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] std_example" - $MY_RUSTC example/std_example.rs --crate-type bin --target "$TARGET_TRIPLE" - $RUN_WRAPPER ./target/out/std_example arg - - echo "[AOT] dst_field_align" - $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 "[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] float-minmax-pass" - $MY_RUSTC example/float-minmax-pass.rs --crate-type bin -Cpanic=abort --target "$TARGET_TRIPLE" - $RUN_WRAPPER ./target/out/float-minmax-pass - - 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-clif clean - if [[ "$HOST_TRIPLE" = "$TARGET_TRIPLE" ]]; then - echo "[TEST] rust-random/rand" - ../build/cargo-clif test --workspace - else - echo "[AOT] rust-random/rand" - ../build/cargo-clif 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-clif clean" \ - "RUSTFLAGS='' cargo build" \ - "../build/cargo-clif 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-clif clean - echo "[BENCH COMPILE] ebobby/simple-raytracer (skipped)" - echo "[COMPILE] ebobby/simple-raytracer" - ../build/cargo-clif 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-clif clean - if [[ "$HOST_TRIPLE" = "$TARGET_TRIPLE" ]]; then - ../../../../../build/cargo-clif test - else - ../../../../../build/cargo-clif build --target $TARGET_TRIPLE --tests - fi - popd - - pushd regex - echo "[TEST] rust-lang/regex example shootout-regex-dna" - ../build/cargo-clif 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-clif build --example shootout-regex-dna --target $TARGET_TRIPLE - if [[ "$HOST_TRIPLE" = "$TARGET_TRIPLE" ]]; then - cat examples/regexdna-input.txt \ - | ../build/cargo-clif 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-clif test --tests -- --exclude-should-panic --test-threads 1 -Zunstable-options -q - else - echo "[AOT] rust-lang/regex tests" - ../build/cargo-clif build --tests --target $TARGET_TRIPLE - fi - popd - - pushd portable-simd - echo "[TEST] rust-lang/portable-simd" - ../build/cargo-clif clean - ../build/cargo-clif build --all-targets --target $TARGET_TRIPLE - if [[ "$HOST_TRIPLE" = "$TARGET_TRIPLE" ]]; then - ../build/cargo-clif 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 diff --git a/src/abi/pass_mode.rs b/src/abi/pass_mode.rs index 6c10baa53d415..f4ad76b3bab3c 100644 --- a/src/abi/pass_mode.rs +++ b/src/abi/pass_mode.rs @@ -23,7 +23,7 @@ fn reg_to_abi_param(reg: Reg) -> AbiParam { (RegKind::Integer, 9..=16) => types::I128, (RegKind::Float, 4) => types::F32, (RegKind::Float, 8) => types::F64, - (RegKind::Vector, size) => types::I8.by(u16::try_from(size).unwrap()).unwrap(), + (RegKind::Vector, size) => types::I8.by(u32::try_from(size).unwrap()).unwrap(), _ => unreachable!("{:?}", reg), }; AbiParam::new(clif_ty) @@ -184,7 +184,7 @@ pub(super) fn from_casted_value<'tcx>( let abi_params = cast_target_to_abi_params(cast); let abi_param_size: u32 = abi_params.iter().map(|param| param.value_type.bytes()).sum(); let layout_size = u32::try_from(layout.size.bytes()).unwrap(); - let stack_slot = fx.bcx.create_stack_slot(StackSlotData { + let stack_slot = fx.bcx.create_sized_stack_slot(StackSlotData { kind: StackSlotKind::ExplicitSlot, // FIXME Don't force the size to a multiple of 16 bytes once Cranelift gets a way to // specify stack slot alignment. @@ -193,7 +193,7 @@ pub(super) fn from_casted_value<'tcx>( // larger alignment than the integer. size: (std::cmp::max(abi_param_size, layout_size) + 15) / 16 * 16, }); - let ptr = Pointer::new(fx.bcx.ins().stack_addr(pointer_ty(fx.tcx), stack_slot, 0)); + let ptr = Pointer::stack_slot(stack_slot); let mut offset = 0; let mut block_params_iter = block_params.iter().copied(); for param in abi_params { diff --git a/src/base.rs b/src/base.rs index 122e103ff62bc..44c34d6c8cb79 100644 --- a/src/base.rs +++ b/src/base.rs @@ -6,21 +6,43 @@ use rustc_middle::ty::adjustment::PointerCast; use rustc_middle::ty::layout::FnAbiOf; use rustc_middle::ty::print::with_no_trimmed_paths; -use indexmap::IndexSet; - use crate::constant::ConstantCx; +use crate::debuginfo::FunctionDebugContext; use crate::prelude::*; use crate::pretty_clif::CommentWriter; -pub(crate) fn codegen_fn<'tcx>( - cx: &mut crate::CodegenCx<'tcx>, +pub(crate) struct CodegenedFunction { + symbol_name: String, + func_id: FuncId, + func: Function, + clif_comments: CommentWriter, + func_debug_cx: Option, +} + +#[cfg_attr(not(feature = "jit"), allow(dead_code))] +pub(crate) fn codegen_and_compile_fn<'tcx>( + tcx: TyCtxt<'tcx>, + cx: &mut crate::CodegenCx, + cached_context: &mut Context, module: &mut dyn Module, instance: Instance<'tcx>, ) { - let tcx = cx.tcx; - let _inst_guard = crate::PrintOnPanic(|| format!("{:?} {}", instance, tcx.symbol_name(instance).name)); + + let cached_func = std::mem::replace(&mut cached_context.func, Function::new()); + let codegened_func = codegen_fn(tcx, cx, cached_func, module, instance); + + compile_fn(cx, cached_context, module, codegened_func); +} + +pub(crate) fn codegen_fn<'tcx>( + tcx: TyCtxt<'tcx>, + cx: &mut crate::CodegenCx, + cached_func: Function, + module: &mut dyn Module, + instance: Instance<'tcx>, +) -> CodegenedFunction { debug_assert!(!instance.substs.needs_infer()); let mir = tcx.instance_mir(instance.def); @@ -34,15 +56,14 @@ pub(crate) fn codegen_fn<'tcx>( }); // Declare function - let symbol_name = tcx.symbol_name(instance); + let symbol_name = tcx.symbol_name(instance).name.to_string(); let sig = get_function_sig(tcx, module.isa().triple(), instance); - let func_id = module.declare_function(symbol_name.name, Linkage::Local, &sig).unwrap(); - - cx.cached_context.clear(); + let func_id = module.declare_function(&symbol_name, Linkage::Local, &sig).unwrap(); // Make the FunctionBuilder let mut func_ctx = FunctionBuilderContext::new(); - let mut func = std::mem::replace(&mut cx.cached_context.func, Function::new()); + let mut func = cached_func; + func.clear(); func.name = ExternalName::user(0, func_id.as_u32()); func.signature = sig; func.collect_debug_info(); @@ -59,6 +80,12 @@ pub(crate) fn codegen_fn<'tcx>( let pointer_type = target_config.pointer_type(); let clif_comments = crate::pretty_clif::CommentWriter::new(tcx, instance); + let func_debug_cx = if let Some(debug_context) = &mut cx.debug_context { + Some(debug_context.define_function(tcx, &symbol_name, mir.span)) + } else { + None + }; + let mut fx = FunctionCx { cx, module, @@ -66,6 +93,7 @@ pub(crate) fn codegen_fn<'tcx>( target_config, pointer_type, constants_cx: ConstantCx::new(), + func_debug_cx, instance, symbol_name, @@ -78,81 +106,48 @@ pub(crate) fn codegen_fn<'tcx>( caller_location: None, // set by `codegen_fn_prelude` clif_comments, - source_info_set: indexmap::IndexSet::new(), + last_source_file: None, next_ssa_var: 0, }; - let arg_uninhabited = fx - .mir - .args_iter() - .any(|arg| fx.layout_of(fx.monomorphize(fx.mir.local_decls[arg].ty)).abi.is_uninhabited()); - - if !crate::constant::check_constants(&mut fx) { - fx.bcx.append_block_params_for_function_params(fx.block_map[START_BLOCK]); - fx.bcx.switch_to_block(fx.block_map[START_BLOCK]); - crate::trap::trap_unreachable(&mut fx, "compilation should have been aborted"); - } else if arg_uninhabited { - fx.bcx.append_block_params_for_function_params(fx.block_map[START_BLOCK]); - fx.bcx.switch_to_block(fx.block_map[START_BLOCK]); - fx.bcx.ins().trap(TrapCode::UnreachableCodeReached); - } else { - tcx.sess.time("codegen clif ir", || { - tcx.sess - .time("codegen prelude", || crate::abi::codegen_fn_prelude(&mut fx, start_block)); - codegen_fn_content(&mut fx); - }); - } + tcx.sess.time("codegen clif ir", || codegen_fn_body(&mut fx, start_block)); // Recover all necessary data from fx, before accessing func will prevent future access to it. - let instance = fx.instance; + let symbol_name = fx.symbol_name; let clif_comments = fx.clif_comments; - let source_info_set = fx.source_info_set; - let local_map = fx.local_map; + let func_debug_cx = fx.func_debug_cx; fx.constants_cx.finalize(fx.tcx, &mut *fx.module); - crate::pretty_clif::write_clif_file( - tcx, - "unopt", - module.isa(), - instance, - &func, - &clif_comments, - ); + if cx.should_write_ir { + crate::pretty_clif::write_clif_file( + tcx.output_filenames(()), + &symbol_name, + "unopt", + module.isa(), + &func, + &clif_comments, + ); + } // Verify function verify_func(tcx, &clif_comments, &func); - compile_fn( - cx, - module, - instance, - symbol_name.name, - func_id, - func, - clif_comments, - source_info_set, - local_map, - ); + CodegenedFunction { symbol_name, func_id, func, clif_comments, func_debug_cx } } -fn compile_fn<'tcx>( - cx: &mut crate::CodegenCx<'tcx>, +pub(crate) fn compile_fn( + cx: &mut crate::CodegenCx, + cached_context: &mut Context, module: &mut dyn Module, - instance: Instance<'tcx>, - symbol_name: &str, - func_id: FuncId, - func: Function, - mut clif_comments: CommentWriter, - source_info_set: IndexSet, - local_map: IndexVec>, + codegened_func: CodegenedFunction, ) { - let tcx = cx.tcx; + let clif_comments = codegened_func.clif_comments; // Store function in context - let context = &mut cx.cached_context; + let context = cached_context; context.clear(); - context.func = func; + context.func = codegened_func.func; // If the return block is not reachable, then the SSA builder may have inserted an `iconst.i128` // instruction, which doesn't have an encoding. @@ -164,17 +159,6 @@ fn compile_fn<'tcx>( // invalidate it when it would change. context.domtree.clear(); - // Perform rust specific optimizations - tcx.sess.time("optimize clif ir", || { - crate::optimize::optimize_function( - tcx, - module.isa(), - instance, - context, - &mut clif_comments, - ); - }); - #[cfg(any())] // This is never true let _clif_guard = { use std::fmt::Write; @@ -203,46 +187,44 @@ fn compile_fn<'tcx>( }; // Define function - tcx.sess.time("define function", || { - context.want_disasm = crate::pretty_clif::should_write_ir(tcx); - module.define_function(func_id, context).unwrap(); + cx.profiler.verbose_generic_activity("define function").run(|| { + context.want_disasm = cx.should_write_ir; + module.define_function(codegened_func.func_id, context).unwrap(); }); - // Write optimized function to file for debugging - crate::pretty_clif::write_clif_file( - tcx, - "opt", - module.isa(), - instance, - &context.func, - &clif_comments, - ); + if cx.should_write_ir { + // Write optimized function to file for debugging + crate::pretty_clif::write_clif_file( + &cx.output_filenames, + &codegened_func.symbol_name, + "opt", + module.isa(), + &context.func, + &clif_comments, + ); - if let Some(disasm) = &context.mach_compile_result.as_ref().unwrap().disasm { - crate::pretty_clif::write_ir_file( - tcx, - || format!("{}.vcode", tcx.symbol_name(instance).name), - |file| file.write_all(disasm.as_bytes()), - ) + if let Some(disasm) = &context.compiled_code().unwrap().disasm { + crate::pretty_clif::write_ir_file( + &cx.output_filenames, + &format!("{}.vcode", codegened_func.symbol_name), + |file| file.write_all(disasm.as_bytes()), + ) + } } // Define debuginfo for function let isa = module.isa(); let debug_context = &mut cx.debug_context; let unwind_context = &mut cx.unwind_context; - tcx.sess.time("generate debug info", || { + cx.profiler.verbose_generic_activity("generate debug info").run(|| { if let Some(debug_context) = debug_context { - debug_context.define_function( - instance, - func_id, - symbol_name, - isa, + codegened_func.func_debug_cx.unwrap().finalize( + debug_context, + codegened_func.func_id, context, - &source_info_set, - local_map, ); } - unwind_context.add_function(func_id, &context, isa); + unwind_context.add_function(codegened_func.func_id, &context, isa); }); } @@ -268,7 +250,27 @@ pub(crate) fn verify_func( }); } -fn codegen_fn_content(fx: &mut FunctionCx<'_, '_, '_>) { +fn codegen_fn_body(fx: &mut FunctionCx<'_, '_, '_>, start_block: Block) { + if !crate::constant::check_constants(fx) { + fx.bcx.append_block_params_for_function_params(fx.block_map[START_BLOCK]); + fx.bcx.switch_to_block(fx.block_map[START_BLOCK]); + // compilation should have been aborted + fx.bcx.ins().trap(TrapCode::UnreachableCodeReached); + return; + } + + let arg_uninhabited = fx + .mir + .args_iter() + .any(|arg| fx.layout_of(fx.monomorphize(fx.mir.local_decls[arg].ty)).abi.is_uninhabited()); + if arg_uninhabited { + fx.bcx.append_block_params_for_function_params(fx.block_map[START_BLOCK]); + fx.bcx.switch_to_block(fx.block_map[START_BLOCK]); + fx.bcx.ins().trap(TrapCode::UnreachableCodeReached); + return; + } + fx.tcx.sess.time("codegen prelude", || crate::abi::codegen_fn_prelude(fx, start_block)); + for (bb, bb_data) in fx.mir.basic_blocks().iter_enumerated() { let block = fx.get_block(bb); fx.bcx.switch_to_block(block); @@ -457,17 +459,8 @@ fn codegen_fn_content(fx: &mut FunctionCx<'_, '_, '_>) { template, operands, *options, + *destination, ); - - match *destination { - Some(destination) => { - let destination_block = fx.get_block(destination); - fx.bcx.ins().jump(destination_block, &[]); - } - None => { - fx.bcx.ins().trap(TrapCode::UnreachableCodeReached); - } - } } TerminatorKind::Resume | TerminatorKind::Abort => { // FIXME implement unwinding @@ -711,9 +704,7 @@ fn codegen_stmt<'tcx>( Rvalue::Discriminant(place) => { let place = codegen_place(fx, place); let value = place.to_cvalue(fx); - let discr = - crate::discriminant::codegen_get_discriminant(fx, value, dest_layout); - lval.write_cvalue(fx, discr); + crate::discriminant::codegen_get_discriminant(fx, lval, value, dest_layout); } Rvalue::Repeat(ref operand, times) => { let operand = codegen_operand(fx, operand); diff --git a/src/common.rs b/src/common.rs index f9dc1b5169e1a..589594465783e 100644 --- a/src/common.rs +++ b/src/common.rs @@ -1,14 +1,18 @@ use cranelift_codegen::isa::TargetFrontendConfig; +use gimli::write::FileId; + +use rustc_data_structures::sync::Lrc; use rustc_index::vec::IndexVec; use rustc_middle::ty::layout::{ FnAbiError, FnAbiOfHelpers, FnAbiRequest, LayoutError, LayoutOfHelpers, }; -use rustc_middle::ty::SymbolName; +use rustc_span::SourceFile; use rustc_target::abi::call::FnAbi; use rustc_target::abi::{Integer, Primitive}; use rustc_target::spec::{HasTargetSpec, Target}; use crate::constant::ConstantCx; +use crate::debuginfo::FunctionDebugContext; use crate::prelude::*; pub(crate) fn pointer_ty(tcx: TyCtxt<'_>) -> types::Type { @@ -74,7 +78,7 @@ fn clif_type_from_ty<'tcx>(tcx: TyCtxt<'tcx>, ty: Ty<'tcx>) -> Option unreachable!(), }; - match scalar_to_clif_type(tcx, element).by(u16::try_from(count).unwrap()) { + match scalar_to_clif_type(tcx, element).by(u32::try_from(count).unwrap()) { // Cranelift currently only implements icmp for 128bit vectors. Some(vector_ty) if vector_ty.bits() == 128 => vector_ty, _ => return None, @@ -232,15 +236,16 @@ pub(crate) fn type_sign(ty: Ty<'_>) -> bool { } pub(crate) struct FunctionCx<'m, 'clif, 'tcx: 'm> { - pub(crate) cx: &'clif mut crate::CodegenCx<'tcx>, + pub(crate) cx: &'clif mut crate::CodegenCx, pub(crate) module: &'m mut dyn Module, pub(crate) tcx: TyCtxt<'tcx>, pub(crate) target_config: TargetFrontendConfig, // Cached from module pub(crate) pointer_type: Type, // Cached from module pub(crate) constants_cx: ConstantCx, + pub(crate) func_debug_cx: Option, pub(crate) instance: Instance<'tcx>, - pub(crate) symbol_name: SymbolName<'tcx>, + pub(crate) symbol_name: String, pub(crate) mir: &'tcx Body<'tcx>, pub(crate) fn_abi: Option<&'tcx FnAbi<'tcx, Ty<'tcx>>>, @@ -252,7 +257,11 @@ pub(crate) struct FunctionCx<'m, 'clif, 'tcx: 'm> { pub(crate) caller_location: Option>, pub(crate) clif_comments: crate::pretty_clif::CommentWriter, - pub(crate) source_info_set: indexmap::IndexSet, + + /// Last accessed source file and it's debuginfo file id. + /// + /// For optimization purposes only + pub(crate) last_source_file: Option<(Lrc, FileId)>, /// This should only be accessed by `CPlace::new_var`. pub(crate) next_ssa_var: u32, @@ -336,8 +345,31 @@ impl<'tcx> FunctionCx<'_, '_, 'tcx> { } pub(crate) fn set_debug_loc(&mut self, source_info: mir::SourceInfo) { - let (index, _) = self.source_info_set.insert_full(source_info); - self.bcx.set_srcloc(SourceLoc::new(index as u32)); + if let Some(debug_context) = &mut self.cx.debug_context { + let (file, line, column) = + DebugContext::get_span_loc(self.tcx, self.mir.span, source_info.span); + + // add_source_file is very slow. + // Optimize for the common case of the current file not being changed. + let mut cached_file_id = None; + if let Some((ref last_source_file, last_file_id)) = self.last_source_file { + // If the allocations are not equal, the files may still be equal, but that + // doesn't matter, as this is just an optimization. + if rustc_data_structures::sync::Lrc::ptr_eq(last_source_file, &file) { + cached_file_id = Some(last_file_id); + } + } + + let file_id = if let Some(file_id) = cached_file_id { + file_id + } else { + debug_context.add_source_file(&file) + }; + + let source_loc = + self.func_debug_cx.as_mut().unwrap().add_dbg_loc(file_id, line, column); + self.bcx.set_srcloc(source_loc); + } } // Note: must be kept in sync with get_caller_location from cg_ssa diff --git a/src/concurrency_limiter.rs b/src/concurrency_limiter.rs new file mode 100644 index 0000000000000..dfde97920461e --- /dev/null +++ b/src/concurrency_limiter.rs @@ -0,0 +1,168 @@ +use std::sync::{Arc, Condvar, Mutex}; + +use rustc_session::Session; + +use jobserver::HelperThread; + +// FIXME don't panic when a worker thread panics + +pub(super) struct ConcurrencyLimiter { + helper_thread: Option, + state: Arc>, + available_token_condvar: Arc, +} + +impl ConcurrencyLimiter { + pub(super) fn new(sess: &Session, pending_jobs: usize) -> Self { + let state = Arc::new(Mutex::new(state::ConcurrencyLimiterState::new(pending_jobs))); + let available_token_condvar = Arc::new(Condvar::new()); + + let state_helper = state.clone(); + let available_token_condvar_helper = available_token_condvar.clone(); + let helper_thread = sess + .jobserver + .clone() + .into_helper_thread(move |token| { + let mut state = state_helper.lock().unwrap(); + state.add_new_token(token.unwrap()); + available_token_condvar_helper.notify_one(); + }) + .unwrap(); + ConcurrencyLimiter { + helper_thread: Some(helper_thread), + state, + available_token_condvar: Arc::new(Condvar::new()), + } + } + + pub(super) fn acquire(&mut self) -> ConcurrencyLimiterToken { + let mut state = self.state.lock().unwrap(); + loop { + state.assert_invariants(); + + if state.try_start_job() { + return ConcurrencyLimiterToken { + state: self.state.clone(), + available_token_condvar: self.available_token_condvar.clone(), + }; + } + + self.helper_thread.as_mut().unwrap().request_token(); + state = self.available_token_condvar.wait(state).unwrap(); + } + } + + pub(super) fn job_already_done(&mut self) { + let mut state = self.state.lock().unwrap(); + state.job_already_done(); + } +} + +impl Drop for ConcurrencyLimiter { + fn drop(&mut self) { + // + self.helper_thread.take(); + + // Assert that all jobs have finished + let state = Mutex::get_mut(Arc::get_mut(&mut self.state).unwrap()).unwrap(); + state.assert_done(); + } +} + +#[derive(Debug)] +pub(super) struct ConcurrencyLimiterToken { + state: Arc>, + available_token_condvar: Arc, +} + +impl Drop for ConcurrencyLimiterToken { + fn drop(&mut self) { + let mut state = self.state.lock().unwrap(); + state.job_finished(); + self.available_token_condvar.notify_one(); + } +} + +mod state { + use jobserver::Acquired; + + #[derive(Debug)] + pub(super) struct ConcurrencyLimiterState { + pending_jobs: usize, + active_jobs: usize, + + // None is used to represent the implicit token, Some to represent explicit tokens + tokens: Vec>, + } + + impl ConcurrencyLimiterState { + pub(super) fn new(pending_jobs: usize) -> Self { + ConcurrencyLimiterState { pending_jobs, active_jobs: 0, tokens: vec![None] } + } + + pub(super) fn assert_invariants(&self) { + // There must be no excess active jobs + assert!(self.active_jobs <= self.pending_jobs); + + // There may not be more active jobs than there are tokens + assert!(self.active_jobs <= self.tokens.len()); + } + + pub(super) fn assert_done(&self) { + assert_eq!(self.pending_jobs, 0); + assert_eq!(self.active_jobs, 0); + } + + pub(super) fn add_new_token(&mut self, token: Acquired) { + self.tokens.push(Some(token)); + self.drop_excess_capacity(); + } + + pub(super) fn try_start_job(&mut self) -> bool { + if self.active_jobs < self.tokens.len() { + // Using existing token + self.job_started(); + return true; + } + + false + } + + pub(super) fn job_started(&mut self) { + self.assert_invariants(); + self.active_jobs += 1; + self.drop_excess_capacity(); + self.assert_invariants(); + } + + pub(super) fn job_finished(&mut self) { + self.assert_invariants(); + self.pending_jobs -= 1; + self.active_jobs -= 1; + self.assert_invariants(); + self.drop_excess_capacity(); + self.assert_invariants(); + } + + pub(super) fn job_already_done(&mut self) { + self.assert_invariants(); + self.pending_jobs -= 1; + self.assert_invariants(); + self.drop_excess_capacity(); + self.assert_invariants(); + } + + fn drop_excess_capacity(&mut self) { + self.assert_invariants(); + + // Drop all tokens that can never be used anymore + self.tokens.truncate(std::cmp::max(self.pending_jobs, 1)); + + // Keep some excess tokens to satisfy requests faster + const MAX_EXTRA_CAPACITY: usize = 2; + self.tokens.truncate(std::cmp::max(self.active_jobs + MAX_EXTRA_CAPACITY, 1)); + + self.assert_invariants(); + } + } +} diff --git a/src/debuginfo/emit.rs b/src/debuginfo/emit.rs index 589910ede9688..9583cd2ec60f8 100644 --- a/src/debuginfo/emit.rs +++ b/src/debuginfo/emit.rs @@ -9,7 +9,7 @@ use gimli::{RunTimeEndian, SectionId}; use super::object::WriteDebugInfo; use super::DebugContext; -impl DebugContext<'_> { +impl DebugContext { pub(crate) fn emit(&mut self, product: &mut ObjectProduct) { let unit_range_list_id = self.dwarf.unit.ranges.add(self.unit_range_list.clone()); let root = self.dwarf.unit.root(); diff --git a/src/debuginfo/line_info.rs b/src/debuginfo/line_info.rs index bbcb9591373dd..3ad0c420eaf0b 100644 --- a/src/debuginfo/line_info.rs +++ b/src/debuginfo/line_info.rs @@ -3,8 +3,10 @@ use std::ffi::OsStr; use std::path::{Component, Path}; +use crate::debuginfo::FunctionDebugContext; use crate::prelude::*; +use rustc_data_structures::sync::Lrc; use rustc_span::{ FileName, Pos, SourceFile, SourceFileAndLine, SourceFileHash, SourceFileHashAlgorithm, }; @@ -14,7 +16,6 @@ use cranelift_codegen::MachSrcLoc; use gimli::write::{ Address, AttributeValue, FileId, FileInfo, LineProgram, LineString, LineStringTable, - UnitEntryId, }; // OPTIMIZATION: It is cheaper to do this in one pass than using `.parent()` and `.file_name()`. @@ -47,9 +48,9 @@ fn osstr_as_utf8_bytes(path: &OsStr) -> &[u8] { } } -pub(crate) const MD5_LEN: usize = 16; +const MD5_LEN: usize = 16; -pub(crate) fn make_file_info(hash: SourceFileHash) -> Option { +fn make_file_info(hash: SourceFileHash) -> Option { if hash.kind == SourceFileHashAlgorithm::Md5 { let mut buf = [0u8; MD5_LEN]; buf.copy_from_slice(hash.hash_bytes()); @@ -59,160 +60,132 @@ pub(crate) fn make_file_info(hash: SourceFileHash) -> Option { } } -fn line_program_add_file( - line_program: &mut LineProgram, - line_strings: &mut LineStringTable, - file: &SourceFile, -) -> FileId { - match &file.name { - FileName::Real(path) => { - let (dir_path, file_name) = split_path_dir_and_file(path.remapped_path_if_available()); - let dir_name = osstr_as_utf8_bytes(dir_path.as_os_str()); - let file_name = osstr_as_utf8_bytes(file_name); - - let dir_id = if !dir_name.is_empty() { - let dir_name = LineString::new(dir_name, line_program.encoding(), line_strings); - line_program.add_directory(dir_name) - } else { - line_program.default_directory() - }; - let file_name = LineString::new(file_name, line_program.encoding(), line_strings); +impl DebugContext { + pub(crate) fn get_span_loc( + tcx: TyCtxt<'_>, + function_span: Span, + span: Span, + ) -> (Lrc, u64, u64) { + // Based on https://github.com/rust-lang/rust/blob/e369d87b015a84653343032833d65d0545fd3f26/src/librustc_codegen_ssa/mir/mod.rs#L116-L131 + // In order to have a good line stepping behavior in debugger, we overwrite debug + // locations of macro expansions with that of the outermost expansion site + // (unless the crate is being compiled with `-Z debug-macros`). + let span = if !span.from_expansion() || tcx.sess.opts.unstable_opts.debug_macros { + span + } else { + // Walk up the macro expansion chain until we reach a non-expanded span. + // We also stop at the function body level because no line stepping can occur + // at the level above that. + rustc_span::hygiene::walk_chain(span, function_span.ctxt()) + }; - let info = make_file_info(file.src_hash); + match tcx.sess.source_map().lookup_line(span.lo()) { + Ok(SourceFileAndLine { sf: file, line }) => { + let line_pos = file.line_begin_pos(span.lo()); - line_program.file_has_md5 &= info.is_some(); - line_program.add_file(file_name, dir_id, info) + ( + file, + u64::try_from(line).unwrap() + 1, + u64::from((span.lo() - line_pos).to_u32()) + 1, + ) + } + Err(file) => (file, 0, 0), } - // FIXME give more appropriate file names - filename => { - let dir_id = line_program.default_directory(); - let dummy_file_name = LineString::new( - filename.prefer_remapped().to_string().into_bytes(), - line_program.encoding(), - line_strings, - ); - line_program.add_file(dummy_file_name, dir_id, None) + } + + pub(crate) fn add_source_file(&mut self, source_file: &SourceFile) -> FileId { + let line_program: &mut LineProgram = &mut self.dwarf.unit.line_program; + let line_strings: &mut LineStringTable = &mut self.dwarf.line_strings; + + match &source_file.name { + FileName::Real(path) => { + let (dir_path, file_name) = + split_path_dir_and_file(path.remapped_path_if_available()); + let dir_name = osstr_as_utf8_bytes(dir_path.as_os_str()); + let file_name = osstr_as_utf8_bytes(file_name); + + let dir_id = if !dir_name.is_empty() { + let dir_name = LineString::new(dir_name, line_program.encoding(), line_strings); + line_program.add_directory(dir_name) + } else { + line_program.default_directory() + }; + let file_name = LineString::new(file_name, line_program.encoding(), line_strings); + + let info = make_file_info(source_file.src_hash); + + line_program.file_has_md5 &= info.is_some(); + line_program.add_file(file_name, dir_id, info) + } + // FIXME give more appropriate file names + filename => { + let dir_id = line_program.default_directory(); + let dummy_file_name = LineString::new( + filename.prefer_remapped().to_string().into_bytes(), + line_program.encoding(), + line_strings, + ); + line_program.add_file(dummy_file_name, dir_id, None) + } } } } -impl<'tcx> DebugContext<'tcx> { - pub(super) fn emit_location(&mut self, entry_id: UnitEntryId, span: Span) { - let loc = self.tcx.sess.source_map().lookup_char_pos(span.lo()); - - let file_id = line_program_add_file( - &mut self.dwarf.unit.line_program, - &mut self.dwarf.line_strings, - &loc.file, - ); - - let entry = self.dwarf.unit.get_mut(entry_id); - - entry.set(gimli::DW_AT_decl_file, AttributeValue::FileIndex(Some(file_id))); - entry.set(gimli::DW_AT_decl_line, AttributeValue::Udata(loc.line as u64)); - entry.set(gimli::DW_AT_decl_column, AttributeValue::Udata(loc.col.to_usize() as u64)); +impl FunctionDebugContext { + pub(crate) fn add_dbg_loc(&mut self, file_id: FileId, line: u64, column: u64) -> SourceLoc { + let (index, _) = self.source_loc_set.insert_full((file_id, line, column)); + SourceLoc::new(u32::try_from(index).unwrap()) } pub(super) fn create_debug_lines( &mut self, + debug_context: &mut DebugContext, symbol: usize, - entry_id: UnitEntryId, context: &Context, - function_span: Span, - source_info_set: &indexmap::IndexSet, ) -> CodeOffset { - let tcx = self.tcx; - let line_program = &mut self.dwarf.unit.line_program; - - let line_strings = &mut self.dwarf.line_strings; - let mut last_span = None; - let mut last_file = None; - let mut create_row_for_span = |line_program: &mut LineProgram, span: Span| { - if let Some(last_span) = last_span { - if span == last_span { - line_program.generate_row(); - return; - } - } - last_span = Some(span); - - // Based on https://github.com/rust-lang/rust/blob/e369d87b015a84653343032833d65d0545fd3f26/src/librustc_codegen_ssa/mir/mod.rs#L116-L131 - // In order to have a good line stepping behavior in debugger, we overwrite debug - // locations of macro expansions with that of the outermost expansion site - // (unless the crate is being compiled with `-Z debug-macros`). - let span = if !span.from_expansion() || tcx.sess.opts.unstable_opts.debug_macros { - span - } else { - // Walk up the macro expansion chain until we reach a non-expanded span. - // We also stop at the function body level because no line stepping can occur - // at the level above that. - rustc_span::hygiene::walk_chain(span, function_span.ctxt()) + let create_row_for_span = + |debug_context: &mut DebugContext, source_loc: (FileId, u64, u64)| { + let (file_id, line, col) = source_loc; + + debug_context.dwarf.unit.line_program.row().file = file_id; + debug_context.dwarf.unit.line_program.row().line = line; + debug_context.dwarf.unit.line_program.row().column = col; + debug_context.dwarf.unit.line_program.generate_row(); }; - let (file, line, col) = match tcx.sess.source_map().lookup_line(span.lo()) { - Ok(SourceFileAndLine { sf: file, line }) => { - let line_pos = file.line_begin_pos(span.lo()); - - ( - file, - u64::try_from(line).unwrap() + 1, - u64::from((span.lo() - line_pos).to_u32()) + 1, - ) - } - Err(file) => (file, 0, 0), - }; - - // line_program_add_file is very slow. - // Optimize for the common case of the current file not being changed. - let current_file_changed = if let Some(last_file) = &last_file { - // If the allocations are not equal, then the files may still be equal, but that - // is not a problem, as this is just an optimization. - !rustc_data_structures::sync::Lrc::ptr_eq(last_file, &file) - } else { - true - }; - if current_file_changed { - let file_id = line_program_add_file(line_program, line_strings, &file); - line_program.row().file = file_id; - last_file = Some(file); - } - - line_program.row().line = line; - line_program.row().column = col; - line_program.generate_row(); - }; - - line_program.begin_sequence(Some(Address::Symbol { symbol, addend: 0 })); + debug_context + .dwarf + .unit + .line_program + .begin_sequence(Some(Address::Symbol { symbol, addend: 0 })); let mut func_end = 0; - let mcr = context.mach_compile_result.as_ref().unwrap(); + let mcr = context.compiled_code().unwrap(); for &MachSrcLoc { start, end, loc } in mcr.buffer.get_srclocs_sorted() { - line_program.row().address_offset = u64::from(start); + debug_context.dwarf.unit.line_program.row().address_offset = u64::from(start); if !loc.is_default() { - let source_info = *source_info_set.get_index(loc.bits() as usize).unwrap(); - create_row_for_span(line_program, source_info.span); + let source_loc = *self.source_loc_set.get_index(loc.bits() as usize).unwrap(); + create_row_for_span(debug_context, source_loc); } else { - create_row_for_span(line_program, function_span); + create_row_for_span(debug_context, self.function_source_loc); } func_end = end; } - line_program.end_sequence(u64::from(func_end)); + debug_context.dwarf.unit.line_program.end_sequence(u64::from(func_end)); let func_end = mcr.buffer.total_size(); assert_ne!(func_end, 0); - let entry = self.dwarf.unit.get_mut(entry_id); + let entry = debug_context.dwarf.unit.get_mut(self.entry_id); entry.set( gimli::DW_AT_low_pc, AttributeValue::Address(Address::Symbol { symbol, addend: 0 }), ); entry.set(gimli::DW_AT_high_pc, AttributeValue::Udata(u64::from(func_end))); - self.emit_location(entry_id, function_span); - func_end } } diff --git a/src/debuginfo/mod.rs b/src/debuginfo/mod.rs index 693092ba543ea..c55db2017ee68 100644 --- a/src/debuginfo/mod.rs +++ b/src/debuginfo/mod.rs @@ -7,35 +7,34 @@ mod unwind; use crate::prelude::*; -use rustc_index::vec::IndexVec; - -use cranelift_codegen::entity::EntityRef; -use cranelift_codegen::ir::{Endianness, LabelValueLoc, ValueLabel}; +use cranelift_codegen::ir::Endianness; use cranelift_codegen::isa::TargetIsa; -use cranelift_codegen::ValueLocRange; use gimli::write::{ - Address, AttributeValue, DwarfUnit, Expression, LineProgram, LineString, Location, - LocationList, Range, RangeList, UnitEntryId, + Address, AttributeValue, DwarfUnit, FileId, LineProgram, LineString, Range, RangeList, + UnitEntryId, }; -use gimli::{Encoding, Format, LineEncoding, RunTimeEndian, X86_64}; +use gimli::{Encoding, Format, LineEncoding, RunTimeEndian}; +use indexmap::IndexSet; pub(crate) use emit::{DebugReloc, DebugRelocName}; pub(crate) use unwind::UnwindContext; -pub(crate) struct DebugContext<'tcx> { - tcx: TyCtxt<'tcx>, - +pub(crate) struct DebugContext { endian: RunTimeEndian, dwarf: DwarfUnit, unit_range_list: RangeList, +} - types: FxHashMap, UnitEntryId>, +pub(crate) struct FunctionDebugContext { + entry_id: UnitEntryId, + function_source_loc: (FileId, u64, u64), + source_loc_set: indexmap::IndexSet<(FileId, u64, u64)>, } -impl<'tcx> DebugContext<'tcx> { - pub(crate) fn new(tcx: TyCtxt<'tcx>, isa: &dyn TargetIsa) -> Self { +impl DebugContext { + pub(crate) fn new(tcx: TyCtxt<'_>, isa: &dyn TargetIsa) -> Self { let encoding = Encoding { format: Format::Dwarf32, // FIXME this should be configurable @@ -101,127 +100,18 @@ impl<'tcx> DebugContext<'tcx> { root.set(gimli::DW_AT_low_pc, AttributeValue::Address(Address::Constant(0))); } - DebugContext { - tcx, - - endian, - - dwarf, - unit_range_list: RangeList(Vec::new()), - - types: FxHashMap::default(), - } - } - - fn dwarf_ty(&mut self, ty: Ty<'tcx>) -> UnitEntryId { - if let Some(type_id) = self.types.get(&ty) { - return *type_id; - } - - let new_entry = |dwarf: &mut DwarfUnit, tag| dwarf.unit.add(dwarf.unit.root(), tag); - - let primitive = |dwarf: &mut DwarfUnit, ate| { - let type_id = new_entry(dwarf, gimli::DW_TAG_base_type); - let type_entry = dwarf.unit.get_mut(type_id); - type_entry.set(gimli::DW_AT_encoding, AttributeValue::Encoding(ate)); - type_id - }; - - let name = format!("{}", ty); - let layout = self.tcx.layout_of(ParamEnv::reveal_all().and(ty)).unwrap(); - - let type_id = match ty.kind() { - ty::Bool => primitive(&mut self.dwarf, gimli::DW_ATE_boolean), - ty::Char => primitive(&mut self.dwarf, gimli::DW_ATE_UTF), - ty::Uint(_) => primitive(&mut self.dwarf, gimli::DW_ATE_unsigned), - ty::Int(_) => primitive(&mut self.dwarf, gimli::DW_ATE_signed), - ty::Float(_) => primitive(&mut self.dwarf, gimli::DW_ATE_float), - ty::Ref(_, pointee_ty, _mutbl) - | ty::RawPtr(ty::TypeAndMut { ty: pointee_ty, mutbl: _mutbl }) => { - let type_id = new_entry(&mut self.dwarf, gimli::DW_TAG_pointer_type); - - // Ensure that type is inserted before recursing to avoid duplicates - self.types.insert(ty, type_id); - - let pointee = self.dwarf_ty(*pointee_ty); - - let type_entry = self.dwarf.unit.get_mut(type_id); - - //type_entry.set(gimli::DW_AT_mutable, AttributeValue::Flag(mutbl == rustc_hir::Mutability::Mut)); - type_entry.set(gimli::DW_AT_type, AttributeValue::UnitRef(pointee)); - - type_id - } - ty::Adt(adt_def, _substs) if adt_def.is_struct() && !layout.is_unsized() => { - let type_id = new_entry(&mut self.dwarf, gimli::DW_TAG_structure_type); - - // Ensure that type is inserted before recursing to avoid duplicates - self.types.insert(ty, type_id); - - let variant = adt_def.non_enum_variant(); - - for (field_idx, field_def) in variant.fields.iter().enumerate() { - let field_offset = layout.fields.offset(field_idx); - let field_layout = layout.field( - &layout::LayoutCx { tcx: self.tcx, param_env: ParamEnv::reveal_all() }, - field_idx, - ); - - let field_type = self.dwarf_ty(field_layout.ty); - - let field_id = self.dwarf.unit.add(type_id, gimli::DW_TAG_member); - let field_entry = self.dwarf.unit.get_mut(field_id); - - field_entry.set( - gimli::DW_AT_name, - AttributeValue::String(field_def.name.as_str().to_string().into_bytes()), - ); - field_entry.set( - gimli::DW_AT_data_member_location, - AttributeValue::Udata(field_offset.bytes()), - ); - field_entry.set(gimli::DW_AT_type, AttributeValue::UnitRef(field_type)); - } - - type_id - } - _ => new_entry(&mut self.dwarf, gimli::DW_TAG_structure_type), - }; - - let type_entry = self.dwarf.unit.get_mut(type_id); - - type_entry.set(gimli::DW_AT_name, AttributeValue::String(name.into_bytes())); - type_entry.set(gimli::DW_AT_byte_size, AttributeValue::Udata(layout.size.bytes())); - - self.types.insert(ty, type_id); - - type_id - } - - fn define_local(&mut self, scope: UnitEntryId, name: String, ty: Ty<'tcx>) -> UnitEntryId { - let dw_ty = self.dwarf_ty(ty); - - let var_id = self.dwarf.unit.add(scope, gimli::DW_TAG_variable); - let var_entry = self.dwarf.unit.get_mut(var_id); - - var_entry.set(gimli::DW_AT_name, AttributeValue::String(name.into_bytes())); - var_entry.set(gimli::DW_AT_type, AttributeValue::UnitRef(dw_ty)); - - var_id + DebugContext { endian, dwarf, unit_range_list: RangeList(Vec::new()) } } pub(crate) fn define_function( &mut self, - instance: Instance<'tcx>, - func_id: FuncId, + tcx: TyCtxt<'_>, name: &str, - isa: &dyn TargetIsa, - context: &Context, - source_info_set: &indexmap::IndexSet, - local_map: IndexVec>, - ) { - let symbol = func_id.as_u32() as usize; - let mir = self.tcx.instance_mir(instance.def); + function_span: Span, + ) -> FunctionDebugContext { + let (file, line, column) = DebugContext::get_span_loc(tcx, function_span, function_span); + + let file_id = self.add_source_file(&file); // FIXME: add to appropriate scope instead of root let scope = self.dwarf.unit.root(); @@ -233,14 +123,35 @@ impl<'tcx> DebugContext<'tcx> { entry.set(gimli::DW_AT_name, AttributeValue::StringRef(name_id)); entry.set(gimli::DW_AT_linkage_name, AttributeValue::StringRef(name_id)); - let end = self.create_debug_lines(symbol, entry_id, context, mir.span, source_info_set); + entry.set(gimli::DW_AT_decl_file, AttributeValue::FileIndex(Some(file_id))); + entry.set(gimli::DW_AT_decl_line, AttributeValue::Udata(line)); + entry.set(gimli::DW_AT_decl_column, AttributeValue::Udata(column)); - self.unit_range_list.0.push(Range::StartLength { + FunctionDebugContext { + entry_id, + function_source_loc: (file_id, line, column), + source_loc_set: IndexSet::new(), + } + } +} + +impl FunctionDebugContext { + pub(crate) fn finalize( + mut self, + debug_context: &mut DebugContext, + func_id: FuncId, + context: &Context, + ) { + let symbol = func_id.as_u32() as usize; + + let end = self.create_debug_lines(debug_context, symbol, context); + + debug_context.unit_range_list.0.push(Range::StartLength { begin: Address::Symbol { symbol, addend: 0 }, length: u64::from(end), }); - let func_entry = self.dwarf.unit.get_mut(entry_id); + let func_entry = debug_context.dwarf.unit.get_mut(self.entry_id); // Gdb requires both DW_AT_low_pc and DW_AT_high_pc. Otherwise the DW_TAG_subprogram is skipped. func_entry.set( gimli::DW_AT_low_pc, @@ -248,110 +159,5 @@ impl<'tcx> DebugContext<'tcx> { ); // Using Udata for DW_AT_high_pc requires at least DWARF4 func_entry.set(gimli::DW_AT_high_pc, AttributeValue::Udata(u64::from(end))); - - // FIXME make it more reliable and implement scopes before re-enabling this. - if false { - let value_labels_ranges = std::collections::HashMap::new(); // FIXME - - for (local, _local_decl) in mir.local_decls.iter_enumerated() { - let ty = self.tcx.subst_and_normalize_erasing_regions( - instance.substs, - ty::ParamEnv::reveal_all(), - mir.local_decls[local].ty, - ); - let var_id = self.define_local(entry_id, format!("{:?}", local), ty); - - let location = place_location( - self, - isa, - symbol, - &local_map, - &value_labels_ranges, - Place { local, projection: ty::List::empty() }, - ); - - let var_entry = self.dwarf.unit.get_mut(var_id); - var_entry.set(gimli::DW_AT_location, location); - } - } - - // FIXME create locals for all entries in mir.var_debug_info - } -} - -fn place_location<'tcx>( - debug_context: &mut DebugContext<'tcx>, - isa: &dyn TargetIsa, - symbol: usize, - local_map: &IndexVec>, - #[allow(rustc::default_hash_types)] value_labels_ranges: &std::collections::HashMap< - ValueLabel, - Vec, - >, - place: Place<'tcx>, -) -> AttributeValue { - assert!(place.projection.is_empty()); // FIXME implement them - - match local_map[place.local].inner() { - CPlaceInner::Var(_local, var) => { - let value_label = cranelift_codegen::ir::ValueLabel::new(var.index()); - if let Some(value_loc_ranges) = value_labels_ranges.get(&value_label) { - let loc_list = LocationList( - value_loc_ranges - .iter() - .map(|value_loc_range| Location::StartEnd { - begin: Address::Symbol { - symbol, - addend: i64::from(value_loc_range.start), - }, - end: Address::Symbol { symbol, addend: i64::from(value_loc_range.end) }, - data: translate_loc(isa, value_loc_range.loc).unwrap(), - }) - .collect(), - ); - let loc_list_id = debug_context.dwarf.unit.locations.add(loc_list); - - AttributeValue::LocationListRef(loc_list_id) - } else { - // FIXME set value labels for unused locals - - AttributeValue::Exprloc(Expression::new()) - } - } - CPlaceInner::VarPair(_, _, _) => { - // FIXME implement this - - AttributeValue::Exprloc(Expression::new()) - } - CPlaceInner::VarLane(_, _, _) => { - // FIXME implement this - - AttributeValue::Exprloc(Expression::new()) - } - CPlaceInner::Addr(_, _) => { - // FIXME implement this (used by arguments and returns) - - AttributeValue::Exprloc(Expression::new()) - - // For PointerBase::Stack: - //AttributeValue::Exprloc(translate_loc(ValueLoc::Stack(*stack_slot)).unwrap()) - } - } -} - -// Adapted from https://github.com/CraneStation/wasmtime/blob/5a1845b4caf7a5dba8eda1fef05213a532ed4259/crates/debug/src/transform/expression.rs#L59-L137 -fn translate_loc(isa: &dyn TargetIsa, loc: LabelValueLoc) -> Option { - match loc { - LabelValueLoc::Reg(reg) => { - let machine_reg = isa.map_regalloc_reg_to_dwarf(reg).unwrap(); - let mut expr = Expression::new(); - expr.op_reg(gimli::Register(machine_reg)); - Some(expr) - } - LabelValueLoc::SPOffset(offset) => { - let mut expr = Expression::new(); - expr.op_breg(X86_64::RSP, offset); - Some(expr) - } } } diff --git a/src/discriminant.rs b/src/discriminant.rs index f619bb5ed5e58..e41ae1fbdbac5 100644 --- a/src/discriminant.rs +++ b/src/discriminant.rs @@ -62,16 +62,14 @@ pub(crate) fn codegen_set_discriminant<'tcx>( pub(crate) fn codegen_get_discriminant<'tcx>( fx: &mut FunctionCx<'_, '_, 'tcx>, + dest: CPlace<'tcx>, value: CValue<'tcx>, dest_layout: TyAndLayout<'tcx>, -) -> CValue<'tcx> { +) { let layout = value.layout(); - if layout.abi == Abi::Uninhabited { - let true_ = fx.bcx.ins().iconst(types::I32, 1); - fx.bcx.ins().trapnz(true_, TrapCode::UnreachableCodeReached); - // Return a dummy value - return CValue::by_ref(Pointer::const_addr(fx, 0), dest_layout); + if layout.abi.is_uninhabited() { + return; } let (tag_scalar, tag_field, tag_encoding) = match &layout.variants { @@ -89,7 +87,9 @@ pub(crate) fn codegen_get_discriminant<'tcx>( } else { ty::ScalarInt::try_from_uint(discr_val, dest_layout.size).unwrap() }; - return CValue::const_val(fx, dest_layout, discr_val); + let res = CValue::const_val(fx, dest_layout, discr_val); + dest.write_cvalue(fx, res); + return; } Variants::Multiple { tag, tag_field, tag_encoding, variants: _ } => { (tag, *tag_field, tag_encoding) @@ -110,7 +110,8 @@ pub(crate) fn codegen_get_discriminant<'tcx>( _ => false, }; let val = clif_intcast(fx, tag, cast_to, signed); - CValue::by_val(val, dest_layout) + let res = CValue::by_val(val, dest_layout); + dest.write_cvalue(fx, res); } TagEncoding::Niche { dataful_variant, ref niche_variants, niche_start } => { // Rebase from niche values to discriminants, and check @@ -170,7 +171,8 @@ pub(crate) fn codegen_get_discriminant<'tcx>( let dataful_variant = fx.bcx.ins().iconst(cast_to, i64::from(dataful_variant.as_u32())); let discr = fx.bcx.ins().select(is_niche, niche_discr, dataful_variant); - CValue::by_val(discr, dest_layout) + let res = CValue::by_val(discr, dest_layout); + dest.write_cvalue(fx, res); } } } diff --git a/src/driver/aot.rs b/src/driver/aot.rs index 3cd1ef5639ef9..8eabe1cbcb150 100644 --- a/src/driver/aot.rs +++ b/src/driver/aot.rs @@ -1,33 +1,129 @@ //! The AOT driver uses [`cranelift_object`] to write object files suitable for linking into a //! standalone executable. +use std::fs::File; use std::path::PathBuf; +use std::sync::Arc; +use std::thread::JoinHandle; -use rustc_ast::{InlineAsmOptions, InlineAsmTemplatePiece}; use rustc_codegen_ssa::back::metadata::create_compressed_metadata_file; use rustc_codegen_ssa::{CodegenResults, CompiledModule, CrateInfo, ModuleKind}; +use rustc_data_structures::profiling::SelfProfilerRef; use rustc_data_structures::stable_hasher::{HashStable, StableHasher}; use rustc_metadata::EncodedMetadata; use rustc_middle::dep_graph::{WorkProduct, WorkProductId}; use rustc_middle::mir::mono::{CodegenUnit, MonoItem}; use rustc_session::cgu_reuse_tracker::CguReuse; -use rustc_session::config::{DebugInfo, OutputType}; +use rustc_session::config::{DebugInfo, OutputFilenames, OutputType}; use rustc_session::Session; -use cranelift_codegen::isa::TargetIsa; use cranelift_object::{ObjectBuilder, ObjectModule}; +use crate::concurrency_limiter::{ConcurrencyLimiter, ConcurrencyLimiterToken}; +use crate::global_asm::GlobalAsmConfig; use crate::{prelude::*, BackendConfig}; -struct ModuleCodegenResult(CompiledModule, Option<(WorkProductId, WorkProduct)>); +struct ModuleCodegenResult { + module_regular: CompiledModule, + module_global_asm: Option, + existing_work_product: Option<(WorkProductId, WorkProduct)>, +} + +enum OngoingModuleCodegen { + Sync(Result), + Async(JoinHandle>), +} -impl HashStable for ModuleCodegenResult { +impl HashStable for OngoingModuleCodegen { fn hash_stable(&self, _: &mut HCX, _: &mut StableHasher) { // do nothing } } -fn make_module(sess: &Session, isa: Box, name: String) -> ObjectModule { +pub(crate) struct OngoingCodegen { + modules: Vec, + allocator_module: Option, + metadata_module: Option, + metadata: EncodedMetadata, + crate_info: CrateInfo, + concurrency_limiter: ConcurrencyLimiter, +} + +impl OngoingCodegen { + pub(crate) fn join( + self, + sess: &Session, + backend_config: &BackendConfig, + ) -> (CodegenResults, FxHashMap) { + let mut work_products = FxHashMap::default(); + let mut modules = vec![]; + + for module_codegen in self.modules { + let module_codegen_result = match module_codegen { + OngoingModuleCodegen::Sync(module_codegen_result) => module_codegen_result, + OngoingModuleCodegen::Async(join_handle) => match join_handle.join() { + Ok(module_codegen_result) => module_codegen_result, + Err(panic) => std::panic::resume_unwind(panic), + }, + }; + + let module_codegen_result = match module_codegen_result { + Ok(module_codegen_result) => module_codegen_result, + Err(err) => sess.fatal(&err), + }; + let ModuleCodegenResult { module_regular, module_global_asm, existing_work_product } = + module_codegen_result; + + if let Some((work_product_id, work_product)) = existing_work_product { + work_products.insert(work_product_id, work_product); + } else { + let work_product = if backend_config.disable_incr_cache { + None + } else if let Some(module_global_asm) = &module_global_asm { + rustc_incremental::copy_cgu_workproduct_to_incr_comp_cache_dir( + sess, + &module_regular.name, + &[ + ("o", &module_regular.object.as_ref().unwrap()), + ("asm.o", &module_global_asm.object.as_ref().unwrap()), + ], + ) + } else { + rustc_incremental::copy_cgu_workproduct_to_incr_comp_cache_dir( + sess, + &module_regular.name, + &[("o", &module_regular.object.as_ref().unwrap())], + ) + }; + if let Some((work_product_id, work_product)) = work_product { + work_products.insert(work_product_id, work_product); + } + } + + modules.push(module_regular); + if let Some(module_global_asm) = module_global_asm { + modules.push(module_global_asm); + } + } + + drop(self.concurrency_limiter); + + ( + CodegenResults { + modules, + allocator_module: self.allocator_module, + metadata_module: self.metadata_module, + metadata: self.metadata, + crate_info: self.crate_info, + }, + work_products, + ) + } +} + +fn make_module(sess: &Session, backend_config: &BackendConfig, name: String) -> ObjectModule { + let isa = crate::build_isa(sess, backend_config); + let mut builder = ObjectBuilder::new(isa, name + ".o", cranelift_module::default_libcall_names()).unwrap(); // Unlike cg_llvm, cg_clif defaults to disabling -Zfunction-sections. For cg_llvm binary size @@ -37,15 +133,15 @@ fn make_module(sess: &Session, isa: Box, name: String) -> ObjectM ObjectModule::new(builder) } -fn emit_module( - tcx: TyCtxt<'_>, - backend_config: &BackendConfig, +fn emit_cgu( + output_filenames: &OutputFilenames, + prof: &SelfProfilerRef, name: String, - kind: ModuleKind, module: ObjectModule, - debug: Option>, + debug: Option, unwind_context: UnwindContext, -) -> ModuleCodegenResult { + global_asm_object_file: Option, +) -> Result { let mut product = module.finish(); if let Some(mut debug) = debug { @@ -54,134 +150,191 @@ fn emit_module( unwind_context.emit(&mut product); - let tmp_file = tcx.output_filenames(()).temp_path(OutputType::Object, Some(&name)); - let obj = product.object.write().unwrap(); + let module_regular = + emit_module(output_filenames, prof, product.object, ModuleKind::Regular, name.clone())?; + + Ok(ModuleCodegenResult { + module_regular, + module_global_asm: global_asm_object_file.map(|global_asm_object_file| CompiledModule { + name: format!("{name}.asm"), + kind: ModuleKind::Regular, + object: Some(global_asm_object_file), + dwarf_object: None, + bytecode: None, + }), + existing_work_product: None, + }) +} - tcx.sess.prof.artifact_size("object_file", name.clone(), obj.len().try_into().unwrap()); +fn emit_module( + output_filenames: &OutputFilenames, + prof: &SelfProfilerRef, + object: cranelift_object::object::write::Object<'_>, + kind: ModuleKind, + name: String, +) -> Result { + let tmp_file = output_filenames.temp_path(OutputType::Object, Some(&name)); + let mut file = match File::create(&tmp_file) { + Ok(file) => file, + Err(err) => return Err(format!("error creating object file: {}", err)), + }; - if let Err(err) = std::fs::write(&tmp_file, obj) { - tcx.sess.fatal(&format!("error writing object file: {}", err)); + if let Err(err) = object.write_stream(&mut file) { + return Err(format!("error writing object file: {}", err)); } - let work_product = if backend_config.disable_incr_cache { - None - } else { - rustc_incremental::copy_cgu_workproduct_to_incr_comp_cache_dir( - tcx.sess, - &name, - &[("o", &tmp_file)], - ) - }; + prof.artifact_size("object_file", &*name, file.metadata().unwrap().len()); - ModuleCodegenResult( - CompiledModule { name, kind, object: Some(tmp_file), dwarf_object: None, bytecode: None }, - work_product, - ) + Ok(CompiledModule { name, kind, object: Some(tmp_file), dwarf_object: None, bytecode: None }) } fn reuse_workproduct_for_cgu( tcx: TyCtxt<'_>, cgu: &CodegenUnit<'_>, - work_products: &mut FxHashMap, -) -> CompiledModule { +) -> Result { let work_product = cgu.previous_work_product(tcx); - let obj_out = tcx.output_filenames(()).temp_path(OutputType::Object, Some(cgu.name().as_str())); - let source_file = rustc_incremental::in_incr_comp_dir_sess( + let obj_out_regular = + tcx.output_filenames(()).temp_path(OutputType::Object, Some(cgu.name().as_str())); + let source_file_regular = rustc_incremental::in_incr_comp_dir_sess( &tcx.sess, &work_product.saved_files.get("o").expect("no saved object file in work product"), ); - if let Err(err) = rustc_fs_util::link_or_copy(&source_file, &obj_out) { - tcx.sess.err(&format!( + + if let Err(err) = rustc_fs_util::link_or_copy(&source_file_regular, &obj_out_regular) { + return Err(format!( "unable to copy {} to {}: {}", - source_file.display(), - obj_out.display(), + source_file_regular.display(), + obj_out_regular.display(), err )); } + let obj_out_global_asm = + crate::global_asm::add_file_stem_postfix(obj_out_regular.clone(), ".asm"); + let has_global_asm = if let Some(asm_o) = work_product.saved_files.get("asm.o") { + let source_file_global_asm = rustc_incremental::in_incr_comp_dir_sess(&tcx.sess, asm_o); + if let Err(err) = rustc_fs_util::link_or_copy(&source_file_global_asm, &obj_out_global_asm) + { + return Err(format!( + "unable to copy {} to {}: {}", + source_file_regular.display(), + obj_out_regular.display(), + err + )); + } + true + } else { + false + }; - work_products.insert(cgu.work_product_id(), work_product); - - CompiledModule { - name: cgu.name().to_string(), - kind: ModuleKind::Regular, - object: Some(obj_out), - dwarf_object: None, - bytecode: None, - } + Ok(ModuleCodegenResult { + module_regular: CompiledModule { + name: cgu.name().to_string(), + kind: ModuleKind::Regular, + object: Some(obj_out_regular), + dwarf_object: None, + bytecode: None, + }, + module_global_asm: if has_global_asm { + Some(CompiledModule { + name: cgu.name().to_string(), + kind: ModuleKind::Regular, + object: Some(obj_out_global_asm), + dwarf_object: None, + bytecode: None, + }) + } else { + None + }, + existing_work_product: Some((cgu.work_product_id(), work_product)), + }) } fn module_codegen( tcx: TyCtxt<'_>, - (backend_config, cgu_name): (BackendConfig, rustc_span::Symbol), -) -> ModuleCodegenResult { - let cgu = tcx.codegen_unit(cgu_name); - let mono_items = cgu.items_in_deterministic_order(tcx); - - let isa = crate::build_isa(tcx.sess, &backend_config); - let mut module = make_module(tcx.sess, isa, cgu_name.as_str().to_string()); - - let mut cx = crate::CodegenCx::new( - tcx, - backend_config.clone(), - module.isa(), - tcx.sess.opts.debuginfo != DebugInfo::None, - cgu_name, - ); - super::predefine_mono_items(tcx, &mut module, &mono_items); - for (mono_item, _) in mono_items { - match mono_item { - MonoItem::Fn(inst) => { - cx.tcx - .sess - .time("codegen fn", || crate::base::codegen_fn(&mut cx, &mut module, inst)); - } - MonoItem::Static(def_id) => crate::constant::codegen_static(tcx, &mut module, def_id), - MonoItem::GlobalAsm(item_id) => { - let item = cx.tcx.hir().item(item_id); - if let rustc_hir::ItemKind::GlobalAsm(asm) = item.kind { - if !asm.options.contains(InlineAsmOptions::ATT_SYNTAX) { - cx.global_asm.push_str("\n.intel_syntax noprefix\n"); - } else { - cx.global_asm.push_str("\n.att_syntax\n"); - } - for piece in asm.template { - match *piece { - InlineAsmTemplatePiece::String(ref s) => cx.global_asm.push_str(s), - InlineAsmTemplatePiece::Placeholder { .. } => todo!(), - } - } - cx.global_asm.push_str("\n.att_syntax\n\n"); - } else { - bug!("Expected GlobalAsm found {:?}", item); + (backend_config, global_asm_config, cgu_name, token): ( + BackendConfig, + Arc, + rustc_span::Symbol, + ConcurrencyLimiterToken, + ), +) -> OngoingModuleCodegen { + let (cgu_name, mut cx, mut module, codegened_functions) = tcx.sess.time("codegen cgu", || { + let cgu = tcx.codegen_unit(cgu_name); + let mono_items = cgu.items_in_deterministic_order(tcx); + + let mut module = make_module(tcx.sess, &backend_config, cgu_name.as_str().to_string()); + + let mut cx = crate::CodegenCx::new( + tcx, + backend_config.clone(), + module.isa(), + tcx.sess.opts.debuginfo != DebugInfo::None, + cgu_name, + ); + super::predefine_mono_items(tcx, &mut module, &mono_items); + let mut codegened_functions = vec![]; + for (mono_item, _) in mono_items { + match mono_item { + MonoItem::Fn(inst) => { + tcx.sess.time("codegen fn", || { + let codegened_function = crate::base::codegen_fn( + tcx, + &mut cx, + Function::new(), + &mut module, + inst, + ); + codegened_functions.push(codegened_function); + }); + } + MonoItem::Static(def_id) => { + crate::constant::codegen_static(tcx, &mut module, def_id) + } + MonoItem::GlobalAsm(item_id) => { + crate::global_asm::codegen_global_asm_item(tcx, &mut cx.global_asm, item_id); } } } - } - crate::main_shim::maybe_create_entry_wrapper( - tcx, - &mut module, - &mut cx.unwind_context, - false, - cgu.is_primary(), - ); - - let debug_context = cx.debug_context; - let unwind_context = cx.unwind_context; - let codegen_result = tcx.sess.time("write object file", || { - emit_module( + crate::main_shim::maybe_create_entry_wrapper( tcx, - &backend_config, - cgu.name().as_str().to_string(), - ModuleKind::Regular, - module, - debug_context, - unwind_context, - ) + &mut module, + &mut cx.unwind_context, + false, + cgu.is_primary(), + ); + + let cgu_name = cgu.name().as_str().to_owned(); + + (cgu_name, cx, module, codegened_functions) }); - codegen_global_asm(tcx, cgu.name().as_str(), &cx.global_asm); + OngoingModuleCodegen::Async(std::thread::spawn(move || { + cx.profiler.clone().verbose_generic_activity("compile functions").run(|| { + let mut cached_context = Context::new(); + for codegened_func in codegened_functions { + crate::base::compile_fn(&mut cx, &mut cached_context, &mut module, codegened_func); + } + }); - codegen_result + let global_asm_object_file = + cx.profiler.verbose_generic_activity("compile assembly").run(|| { + crate::global_asm::compile_global_asm(&global_asm_config, &cgu_name, &cx.global_asm) + })?; + + let codegen_result = cx.profiler.verbose_generic_activity("write object file").run(|| { + emit_cgu( + &global_asm_config.output_filenames, + &cx.profiler, + cgu_name, + module, + cx.debug_context, + cx.unwind_context, + global_asm_object_file, + ) + }); + std::mem::drop(token); + codegen_result + })) } pub(crate) fn run_aot( @@ -189,9 +342,7 @@ pub(crate) fn run_aot( backend_config: BackendConfig, metadata: EncodedMetadata, need_metadata_module: bool, -) -> Box<(CodegenResults, FxHashMap)> { - let mut work_products = FxHashMap::default(); - +) -> Box { let cgus = if tcx.sess.opts.output_types.should_codegen() { tcx.collect_and_partition_mono_items(()).1 } else { @@ -206,62 +357,69 @@ pub(crate) fn run_aot( } } + let global_asm_config = Arc::new(crate::global_asm::GlobalAsmConfig::new(tcx)); + + let mut concurrency_limiter = ConcurrencyLimiter::new(tcx.sess, cgus.len()); + let modules = super::time(tcx, backend_config.display_cg_time, "codegen mono items", || { cgus.iter() .map(|cgu| { - let cgu_reuse = determine_cgu_reuse(tcx, cgu); + let cgu_reuse = if backend_config.disable_incr_cache { + CguReuse::No + } else { + determine_cgu_reuse(tcx, cgu) + }; tcx.sess.cgu_reuse_tracker.set_actual_reuse(cgu.name().as_str(), cgu_reuse); match cgu_reuse { - _ if backend_config.disable_incr_cache => {} - CguReuse::No => {} - CguReuse::PreLto => { - return reuse_workproduct_for_cgu(tcx, &*cgu, &mut work_products); + CguReuse::No => { + let dep_node = cgu.codegen_dep_node(tcx); + tcx.dep_graph + .with_task( + dep_node, + tcx, + ( + backend_config.clone(), + global_asm_config.clone(), + cgu.name(), + concurrency_limiter.acquire(), + ), + module_codegen, + Some(rustc_middle::dep_graph::hash_result), + ) + .0 + } + CguReuse::PreLto => unreachable!(), + CguReuse::PostLto => { + concurrency_limiter.job_already_done(); + OngoingModuleCodegen::Sync(reuse_workproduct_for_cgu(tcx, &*cgu)) } - CguReuse::PostLto => unreachable!(), - } - - let dep_node = cgu.codegen_dep_node(tcx); - let (ModuleCodegenResult(module, work_product), _) = tcx.dep_graph.with_task( - dep_node, - tcx, - (backend_config.clone(), cgu.name()), - module_codegen, - Some(rustc_middle::dep_graph::hash_result), - ); - - if let Some((id, product)) = work_product { - work_products.insert(id, product); } - - module }) .collect::>() }); tcx.sess.abort_if_errors(); - let isa = crate::build_isa(tcx.sess, &backend_config); - let mut allocator_module = make_module(tcx.sess, isa, "allocator_shim".to_string()); - assert_eq!(pointer_ty(tcx), allocator_module.target_config().pointer_type()); + let mut allocator_module = make_module(tcx.sess, &backend_config, "allocator_shim".to_string()); let mut allocator_unwind_context = UnwindContext::new(allocator_module.isa(), true); let created_alloc_shim = crate::allocator::codegen(tcx, &mut allocator_module, &mut allocator_unwind_context); let allocator_module = if created_alloc_shim { - let ModuleCodegenResult(module, work_product) = emit_module( - tcx, - &backend_config, - "allocator_shim".to_string(), + let mut product = allocator_module.finish(); + allocator_unwind_context.emit(&mut product); + + match emit_module( + tcx.output_filenames(()), + &tcx.sess.prof, + product.object, ModuleKind::Allocator, - allocator_module, - None, - allocator_unwind_context, - ); - if let Some((id, product)) = work_product { - work_products.insert(id, product); + "allocator_shim".to_owned(), + ) { + Ok(allocator_module) => Some(allocator_module), + Err(err) => tcx.sess.fatal(err), } - Some(module) } else { None }; @@ -308,102 +466,14 @@ pub(crate) fn run_aot( } .to_owned(); - Box::new(( - CodegenResults { - modules, - allocator_module, - metadata_module, - metadata, - crate_info: CrateInfo::new(tcx, target_cpu), - }, - work_products, - )) -} - -fn codegen_global_asm(tcx: TyCtxt<'_>, cgu_name: &str, global_asm: &str) { - use std::io::Write; - use std::process::{Command, Stdio}; - - if global_asm.is_empty() { - return; - } - - if cfg!(not(feature = "inline_asm")) - || tcx.sess.target.is_like_osx - || tcx.sess.target.is_like_windows - { - if global_asm.contains("__rust_probestack") { - return; - } - - // FIXME fix linker error on macOS - if cfg!(not(feature = "inline_asm")) { - tcx.sess.fatal( - "asm! and global_asm! support is disabled while compiling rustc_codegen_cranelift", - ); - } else { - tcx.sess.fatal("asm! and global_asm! are not yet supported on macOS and Windows"); - } - } - - let assembler = crate::toolchain::get_toolchain_binary(tcx.sess, "as"); - let linker = crate::toolchain::get_toolchain_binary(tcx.sess, "ld"); - - // Remove all LLVM style comments - let global_asm = global_asm - .lines() - .map(|line| if let Some(index) = line.find("//") { &line[0..index] } else { line }) - .collect::>() - .join("\n"); - - let output_object_file = tcx.output_filenames(()).temp_path(OutputType::Object, Some(cgu_name)); - - // Assemble `global_asm` - let global_asm_object_file = add_file_stem_postfix(output_object_file.clone(), ".asm"); - let mut child = Command::new(assembler) - .arg("-o") - .arg(&global_asm_object_file) - .stdin(Stdio::piped()) - .spawn() - .expect("Failed to spawn `as`."); - child.stdin.take().unwrap().write_all(global_asm.as_bytes()).unwrap(); - let status = child.wait().expect("Failed to wait for `as`."); - if !status.success() { - tcx.sess.fatal(&format!("Failed to assemble `{}`", global_asm)); - } - - // Link the global asm and main object file together - let main_object_file = add_file_stem_postfix(output_object_file.clone(), ".main"); - std::fs::rename(&output_object_file, &main_object_file).unwrap(); - let status = Command::new(linker) - .arg("-r") // Create a new object file - .arg("-o") - .arg(output_object_file) - .arg(&main_object_file) - .arg(&global_asm_object_file) - .status() - .unwrap(); - if !status.success() { - tcx.sess.fatal(&format!( - "Failed to link `{}` and `{}` together", - main_object_file.display(), - global_asm_object_file.display(), - )); - } - - std::fs::remove_file(global_asm_object_file).unwrap(); - std::fs::remove_file(main_object_file).unwrap(); -} - -fn add_file_stem_postfix(mut path: PathBuf, postfix: &str) -> PathBuf { - let mut new_filename = path.file_stem().unwrap().to_owned(); - new_filename.push(postfix); - if let Some(extension) = path.extension() { - new_filename.push("."); - new_filename.push(extension); - } - path.set_file_name(new_filename); - path + Box::new(OngoingCodegen { + modules, + allocator_module, + metadata_module, + metadata, + crate_info: CrateInfo::new(tcx, target_cpu), + concurrency_limiter, + }) } // Adapted from https://github.com/rust-lang/rust/blob/303d8aff6092709edd4dbd35b1c88e9aa40bf6d8/src/librustc_codegen_ssa/base.rs#L922-L953 @@ -432,5 +502,5 @@ fn determine_cgu_reuse<'tcx>(tcx: TyCtxt<'tcx>, cgu: &CodegenUnit<'tcx>) -> CguR cgu.name() ); - if tcx.try_mark_green(&dep_node) { CguReuse::PreLto } else { CguReuse::No } + if tcx.try_mark_green(&dep_node) { CguReuse::PostLto } else { CguReuse::No } } diff --git a/src/driver/jit.rs b/src/driver/jit.rs index a56a91000596c..0e77e4004c0bb 100644 --- a/src/driver/jit.rs +++ b/src/driver/jit.rs @@ -61,11 +61,11 @@ impl UnsafeMessage { } } -fn create_jit_module<'tcx>( - tcx: TyCtxt<'tcx>, +fn create_jit_module( + tcx: TyCtxt<'_>, backend_config: &BackendConfig, hotswap: bool, -) -> (JITModule, CodegenCx<'tcx>) { +) -> (JITModule, CodegenCx) { let crate_info = CrateInfo::new(tcx, "dummy_target_cpu".to_string()); let imported_symbols = load_imported_symbols_for_jit(tcx.sess, crate_info); @@ -111,6 +111,7 @@ pub(crate) fn run_jit(tcx: TyCtxt<'_>, backend_config: BackendConfig) -> ! { &backend_config, matches!(backend_config.codegen_mode, CodegenMode::JitLazy), ); + let mut cached_context = Context::new(); let (_, cgus) = tcx.collect_and_partition_mono_items(()); let mono_items = cgus @@ -128,11 +129,19 @@ pub(crate) fn run_jit(tcx: TyCtxt<'_>, backend_config: BackendConfig) -> ! { MonoItem::Fn(inst) => match backend_config.codegen_mode { CodegenMode::Aot => unreachable!(), CodegenMode::Jit => { - cx.tcx.sess.time("codegen fn", || { - crate::base::codegen_fn(&mut cx, &mut jit_module, inst) + tcx.sess.time("codegen fn", || { + crate::base::codegen_and_compile_fn( + tcx, + &mut cx, + &mut cached_context, + &mut jit_module, + inst, + ) }); } - CodegenMode::JitLazy => codegen_shim(&mut cx, &mut jit_module, inst), + CodegenMode::JitLazy => { + codegen_shim(tcx, &mut cx, &mut cached_context, &mut jit_module, inst) + } }, MonoItem::Static(def_id) => { crate::constant::codegen_static(tcx, &mut jit_module, def_id); @@ -259,7 +268,15 @@ fn jit_fn(instance_ptr: *const Instance<'static>, trampoline_ptr: *const u8) -> false, Symbol::intern("dummy_cgu_name"), ); - tcx.sess.time("codegen fn", || crate::base::codegen_fn(&mut cx, jit_module, instance)); + tcx.sess.time("codegen fn", || { + crate::base::codegen_and_compile_fn( + tcx, + &mut cx, + &mut Context::new(), + jit_module, + instance, + ) + }); assert!(cx.global_asm.is_empty()); jit_module.finalize_definitions(); @@ -334,9 +351,13 @@ fn load_imported_symbols_for_jit( imported_symbols } -fn codegen_shim<'tcx>(cx: &mut CodegenCx<'tcx>, module: &mut JITModule, inst: Instance<'tcx>) { - let tcx = cx.tcx; - +fn codegen_shim<'tcx>( + tcx: TyCtxt<'tcx>, + cx: &mut CodegenCx, + cached_context: &mut Context, + module: &mut JITModule, + inst: Instance<'tcx>, +) { let pointer_type = module.target_config().pointer_type(); let name = tcx.symbol_name(inst).name; @@ -357,8 +378,9 @@ fn codegen_shim<'tcx>(cx: &mut CodegenCx<'tcx>, module: &mut JITModule, inst: In ) .unwrap(); - cx.cached_context.clear(); - let trampoline = &mut cx.cached_context.func; + let context = cached_context; + context.clear(); + let trampoline = &mut context.func; trampoline.signature = sig.clone(); let mut builder_ctx = FunctionBuilderContext::new(); @@ -381,5 +403,6 @@ fn codegen_shim<'tcx>(cx: &mut CodegenCx<'tcx>, module: &mut JITModule, inst: In let ret_vals = trampoline_builder.func.dfg.inst_results(call_inst).to_vec(); trampoline_builder.ins().return_(&ret_vals); - module.define_function(func_id, &mut cx.cached_context).unwrap(); + module.define_function(func_id, context).unwrap(); + cx.unwind_context.add_function(func_id, context, module.isa()); } diff --git a/src/global_asm.rs b/src/global_asm.rs new file mode 100644 index 0000000000000..dcbcaba30feed --- /dev/null +++ b/src/global_asm.rs @@ -0,0 +1,114 @@ +//! The AOT driver uses [`cranelift_object`] to write object files suitable for linking into a +//! standalone executable. + +use std::io::Write; +use std::path::PathBuf; +use std::process::{Command, Stdio}; +use std::sync::Arc; + +use rustc_ast::{InlineAsmOptions, InlineAsmTemplatePiece}; +use rustc_hir::ItemId; +use rustc_session::config::{OutputFilenames, OutputType}; + +use crate::prelude::*; + +pub(crate) fn codegen_global_asm_item(tcx: TyCtxt<'_>, global_asm: &mut String, item_id: ItemId) { + let item = tcx.hir().item(item_id); + if let rustc_hir::ItemKind::GlobalAsm(asm) = item.kind { + if !asm.options.contains(InlineAsmOptions::ATT_SYNTAX) { + global_asm.push_str("\n.intel_syntax noprefix\n"); + } else { + global_asm.push_str("\n.att_syntax\n"); + } + for piece in asm.template { + match *piece { + InlineAsmTemplatePiece::String(ref s) => global_asm.push_str(s), + InlineAsmTemplatePiece::Placeholder { .. } => todo!(), + } + } + global_asm.push_str("\n.att_syntax\n\n"); + } else { + bug!("Expected GlobalAsm found {:?}", item); + } +} + +#[derive(Debug)] +pub(crate) struct GlobalAsmConfig { + asm_enabled: bool, + assembler: PathBuf, + pub(crate) output_filenames: Arc, +} + +impl GlobalAsmConfig { + pub(crate) fn new(tcx: TyCtxt<'_>) -> Self { + let asm_enabled = cfg!(feature = "inline_asm") && !tcx.sess.target.is_like_windows; + + GlobalAsmConfig { + asm_enabled, + assembler: crate::toolchain::get_toolchain_binary(tcx.sess, "as"), + output_filenames: tcx.output_filenames(()).clone(), + } + } +} + +pub(crate) fn compile_global_asm( + config: &GlobalAsmConfig, + cgu_name: &str, + global_asm: &str, +) -> Result, String> { + if global_asm.is_empty() { + return Ok(None); + } + + if !config.asm_enabled { + if global_asm.contains("__rust_probestack") { + return Ok(None); + } + + // FIXME fix linker error on macOS + if cfg!(not(feature = "inline_asm")) { + return Err( + "asm! and global_asm! support is disabled while compiling rustc_codegen_cranelift" + .to_owned(), + ); + } else { + return Err("asm! and global_asm! are not yet supported on Windows".to_owned()); + } + } + + // Remove all LLVM style comments + let global_asm = global_asm + .lines() + .map(|line| if let Some(index) = line.find("//") { &line[0..index] } else { line }) + .collect::>() + .join("\n"); + + let output_object_file = config.output_filenames.temp_path(OutputType::Object, Some(cgu_name)); + + // Assemble `global_asm` + let global_asm_object_file = add_file_stem_postfix(output_object_file.clone(), ".asm"); + let mut child = Command::new(&config.assembler) + .arg("-o") + .arg(&global_asm_object_file) + .stdin(Stdio::piped()) + .spawn() + .expect("Failed to spawn `as`."); + child.stdin.take().unwrap().write_all(global_asm.as_bytes()).unwrap(); + let status = child.wait().expect("Failed to wait for `as`."); + if !status.success() { + return Err(format!("Failed to assemble `{}`", global_asm)); + } + + Ok(Some(global_asm_object_file)) +} + +pub(crate) fn add_file_stem_postfix(mut path: PathBuf, postfix: &str) -> PathBuf { + let mut new_filename = path.file_stem().unwrap().to_owned(); + new_filename.push(postfix); + if let Some(extension) = path.extension() { + new_filename.push("."); + new_filename.push(extension); + } + path.set_file_name(new_filename); + path +} diff --git a/src/inline_asm.rs b/src/inline_asm.rs index 241de5e36530c..8b3d475cb1802 100644 --- a/src/inline_asm.rs +++ b/src/inline_asm.rs @@ -15,15 +15,19 @@ pub(crate) fn codegen_inline_asm<'tcx>( template: &[InlineAsmTemplatePiece], operands: &[InlineAsmOperand<'tcx>], options: InlineAsmOptions, + destination: Option, ) { // FIXME add .eh_frame unwind info directives if !template.is_empty() { + // Used by panic_abort if template[0] == InlineAsmTemplatePiece::String("int $$0x29".to_string()) { - let true_ = fx.bcx.ins().iconst(types::I32, 1); - fx.bcx.ins().trapnz(true_, TrapCode::User(1)); + fx.bcx.ins().trap(TrapCode::User(1)); return; - } else if template[0] == InlineAsmTemplatePiece::String("movq %rbx, ".to_string()) + } + + // Used by stdarch + if template[0] == InlineAsmTemplatePiece::String("movq %rbx, ".to_string()) && matches!( template[1], InlineAsmTemplatePiece::Placeholder { @@ -47,51 +51,46 @@ pub(crate) fn codegen_inline_asm<'tcx>( { assert_eq!(operands.len(), 4); let (leaf, eax_place) = match operands[1] { - InlineAsmOperand::InOut { reg, late: true, ref in_value, out_place } => { - assert_eq!( - reg, - InlineAsmRegOrRegClass::Reg(InlineAsmReg::X86(X86InlineAsmReg::ax)) - ); - ( - crate::base::codegen_operand(fx, in_value).load_scalar(fx), - crate::base::codegen_place(fx, out_place.unwrap()), - ) - } + InlineAsmOperand::InOut { + reg: InlineAsmRegOrRegClass::Reg(InlineAsmReg::X86(X86InlineAsmReg::ax)), + late: true, + ref in_value, + out_place: Some(out_place), + } => ( + crate::base::codegen_operand(fx, in_value).load_scalar(fx), + crate::base::codegen_place(fx, out_place), + ), _ => unreachable!(), }; let ebx_place = match operands[0] { - InlineAsmOperand::Out { reg, late: true, place } => { - assert_eq!( - reg, + InlineAsmOperand::Out { + reg: InlineAsmRegOrRegClass::RegClass(InlineAsmRegClass::X86( - X86InlineAsmRegClass::reg - )) - ); - crate::base::codegen_place(fx, place.unwrap()) - } + X86InlineAsmRegClass::reg, + )), + late: true, + place: Some(place), + } => crate::base::codegen_place(fx, place), _ => unreachable!(), }; let (sub_leaf, ecx_place) = match operands[2] { - InlineAsmOperand::InOut { reg, late: true, ref in_value, out_place } => { - assert_eq!( - reg, - InlineAsmRegOrRegClass::Reg(InlineAsmReg::X86(X86InlineAsmReg::cx)) - ); - ( - crate::base::codegen_operand(fx, in_value).load_scalar(fx), - crate::base::codegen_place(fx, out_place.unwrap()), - ) - } + InlineAsmOperand::InOut { + reg: InlineAsmRegOrRegClass::Reg(InlineAsmReg::X86(X86InlineAsmReg::cx)), + late: true, + ref in_value, + out_place: Some(out_place), + } => ( + crate::base::codegen_operand(fx, in_value).load_scalar(fx), + crate::base::codegen_place(fx, out_place), + ), _ => unreachable!(), }; let edx_place = match operands[3] { - InlineAsmOperand::Out { reg, late: true, place } => { - assert_eq!( - reg, - InlineAsmRegOrRegClass::Reg(InlineAsmReg::X86(X86InlineAsmReg::dx)) - ); - crate::base::codegen_place(fx, place.unwrap()) - } + InlineAsmOperand::Out { + reg: InlineAsmRegOrRegClass::Reg(InlineAsmReg::X86(X86InlineAsmReg::dx)), + late: true, + place: Some(place), + } => crate::base::codegen_place(fx, place), _ => unreachable!(), }; @@ -101,12 +100,99 @@ pub(crate) fn codegen_inline_asm<'tcx>( ebx_place.write_cvalue(fx, CValue::by_val(ebx, fx.layout_of(fx.tcx.types.u32))); ecx_place.write_cvalue(fx, CValue::by_val(ecx, fx.layout_of(fx.tcx.types.u32))); edx_place.write_cvalue(fx, CValue::by_val(edx, fx.layout_of(fx.tcx.types.u32))); + let destination_block = fx.get_block(destination.unwrap()); + fx.bcx.ins().jump(destination_block, &[]); return; - } else if fx.tcx.symbol_name(fx.instance).name.starts_with("___chkstk") { + } + + // Used by compiler-builtins + if fx.tcx.symbol_name(fx.instance).name.starts_with("___chkstk") { // ___chkstk, ___chkstk_ms and __alloca are only used on Windows crate::trap::trap_unimplemented(fx, "Stack probes are not supported"); + return; } else if fx.tcx.symbol_name(fx.instance).name == "__alloca" { crate::trap::trap_unimplemented(fx, "Alloca is not supported"); + return; + } + + // Used by measureme + if template[0] == InlineAsmTemplatePiece::String("xor %eax, %eax".to_string()) + && template[1] == InlineAsmTemplatePiece::String("\n".to_string()) + && template[2] == InlineAsmTemplatePiece::String("mov %rbx, ".to_string()) + && matches!( + template[3], + InlineAsmTemplatePiece::Placeholder { + operand_idx: 0, + modifier: Some('r'), + span: _ + } + ) + && template[4] == InlineAsmTemplatePiece::String("\n".to_string()) + && template[5] == InlineAsmTemplatePiece::String("cpuid".to_string()) + && template[6] == InlineAsmTemplatePiece::String("\n".to_string()) + && template[7] == InlineAsmTemplatePiece::String("mov ".to_string()) + && matches!( + template[8], + InlineAsmTemplatePiece::Placeholder { + operand_idx: 0, + modifier: Some('r'), + span: _ + } + ) + && template[9] == InlineAsmTemplatePiece::String(", %rbx".to_string()) + { + let destination_block = fx.get_block(destination.unwrap()); + fx.bcx.ins().jump(destination_block, &[]); + return; + } else if template[0] == InlineAsmTemplatePiece::String("rdpmc".to_string()) { + // Return zero dummy values for all performance counters + match operands[0] { + InlineAsmOperand::In { + reg: InlineAsmRegOrRegClass::Reg(InlineAsmReg::X86(X86InlineAsmReg::cx)), + value: _, + } => {} + _ => unreachable!(), + }; + let lo = match operands[1] { + InlineAsmOperand::Out { + reg: InlineAsmRegOrRegClass::Reg(InlineAsmReg::X86(X86InlineAsmReg::ax)), + late: true, + place: Some(place), + } => crate::base::codegen_place(fx, place), + _ => unreachable!(), + }; + let hi = match operands[2] { + InlineAsmOperand::Out { + reg: InlineAsmRegOrRegClass::Reg(InlineAsmReg::X86(X86InlineAsmReg::dx)), + late: true, + place: Some(place), + } => crate::base::codegen_place(fx, place), + _ => unreachable!(), + }; + + let u32_layout = fx.layout_of(fx.tcx.types.u32); + let zero = fx.bcx.ins().iconst(types::I32, 0); + lo.write_cvalue(fx, CValue::by_val(zero, u32_layout)); + hi.write_cvalue(fx, CValue::by_val(zero, u32_layout)); + + let destination_block = fx.get_block(destination.unwrap()); + fx.bcx.ins().jump(destination_block, &[]); + return; + } else if template[0] == InlineAsmTemplatePiece::String("lock xadd ".to_string()) + && matches!( + template[1], + InlineAsmTemplatePiece::Placeholder { operand_idx: 1, modifier: None, span: _ } + ) + && template[2] == InlineAsmTemplatePiece::String(", (".to_string()) + && matches!( + template[3], + InlineAsmTemplatePiece::Placeholder { operand_idx: 0, modifier: None, span: _ } + ) + && template[4] == InlineAsmTemplatePiece::String(")".to_string()) + { + let destination_block = fx.get_block(destination.unwrap()); + fx.bcx.ins().jump(destination_block, &[]); + return; } } @@ -175,6 +261,16 @@ pub(crate) fn codegen_inline_asm<'tcx>( } call_inline_asm(fx, &asm_name, asm_gen.stack_slot_size, inputs, outputs); + + match destination { + Some(destination) => { + let destination_block = fx.get_block(destination); + fx.bcx.ins().jump(destination_block, &[]); + } + None => { + fx.bcx.ins().trap(TrapCode::UnreachableCodeReached); + } + } } struct InlineAssemblyGenerator<'a, 'tcx> { @@ -637,7 +733,7 @@ fn call_inline_asm<'tcx>( inputs: Vec<(Size, Value)>, outputs: Vec<(Size, CPlace<'tcx>)>, ) { - let stack_slot = fx.bcx.func.create_stack_slot(StackSlotData { + let stack_slot = fx.bcx.func.create_sized_stack_slot(StackSlotData { kind: StackSlotKind::ExplicitSlot, size: u32::try_from(slot_size.bytes()).unwrap(), }); diff --git a/src/intrinsics/cpuid.rs b/src/intrinsics/cpuid.rs index d02dfd93c3ee3..5120b89c4e8b0 100644 --- a/src/intrinsics/cpuid.rs +++ b/src/intrinsics/cpuid.rs @@ -62,7 +62,7 @@ pub(crate) fn codegen_cpuid_call<'tcx>( fx.bcx.ins().jump(dest, &[zero, zero, proc_info_ecx, proc_info_edx]); fx.bcx.switch_to_block(unsupported_leaf); - crate::trap::trap_unreachable( + crate::trap::trap_unimplemented( fx, "__cpuid_count arch intrinsic doesn't yet support specified leaf", ); diff --git a/src/intrinsics/llvm.rs b/src/intrinsics/llvm.rs index 869670c8cfac7..a799dca938e21 100644 --- a/src/intrinsics/llvm.rs +++ b/src/intrinsics/llvm.rs @@ -139,6 +139,7 @@ pub(crate) fn codegen_llvm_intrinsic_call<'tcx>( .sess .warn(&format!("unsupported llvm intrinsic {}; replacing with trap", intrinsic)); crate::trap::trap_unimplemented(fx, intrinsic); + return; } } diff --git a/src/intrinsics/mod.rs b/src/intrinsics/mod.rs index b2a83e1d4ebc9..ef3d5ccea8a24 100644 --- a/src/intrinsics/mod.rs +++ b/src/intrinsics/mod.rs @@ -44,7 +44,7 @@ fn report_atomic_type_validation_error<'tcx>( ), ); // Prevent verifier error - crate::trap::trap_unreachable(fx, "compilation should not have succeeded"); + fx.bcx.ins().trap(TrapCode::UnreachableCodeReached); } pub(crate) fn clif_vector_type<'tcx>(tcx: TyCtxt<'tcx>, layout: TyAndLayout<'tcx>) -> Option { @@ -53,7 +53,7 @@ pub(crate) fn clif_vector_type<'tcx>(tcx: TyCtxt<'tcx>, layout: TyAndLayout<'tcx _ => unreachable!(), }; - match scalar_to_clif_type(tcx, element).by(u16::try_from(count).unwrap()) { + match scalar_to_clif_type(tcx, element).by(u32::try_from(count).unwrap()) { // Cranelift currently only implements icmp for 128bit vectors. Some(vector_ty) if vector_ty.bits() == 128 => Some(vector_ty), _ => None, @@ -301,7 +301,44 @@ fn codegen_float_intrinsic_call<'tcx>( _ => unreachable!(), }; - let res = fx.easy_call(name, &args, ty); + let layout = fx.layout_of(ty); + let res = match intrinsic { + sym::fmaf32 | sym::fmaf64 => { + let a = args[0].load_scalar(fx); + let b = args[1].load_scalar(fx); + let c = args[2].load_scalar(fx); + CValue::by_val(fx.bcx.ins().fma(a, b, c), layout) + } + sym::copysignf32 | sym::copysignf64 => { + let a = args[0].load_scalar(fx); + let b = args[1].load_scalar(fx); + CValue::by_val(fx.bcx.ins().fcopysign(a, b), layout) + } + sym::fabsf32 + | sym::fabsf64 + | sym::floorf32 + | sym::floorf64 + | sym::ceilf32 + | sym::ceilf64 + | sym::truncf32 + | sym::truncf64 => { + let a = args[0].load_scalar(fx); + + let val = match intrinsic { + sym::fabsf32 | sym::fabsf64 => fx.bcx.ins().fabs(a), + sym::floorf32 | sym::floorf64 => fx.bcx.ins().floor(a), + sym::ceilf32 | sym::ceilf64 => fx.bcx.ins().ceil(a), + sym::truncf32 | sym::truncf64 => fx.bcx.ins().trunc(a), + _ => unreachable!(), + }; + + CValue::by_val(val, layout) + } + // These intrinsics aren't supported natively by Cranelift. + // Lower them to a libcall. + _ => fx.easy_call(name, &args, ty), + }; + ret.write_cvalue(fx, res); true @@ -818,8 +855,6 @@ fn codegen_regular_intrinsic_call<'tcx>( if fx.tcx.is_compiler_builtins(LOCAL_CRATE) { // special case for compiler-builtins to avoid having to patch it crate::trap::trap_unimplemented(fx, "128bit atomics not yet supported"); - let ret_block = fx.get_block(destination.unwrap()); - fx.bcx.ins().jump(ret_block, &[]); return; } else { fx.tcx @@ -851,8 +886,6 @@ fn codegen_regular_intrinsic_call<'tcx>( if fx.tcx.is_compiler_builtins(LOCAL_CRATE) { // special case for compiler-builtins to avoid having to patch it crate::trap::trap_unimplemented(fx, "128bit atomics not yet supported"); - let ret_block = fx.get_block(destination.unwrap()); - fx.bcx.ins().jump(ret_block, &[]); return; } else { fx.tcx diff --git a/src/intrinsics/simd.rs b/src/intrinsics/simd.rs index 30e3d112594a6..a32b413d45f93 100644 --- a/src/intrinsics/simd.rs +++ b/src/intrinsics/simd.rs @@ -14,7 +14,7 @@ fn report_simd_type_validation_error( ) { fx.tcx.sess.span_err(span, &format!("invalid monomorphization of `{}` intrinsic: expected SIMD input type, found non-SIMD `{}`", intrinsic, ty)); // Prevent verifier error - crate::trap::trap_unreachable(fx, "compilation should not have succeeded"); + fx.bcx.ins().trap(TrapCode::UnreachableCodeReached); } pub(super) fn codegen_simd_intrinsic_call<'tcx>( @@ -157,7 +157,7 @@ pub(super) fn codegen_simd_intrinsic_call<'tcx>( ), ); // Prevent verifier error - crate::trap::trap_unreachable(fx, "compilation should not have succeeded"); + fx.bcx.ins().trap(TrapCode::UnreachableCodeReached); return; } } @@ -274,12 +274,17 @@ pub(super) fn codegen_simd_intrinsic_call<'tcx>( idx_const } else { fx.tcx.sess.span_warn(span, "Index argument for `simd_extract` is not a constant"); - let res = crate::trap::trap_unimplemented_ret_value( + let trap_block = fx.bcx.create_block(); + let dummy_block = fx.bcx.create_block(); + let true_ = fx.bcx.ins().iconst(types::I8, 1); + fx.bcx.ins().brnz(true_, trap_block, &[]); + fx.bcx.ins().jump(dummy_block, &[]); + fx.bcx.switch_to_block(trap_block); + crate::trap::trap_unimplemented( fx, - ret.layout(), "Index argument for `simd_extract` is not a constant", ); - ret.write_cvalue(fx, res); + fx.bcx.switch_to_block(dummy_block); return; }; @@ -392,21 +397,15 @@ pub(super) fn codegen_simd_intrinsic_call<'tcx>( let layout = a.layout(); let (lane_count, lane_ty) = layout.ty.simd_size_and_type(fx.tcx); + let res_lane_layout = fx.layout_of(lane_ty); for lane in 0..lane_count { - let a_lane = a.value_lane(fx, lane); - let b_lane = b.value_lane(fx, lane); - let c_lane = c.value_lane(fx, lane); + let a_lane = a.value_lane(fx, lane).load_scalar(fx); + let b_lane = b.value_lane(fx, lane).load_scalar(fx); + let c_lane = c.value_lane(fx, lane).load_scalar(fx); - let res_lane = match lane_ty.kind() { - ty::Float(FloatTy::F32) => { - fx.easy_call("fmaf", &[a_lane, b_lane, c_lane], lane_ty) - } - ty::Float(FloatTy::F64) => { - fx.easy_call("fma", &[a_lane, b_lane, c_lane], lane_ty) - } - _ => unreachable!(), - }; + let res_lane = fx.bcx.ins().fma(a_lane, b_lane, c_lane); + let res_lane = CValue::by_val(res_lane, res_lane_layout); ret.place_lane(fx, lane).write_cvalue(fx, res_lane); } diff --git a/src/lib.rs b/src/lib.rs index bb0793b1deb2e..913414e761821 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -4,6 +4,7 @@ #![warn(unused_lifetimes)] #![warn(unreachable_pub)] +extern crate jobserver; #[macro_use] extern crate rustc_middle; extern crate rustc_ast; @@ -25,10 +26,12 @@ extern crate rustc_target; extern crate rustc_driver; use std::any::Any; -use std::cell::Cell; +use std::cell::{Cell, RefCell}; +use std::sync::Arc; use rustc_codegen_ssa::traits::CodegenBackend; use rustc_codegen_ssa::CodegenResults; +use rustc_data_structures::profiling::SelfProfilerRef; use rustc_errors::ErrorGuaranteed; use rustc_metadata::EncodedMetadata; use rustc_middle::dep_graph::{WorkProduct, WorkProductId}; @@ -51,11 +54,13 @@ mod cast; mod codegen_i128; mod common; mod compiler_builtins; +mod concurrency_limiter; mod config; mod constant; mod debuginfo; mod discriminant; mod driver; +mod global_asm; mod inline_asm; mod intrinsics; mod linkage; @@ -119,19 +124,20 @@ impl String> Drop for PrintOnPanic { /// The codegen context holds any information shared between the codegen of individual functions /// inside a single codegen unit with the exception of the Cranelift [`Module`](cranelift_module::Module). -struct CodegenCx<'tcx> { - tcx: TyCtxt<'tcx>, +struct CodegenCx { + profiler: SelfProfilerRef, + output_filenames: Arc, + should_write_ir: bool, global_asm: String, inline_asm_index: Cell, - cached_context: Context, - debug_context: Option>, + debug_context: Option, unwind_context: UnwindContext, cgu_name: Symbol, } -impl<'tcx> CodegenCx<'tcx> { +impl CodegenCx { fn new( - tcx: TyCtxt<'tcx>, + tcx: TyCtxt<'_>, backend_config: BackendConfig, isa: &dyn TargetIsa, debug_info: bool, @@ -147,10 +153,11 @@ impl<'tcx> CodegenCx<'tcx> { None }; CodegenCx { - tcx, + profiler: tcx.prof.clone(), + output_filenames: tcx.output_filenames(()).clone(), + should_write_ir: crate::pretty_clif::should_write_ir(tcx), global_asm: String::new(), inline_asm_index: Cell::new(0), - cached_context: Context::new(), debug_context, unwind_context, cgu_name, @@ -159,7 +166,7 @@ impl<'tcx> CodegenCx<'tcx> { } pub struct CraneliftCodegenBackend { - pub config: Option, + pub config: RefCell>, } impl CodegenBackend for CraneliftCodegenBackend { @@ -169,6 +176,13 @@ impl CodegenBackend for CraneliftCodegenBackend { Lto::No | Lto::ThinLocal => {} Lto::Thin | Lto::Fat => sess.warn("LTO is not supported. You may get a linker error."), } + + let mut config = self.config.borrow_mut(); + if config.is_none() { + let new_config = BackendConfig::from_opts(&sess.opts.cg.llvm_args) + .unwrap_or_else(|err| sess.fatal(&err)); + *config = Some(new_config); + } } fn target_features(&self, _sess: &Session, _allow_unstable: bool) -> Vec { @@ -186,15 +200,7 @@ impl CodegenBackend for CraneliftCodegenBackend { need_metadata_module: bool, ) -> Box { tcx.sess.abort_if_errors(); - let config = if let Some(config) = self.config.clone() { - config - } else { - if !tcx.sess.unstable_options() && !tcx.sess.opts.cg.llvm_args.is_empty() { - tcx.sess.fatal("`-Z unstable-options` must be passed to allow configuring cg_clif"); - } - BackendConfig::from_opts(&tcx.sess.opts.cg.llvm_args) - .unwrap_or_else(|err| tcx.sess.fatal(&err)) - }; + let config = self.config.borrow().clone().unwrap(); match config.codegen_mode { CodegenMode::Aot => driver::aot::run_aot(tcx, config, metadata, need_metadata_module), CodegenMode::Jit | CodegenMode::JitLazy => { @@ -210,12 +216,13 @@ impl CodegenBackend for CraneliftCodegenBackend { fn join_codegen( &self, ongoing_codegen: Box, - _sess: &Session, + sess: &Session, _outputs: &OutputFilenames, ) -> Result<(CodegenResults, FxHashMap), ErrorGuaranteed> { - Ok(*ongoing_codegen - .downcast::<(CodegenResults, FxHashMap)>() - .unwrap()) + Ok(ongoing_codegen + .downcast::() + .unwrap() + .join(sess, self.config.borrow().as_ref().unwrap())) } fn link( @@ -312,5 +319,5 @@ fn build_isa(sess: &Session, backend_config: &BackendConfig) -> Box Box { - Box::new(CraneliftCodegenBackend { config: None }) + Box::new(CraneliftCodegenBackend { config: RefCell::new(None) }) } diff --git a/src/optimize/mod.rs b/src/optimize/mod.rs index d1f89adb3bb91..0df7e82294bd2 100644 --- a/src/optimize/mod.rs +++ b/src/optimize/mod.rs @@ -1,20 +1,3 @@ //! Various optimizations specific to cg_clif -use cranelift_codegen::isa::TargetIsa; - -use crate::prelude::*; - pub(crate) mod peephole; - -pub(crate) fn optimize_function<'tcx>( - tcx: TyCtxt<'tcx>, - isa: &dyn TargetIsa, - instance: Instance<'tcx>, - ctx: &mut Context, - clif_comments: &mut crate::pretty_clif::CommentWriter, -) { - // FIXME classify optimizations over opt levels once we have more - - crate::pretty_clif::write_clif_file(tcx, "preopt", isa, instance, &ctx.func, &*clif_comments); - crate::base::verify_func(tcx, &*clif_comments, &ctx.func); -} diff --git a/src/pretty_clif.rs b/src/pretty_clif.rs index 1d1ec21680e30..a7af162687c34 100644 --- a/src/pretty_clif.rs +++ b/src/pretty_clif.rs @@ -62,7 +62,7 @@ use cranelift_codegen::{ }; use rustc_middle::ty::layout::FnAbiOf; -use rustc_session::config::OutputType; +use rustc_session::config::{OutputFilenames, OutputType}; use crate::prelude::*; @@ -205,15 +205,11 @@ pub(crate) fn should_write_ir(tcx: TyCtxt<'_>) -> bool { } pub(crate) fn write_ir_file( - tcx: TyCtxt<'_>, - name: impl FnOnce() -> String, + output_filenames: &OutputFilenames, + name: &str, write: impl FnOnce(&mut dyn Write) -> std::io::Result<()>, ) { - if !should_write_ir(tcx) { - return; - } - - let clif_output_dir = tcx.output_filenames(()).with_extension("clif"); + let clif_output_dir = output_filenames.with_extension("clif"); match std::fs::create_dir(&clif_output_dir) { Ok(()) => {} @@ -221,44 +217,43 @@ pub(crate) fn write_ir_file( res @ Err(_) => res.unwrap(), } - let clif_file_name = clif_output_dir.join(name()); + let clif_file_name = clif_output_dir.join(name); let res = std::fs::File::create(clif_file_name).and_then(|mut file| write(&mut file)); if let Err(err) = res { - tcx.sess.warn(&format!("error writing ir file: {}", err)); + // Using early_warn as no Session is available here + rustc_session::early_warn( + rustc_session::config::ErrorOutputType::default(), + &format!("error writing ir file: {}", err), + ); } } -pub(crate) fn write_clif_file<'tcx>( - tcx: TyCtxt<'tcx>, +pub(crate) fn write_clif_file( + output_filenames: &OutputFilenames, + symbol_name: &str, postfix: &str, isa: &dyn cranelift_codegen::isa::TargetIsa, - instance: Instance<'tcx>, func: &cranelift_codegen::ir::Function, mut clif_comments: &CommentWriter, ) { // FIXME work around filename too long errors - write_ir_file( - tcx, - || format!("{}.{}.clif", tcx.symbol_name(instance).name, postfix), - |file| { - let mut clif = String::new(); - cranelift_codegen::write::decorate_function(&mut clif_comments, &mut clif, func) - .unwrap(); + write_ir_file(output_filenames, &format!("{}.{}.clif", symbol_name, postfix), |file| { + let mut clif = String::new(); + cranelift_codegen::write::decorate_function(&mut clif_comments, &mut clif, func).unwrap(); - for flag in isa.flags().iter() { - writeln!(file, "set {}", flag)?; - } - write!(file, "target {}", isa.triple().architecture.to_string())?; - for isa_flag in isa.isa_flags().iter() { - write!(file, " {}", isa_flag)?; - } - writeln!(file, "\n")?; - writeln!(file)?; - file.write_all(clif.as_bytes())?; - Ok(()) - }, - ); + for flag in isa.flags().iter() { + writeln!(file, "set {}", flag)?; + } + write!(file, "target {}", isa.triple().architecture.to_string())?; + for isa_flag in isa.isa_flags().iter() { + write!(file, " {}", isa_flag)?; + } + writeln!(file, "\n")?; + writeln!(file)?; + file.write_all(clif.as_bytes())?; + Ok(()) + }); } impl fmt::Debug for FunctionCx<'_, '_, '_> { diff --git a/src/toolchain.rs b/src/toolchain.rs index f86236ef3eafc..b6b465e1f4e0a 100644 --- a/src/toolchain.rs +++ b/src/toolchain.rs @@ -8,10 +8,8 @@ use rustc_session::Session; /// Tries to infer the path of a binary for the target toolchain from the linker name. pub(crate) fn get_toolchain_binary(sess: &Session, tool: &str) -> PathBuf { let (mut linker, _linker_flavor) = linker_and_flavor(sess); - let linker_file_name = linker - .file_name() - .and_then(|name| name.to_str()) - .unwrap_or_else(|| sess.fatal("couldn't extract file name from specified linker")); + let linker_file_name = + linker.file_name().unwrap().to_str().expect("linker filename should be valid UTF-8"); if linker_file_name == "ld.lld" { if tool != "ld" { diff --git a/src/trap.rs b/src/trap.rs index 923269c4de9ab..82a2ec5795496 100644 --- a/src/trap.rs +++ b/src/trap.rs @@ -25,33 +25,10 @@ fn codegen_print(fx: &mut FunctionCx<'_, '_, '_>, msg: &str) { fx.bcx.ins().call(puts, &[msg_ptr]); } -/// Use this for example when a function call should never return. This will fill the current block, -/// so you can **not** add instructions to it afterwards. -/// -/// Trap code: user65535 -pub(crate) fn trap_unreachable(fx: &mut FunctionCx<'_, '_, '_>, msg: impl AsRef) { - codegen_print(fx, msg.as_ref()); - fx.bcx.ins().trap(TrapCode::UnreachableCodeReached); -} /// Use this when something is unimplemented, but `libcore` or `libstd` requires it to codegen. -/// Unlike `trap_unreachable` this will not fill the current block, so you **must** add instructions -/// to it afterwards. /// /// Trap code: user65535 pub(crate) fn trap_unimplemented(fx: &mut FunctionCx<'_, '_, '_>, msg: impl AsRef) { codegen_print(fx, msg.as_ref()); - let true_ = fx.bcx.ins().iconst(types::I32, 1); - fx.bcx.ins().trapnz(true_, TrapCode::User(!0)); -} - -/// Like `trap_unimplemented` but returns a fake value of the specified type. -/// -/// Trap code: user65535 -pub(crate) fn trap_unimplemented_ret_value<'tcx>( - fx: &mut FunctionCx<'_, '_, 'tcx>, - dest_layout: TyAndLayout<'tcx>, - msg: impl AsRef, -) -> CValue<'tcx> { - trap_unimplemented(fx, msg); - CValue::by_ref(Pointer::const_addr(fx, 0), dest_layout) + fx.bcx.ins().trap(TrapCode::User(!0)); } diff --git a/src/value_and_place.rs b/src/value_and_place.rs index 45ae2bd8f07cb..2ee98546c992a 100644 --- a/src/value_and_place.rs +++ b/src/value_and_place.rs @@ -122,7 +122,7 @@ impl<'tcx> CValue<'tcx> { let clif_ty = match layout.abi { Abi::Scalar(scalar) => scalar_to_clif_type(fx.tcx, scalar), Abi::Vector { element, count } => scalar_to_clif_type(fx.tcx, element) - .by(u16::try_from(count).unwrap()) + .by(u32::try_from(count).unwrap()) .unwrap(), _ => unreachable!("{:?}", layout.ty), }; @@ -330,7 +330,7 @@ impl<'tcx> CPlace<'tcx> { .fatal(&format!("values of type {} are too big to store on the stack", layout.ty)); } - let stack_slot = fx.bcx.create_stack_slot(StackSlotData { + let stack_slot = fx.bcx.create_sized_stack_slot(StackSlotData { kind: StackSlotKind::ExplicitSlot, // FIXME Don't force the size to a multiple of 16 bytes once Cranelift gets a way to // specify stack slot alignment. @@ -472,7 +472,7 @@ impl<'tcx> CPlace<'tcx> { } _ if src_ty.is_vector() || dst_ty.is_vector() => { // FIXME do something more efficient for transmutes between vectors and integers. - let stack_slot = fx.bcx.create_stack_slot(StackSlotData { + let stack_slot = fx.bcx.create_sized_stack_slot(StackSlotData { kind: StackSlotKind::ExplicitSlot, // FIXME Don't force the size to a multiple of 16 bytes once Cranelift gets a way to // specify stack slot alignment. @@ -519,7 +519,7 @@ impl<'tcx> CPlace<'tcx> { if let ty::Array(element, len) = dst_layout.ty.kind() { // Can only happen for vector types let len = - u16::try_from(len.eval_usize(fx.tcx, ParamEnv::reveal_all())).unwrap(); + u32::try_from(len.eval_usize(fx.tcx, ParamEnv::reveal_all())).unwrap(); let vector_ty = fx.clif_type(*element).unwrap().by(len).unwrap(); let data = match from.0 { @@ -614,7 +614,7 @@ impl<'tcx> CPlace<'tcx> { dst_align, src_align, true, - MemFlags::trusted(), + flags, ); } CValueInner::ByRef(_, Some(_)) => todo!(), diff --git a/test.sh b/test.sh index a10924628bb0e..3d929a1d50ce2 100755 --- a/test.sh +++ b/test.sh @@ -1,13 +1,2 @@ #!/usr/bin/env bash -set -e - -./y.rs build --sysroot none "$@" - -rm -r target/out || true - -scripts/tests.sh no_sysroot - -./y.rs build "$@" - -scripts/tests.sh base_sysroot -scripts/tests.sh extended_sysroot +exec ./y.rs test From d9bbac069b1c8f235bcf2415a47b783fb945b4a7 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Wed, 24 Aug 2022 17:06:47 +0000 Subject: [PATCH 05/98] Rustfmt --- build_system/tests.rs | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/build_system/tests.rs b/build_system/tests.rs index dc83b10958e01..e21397cece8b3 100644 --- a/build_system/tests.rs +++ b/build_system/tests.rs @@ -465,7 +465,8 @@ impl TestRunner { out_dir.push("out"); let is_native = host_triple == target_triple; - let jit_supported = target_triple.contains("x86_64") && is_native && !host_triple.contains("windows"); + let jit_supported = + target_triple.contains("x86_64") && is_native && !host_triple.contains("windows"); let mut rust_flags = env::var("RUSTFLAGS").ok().unwrap_or("".to_string()); let mut run_wrapper = Vec::new(); From 8c93170965d026962b59052ee579dd436883d195 Mon Sep 17 00:00:00 2001 From: Nathan Stocks Date: Wed, 24 Aug 2022 16:52:46 -0600 Subject: [PATCH 06/98] adjust to new error value --- src/base.rs | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/src/base.rs b/src/base.rs index 44c34d6c8cb79..3a2875e5d27d5 100644 --- a/src/base.rs +++ b/src/base.rs @@ -925,8 +925,11 @@ pub(crate) fn codegen_panic_inner<'tcx>( args: &[Value], span: Span, ) { - let def_id = - fx.tcx.lang_items().require(lang_item).unwrap_or_else(|s| fx.tcx.sess.span_fatal(span, &s)); + let def_id = fx + .tcx + .lang_items() + .require(lang_item) + .unwrap_or_else(|e| fx.tcx.sess.span_fatal(span, e.to_string())); let instance = Instance::mono(fx.tcx, def_id).polymorphize(fx.tcx); let symbol_name = fx.tcx.symbol_name(instance).name; From 1c989472e41f0b6033bcf62b76dcd28f75e7b25b Mon Sep 17 00:00:00 2001 From: Nicholas Nethercote Date: Thu, 25 Aug 2022 17:52:37 +1000 Subject: [PATCH 07/98] Box `CastTarget` within `PassMode`. Because `PassMode::Cast` is by far the largest variant, but is relatively rare. This requires making `PassMode` not impl `Copy`, and `Clone` is no longer necessary. This causes lots of sigil adjusting, but nothing very notable. --- src/abi/comments.rs | 2 +- src/abi/pass_mode.rs | 20 ++++++++++++-------- src/abi/returning.rs | 6 +++--- 3 files changed, 16 insertions(+), 12 deletions(-) diff --git a/src/abi/comments.rs b/src/abi/comments.rs index 37d2679c10d70..7f4619b5c940b 100644 --- a/src/abi/comments.rs +++ b/src/abi/comments.rs @@ -24,7 +24,7 @@ pub(super) fn add_arg_comment<'tcx>( local: Option, local_field: Option, params: &[Value], - arg_abi_mode: PassMode, + arg_abi_mode: &PassMode, arg_layout: TyAndLayout<'tcx>, ) { if !fx.clif_comments.enabled() { diff --git a/src/abi/pass_mode.rs b/src/abi/pass_mode.rs index 6c10baa53d415..058dee176e243 100644 --- a/src/abi/pass_mode.rs +++ b/src/abi/pass_mode.rs @@ -38,7 +38,7 @@ fn apply_arg_attrs_to_abi_param(mut param: AbiParam, arg_attrs: ArgAttributes) - param } -fn cast_target_to_abi_params(cast: CastTarget) -> SmallVec<[AbiParam; 2]> { +fn cast_target_to_abi_params(cast: &CastTarget) -> SmallVec<[AbiParam; 2]> { let (rest_count, rem_bytes) = if cast.rest.unit.size.bytes() == 0 { (0, 0) } else { @@ -100,7 +100,7 @@ impl<'tcx> ArgAbiExt<'tcx> for ArgAbi<'tcx, Ty<'tcx>> { } _ => unreachable!("{:?}", self.layout.abi), }, - PassMode::Cast(cast) => cast_target_to_abi_params(cast), + PassMode::Cast(ref cast) => cast_target_to_abi_params(cast), PassMode::Indirect { attrs, extra_attrs: None, on_stack } => { if on_stack { // Abi requires aligning struct size to pointer size @@ -145,7 +145,9 @@ impl<'tcx> ArgAbiExt<'tcx> for ArgAbi<'tcx, Ty<'tcx>> { } _ => unreachable!("{:?}", self.layout.abi), }, - PassMode::Cast(cast) => (None, cast_target_to_abi_params(cast).into_iter().collect()), + PassMode::Cast(ref cast) => { + (None, cast_target_to_abi_params(cast).into_iter().collect()) + } PassMode::Indirect { attrs: _, extra_attrs: None, on_stack } => { assert!(!on_stack); (Some(AbiParam::special(pointer_ty(tcx), ArgumentPurpose::StructReturn)), vec![]) @@ -160,7 +162,7 @@ impl<'tcx> ArgAbiExt<'tcx> for ArgAbi<'tcx, Ty<'tcx>> { pub(super) fn to_casted_value<'tcx>( fx: &mut FunctionCx<'_, '_, 'tcx>, arg: CValue<'tcx>, - cast: CastTarget, + cast: &CastTarget, ) -> SmallVec<[Value; 2]> { let (ptr, meta) = arg.force_stack(fx); assert!(meta.is_none()); @@ -179,7 +181,7 @@ pub(super) fn from_casted_value<'tcx>( fx: &mut FunctionCx<'_, '_, 'tcx>, block_params: &[Value], layout: TyAndLayout<'tcx>, - cast: CastTarget, + cast: &CastTarget, ) -> CValue<'tcx> { let abi_params = cast_target_to_abi_params(cast); let abi_param_size: u32 = abi_params.iter().map(|param| param.value_type.bytes()).sum(); @@ -224,7 +226,7 @@ pub(super) fn adjust_arg_for_abi<'tcx>( let (a, b) = arg.load_scalar_pair(fx); smallvec![a, b] } - PassMode::Cast(cast) => to_casted_value(fx, arg, cast), + PassMode::Cast(ref cast) => to_casted_value(fx, arg, cast), PassMode::Indirect { .. } => { if is_owned { match arg.force_stack(fx) { @@ -268,7 +270,7 @@ pub(super) fn cvalue_for_param<'tcx>( local, local_field, &block_params, - arg_abi.mode, + &arg_abi.mode, arg_abi.layout, ); @@ -282,7 +284,9 @@ pub(super) fn cvalue_for_param<'tcx>( assert_eq!(block_params.len(), 2, "{:?}", block_params); Some(CValue::by_val_pair(block_params[0], block_params[1], arg_abi.layout)) } - PassMode::Cast(cast) => Some(from_casted_value(fx, &block_params, arg_abi.layout, cast)), + PassMode::Cast(ref cast) => { + Some(from_casted_value(fx, &block_params, arg_abi.layout, cast)) + } PassMode::Indirect { attrs: _, extra_attrs: None, on_stack: _ } => { assert_eq!(block_params.len(), 1, "{:?}", block_params); Some(CValue::by_ref(Pointer::new(block_params[0]), arg_abi.layout)) diff --git a/src/abi/returning.rs b/src/abi/returning.rs index ff3bb2dfd000f..29ef5e2dfdae6 100644 --- a/src/abi/returning.rs +++ b/src/abi/returning.rs @@ -44,7 +44,7 @@ pub(super) fn codegen_return_param<'tcx>( Some(RETURN_PLACE), None, &ret_param, - fx.fn_abi.as_ref().unwrap().ret.mode, + &fx.fn_abi.as_ref().unwrap().ret.mode, fx.fn_abi.as_ref().unwrap().ret.layout, ); @@ -92,7 +92,7 @@ pub(super) fn codegen_with_call_return_arg<'tcx>( ret_place .write_cvalue(fx, CValue::by_val_pair(ret_val_a, ret_val_b, ret_arg_abi.layout)); } - PassMode::Cast(cast) => { + PassMode::Cast(ref cast) => { let results = fx.bcx.inst_results(call_inst).iter().copied().collect::>(); let result = @@ -131,7 +131,7 @@ pub(crate) fn codegen_return(fx: &mut FunctionCx<'_, '_, '_>) { let (ret_val_a, ret_val_b) = place.to_cvalue(fx).load_scalar_pair(fx); fx.bcx.ins().return_(&[ret_val_a, ret_val_b]); } - PassMode::Cast(cast) => { + PassMode::Cast(ref cast) => { let place = fx.get_local_place(RETURN_PLACE); let ret_val = place.to_cvalue(fx); let ret_vals = super::pass_mode::to_casted_value(fx, ret_val, cast); From 2d2a3be651db8da69c391e0bdfe0189fe1d504d5 Mon Sep 17 00:00:00 2001 From: Nicholas Nethercote Date: Thu, 25 Aug 2022 22:19:38 +1000 Subject: [PATCH 08/98] Move `ArgAbi::pad_i32` into `PassMode::Cast`. Because it's only needed for that variant. This shrinks the types and clarifies the logic. --- src/abi/pass_mode.rs | 11 +++++++---- src/abi/returning.rs | 8 ++++---- 2 files changed, 11 insertions(+), 8 deletions(-) diff --git a/src/abi/pass_mode.rs b/src/abi/pass_mode.rs index 058dee176e243..165f15bb3f122 100644 --- a/src/abi/pass_mode.rs +++ b/src/abi/pass_mode.rs @@ -100,7 +100,10 @@ impl<'tcx> ArgAbiExt<'tcx> for ArgAbi<'tcx, Ty<'tcx>> { } _ => unreachable!("{:?}", self.layout.abi), }, - PassMode::Cast(ref cast) => cast_target_to_abi_params(cast), + PassMode::Cast(ref cast, pad_i32) => { + assert!(!pad_i32, "padding support not yet implemented"); + cast_target_to_abi_params(cast) + } PassMode::Indirect { attrs, extra_attrs: None, on_stack } => { if on_stack { // Abi requires aligning struct size to pointer size @@ -145,7 +148,7 @@ impl<'tcx> ArgAbiExt<'tcx> for ArgAbi<'tcx, Ty<'tcx>> { } _ => unreachable!("{:?}", self.layout.abi), }, - PassMode::Cast(ref cast) => { + PassMode::Cast(ref cast, _) => { (None, cast_target_to_abi_params(cast).into_iter().collect()) } PassMode::Indirect { attrs: _, extra_attrs: None, on_stack } => { @@ -226,7 +229,7 @@ pub(super) fn adjust_arg_for_abi<'tcx>( let (a, b) = arg.load_scalar_pair(fx); smallvec![a, b] } - PassMode::Cast(ref cast) => to_casted_value(fx, arg, cast), + PassMode::Cast(ref cast, _) => to_casted_value(fx, arg, cast), PassMode::Indirect { .. } => { if is_owned { match arg.force_stack(fx) { @@ -284,7 +287,7 @@ pub(super) fn cvalue_for_param<'tcx>( assert_eq!(block_params.len(), 2, "{:?}", block_params); Some(CValue::by_val_pair(block_params[0], block_params[1], arg_abi.layout)) } - PassMode::Cast(ref cast) => { + PassMode::Cast(ref cast, _) => { Some(from_casted_value(fx, &block_params, arg_abi.layout, cast)) } PassMode::Indirect { attrs: _, extra_attrs: None, on_stack: _ } => { diff --git a/src/abi/returning.rs b/src/abi/returning.rs index 29ef5e2dfdae6..aaa1418767a35 100644 --- a/src/abi/returning.rs +++ b/src/abi/returning.rs @@ -13,7 +13,7 @@ pub(super) fn codegen_return_param<'tcx>( block_params_iter: &mut impl Iterator, ) -> CPlace<'tcx> { let (ret_place, ret_param): (_, SmallVec<[_; 2]>) = match fx.fn_abi.as_ref().unwrap().ret.mode { - PassMode::Ignore | PassMode::Direct(_) | PassMode::Pair(_, _) | PassMode::Cast(_) => { + PassMode::Ignore | PassMode::Direct(_) | PassMode::Pair(_, _) | PassMode::Cast(..) => { let is_ssa = ssa_analyzed[RETURN_PLACE] == crate::analyze::SsaKind::Ssa; ( super::make_local_place( @@ -75,7 +75,7 @@ pub(super) fn codegen_with_call_return_arg<'tcx>( PassMode::Indirect { attrs: _, extra_attrs: Some(_), on_stack: _ } => { unreachable!("unsized return value") } - PassMode::Direct(_) | PassMode::Pair(_, _) | PassMode::Cast(_) => (None, None), + PassMode::Direct(_) | PassMode::Pair(_, _) | PassMode::Cast(..) => (None, None), }; let call_inst = f(fx, return_ptr); @@ -92,7 +92,7 @@ pub(super) fn codegen_with_call_return_arg<'tcx>( ret_place .write_cvalue(fx, CValue::by_val_pair(ret_val_a, ret_val_b, ret_arg_abi.layout)); } - PassMode::Cast(ref cast) => { + PassMode::Cast(ref cast, _) => { let results = fx.bcx.inst_results(call_inst).iter().copied().collect::>(); let result = @@ -131,7 +131,7 @@ pub(crate) fn codegen_return(fx: &mut FunctionCx<'_, '_, '_>) { let (ret_val_a, ret_val_b) = place.to_cvalue(fx).load_scalar_pair(fx); fx.bcx.ins().return_(&[ret_val_a, ret_val_b]); } - PassMode::Cast(ref cast) => { + PassMode::Cast(ref cast, _) => { let place = fx.get_local_place(RETURN_PLACE); let ret_val = place.to_cvalue(fx); let ret_vals = super::pass_mode::to_casted_value(fx, ret_val, cast); From 1071c4c10bb24f12b65bfface2859c1fd8898575 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tomasz=20Mi=C4=85sko?= Date: Tue, 5 Jul 2022 00:00:00 +0000 Subject: [PATCH 09/98] Replace `Body::basic_blocks()` with field access --- src/analyze.rs | 2 +- src/base.rs | 4 ++-- src/constant.rs | 2 +- 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/src/analyze.rs b/src/analyze.rs index 35b89358b1984..0cbb9f3ec2d80 100644 --- a/src/analyze.rs +++ b/src/analyze.rs @@ -26,7 +26,7 @@ pub(crate) fn analyze(fx: &FunctionCx<'_, '_, '_>) -> IndexVec { }) .collect::>(); - for bb in fx.mir.basic_blocks().iter() { + for bb in fx.mir.basic_blocks.iter() { for stmt in bb.statements.iter() { match &stmt.kind { Assign(place_and_rval) => match &place_and_rval.1 { diff --git a/src/base.rs b/src/base.rs index 44c34d6c8cb79..3011813c7035b 100644 --- a/src/base.rs +++ b/src/base.rs @@ -73,7 +73,7 @@ pub(crate) fn codegen_fn<'tcx>( // Predefine blocks let start_block = bcx.create_block(); let block_map: IndexVec = - (0..mir.basic_blocks().len()).map(|_| bcx.create_block()).collect(); + (0..mir.basic_blocks.len()).map(|_| bcx.create_block()).collect(); // Make FunctionCx let target_config = module.target_config(); @@ -271,7 +271,7 @@ fn codegen_fn_body(fx: &mut FunctionCx<'_, '_, '_>, start_block: Block) { } fx.tcx.sess.time("codegen prelude", || crate::abi::codegen_fn_prelude(fx, start_block)); - for (bb, bb_data) in fx.mir.basic_blocks().iter_enumerated() { + for (bb, bb_data) in fx.mir.basic_blocks.iter_enumerated() { let block = fx.get_block(bb); fx.bcx.switch_to_block(block); diff --git a/src/constant.rs b/src/constant.rs index 7f7fd0e9c579d..e2b68f24a21dc 100644 --- a/src/constant.rs +++ b/src/constant.rs @@ -505,7 +505,7 @@ pub(crate) fn mir_operand_get_const_val<'tcx>( return None; } let mut computed_const_val = None; - for bb_data in fx.mir.basic_blocks() { + for bb_data in fx.mir.basic_blocks.iter() { for stmt in &bb_data.statements { match &stmt.kind { StatementKind::Assign(local_and_rvalue) if &local_and_rvalue.0 == place => { From 0644a8c8582205b065aa902aeacfc45e87ee053d Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Sat, 27 Aug 2022 14:11:19 -0400 Subject: [PATCH 10/98] =?UTF-8?q?interpret:=20rename=20relocation=20?= =?UTF-8?q?=E2=86=92=20provenance?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/constant.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/constant.rs b/src/constant.rs index 7f7fd0e9c579d..4f1531139322b 100644 --- a/src/constant.rs +++ b/src/constant.rs @@ -430,7 +430,7 @@ fn define_all_allocs(tcx: TyCtxt<'_>, module: &mut dyn Module, cx: &mut Constant let bytes = alloc.inspect_with_uninit_and_ptr_outside_interpreter(0..alloc.len()).to_vec(); data_ctx.define(bytes.into_boxed_slice()); - for &(offset, alloc_id) in alloc.relocations().iter() { + for &(offset, alloc_id) in alloc.provenance().iter() { let addend = { let endianness = tcx.data_layout.endian; let offset = offset.bytes() as usize; From 94f2fef4ccadb716f4662475afdb9905143d53f2 Mon Sep 17 00:00:00 2001 From: Ralf Jung Date: Sat, 27 Aug 2022 14:54:02 -0400 Subject: [PATCH 11/98] interpret: make read-pointer-as-bytes *always* work in Miri and show some extra information when it happens in CTFE --- src/intrinsics/simd.rs | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/src/intrinsics/simd.rs b/src/intrinsics/simd.rs index a32b413d45f93..1f358b1bbb96e 100644 --- a/src/intrinsics/simd.rs +++ b/src/intrinsics/simd.rs @@ -186,7 +186,10 @@ pub(super) fn codegen_simd_intrinsic_call<'tcx>( let size = Size::from_bytes( 4 * ret_lane_count, /* size_of([u32; ret_lane_count]) */ ); - alloc.inner().get_bytes(fx, alloc_range(offset, size)).unwrap() + alloc + .inner() + .get_bytes_strip_provenance(fx, alloc_range(offset, size)) + .unwrap() } _ => unreachable!("{:?}", idx_const), }; From a7de42f61b38dd69a4a58dcf2c7ee69bd4aed50f Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Sun, 28 Aug 2022 10:43:19 +0200 Subject: [PATCH 12/98] Use pull instead of push based model for getting dylib symbols in the jit This avoids having to parse the dylibs to get all symbols and matches the way the dynamic linker resolves symbols. Furthermore it fixes the jit on Windows. --- build_system/tests.rs | 3 +-- src/driver/jit.rs | 51 +++++++++++++++---------------------------- 2 files changed, 18 insertions(+), 36 deletions(-) diff --git a/build_system/tests.rs b/build_system/tests.rs index e21397cece8b3..3f225b4efa2b1 100644 --- a/build_system/tests.rs +++ b/build_system/tests.rs @@ -465,8 +465,7 @@ impl TestRunner { out_dir.push("out"); let is_native = host_triple == target_triple; - let jit_supported = - target_triple.contains("x86_64") && is_native && !host_triple.contains("windows"); + let jit_supported = target_triple.contains("x86_64") && is_native; let mut rust_flags = env::var("RUSTFLAGS").ok().unwrap_or("".to_string()); let mut run_wrapper = Vec::new(); diff --git a/src/driver/jit.rs b/src/driver/jit.rs index 0e77e4004c0bb..4ad859b6d8378 100644 --- a/src/driver/jit.rs +++ b/src/driver/jit.rs @@ -67,13 +67,12 @@ fn create_jit_module( hotswap: bool, ) -> (JITModule, CodegenCx) { let crate_info = CrateInfo::new(tcx, "dummy_target_cpu".to_string()); - let imported_symbols = load_imported_symbols_for_jit(tcx.sess, crate_info); let isa = crate::build_isa(tcx.sess, backend_config); let mut jit_builder = JITBuilder::with_isa(isa, cranelift_module::default_libcall_names()); jit_builder.hotswap(hotswap); crate::compiler_builtins::register_functions_for_jit(&mut jit_builder); - jit_builder.symbols(imported_symbols); + jit_builder.symbol_lookup_fn(dep_symbol_lookup_fn(tcx.sess, crate_info)); jit_builder.symbol("__clif_jit_fn", clif_jit_fn as *const u8); let mut jit_module = JITModule::new(jit_builder); @@ -286,10 +285,10 @@ fn jit_fn(instance_ptr: *const Instance<'static>, trampoline_ptr: *const u8) -> }) } -fn load_imported_symbols_for_jit( +fn dep_symbol_lookup_fn( sess: &Session, crate_info: CrateInfo, -) -> Vec<(String, *const u8)> { +) -> Box Option<*const u8>> { use rustc_middle::middle::dependency_format::Linkage; let mut dylib_paths = Vec::new(); @@ -316,39 +315,23 @@ fn load_imported_symbols_for_jit( } } - let mut imported_symbols = Vec::new(); - for path in dylib_paths { - use object::{Object, ObjectSymbol}; - let lib = libloading::Library::new(&path).unwrap(); - let obj = std::fs::read(path).unwrap(); - let obj = object::File::parse(&*obj).unwrap(); - imported_symbols.extend(obj.dynamic_symbols().filter_map(|symbol| { - let name = symbol.name().unwrap().to_string(); - if name.is_empty() || !symbol.is_global() || symbol.is_undefined() { - return None; - } - if name.starts_with("rust_metadata_") { - // The metadata is part of a section that is not loaded by the dynamic linker in - // case of cg_llvm. - return None; - } - let dlsym_name = if cfg!(target_os = "macos") { - // On macOS `dlsym` expects the name without leading `_`. - assert!(name.starts_with('_'), "{:?}", name); - &name[1..] - } else { - &name - }; - let symbol: libloading::Symbol<'_, *const u8> = - unsafe { lib.get(dlsym_name.as_bytes()) }.unwrap(); - Some((name, *symbol)) - })); - std::mem::forget(lib) - } + let imported_dylibs = Box::leak( + dylib_paths + .into_iter() + .map(|path| libloading::Library::new(&path).unwrap()) + .collect::>(), + ); sess.abort_if_errors(); - imported_symbols + Box::new(move |sym_name| { + for dylib in &*imported_dylibs { + if let Ok(sym) = unsafe { dylib.get::<*const u8>(sym_name.as_bytes()) } { + return Some(*sym); + } + } + None + }) } fn codegen_shim<'tcx>( From 4b3aa91b03c3dbfd05becbd890b4b06574092aab Mon Sep 17 00:00:00 2001 From: Martin Nordholts Date: Tue, 5 Jul 2022 19:56:22 +0200 Subject: [PATCH 13/98] Support `#[unix_sigpipe = "inherit|sig_dfl|sig_ign"]` on `fn main()` This makes it possible to instruct libstd to never touch the signal handler for `SIGPIPE`, which makes programs pipeable by default (e.g. with `./your-program | head -n 1`) without `ErrorKind::BrokenPipe` errors. --- src/main_shim.rs | 15 +++++++++------ 1 file changed, 9 insertions(+), 6 deletions(-) diff --git a/src/main_shim.rs b/src/main_shim.rs index c67b6e98b32c7..3c024a84d9091 100644 --- a/src/main_shim.rs +++ b/src/main_shim.rs @@ -1,7 +1,7 @@ use rustc_hir::LangItem; use rustc_middle::ty::subst::GenericArg; use rustc_middle::ty::AssocKind; -use rustc_session::config::EntryFnType; +use rustc_session::config::{sigpipe, EntryFnType}; use rustc_span::symbol::Ident; use crate::prelude::*; @@ -15,12 +15,12 @@ pub(crate) fn maybe_create_entry_wrapper( is_jit: bool, is_primary_cgu: bool, ) { - let (main_def_id, is_main_fn) = match tcx.entry_fn(()) { + let (main_def_id, (is_main_fn, sigpipe)) = match tcx.entry_fn(()) { Some((def_id, entry_ty)) => ( def_id, match entry_ty { - EntryFnType::Main => true, - EntryFnType::Start => false, + EntryFnType::Main { sigpipe } => (true, sigpipe), + EntryFnType::Start => (false, sigpipe::DEFAULT), }, ), None => return, @@ -35,7 +35,7 @@ pub(crate) fn maybe_create_entry_wrapper( return; } - create_entry_fn(tcx, module, unwind_context, main_def_id, is_jit, is_main_fn); + create_entry_fn(tcx, module, unwind_context, main_def_id, is_jit, is_main_fn, sigpipe); fn create_entry_fn( tcx: TyCtxt<'_>, @@ -44,6 +44,7 @@ pub(crate) fn maybe_create_entry_wrapper( rust_main_def_id: DefId, ignore_lang_start_wrapper: bool, is_main_fn: bool, + sigpipe: u8, ) { let main_ret_ty = tcx.fn_sig(rust_main_def_id).output(); // Given that `main()` has no arguments, @@ -83,6 +84,7 @@ pub(crate) fn maybe_create_entry_wrapper( bcx.switch_to_block(block); let arg_argc = bcx.append_block_param(block, m.target_config().pointer_type()); let arg_argv = bcx.append_block_param(block, m.target_config().pointer_type()); + let arg_sigpipe = bcx.ins().iconst(types::I8, sigpipe as i64); let main_func_ref = m.declare_func_in_func(main_func_id, &mut bcx.func); @@ -143,7 +145,8 @@ pub(crate) fn maybe_create_entry_wrapper( let main_val = bcx.ins().func_addr(m.target_config().pointer_type(), main_func_ref); let func_ref = m.declare_func_in_func(start_func_id, &mut bcx.func); - let call_inst = bcx.ins().call(func_ref, &[main_val, arg_argc, arg_argv]); + let call_inst = + bcx.ins().call(func_ref, &[main_val, arg_argc, arg_argv, arg_sigpipe]); bcx.inst_results(call_inst)[0] } else { // using user-defined start fn From eb9fb29395af3ca0258b70c9f99ec9d029f2ace5 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Tue, 30 Aug 2022 10:14:55 +0200 Subject: [PATCH 14/98] Rustup to rustc 1.65.0-nightly (bc4b39c27 2022-08-29) --- rust-toolchain | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/rust-toolchain b/rust-toolchain index 14f2746ecb19f..acc86748867be 100644 --- a/rust-toolchain +++ b/rust-toolchain @@ -1,3 +1,3 @@ [toolchain] -channel = "nightly-2022-08-24" +channel = "nightly-2022-08-30" components = ["rust-src", "rustc-dev", "llvm-tools-preview"] From 8d76b2ffb9df53225e7ac08abcf90b1f9eefccae Mon Sep 17 00:00:00 2001 From: Dezhi Wu Date: Thu, 18 Aug 2022 10:13:37 +0800 Subject: [PATCH 15/98] Fix a bunch of typo This PR will fix some typos detected by [typos]. I only picked the ones I was sure were spelling errors to fix, mostly in the comments. [typos]: https://github.com/crate-ci/typos --- src/abi/mod.rs | 2 +- src/constant.rs | 2 +- src/intrinsics/mod.rs | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/abi/mod.rs b/src/abi/mod.rs index 815450f689e4a..0497c2570e622 100644 --- a/src/abi/mod.rs +++ b/src/abi/mod.rs @@ -342,7 +342,7 @@ pub(crate) fn codegen_terminator_call<'tcx>( let ret_place = codegen_place(fx, destination); - // Handle special calls like instrinsics and empty drop glue. + // Handle special calls like intrinsics and empty drop glue. let instance = if let ty::FnDef(def_id, substs) = *fn_ty.kind() { let instance = ty::Instance::resolve(fx.tcx, ty::ParamEnv::reveal_all(), def_id, substs) .unwrap() diff --git a/src/constant.rs b/src/constant.rs index cb5d73a7e0ba9..9224f499339cb 100644 --- a/src/constant.rs +++ b/src/constant.rs @@ -59,7 +59,7 @@ pub(crate) fn check_constants(fx: &mut FunctionCx<'_, '_, '_>) -> bool { ErrorHandled::TooGeneric => { span_bug!( constant.span, - "codgen encountered polymorphic constant: {:?}", + "codegen encountered polymorphic constant: {:?}", err ); } diff --git a/src/intrinsics/mod.rs b/src/intrinsics/mod.rs index 95239f415a99b..4aeb1e3aab953 100644 --- a/src/intrinsics/mod.rs +++ b/src/intrinsics/mod.rs @@ -203,7 +203,7 @@ pub(crate) fn codegen_intrinsic_call<'tcx>( sym::transmute => { crate::base::codegen_panic(fx, "Transmuting to uninhabited type.", source_info); } - _ => unimplemented!("unsupported instrinsic {}", intrinsic), + _ => unimplemented!("unsupported intrinsics {}", intrinsic), } return; }; From 3d9cee13dd4b6cf7fac4d8489ef33d8b669aa2b8 Mon Sep 17 00:00:00 2001 From: Dezhi Wu Date: Thu, 18 Aug 2022 16:36:49 +0800 Subject: [PATCH 16/98] Correct typo --- src/intrinsics/mod.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/intrinsics/mod.rs b/src/intrinsics/mod.rs index 4aeb1e3aab953..39e9e784a478b 100644 --- a/src/intrinsics/mod.rs +++ b/src/intrinsics/mod.rs @@ -203,7 +203,7 @@ pub(crate) fn codegen_intrinsic_call<'tcx>( sym::transmute => { crate::base::codegen_panic(fx, "Transmuting to uninhabited type.", source_info); } - _ => unimplemented!("unsupported intrinsics {}", intrinsic), + _ => unimplemented!("unsupported intrinsic {}", intrinsic), } return; }; From 096611855c90561188cb73d0e4a656e27a710d91 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Thu, 1 Sep 2022 11:53:35 +0200 Subject: [PATCH 17/98] Update abi-checker This updates a test expectation for s390x --- build_system/prepare.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build_system/prepare.rs b/build_system/prepare.rs index d23b7f00dcf16..eb032fb8bcb51 100644 --- a/build_system/prepare.rs +++ b/build_system/prepare.rs @@ -18,7 +18,7 @@ pub(crate) fn prepare() { "abi-checker", "Gankra", "abi-checker", - "a2232d45f202846f5c02203c9f27355360f9a2ff", + "4c6dc8c9c687e2b3a760ff2176ce236872b37212", ); apply_patches("abi-checker", Path::new("abi-checker")); From 2bcc936a5aeea322cec6d1f04d5323d11e033723 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Thu, 1 Sep 2022 13:53:47 +0200 Subject: [PATCH 18/98] Remove all uses of Function::with_name_signature The current main branch of Cranelift changed it's signature. Removing it's use is the easiest way to deal with this. --- src/allocator.rs | 4 ++-- src/main_shim.rs | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/allocator.rs b/src/allocator.rs index 6d321c7b298a7..bad8a87b9bee4 100644 --- a/src/allocator.rs +++ b/src/allocator.rs @@ -78,7 +78,7 @@ fn codegen_inner( let callee_func_id = module.declare_function(&callee_name, Linkage::Import, &sig).unwrap(); let mut ctx = Context::new(); - ctx.func = Function::with_name_signature(ExternalName::user(0, 0), sig.clone()); + ctx.func.signature = sig.clone(); { let mut func_ctx = FunctionBuilderContext::new(); let mut bcx = FunctionBuilder::new(&mut ctx.func, &mut func_ctx); @@ -116,7 +116,7 @@ fn codegen_inner( let callee_func_id = module.declare_function(callee_name, Linkage::Import, &sig).unwrap(); let mut ctx = Context::new(); - ctx.func = Function::with_name_signature(ExternalName::user(0, 0), sig); + ctx.func.signature = sig; { let mut func_ctx = FunctionBuilderContext::new(); let mut bcx = FunctionBuilder::new(&mut ctx.func, &mut func_ctx); diff --git a/src/main_shim.rs b/src/main_shim.rs index c67b6e98b32c7..b5a17ee153d1b 100644 --- a/src/main_shim.rs +++ b/src/main_shim.rs @@ -74,7 +74,7 @@ pub(crate) fn maybe_create_entry_wrapper( let main_func_id = m.declare_function(main_name, Linkage::Import, &main_sig).unwrap(); let mut ctx = Context::new(); - ctx.func = Function::with_name_signature(ExternalName::user(0, 0), cmain_sig); + ctx.func.signature = cmain_sig; { let mut func_ctx = FunctionBuilderContext::new(); let mut bcx = FunctionBuilder::new(&mut ctx.func, &mut func_ctx); From 2231545ebf83901ced90d469b891b04a1fe89b97 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Thu, 1 Sep 2022 14:00:21 +0200 Subject: [PATCH 19/98] Use pointer_ty instead of func.dfg.value_type This fixes a borrowck error with the current main branch of Cranelift. --- src/intrinsics/mod.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/intrinsics/mod.rs b/src/intrinsics/mod.rs index 95239f415a99b..186772d807d1f 100644 --- a/src/intrinsics/mod.rs +++ b/src/intrinsics/mod.rs @@ -1216,7 +1216,7 @@ fn codegen_regular_intrinsic_call<'tcx>( // FIXME once unwinding is supported, change this to actually catch panics let f_sig = fx.bcx.func.import_signature(Signature { call_conv: fx.target_config.default_call_conv, - params: vec![AbiParam::new(fx.bcx.func.dfg.value_type(data))], + params: vec![AbiParam::new(pointer_ty(fx.tcx))], returns: vec![], }); From eef75dde3ba669044e1f2c85d83ebd448efb97c7 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Thu, 1 Sep 2022 15:36:12 +0000 Subject: [PATCH 20/98] Update libloading to 0.7.3 This was previously done in bfcf97bd8360931eb088d65f247fc9e1016f8199, but got reverted due to a bug. The bug seems to be fixed now. Fixes #1137 --- Cargo.lock | 4 ++-- Cargo.toml | 2 +- src/driver/jit.rs | 2 +- 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index edae7e471578a..b4c607d482e53 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -232,9 +232,9 @@ checksum = "505e71a4706fa491e9b1b55f51b95d4037d0821ee40131190475f692b35b009b" [[package]] name = "libloading" -version = "0.6.7" +version = "0.7.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "351a32417a12d5f7e82c368a66781e307834dae04c6ce0cd4456d52989229883" +checksum = "efbc0f03f9a775e9f6aed295c6a1ba2253c5757a9e03d55c6caa46a681abcddd" dependencies = [ "cfg-if", "winapi", diff --git a/Cargo.toml b/Cargo.toml index e7c3427485480..7a9e8f5d8e0c6 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -20,7 +20,7 @@ object = { version = "0.29.0", default-features = false, features = ["std", "rea ar = { git = "https://github.com/bjorn3/rust-ar.git", branch = "do_not_remove_cg_clif_ranlib" } indexmap = "1.9.1" -libloading = { version = "0.6.0", optional = true } +libloading = { version = "0.7.3", optional = true } once_cell = "1.10.0" smallvec = "1.8.1" diff --git a/src/driver/jit.rs b/src/driver/jit.rs index 4ad859b6d8378..6a430b5215e36 100644 --- a/src/driver/jit.rs +++ b/src/driver/jit.rs @@ -318,7 +318,7 @@ fn dep_symbol_lookup_fn( let imported_dylibs = Box::leak( dylib_paths .into_iter() - .map(|path| libloading::Library::new(&path).unwrap()) + .map(|path| unsafe { libloading::Library::new(&path).unwrap() }) .collect::>(), ); From de7342b4446476a2d9375a7f93be54dc9f8707d1 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Thu, 1 Sep 2022 16:18:39 +0000 Subject: [PATCH 21/98] Implement core::hint::spin_loop() on AArch64 This is used in the futex based mutex implementation of libstd --- src/intrinsics/llvm.rs | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/intrinsics/llvm.rs b/src/intrinsics/llvm.rs index a799dca938e21..598c13e757ef2 100644 --- a/src/intrinsics/llvm.rs +++ b/src/intrinsics/llvm.rs @@ -14,6 +14,10 @@ pub(crate) fn codegen_llvm_intrinsic_call<'tcx>( target: Option, ) { match intrinsic { + "llvm.x86.sse2.pause" | "llvm.aarch64.isb" => { + // Spin loop hint + } + // Used by `_mm_movemask_epi8` and `_mm256_movemask_epi8` "llvm.x86.sse2.pmovmskb.128" | "llvm.x86.avx2.pmovmskb" | "llvm.x86.sse2.movmsk.pd" => { intrinsic_args!(fx, args => (a); intrinsic); From 244455d8e3137f3bd3e2ee6a49ebb787e7d7f792 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Thu, 1 Sep 2022 16:41:01 +0000 Subject: [PATCH 22/98] Apply sysroot patches to rustc bootstrap and rustc test suite tests This is necessary on AArch64 as 128bit atomics aren't yet supported by Cranelift. --- scripts/setup_rust_fork.sh | 2 ++ 1 file changed, 2 insertions(+) diff --git a/scripts/setup_rust_fork.sh b/scripts/setup_rust_fork.sh index 091bfa1e9926f..6ae8b14f4c015 100644 --- a/scripts/setup_rust_fork.sh +++ b/scripts/setup_rust_fork.sh @@ -10,6 +10,8 @@ git fetch git checkout -- . git checkout "$(rustc -V | cut -d' ' -f3 | tr -d '(')" +git am ../patches/*-sysroot-*.patch + git apply - < Date: Fri, 2 Sep 2022 09:34:37 +0000 Subject: [PATCH 23/98] Fix panic in ConcurrencyLimiter when unwinding Fixes #1275 --- src/concurrency_limiter.rs | 17 +++++++++++++---- src/driver/aot.rs | 2 +- 2 files changed, 14 insertions(+), 5 deletions(-) diff --git a/src/concurrency_limiter.rs b/src/concurrency_limiter.rs index dfde97920461e..f855e20e0a1a3 100644 --- a/src/concurrency_limiter.rs +++ b/src/concurrency_limiter.rs @@ -10,6 +10,7 @@ pub(super) struct ConcurrencyLimiter { helper_thread: Option, state: Arc>, available_token_condvar: Arc, + finished: bool, } impl ConcurrencyLimiter { @@ -32,6 +33,7 @@ impl ConcurrencyLimiter { helper_thread: Some(helper_thread), state, available_token_condvar: Arc::new(Condvar::new()), + finished: false, } } @@ -56,16 +58,23 @@ impl ConcurrencyLimiter { let mut state = self.state.lock().unwrap(); state.job_already_done(); } -} -impl Drop for ConcurrencyLimiter { - fn drop(&mut self) { - // + pub(crate) fn finished(mut self) { self.helper_thread.take(); // Assert that all jobs have finished let state = Mutex::get_mut(Arc::get_mut(&mut self.state).unwrap()).unwrap(); state.assert_done(); + + self.finished = true; + } +} + +impl Drop for ConcurrencyLimiter { + fn drop(&mut self) { + if !self.finished && !std::thread::panicking() { + panic!("Forgot to call finished() on ConcurrencyLimiter"); + } } } diff --git a/src/driver/aot.rs b/src/driver/aot.rs index 8eabe1cbcb150..f873561c1713f 100644 --- a/src/driver/aot.rs +++ b/src/driver/aot.rs @@ -106,7 +106,7 @@ impl OngoingCodegen { } } - drop(self.concurrency_limiter); + self.concurrency_limiter.finished(); ( CodegenResults { From 7f260a953b583fdca533d57f92639d69024c262b Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Sun, 4 Sep 2022 13:35:58 +0200 Subject: [PATCH 24/98] Rustup to rustc 1.65.0-nightly (84f0c3f79 2022-09-03) --- example/mini_core_hello_world.rs | 1 + rust-toolchain | 2 +- 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/example/mini_core_hello_world.rs b/example/mini_core_hello_world.rs index e83be3a3df5c4..215d3556a17ca 100644 --- a/example/mini_core_hello_world.rs +++ b/example/mini_core_hello_world.rs @@ -93,6 +93,7 @@ fn start( main: fn() -> T, argc: isize, argv: *const *const u8, + _sigpipe: u8, ) -> isize { if argc == 3 { unsafe { puts(*argv as *const i8); } diff --git a/rust-toolchain b/rust-toolchain index acc86748867be..f17897e48adf5 100644 --- a/rust-toolchain +++ b/rust-toolchain @@ -1,3 +1,3 @@ [toolchain] -channel = "nightly-2022-08-30" +channel = "nightly-2022-09-04" components = ["rust-src", "rustc-dev", "llvm-tools-preview"] From c4c393c78ede150fbdf693e23689d472fc54bfa6 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Mon, 5 Sep 2022 12:01:37 +0000 Subject: [PATCH 25/98] Update portable-simd --- build_system/prepare.rs | 2 +- ...table-simd-Disable-unsupported-tests.patch | 229 +++++++++++++----- src/intrinsics/simd.rs | 2 +- 3 files changed, 170 insertions(+), 63 deletions(-) diff --git a/build_system/prepare.rs b/build_system/prepare.rs index eb032fb8bcb51..b7368e8ffaba5 100644 --- a/build_system/prepare.rs +++ b/build_system/prepare.rs @@ -41,7 +41,7 @@ pub(crate) fn prepare() { "portable-simd", "rust-lang", "portable-simd", - "b8d6b6844602f80af79cd96401339ec594d472d8", + "d5cd4a8112d958bd3a252327e0d069a6363249bd", ); apply_patches("portable-simd", Path::new("portable-simd")); diff --git a/patches/0001-portable-simd-Disable-unsupported-tests.patch b/patches/0001-portable-simd-Disable-unsupported-tests.patch index 54e13b090abda..a1824f86ce2d7 100644 --- a/patches/0001-portable-simd-Disable-unsupported-tests.patch +++ b/patches/0001-portable-simd-Disable-unsupported-tests.patch @@ -1,80 +1,188 @@ -From 97c473937382a5b5858d9cce3c947855d23b2dc5 Mon Sep 17 00:00:00 2001 +From 82f597cf81b169b0e72a576ac8751f598c059c48 Mon Sep 17 00:00:00 2001 From: bjorn3 Date: Thu, 18 Nov 2021 19:28:40 +0100 Subject: [PATCH] Disable unsupported tests --- - crates/core_simd/src/math.rs | 6 ++++++ - crates/core_simd/src/vector.rs | 2 ++ - crates/core_simd/tests/masks.rs | 2 ++ - crates/core_simd/tests/ops_macros.rs | 4 ++++ - 4 files changed, 14 insertions(+) + crates/core_simd/src/elements/int.rs | 8 ++++++++ + crates/core_simd/src/elements/uint.rs | 4 ++++ + crates/core_simd/src/masks/full_masks.rs | 9 +++++++++ + crates/core_simd/src/vector.rs | 2 ++ + crates/core_simd/tests/masks.rs | 2 ++ + 5 files changed, 25 insertions(+) -diff --git a/crates/core_simd/src/math.rs b/crates/core_simd/src/math.rs -index 2bae414..2f87499 100644 ---- a/crates/core_simd/src/math.rs -+++ b/crates/core_simd/src/math.rs -@@ -5,6 +5,7 @@ macro_rules! impl_uint_arith { - ($($ty:ty),+) => { - $( impl Simd<$ty, LANES> where LaneCount: SupportedLaneCount { +diff --git a/crates/core_simd/src/elements/int.rs b/crates/core_simd/src/elements/int.rs +index 9b8c37e..ea95f08 100644 +--- a/crates/core_simd/src/elements/int.rs ++++ b/crates/core_simd/src/elements/int.rs +@@ -11,6 +11,7 @@ pub trait SimdInt: Copy + Sealed { + /// Scalar type contained by this SIMD vector type. + type Scalar; -+ /* - /// Lanewise saturating add. - /// - /// # Examples -@@ -43,6 +44,7 @@ macro_rules! impl_uint_arith { - pub fn saturating_sub(self, second: Self) -> Self { - unsafe { simd_saturating_sub(self, second) } - } -+ */ - })+ - } - } -@@ -51,6 +53,7 @@ macro_rules! impl_int_arith { - ($($ty:ty),+) => { - $( impl Simd<$ty, LANES> where LaneCount: SupportedLaneCount { ++ /* + /// Lanewise saturating add. + /// + /// # Examples +@@ -45,6 +46,7 @@ pub trait SimdInt: Copy + Sealed { + /// assert_eq!(unsat, Simd::from_array([1, MAX, MIN, 0])); + /// assert_eq!(sat, Simd::from_array([MIN, MIN, MIN, 0])); + fn saturating_sub(self, second: Self) -> Self; ++ */ + + /// Lanewise absolute value, implemented in Rust. + /// Every lane becomes its absolute value. +@@ -61,6 +63,7 @@ pub trait SimdInt: Copy + Sealed { + /// ``` + fn abs(self) -> Self; + ++ /* + /// Lanewise saturating absolute value, implemented in Rust. + /// As abs(), except the MIN value becomes MAX instead of itself. + /// +@@ -96,6 +99,7 @@ pub trait SimdInt: Copy + Sealed { + /// assert_eq!(sat, Simd::from_array([MAX, 2, -3, MIN + 1])); + /// ``` + fn saturating_neg(self) -> Self; ++ */ + + /// Returns true for each positive lane and false if it is zero or negative. + fn is_positive(self) -> Self::Mask; +@@ -199,6 +203,7 @@ macro_rules! impl_trait { + type Mask = Mask<<$ty as SimdElement>::Mask, LANES>; + type Scalar = $ty; + /* - /// Lanewise saturating add. - /// - /// # Examples -@@ -89,6 +92,7 @@ macro_rules! impl_int_arith { - pub fn saturating_sub(self, second: Self) -> Self { - unsafe { simd_saturating_sub(self, second) } + #[inline] + fn saturating_add(self, second: Self) -> Self { + // Safety: `self` is a vector +@@ -210,6 +215,7 @@ macro_rules! impl_trait { + // Safety: `self` is a vector + unsafe { intrinsics::simd_saturating_sub(self, second) } } + */ - /// Lanewise absolute value, implemented in Rust. - /// Every lane becomes its absolute value. -@@ -109,6 +113,7 @@ macro_rules! impl_int_arith { + #[inline] + fn abs(self) -> Self { +@@ -218,6 +224,7 @@ macro_rules! impl_trait { (self^m) - m } + /* - /// Lanewise saturating absolute value, implemented in Rust. - /// As abs(), except the MIN value becomes MAX instead of itself. - /// -@@ -151,6 +156,7 @@ macro_rules! impl_int_arith { - pub fn saturating_neg(self) -> Self { + #[inline] + fn saturating_abs(self) -> Self { + // arith shift for -1 or 0 mask based on sign bit, giving 2s complement +@@ -230,6 +237,7 @@ macro_rules! impl_trait { + fn saturating_neg(self) -> Self { Self::splat(0).saturating_sub(self) } + */ - })+ + + #[inline] + fn is_positive(self) -> Self::Mask { +diff --git a/crates/core_simd/src/elements/uint.rs b/crates/core_simd/src/elements/uint.rs +index 21e7e76..0d6dee2 100644 +--- a/crates/core_simd/src/elements/uint.rs ++++ b/crates/core_simd/src/elements/uint.rs +@@ -6,6 +6,7 @@ pub trait SimdUint: Copy + Sealed { + /// Scalar type contained by this SIMD vector type. + type Scalar; + ++ /* + /// Lanewise saturating add. + /// + /// # Examples +@@ -40,6 +41,7 @@ pub trait SimdUint: Copy + Sealed { + /// assert_eq!(unsat, Simd::from_array([3, 2, 1, 0])); + /// assert_eq!(sat, Simd::splat(0)); + fn saturating_sub(self, second: Self) -> Self; ++ */ + + /// Returns the sum of the lanes of the vector, with wrapping addition. + fn reduce_sum(self) -> Self::Scalar; +@@ -78,6 +80,7 @@ macro_rules! impl_trait { + { + type Scalar = $ty; + ++ /* + #[inline] + fn saturating_add(self, second: Self) -> Self { + // Safety: `self` is a vector +@@ -89,6 +92,7 @@ macro_rules! impl_trait { + // Safety: `self` is a vector + unsafe { intrinsics::simd_saturating_sub(self, second) } + } ++ */ + + #[inline] + fn reduce_sum(self) -> Self::Scalar { +diff --git a/crates/core_simd/src/masks/full_masks.rs b/crates/core_simd/src/masks/full_masks.rs +index adf0fcb..5b10292 100644 +--- a/crates/core_simd/src/masks/full_masks.rs ++++ b/crates/core_simd/src/masks/full_masks.rs +@@ -150,6 +150,7 @@ where + super::Mask: ToBitMaskArray, + [(); as ToBitMaskArray>::BYTES]: Sized, + { ++ /* + assert_eq!( as ToBitMaskArray>::BYTES, N); + + // Safety: N is the correct bitmask size +@@ -170,6 +171,8 @@ where + + bitmask + } ++ */ ++ panic!(); } - } + + #[cfg(feature = "generic_const_exprs")] +@@ -209,6 +212,7 @@ where + where + super::Mask: ToBitMask, + { ++ /* + // Safety: U is required to be the appropriate bitmask type + let bitmask: U = unsafe { intrinsics::simd_bitmask(self.0) }; + +@@ -218,6 +222,8 @@ where + } else { + bitmask + } ++ */ ++ panic!(); + } + + #[inline] +@@ -225,6 +231,7 @@ where + where + super::Mask: ToBitMask, + { ++ /* + // LLVM assumes bit order should match endianness + let bitmask = if cfg!(target_endian = "big") { + bitmask.reverse_bits(LANES) +@@ -240,6 +247,8 @@ where + Self::splat(false).to_int(), + )) + } ++ */ ++ panic!(); + } + + #[inline] diff --git a/crates/core_simd/src/vector.rs b/crates/core_simd/src/vector.rs -index 7c5ec2b..c8631e8 100644 +index e8e8f68..7173c24 100644 --- a/crates/core_simd/src/vector.rs +++ b/crates/core_simd/src/vector.rs -@@ -75,6 +75,7 @@ where - Self(array) +@@ -250,6 +250,7 @@ where + unsafe { intrinsics::simd_cast(self) } } + /* /// Reads from potentially discontiguous indices in `slice` to construct a SIMD vector. /// If an index is out-of-bounds, the lane is instead selected from the `or` vector. /// -@@ -297,6 +298,7 @@ where +@@ -473,6 +474,7 @@ where // Cleared ☢️ *mut T Zone } } @@ -83,25 +191,24 @@ index 7c5ec2b..c8631e8 100644 impl Copy for Simd diff --git a/crates/core_simd/tests/masks.rs b/crates/core_simd/tests/masks.rs -index 6a8ecd3..68fcb49 100644 +index 673d0db..0d68b01 100644 --- a/crates/core_simd/tests/masks.rs +++ b/crates/core_simd/tests/masks.rs -@@ -68,6 +68,7 @@ macro_rules! test_mask_api { - assert_eq!(core_simd::Mask::<$type, 8>::from_int(int), mask); +@@ -59,6 +59,7 @@ macro_rules! test_mask_api { + assert!(!v.all()); } + /* - #[cfg(feature = "generic_const_exprs")] #[test] - fn roundtrip_bitmask_conversion() { -@@ -80,6 +81,7 @@ macro_rules! test_mask_api { - assert_eq!(bitmask, [0b01001001, 0b10000011]); - assert_eq!(core_simd::Mask::<$type, 16>::from_bitmask(bitmask), mask); + fn roundtrip_int_conversion() { + let values = [true, false, false, true, false, false, true, false]; +@@ -99,6 +100,7 @@ macro_rules! test_mask_api { + assert_eq!(bitmask, 0b01); + assert_eq!(core_simd::Mask::<$type, 2>::from_bitmask(bitmask), mask); } + */ - } - } - } + + #[test] + fn cast() { -- -2.26.2.7.g19db9cfb68 - +2.25.1 diff --git a/src/intrinsics/simd.rs b/src/intrinsics/simd.rs index 1f358b1bbb96e..a8aefcf30b5e1 100644 --- a/src/intrinsics/simd.rs +++ b/src/intrinsics/simd.rs @@ -26,7 +26,7 @@ pub(super) fn codegen_simd_intrinsic_call<'tcx>( span: Span, ) { match intrinsic { - sym::simd_cast => { + sym::simd_as | sym::simd_cast => { intrinsic_args!(fx, args => (a); intrinsic); if !a.layout().ty.is_simd() { From 0bb9bdf8e337b494c5ea385a309425c46f6aa383 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Mon, 5 Sep 2022 15:31:14 +0000 Subject: [PATCH 26/98] Use value_lane instead of value_field in simd/llvm.rs --- src/intrinsics/llvm.rs | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/intrinsics/llvm.rs b/src/intrinsics/llvm.rs index 598c13e757ef2..783d426c30bcc 100644 --- a/src/intrinsics/llvm.rs +++ b/src/intrinsics/llvm.rs @@ -29,8 +29,7 @@ pub(crate) fn codegen_llvm_intrinsic_call<'tcx>( let mut res = fx.bcx.ins().iconst(types::I32, 0); for lane in (0..lane_count).rev() { - let a_lane = - a.value_field(fx, mir::Field::new(lane.try_into().unwrap())).load_scalar(fx); + let a_lane = a.value_lane(fx, lane).load_scalar(fx); // cast float to int let a_lane = match lane_ty { From f200fbca10b4cc066120c4d19b58d2f244c6e638 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Mon, 5 Sep 2022 15:37:56 +0000 Subject: [PATCH 27/98] Implement simd_bitmask --- ...table-simd-Disable-unsupported-tests.patch | 65 ++++++-------- src/intrinsics/simd.rs | 86 ++++++++++++++++++- 2 files changed, 111 insertions(+), 40 deletions(-) diff --git a/patches/0001-portable-simd-Disable-unsupported-tests.patch b/patches/0001-portable-simd-Disable-unsupported-tests.patch index a1824f86ce2d7..c75d5dda5caf5 100644 --- a/patches/0001-portable-simd-Disable-unsupported-tests.patch +++ b/patches/0001-portable-simd-Disable-unsupported-tests.patch @@ -1,4 +1,4 @@ -From 82f597cf81b169b0e72a576ac8751f598c059c48 Mon Sep 17 00:00:00 2001 +From b742f03694b920cc14400727d54424e8e1b60928 Mon Sep 17 00:00:00 2001 From: bjorn3 Date: Thu, 18 Nov 2021 19:28:40 +0100 Subject: [PATCH] Disable unsupported tests @@ -6,10 +6,10 @@ Subject: [PATCH] Disable unsupported tests --- crates/core_simd/src/elements/int.rs | 8 ++++++++ crates/core_simd/src/elements/uint.rs | 4 ++++ - crates/core_simd/src/masks/full_masks.rs | 9 +++++++++ + crates/core_simd/src/masks/full_masks.rs | 6 ++++++ crates/core_simd/src/vector.rs | 2 ++ - crates/core_simd/tests/masks.rs | 2 ++ - 5 files changed, 25 insertions(+) + crates/core_simd/tests/masks.rs | 3 --- + 5 files changed, 20 insertions(+), 3 deletions(-) diff --git a/crates/core_simd/src/elements/int.rs b/crates/core_simd/src/elements/int.rs index 9b8c37e..ea95f08 100644 @@ -116,10 +116,10 @@ index 21e7e76..0d6dee2 100644 #[inline] fn reduce_sum(self) -> Self::Scalar { diff --git a/crates/core_simd/src/masks/full_masks.rs b/crates/core_simd/src/masks/full_masks.rs -index adf0fcb..5b10292 100644 +index adf0fcb..e7e657e 100644 --- a/crates/core_simd/src/masks/full_masks.rs +++ b/crates/core_simd/src/masks/full_masks.rs -@@ -150,6 +150,7 @@ where +@@ -180,6 +180,7 @@ where super::Mask: ToBitMaskArray, [(); as ToBitMaskArray>::BYTES]: Sized, { @@ -127,33 +127,16 @@ index adf0fcb..5b10292 100644 assert_eq!( as ToBitMaskArray>::BYTES, N); // Safety: N is the correct bitmask size -@@ -170,6 +171,8 @@ where - - bitmask - } -+ */ -+ panic!(); - } - - #[cfg(feature = "generic_const_exprs")] -@@ -209,6 +212,7 @@ where - where - super::Mask: ToBitMask, - { -+ /* - // Safety: U is required to be the appropriate bitmask type - let bitmask: U = unsafe { intrinsics::simd_bitmask(self.0) }; - -@@ -218,6 +222,8 @@ where - } else { - bitmask +@@ -202,6 +203,8 @@ where + Self::splat(false).to_int(), + )) } + */ + panic!(); } #[inline] -@@ -225,6 +231,7 @@ where +@@ -225,6 +228,7 @@ where where super::Mask: ToBitMask, { @@ -161,7 +144,7 @@ index adf0fcb..5b10292 100644 // LLVM assumes bit order should match endianness let bitmask = if cfg!(target_endian = "big") { bitmask.reverse_bits(LANES) -@@ -240,6 +247,8 @@ where +@@ -240,6 +244,8 @@ where Self::splat(false).to_int(), )) } @@ -191,24 +174,30 @@ index e8e8f68..7173c24 100644 impl Copy for Simd diff --git a/crates/core_simd/tests/masks.rs b/crates/core_simd/tests/masks.rs -index 673d0db..0d68b01 100644 +index 673d0db..3ebfcd1 100644 --- a/crates/core_simd/tests/masks.rs +++ b/crates/core_simd/tests/masks.rs -@@ -59,6 +59,7 @@ macro_rules! test_mask_api { - assert!(!v.all()); +@@ -78,7 +78,6 @@ macro_rules! test_mask_api { + let mask = core_simd::Mask::<$type, 16>::from_array(values); + let bitmask = mask.to_bitmask(); + assert_eq!(bitmask, 0b1000001101001001); +- assert_eq!(core_simd::Mask::<$type, 16>::from_bitmask(bitmask), mask); } -+ /* #[test] - fn roundtrip_int_conversion() { - let values = [true, false, false, true, false, false, true, false]; -@@ -99,6 +100,7 @@ macro_rules! test_mask_api { +@@ -91,13 +90,11 @@ macro_rules! test_mask_api { + let mask = core_simd::Mask::<$type, 4>::from_array(values); + let bitmask = mask.to_bitmask(); + assert_eq!(bitmask, 0b1000); +- assert_eq!(core_simd::Mask::<$type, 4>::from_bitmask(bitmask), mask); + + let values = [true, false]; + let mask = core_simd::Mask::<$type, 2>::from_array(values); + let bitmask = mask.to_bitmask(); assert_eq!(bitmask, 0b01); - assert_eq!(core_simd::Mask::<$type, 2>::from_bitmask(bitmask), mask); +- assert_eq!(core_simd::Mask::<$type, 2>::from_bitmask(bitmask), mask); } -+ */ #[test] - fn cast() { -- 2.25.1 diff --git a/src/intrinsics/simd.rs b/src/intrinsics/simd.rs index a8aefcf30b5e1..4d77370dfc520 100644 --- a/src/intrinsics/simd.rs +++ b/src/intrinsics/simd.rs @@ -2,6 +2,7 @@ use rustc_middle::ty::subst::SubstsRef; use rustc_span::Symbol; +use rustc_target::abi::Endian; use super::*; use crate::prelude::*; @@ -162,6 +163,7 @@ pub(super) fn codegen_simd_intrinsic_call<'tcx>( } } } else { + // FIXME remove this case intrinsic.as_str()["simd_shuffle".len()..].parse().unwrap() }; @@ -650,10 +652,90 @@ pub(super) fn codegen_simd_intrinsic_call<'tcx>( } } - // simd_saturating_* - // simd_bitmask + sym::simd_bitmask => { + intrinsic_args!(fx, args => (a); intrinsic); + + let (lane_count, lane_ty) = a.layout().ty.simd_size_and_type(fx.tcx); + let lane_clif_ty = fx.clif_type(lane_ty).unwrap(); + + // The `fn simd_bitmask(vector) -> unsigned integer` intrinsic takes a + // vector mask and returns the most significant bit (MSB) of each lane in the form + // of either: + // * an unsigned integer + // * an array of `u8` + // If the vector has less than 8 lanes, a u8 is returned with zeroed trailing bits. + // + // The bit order of the result depends on the byte endianness, LSB-first for little + // endian and MSB-first for big endian. + let expected_int_bits = lane_count.max(8); + let expected_bytes = expected_int_bits / 8 + ((expected_int_bits % 8 > 0) as u64); + + match lane_ty.kind() { + ty::Int(_) | ty::Uint(_) => {} + _ => { + fx.tcx.sess.span_fatal( + span, + &format!( + "invalid monomorphization of `simd_bitmask` intrinsic: \ + vector argument `{}`'s element type `{}`, expected integer element \ + type", + a.layout().ty, + lane_ty + ), + ); + } + } + + let res_type = + Type::int_with_byte_size(u16::try_from(expected_bytes).unwrap()).unwrap(); + let mut res = fx.bcx.ins().iconst(res_type, 0); + + let lanes = match fx.tcx.sess.target.endian { + Endian::Big => Box::new(0..lane_count) as Box>, + Endian::Little => Box::new((0..lane_count).rev()) as Box>, + }; + for lane in lanes { + let a_lane = a.value_lane(fx, lane).load_scalar(fx); + + // extract sign bit of an int + let a_lane_sign = fx.bcx.ins().ushr_imm(a_lane, i64::from(lane_clif_ty.bits() - 1)); + + // shift sign bit into result + let a_lane_sign = clif_intcast(fx, a_lane_sign, res_type, false); + res = fx.bcx.ins().ishl_imm(res, 1); + res = fx.bcx.ins().bor(res, a_lane_sign); + } + + match ret.layout().ty.kind() { + ty::Uint(i) if i.bit_width() == Some(expected_int_bits) => {} + ty::Array(elem, len) + if matches!(elem.kind(), ty::Uint(ty::UintTy::U8)) + && len.try_eval_usize(fx.tcx, ty::ParamEnv::reveal_all()) + == Some(expected_bytes) => {} + _ => { + fx.tcx.sess.span_fatal( + span, + &format!( + "invalid monomorphization of `simd_bitmask` intrinsic: \ + cannot return `{}`, expected `u{}` or `[u8; {}]`", + ret.layout().ty, + expected_int_bits, + expected_bytes + ), + ); + } + } + + let res = CValue::by_val(res, ret.layout()); + ret.write_cvalue(fx, res); + } + + // simd_arith_offset + // simd_saturating_add + // simd_saturating_sub // simd_scatter // simd_gather + // simd_select_bitmask _ => { fx.tcx.sess.span_fatal(span, &format!("Unknown SIMD intrinsic {}", intrinsic)); } From 0980596271fd99665921052c8f666f7fb718a3cc Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Mon, 5 Sep 2022 16:13:08 +0000 Subject: [PATCH 28/98] Extract codegen_saturating_int_binop function --- src/intrinsics/mod.rs | 32 +------------------------------- src/num.rs | 36 ++++++++++++++++++++++++++++++++++++ 2 files changed, 37 insertions(+), 31 deletions(-) diff --git a/src/intrinsics/mod.rs b/src/intrinsics/mod.rs index b0863e096540d..e06166d0ab7cd 100644 --- a/src/intrinsics/mod.rs +++ b/src/intrinsics/mod.rs @@ -507,37 +507,7 @@ fn codegen_regular_intrinsic_call<'tcx>( _ => unreachable!(), }; - let signed = type_sign(lhs.layout().ty); - - let checked_res = crate::num::codegen_checked_int_binop(fx, bin_op, lhs, rhs); - - let (val, has_overflow) = checked_res.load_scalar_pair(fx); - let clif_ty = fx.clif_type(lhs.layout().ty).unwrap(); - - let (min, max) = type_min_max_value(&mut fx.bcx, clif_ty, signed); - - let val = match (intrinsic, signed) { - (sym::saturating_add, false) => fx.bcx.ins().select(has_overflow, max, val), - (sym::saturating_sub, false) => fx.bcx.ins().select(has_overflow, min, val), - (sym::saturating_add, true) => { - let rhs = rhs.load_scalar(fx); - let rhs_ge_zero = - fx.bcx.ins().icmp_imm(IntCC::SignedGreaterThanOrEqual, rhs, 0); - let sat_val = fx.bcx.ins().select(rhs_ge_zero, max, min); - fx.bcx.ins().select(has_overflow, sat_val, val) - } - (sym::saturating_sub, true) => { - let rhs = rhs.load_scalar(fx); - let rhs_ge_zero = - fx.bcx.ins().icmp_imm(IntCC::SignedGreaterThanOrEqual, rhs, 0); - let sat_val = fx.bcx.ins().select(rhs_ge_zero, min, max); - fx.bcx.ins().select(has_overflow, sat_val, val) - } - _ => unreachable!(), - }; - - let res = CValue::by_val(val, lhs.layout()); - + let res = crate::num::codegen_saturating_int_binop(fx, bin_op, lhs, rhs); ret.write_cvalue(fx, res); } sym::rotate_left => { diff --git a/src/num.rs b/src/num.rs index 4ce8adb182e0f..4fadbf24d8a83 100644 --- a/src/num.rs +++ b/src/num.rs @@ -309,6 +309,42 @@ pub(crate) fn codegen_checked_int_binop<'tcx>( CValue::by_val_pair(res, has_overflow, out_layout) } +pub(crate) fn codegen_saturating_int_binop<'tcx>( + fx: &mut FunctionCx<'_, '_, 'tcx>, + bin_op: BinOp, + lhs: CValue<'tcx>, + rhs: CValue<'tcx>, +) -> CValue<'tcx> { + assert_eq!(lhs.layout().ty, rhs.layout().ty); + + let signed = type_sign(lhs.layout().ty); + let clif_ty = fx.clif_type(lhs.layout().ty).unwrap(); + let (min, max) = type_min_max_value(&mut fx.bcx, clif_ty, signed); + + let checked_res = crate::num::codegen_checked_int_binop(fx, bin_op, lhs, rhs); + let (val, has_overflow) = checked_res.load_scalar_pair(fx); + + let val = match (bin_op, signed) { + (BinOp::Add, false) => fx.bcx.ins().select(has_overflow, max, val), + (BinOp::Sub, false) => fx.bcx.ins().select(has_overflow, min, val), + (BinOp::Add, true) => { + let rhs = rhs.load_scalar(fx); + let rhs_ge_zero = fx.bcx.ins().icmp_imm(IntCC::SignedGreaterThanOrEqual, rhs, 0); + let sat_val = fx.bcx.ins().select(rhs_ge_zero, max, min); + fx.bcx.ins().select(has_overflow, sat_val, val) + } + (BinOp::Sub, true) => { + let rhs = rhs.load_scalar(fx); + let rhs_ge_zero = fx.bcx.ins().icmp_imm(IntCC::SignedGreaterThanOrEqual, rhs, 0); + let sat_val = fx.bcx.ins().select(rhs_ge_zero, min, max); + fx.bcx.ins().select(has_overflow, sat_val, val) + } + _ => unreachable!(), + }; + + CValue::by_val(val, lhs.layout()) +} + pub(crate) fn codegen_float_binop<'tcx>( fx: &mut FunctionCx<'_, '_, 'tcx>, bin_op: BinOp, From 782b5fe7ac97554f7bf4b9121e985871e650ca41 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Mon, 5 Sep 2022 16:13:36 +0000 Subject: [PATCH 29/98] Implement simd_saturating_{add,sub} --- ...table-simd-Disable-unsupported-tests.patch | 104 ------------------ src/intrinsics/mod.rs | 24 ++++ src/intrinsics/simd.rs | 17 ++- 3 files changed, 39 insertions(+), 106 deletions(-) diff --git a/patches/0001-portable-simd-Disable-unsupported-tests.patch b/patches/0001-portable-simd-Disable-unsupported-tests.patch index c75d5dda5caf5..e23dea976944b 100644 --- a/patches/0001-portable-simd-Disable-unsupported-tests.patch +++ b/patches/0001-portable-simd-Disable-unsupported-tests.patch @@ -11,110 +11,6 @@ Subject: [PATCH] Disable unsupported tests crates/core_simd/tests/masks.rs | 3 --- 5 files changed, 20 insertions(+), 3 deletions(-) -diff --git a/crates/core_simd/src/elements/int.rs b/crates/core_simd/src/elements/int.rs -index 9b8c37e..ea95f08 100644 ---- a/crates/core_simd/src/elements/int.rs -+++ b/crates/core_simd/src/elements/int.rs -@@ -11,6 +11,7 @@ pub trait SimdInt: Copy + Sealed { - /// Scalar type contained by this SIMD vector type. - type Scalar; - -+ /* - /// Lanewise saturating add. - /// - /// # Examples -@@ -45,6 +46,7 @@ pub trait SimdInt: Copy + Sealed { - /// assert_eq!(unsat, Simd::from_array([1, MAX, MIN, 0])); - /// assert_eq!(sat, Simd::from_array([MIN, MIN, MIN, 0])); - fn saturating_sub(self, second: Self) -> Self; -+ */ - - /// Lanewise absolute value, implemented in Rust. - /// Every lane becomes its absolute value. -@@ -61,6 +63,7 @@ pub trait SimdInt: Copy + Sealed { - /// ``` - fn abs(self) -> Self; - -+ /* - /// Lanewise saturating absolute value, implemented in Rust. - /// As abs(), except the MIN value becomes MAX instead of itself. - /// -@@ -96,6 +99,7 @@ pub trait SimdInt: Copy + Sealed { - /// assert_eq!(sat, Simd::from_array([MAX, 2, -3, MIN + 1])); - /// ``` - fn saturating_neg(self) -> Self; -+ */ - - /// Returns true for each positive lane and false if it is zero or negative. - fn is_positive(self) -> Self::Mask; -@@ -199,6 +203,7 @@ macro_rules! impl_trait { - type Mask = Mask<<$ty as SimdElement>::Mask, LANES>; - type Scalar = $ty; - -+ /* - #[inline] - fn saturating_add(self, second: Self) -> Self { - // Safety: `self` is a vector -@@ -210,6 +215,7 @@ macro_rules! impl_trait { - // Safety: `self` is a vector - unsafe { intrinsics::simd_saturating_sub(self, second) } - } -+ */ - - #[inline] - fn abs(self) -> Self { -@@ -218,6 +224,7 @@ macro_rules! impl_trait { - (self^m) - m - } - -+ /* - #[inline] - fn saturating_abs(self) -> Self { - // arith shift for -1 or 0 mask based on sign bit, giving 2s complement -@@ -230,6 +237,7 @@ macro_rules! impl_trait { - fn saturating_neg(self) -> Self { - Self::splat(0).saturating_sub(self) - } -+ */ - - #[inline] - fn is_positive(self) -> Self::Mask { -diff --git a/crates/core_simd/src/elements/uint.rs b/crates/core_simd/src/elements/uint.rs -index 21e7e76..0d6dee2 100644 ---- a/crates/core_simd/src/elements/uint.rs -+++ b/crates/core_simd/src/elements/uint.rs -@@ -6,6 +6,7 @@ pub trait SimdUint: Copy + Sealed { - /// Scalar type contained by this SIMD vector type. - type Scalar; - -+ /* - /// Lanewise saturating add. - /// - /// # Examples -@@ -40,6 +41,7 @@ pub trait SimdUint: Copy + Sealed { - /// assert_eq!(unsat, Simd::from_array([3, 2, 1, 0])); - /// assert_eq!(sat, Simd::splat(0)); - fn saturating_sub(self, second: Self) -> Self; -+ */ - - /// Returns the sum of the lanes of the vector, with wrapping addition. - fn reduce_sum(self) -> Self::Scalar; -@@ -78,6 +80,7 @@ macro_rules! impl_trait { - { - type Scalar = $ty; - -+ /* - #[inline] - fn saturating_add(self, second: Self) -> Self { - // Safety: `self` is a vector -@@ -89,6 +92,7 @@ macro_rules! impl_trait { - // Safety: `self` is a vector - unsafe { intrinsics::simd_saturating_sub(self, second) } - } -+ */ - - #[inline] - fn reduce_sum(self) -> Self::Scalar { diff --git a/crates/core_simd/src/masks/full_masks.rs b/crates/core_simd/src/masks/full_masks.rs index adf0fcb..e7e657e 100644 --- a/crates/core_simd/src/masks/full_masks.rs diff --git a/src/intrinsics/mod.rs b/src/intrinsics/mod.rs index e06166d0ab7cd..1e47ccbd49fa8 100644 --- a/src/intrinsics/mod.rs +++ b/src/intrinsics/mod.rs @@ -84,6 +84,30 @@ fn simd_for_each_lane<'tcx>( } } +fn simd_pair_for_each_lane_typed<'tcx>( + fx: &mut FunctionCx<'_, '_, 'tcx>, + x: CValue<'tcx>, + y: CValue<'tcx>, + ret: CPlace<'tcx>, + f: &dyn Fn(&mut FunctionCx<'_, '_, 'tcx>, CValue<'tcx>, CValue<'tcx>) -> CValue<'tcx>, +) { + assert_eq!(x.layout(), y.layout()); + let layout = x.layout(); + + let (lane_count, _lane_ty) = layout.ty.simd_size_and_type(fx.tcx); + let (ret_lane_count, _ret_lane_ty) = ret.layout().ty.simd_size_and_type(fx.tcx); + assert_eq!(lane_count, ret_lane_count); + + for lane_idx in 0..lane_count { + let x_lane = x.value_lane(fx, lane_idx); + let y_lane = y.value_lane(fx, lane_idx); + + let res_lane = f(fx, x_lane, y_lane); + + ret.place_lane(fx, lane_idx).write_cvalue(fx, res_lane); + } +} + fn simd_pair_for_each_lane<'tcx>( fx: &mut FunctionCx<'_, '_, 'tcx>, x: CValue<'tcx>, diff --git a/src/intrinsics/simd.rs b/src/intrinsics/simd.rs index 4d77370dfc520..a70ced7472f5a 100644 --- a/src/intrinsics/simd.rs +++ b/src/intrinsics/simd.rs @@ -730,9 +730,22 @@ pub(super) fn codegen_simd_intrinsic_call<'tcx>( ret.write_cvalue(fx, res); } + sym::simd_saturating_add | sym::simd_saturating_sub => { + intrinsic_args!(fx, args => (x, y); intrinsic); + + let bin_op = match intrinsic { + sym::simd_saturating_add => BinOp::Add, + sym::simd_saturating_sub => BinOp::Sub, + _ => unreachable!(), + }; + + // FIXME use vector instructions when possible + simd_pair_for_each_lane_typed(fx, x, y, ret, &|fx, x_lane, y_lane| { + crate::num::codegen_saturating_int_binop(fx, bin_op, x_lane, y_lane) + }); + } + // simd_arith_offset - // simd_saturating_add - // simd_saturating_sub // simd_scatter // simd_gather // simd_select_bitmask From 13fcf476001ff511103d9bec44e5be4e24eb0c96 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Mon, 5 Sep 2022 16:37:22 +0000 Subject: [PATCH 30/98] Implement simd_select_bitmask --- ...table-simd-Disable-unsupported-tests.patch | 64 ------------------- src/intrinsics/simd.rs | 29 ++++++++- 2 files changed, 28 insertions(+), 65 deletions(-) diff --git a/patches/0001-portable-simd-Disable-unsupported-tests.patch b/patches/0001-portable-simd-Disable-unsupported-tests.patch index e23dea976944b..89e2b61c1fc85 100644 --- a/patches/0001-portable-simd-Disable-unsupported-tests.patch +++ b/patches/0001-portable-simd-Disable-unsupported-tests.patch @@ -11,44 +11,6 @@ Subject: [PATCH] Disable unsupported tests crates/core_simd/tests/masks.rs | 3 --- 5 files changed, 20 insertions(+), 3 deletions(-) -diff --git a/crates/core_simd/src/masks/full_masks.rs b/crates/core_simd/src/masks/full_masks.rs -index adf0fcb..e7e657e 100644 ---- a/crates/core_simd/src/masks/full_masks.rs -+++ b/crates/core_simd/src/masks/full_masks.rs -@@ -180,6 +180,7 @@ where - super::Mask: ToBitMaskArray, - [(); as ToBitMaskArray>::BYTES]: Sized, - { -+ /* - assert_eq!( as ToBitMaskArray>::BYTES, N); - - // Safety: N is the correct bitmask size -@@ -202,6 +203,8 @@ where - Self::splat(false).to_int(), - )) - } -+ */ -+ panic!(); - } - - #[inline] -@@ -225,6 +228,7 @@ where - where - super::Mask: ToBitMask, - { -+ /* - // LLVM assumes bit order should match endianness - let bitmask = if cfg!(target_endian = "big") { - bitmask.reverse_bits(LANES) -@@ -240,6 +244,8 @@ where - Self::splat(false).to_int(), - )) - } -+ */ -+ panic!(); - } - - #[inline] diff --git a/crates/core_simd/src/vector.rs b/crates/core_simd/src/vector.rs index e8e8f68..7173c24 100644 --- a/crates/core_simd/src/vector.rs @@ -69,31 +31,5 @@ index e8e8f68..7173c24 100644 } impl Copy for Simd -diff --git a/crates/core_simd/tests/masks.rs b/crates/core_simd/tests/masks.rs -index 673d0db..3ebfcd1 100644 ---- a/crates/core_simd/tests/masks.rs -+++ b/crates/core_simd/tests/masks.rs -@@ -78,7 +78,6 @@ macro_rules! test_mask_api { - let mask = core_simd::Mask::<$type, 16>::from_array(values); - let bitmask = mask.to_bitmask(); - assert_eq!(bitmask, 0b1000001101001001); -- assert_eq!(core_simd::Mask::<$type, 16>::from_bitmask(bitmask), mask); - } - - #[test] -@@ -91,13 +90,11 @@ macro_rules! test_mask_api { - let mask = core_simd::Mask::<$type, 4>::from_array(values); - let bitmask = mask.to_bitmask(); - assert_eq!(bitmask, 0b1000); -- assert_eq!(core_simd::Mask::<$type, 4>::from_bitmask(bitmask), mask); - - let values = [true, false]; - let mask = core_simd::Mask::<$type, 2>::from_array(values); - let bitmask = mask.to_bitmask(); - assert_eq!(bitmask, 0b01); -- assert_eq!(core_simd::Mask::<$type, 2>::from_bitmask(bitmask), mask); - } - - #[test] -- 2.25.1 diff --git a/src/intrinsics/simd.rs b/src/intrinsics/simd.rs index a70ced7472f5a..51fce8c854bdb 100644 --- a/src/intrinsics/simd.rs +++ b/src/intrinsics/simd.rs @@ -652,6 +652,34 @@ pub(super) fn codegen_simd_intrinsic_call<'tcx>( } } + sym::simd_select_bitmask => { + intrinsic_args!(fx, args => (m, a, b); intrinsic); + + if !a.layout().ty.is_simd() { + report_simd_type_validation_error(fx, intrinsic, span, a.layout().ty); + return; + } + assert_eq!(a.layout(), b.layout()); + + let (lane_count, lane_ty) = a.layout().ty.simd_size_and_type(fx.tcx); + let lane_layout = fx.layout_of(lane_ty); + + let m = m.load_scalar(fx); + + for lane in 0..lane_count { + let m_lane = fx.bcx.ins().ushr_imm(m, u64::from(lane) as i64); + let m_lane = fx.bcx.ins().band_imm(m_lane, 1); + let a_lane = a.value_lane(fx, lane).load_scalar(fx); + let b_lane = b.value_lane(fx, lane).load_scalar(fx); + + let m_lane = fx.bcx.ins().icmp_imm(IntCC::Equal, m_lane, 0); + let res_lane = + CValue::by_val(fx.bcx.ins().select(m_lane, b_lane, a_lane), lane_layout); + + ret.place_lane(fx, lane).write_cvalue(fx, res_lane); + } + } + sym::simd_bitmask => { intrinsic_args!(fx, args => (a); intrinsic); @@ -748,7 +776,6 @@ pub(super) fn codegen_simd_intrinsic_call<'tcx>( // simd_arith_offset // simd_scatter // simd_gather - // simd_select_bitmask _ => { fx.tcx.sess.span_fatal(span, &format!("Unknown SIMD intrinsic {}", intrinsic)); } From 088e03fe224e4e7adf3fe1c3d5365a699418b7d9 Mon Sep 17 00:00:00 2001 From: Oli Scherer Date: Thu, 30 Jun 2022 08:16:05 +0000 Subject: [PATCH 31/98] Lower the assume intrinsic to a MIR statement --- src/base.rs | 2 ++ src/constant.rs | 1 + src/intrinsics/mod.rs | 3 --- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/base.rs b/src/base.rs index c412e451a033e..1f49ead93a3e8 100644 --- a/src/base.rs +++ b/src/base.rs @@ -791,6 +791,8 @@ fn codegen_stmt<'tcx>( | StatementKind::Nop | StatementKind::FakeRead(..) | StatementKind::Retag { .. } + // We ignore `assume` intrinsics, they are only useful for optimizations + | StatementKind::Assume(..) | StatementKind::AscribeUserType(..) => {} StatementKind::Coverage { .. } => fx.tcx.sess.fatal("-Zcoverage is unimplemented"), diff --git a/src/constant.rs b/src/constant.rs index 9224f499339cb..f75de9096f3ae 100644 --- a/src/constant.rs +++ b/src/constant.rs @@ -540,6 +540,7 @@ pub(crate) fn mir_operand_get_const_val<'tcx>( return None; } // conservative handling StatementKind::Assign(_) + | StatementKind::Assume(_) | StatementKind::FakeRead(_) | StatementKind::SetDiscriminant { .. } | StatementKind::Deinit(_) diff --git a/src/intrinsics/mod.rs b/src/intrinsics/mod.rs index 39e9e784a478b..0cd9332a58bef 100644 --- a/src/intrinsics/mod.rs +++ b/src/intrinsics/mod.rs @@ -357,9 +357,6 @@ fn codegen_regular_intrinsic_call<'tcx>( let usize_layout = fx.layout_of(fx.tcx.types.usize); match intrinsic { - sym::assume => { - intrinsic_args!(fx, args => (_a); intrinsic); - } sym::likely | sym::unlikely => { intrinsic_args!(fx, args => (a); intrinsic); From 104168a0f8ec9f218af84c315c0006c2d72450fe Mon Sep 17 00:00:00 2001 From: Oli Scherer Date: Tue, 12 Jul 2022 10:05:00 +0000 Subject: [PATCH 32/98] Generalize the Assume intrinsic statement to a general Intrinsic statement --- src/base.rs | 41 +++++++++++++++++++++++++---------------- src/constant.rs | 9 +++++---- 2 files changed, 30 insertions(+), 20 deletions(-) diff --git a/src/base.rs b/src/base.rs index 1f49ead93a3e8..2aa11ac2eeaa6 100644 --- a/src/base.rs +++ b/src/base.rs @@ -791,25 +791,34 @@ fn codegen_stmt<'tcx>( | StatementKind::Nop | StatementKind::FakeRead(..) | StatementKind::Retag { .. } - // We ignore `assume` intrinsics, they are only useful for optimizations - | StatementKind::Assume(..) | StatementKind::AscribeUserType(..) => {} StatementKind::Coverage { .. } => fx.tcx.sess.fatal("-Zcoverage is unimplemented"), - StatementKind::CopyNonOverlapping(inner) => { - let dst = codegen_operand(fx, &inner.dst); - let pointee = dst - .layout() - .pointee_info_at(fx, rustc_target::abi::Size::ZERO) - .expect("Expected pointer"); - let dst = dst.load_scalar(fx); - let src = codegen_operand(fx, &inner.src).load_scalar(fx); - let count = codegen_operand(fx, &inner.count).load_scalar(fx); - let elem_size: u64 = pointee.size.bytes(); - let bytes = - if elem_size != 1 { fx.bcx.ins().imul_imm(count, elem_size as i64) } else { count }; - fx.bcx.call_memcpy(fx.target_config, dst, src, bytes); - } + StatementKind::Intrinsic(ref intrinsic) => match &**intrinsic { + // We ignore `assume` intrinsics, they are only useful for optimizations + NonDivergingIntrinsic::Assume(_) => {} + NonDivergingIntrinsic::CopyNonOverlapping(mir::CopyNonOverlapping { + src, + dst, + count, + }) => { + let dst = codegen_operand(fx, dst); + let pointee = dst + .layout() + .pointee_info_at(fx, rustc_target::abi::Size::ZERO) + .expect("Expected pointer"); + let dst = dst.load_scalar(fx); + let src = codegen_operand(fx, src).load_scalar(fx); + let count = codegen_operand(fx, count).load_scalar(fx); + let elem_size: u64 = pointee.size.bytes(); + let bytes = if elem_size != 1 { + fx.bcx.ins().imul_imm(count, elem_size as i64) + } else { + count + }; + fx.bcx.call_memcpy(fx.target_config, dst, src, bytes); + } + }, } } diff --git a/src/constant.rs b/src/constant.rs index f75de9096f3ae..0305341da784e 100644 --- a/src/constant.rs +++ b/src/constant.rs @@ -536,11 +536,12 @@ pub(crate) fn mir_operand_get_const_val<'tcx>( { return None; } - StatementKind::CopyNonOverlapping(_) => { - return None; - } // conservative handling + StatementKind::Intrinsic(ref intrinsic) => match **intrinsic { + NonDivergingIntrinsic::CopyNonOverlapping(..) => return None, + NonDivergingIntrinsic::Assume(..) => {} + }, + // conservative handling StatementKind::Assign(_) - | StatementKind::Assume(_) | StatementKind::FakeRead(_) | StatementKind::SetDiscriminant { .. } | StatementKind::Deinit(_) From 1cf9be98cdc2d2753b11dd71d83c03c82897b006 Mon Sep 17 00:00:00 2001 From: David Wood Date: Thu, 21 Jul 2022 16:19:22 +0100 Subject: [PATCH 33/98] ssa: implement `#[collapse_debuginfo]` Debuginfo line information for macro invocations are collapsed by default - line information are replaced by the line of the outermost expansion site. Using `-Zdebug-macros` disables this behaviour. When the `collapse_debuginfo` feature is enabled, the default behaviour is reversed so that debuginfo is not collapsed by default. In addition, the `#[collapse_debuginfo]` attribute is available and can be applied to macro definitions which will then have their line information collapsed. Signed-off-by: David Wood --- src/debuginfo/line_info.rs | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/debuginfo/line_info.rs b/src/debuginfo/line_info.rs index 3ad0c420eaf0b..463de6a91c74c 100644 --- a/src/debuginfo/line_info.rs +++ b/src/debuginfo/line_info.rs @@ -68,9 +68,9 @@ impl DebugContext { ) -> (Lrc, u64, u64) { // Based on https://github.com/rust-lang/rust/blob/e369d87b015a84653343032833d65d0545fd3f26/src/librustc_codegen_ssa/mir/mod.rs#L116-L131 // In order to have a good line stepping behavior in debugger, we overwrite debug - // locations of macro expansions with that of the outermost expansion site - // (unless the crate is being compiled with `-Z debug-macros`). - let span = if !span.from_expansion() || tcx.sess.opts.unstable_opts.debug_macros { + // locations of macro expansions with that of the outermost expansion site (when the macro is + // annotated with `#[collapse_debuginfo]` or when `-Zdebug-macros` is provided). + let span = if tcx.should_collapse_debuginfo(span) { span } else { // Walk up the macro expansion chain until we reach a non-expanded span. From 944a142bfae7ee0d10cb12e9c3383b05e311f57e Mon Sep 17 00:00:00 2001 From: Michael Benfield Date: Thu, 25 Aug 2022 01:14:23 +0000 Subject: [PATCH 34/98] Change name of "dataful" variant to "untagged" This is in anticipation of a new enum layout, in which the niche optimization may be applied even when multiple variants have data. --- src/discriminant.rs | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) diff --git a/src/discriminant.rs b/src/discriminant.rs index e41ae1fbdbac5..97b395bcd0518 100644 --- a/src/discriminant.rs +++ b/src/discriminant.rs @@ -42,10 +42,10 @@ pub(crate) fn codegen_set_discriminant<'tcx>( Variants::Multiple { tag: _, tag_field, - tag_encoding: TagEncoding::Niche { dataful_variant, ref niche_variants, niche_start }, + tag_encoding: TagEncoding::Niche { untagged_variant, ref niche_variants, niche_start }, variants: _, } => { - if variant_index != dataful_variant { + if variant_index != untagged_variant { let niche = place.place_field(fx, mir::Field::new(tag_field)); let niche_value = variant_index.as_u32() - niche_variants.start().as_u32(); let niche_value = ty::ScalarInt::try_from_uint( @@ -113,7 +113,7 @@ pub(crate) fn codegen_get_discriminant<'tcx>( let res = CValue::by_val(val, dest_layout); dest.write_cvalue(fx, res); } - TagEncoding::Niche { dataful_variant, ref niche_variants, niche_start } => { + TagEncoding::Niche { untagged_variant, ref niche_variants, niche_start } => { // Rebase from niche values to discriminants, and check // whether the result is in range for the niche variants. @@ -169,8 +169,9 @@ pub(crate) fn codegen_get_discriminant<'tcx>( fx.bcx.ins().iadd_imm(relative_discr, i64::from(niche_variants.start().as_u32())) }; - let dataful_variant = fx.bcx.ins().iconst(cast_to, i64::from(dataful_variant.as_u32())); - let discr = fx.bcx.ins().select(is_niche, niche_discr, dataful_variant); + let untagged_variant = + fx.bcx.ins().iconst(cast_to, i64::from(untagged_variant.as_u32())); + let discr = fx.bcx.ins().select(is_niche, niche_discr, untagged_variant); let res = CValue::by_val(discr, dest_layout); dest.write_cvalue(fx, res); } From 931c07c94f5e6d2e24c08a1c4941612aab69872a Mon Sep 17 00:00:00 2001 From: Oli Scherer Date: Tue, 6 Sep 2022 14:08:59 +0000 Subject: [PATCH 35/98] The `<*const T>::guaranteed_*` methods now return an option for the unknown case --- src/intrinsics/mod.rs | 9 +-------- 1 file changed, 1 insertion(+), 8 deletions(-) diff --git a/src/intrinsics/mod.rs b/src/intrinsics/mod.rs index 39e9e784a478b..586c9489dd44b 100644 --- a/src/intrinsics/mod.rs +++ b/src/intrinsics/mod.rs @@ -819,20 +819,13 @@ fn codegen_regular_intrinsic_call<'tcx>( ret.write_cvalue(fx, val); } - sym::ptr_guaranteed_eq => { + sym::ptr_guaranteed_cmp => { intrinsic_args!(fx, args => (a, b); intrinsic); let val = crate::num::codegen_ptr_binop(fx, BinOp::Eq, a, b); ret.write_cvalue(fx, val); } - sym::ptr_guaranteed_ne => { - intrinsic_args!(fx, args => (a, b); intrinsic); - - let val = crate::num::codegen_ptr_binop(fx, BinOp::Ne, a, b); - ret.write_cvalue(fx, val); - } - sym::caller_location => { intrinsic_args!(fx, args => (); intrinsic); From 87bbc2d4135b0ee8c5fd5f33db7411029b5484e5 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Mon, 12 Sep 2022 12:28:14 +0200 Subject: [PATCH 36/98] Rustup to rustc 1.65.0-nightly (59e7a308e 2022-09-11) --- build_sysroot/Cargo.lock | 4 ++-- rust-toolchain | 2 +- src/intrinsics/mod.rs | 4 ++-- 3 files changed, 5 insertions(+), 5 deletions(-) diff --git a/build_sysroot/Cargo.lock b/build_sysroot/Cargo.lock index 6c5043bb6f8e1..17338aeaadaa2 100644 --- a/build_sysroot/Cargo.lock +++ b/build_sysroot/Cargo.lock @@ -123,9 +123,9 @@ dependencies = [ [[package]] name = "hermit-abi" -version = "0.2.5" +version = "0.2.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "897cd85af6387be149f55acf168e41be176a02de7872403aaab184afc2f327e6" +checksum = "ee512640fe35acbfb4bb779db6f0d80704c2cacfa2e39b601ef3e3f47d1ae4c7" dependencies = [ "compiler_builtins", "libc", diff --git a/rust-toolchain b/rust-toolchain index f17897e48adf5..4a228e3f8a87e 100644 --- a/rust-toolchain +++ b/rust-toolchain @@ -1,3 +1,3 @@ [toolchain] -channel = "nightly-2022-09-04" +channel = "nightly-2022-09-12" components = ["rust-src", "rustc-dev", "llvm-tools-preview"] diff --git a/src/intrinsics/mod.rs b/src/intrinsics/mod.rs index 971cd9f63a4aa..0302b843aa226 100644 --- a/src/intrinsics/mod.rs +++ b/src/intrinsics/mod.rs @@ -813,8 +813,8 @@ fn codegen_regular_intrinsic_call<'tcx>( sym::ptr_guaranteed_cmp => { intrinsic_args!(fx, args => (a, b); intrinsic); - let val = crate::num::codegen_ptr_binop(fx, BinOp::Eq, a, b); - ret.write_cvalue(fx, val); + let val = crate::num::codegen_ptr_binop(fx, BinOp::Eq, a, b).load_scalar(fx); + ret.write_cvalue(fx, CValue::by_val(val, fx.layout_of(fx.tcx.types.u8))); } sym::caller_location => { From 917be273ab827c45e3b46e24157525339844e121 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Sun, 28 Aug 2022 16:05:45 +0000 Subject: [PATCH 37/98] Minor improvement to apply_patches --- build_system/prepare.rs | 30 +++++++++++++++++++----------- 1 file changed, 19 insertions(+), 11 deletions(-) diff --git a/build_system/prepare.rs b/build_system/prepare.rs index b7368e8ffaba5..9b89525395fc5 100644 --- a/build_system/prepare.rs +++ b/build_system/prepare.rs @@ -1,8 +1,7 @@ use std::env; use std::ffi::OsStr; -use std::ffi::OsString; use std::fs; -use std::path::Path; +use std::path::{Path, PathBuf}; use std::process::Command; use super::rustc_info::{get_file_name, get_rustc_path, get_rustc_version}; @@ -156,14 +155,20 @@ fn init_git_repo(repo_dir: &Path) { spawn_and_wait(git_commit_cmd); } -fn get_patches(crate_name: &str) -> Vec { - let mut patches: Vec<_> = fs::read_dir("patches") +fn get_patches(source_dir: &Path, crate_name: &str) -> Vec { + let mut patches: Vec<_> = fs::read_dir(source_dir.join("patches")) .unwrap() .map(|entry| entry.unwrap().path()) .filter(|path| path.extension() == Some(OsStr::new("patch"))) - .map(|path| path.file_name().unwrap().to_owned()) - .filter(|file_name| { - file_name.to_str().unwrap().split_once("-").unwrap().1.starts_with(crate_name) + .filter(|path| { + path.file_name() + .unwrap() + .to_str() + .unwrap() + .split_once("-") + .unwrap() + .1 + .starts_with(crate_name) }) .collect(); patches.sort(); @@ -171,11 +176,14 @@ fn get_patches(crate_name: &str) -> Vec { } fn apply_patches(crate_name: &str, target_dir: &Path) { - for patch in get_patches(crate_name) { - eprintln!("[PATCH] {:?} <- {:?}", target_dir.file_name().unwrap(), patch); - let patch_arg = env::current_dir().unwrap().join("patches").join(patch); + for patch in get_patches(&std::env::current_dir().unwrap(), crate_name) { + eprintln!( + "[PATCH] {:?} <- {:?}", + target_dir.file_name().unwrap(), + patch.file_name().unwrap() + ); let mut apply_patch_cmd = Command::new("git"); - apply_patch_cmd.arg("am").arg(patch_arg).arg("-q").current_dir(target_dir); + apply_patch_cmd.arg("am").arg(patch).arg("-q").current_dir(target_dir); spawn_and_wait(apply_patch_cmd); } } From b12286fec3334238e899420a6586b3c1c7498a98 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Sun, 28 Aug 2022 16:46:09 +0000 Subject: [PATCH 38/98] Let abi-checker take the full path to the cg_clif dylib --- build_system/abi_checker.rs | 11 +++-------- build_system/build_backend.rs | 6 +++++- build_system/build_sysroot.rs | 7 +++---- build_system/mod.rs | 8 ++++---- build_system/tests.rs | 6 +++--- 5 files changed, 18 insertions(+), 20 deletions(-) diff --git a/build_system/abi_checker.rs b/build_system/abi_checker.rs index 67dbd0a38a4fb..faff081745f8e 100644 --- a/build_system/abi_checker.rs +++ b/build_system/abi_checker.rs @@ -10,7 +10,7 @@ pub(crate) fn run( channel: &str, sysroot_kind: SysrootKind, target_dir: &Path, - cg_clif_build_dir: &Path, + cg_clif_dylib: &Path, host_triple: &str, target_triple: &str, ) { @@ -29,7 +29,7 @@ pub(crate) fn run( channel, sysroot_kind, target_dir, - cg_clif_build_dir, + cg_clif_dylib, host_triple, target_triple, ); @@ -39,11 +39,6 @@ pub(crate) fn run( abi_checker_path.push("abi-checker"); env::set_current_dir(abi_checker_path.clone()).unwrap(); - let build_dir = abi_checker_path.parent().unwrap().join("build"); - let cg_clif_dylib_path = build_dir.join(if cfg!(windows) { "bin" } else { "lib" }).join( - env::consts::DLL_PREFIX.to_string() + "rustc_codegen_cranelift" + env::consts::DLL_SUFFIX, - ); - let pairs = ["rustc_calls_cgclif", "cgclif_calls_rustc", "cgclif_calls_cc", "cc_calls_cgclif"]; let mut cmd = Command::new("cargo"); @@ -54,7 +49,7 @@ pub(crate) fn run( cmd.arg("--pairs"); cmd.args(pairs); cmd.arg("--add-rustc-codegen-backend"); - cmd.arg(format!("cgclif:{}", cg_clif_dylib_path.display())); + cmd.arg(format!("cgclif:{}", cg_clif_dylib.display())); spawn_and_wait(cmd); } diff --git a/build_system/build_backend.rs b/build_system/build_backend.rs index 9e59b8199b412..d199d9906c342 100644 --- a/build_system/build_backend.rs +++ b/build_system/build_backend.rs @@ -2,6 +2,7 @@ use std::env; use std::path::{Path, PathBuf}; use std::process::Command; +use super::rustc_info::get_file_name; use super::utils::is_ci; pub(crate) fn build_backend( @@ -41,5 +42,8 @@ pub(crate) fn build_backend( eprintln!("[BUILD] rustc_codegen_cranelift"); super::utils::spawn_and_wait(cmd); - Path::new("target").join(host_triple).join(channel) + Path::new("target") + .join(host_triple) + .join(channel) + .join(get_file_name("rustc_codegen_cranelift", "dylib")) } diff --git a/build_system/build_sysroot.rs b/build_system/build_sysroot.rs index 7e205b0fd0b3b..5b18982fa7ef0 100644 --- a/build_system/build_sysroot.rs +++ b/build_system/build_sysroot.rs @@ -10,7 +10,7 @@ pub(crate) fn build_sysroot( channel: &str, sysroot_kind: SysrootKind, target_dir: &Path, - cg_clif_build_dir: &Path, + cg_clif_dylib_src: &Path, host_triple: &str, target_triple: &str, ) { @@ -23,7 +23,6 @@ pub(crate) fn build_sysroot( fs::create_dir_all(target_dir.join("lib")).unwrap(); // Copy the backend - let cg_clif_dylib = get_file_name("rustc_codegen_cranelift", "dylib"); let cg_clif_dylib_path = target_dir .join(if cfg!(windows) { // Windows doesn't have rpath support, so the cg_clif dylib needs to be next to the @@ -32,8 +31,8 @@ pub(crate) fn build_sysroot( } else { "lib" }) - .join(&cg_clif_dylib); - try_hard_link(cg_clif_build_dir.join(cg_clif_dylib), &cg_clif_dylib_path); + .join(get_file_name("rustc_codegen_cranelift", "dylib")); + try_hard_link(cg_clif_dylib_src, &cg_clif_dylib_path); // Build and copy rustc and cargo wrappers for wrapper in ["rustc-clif", "cargo-clif"] { diff --git a/build_system/mod.rs b/build_system/mod.rs index c3706dc6f8203..c665d1ef71c27 100644 --- a/build_system/mod.rs +++ b/build_system/mod.rs @@ -130,7 +130,7 @@ pub fn main() { process::exit(1); } - let cg_clif_build_dir = + let cg_clif_dylib = build_backend::build_backend(channel, &host_triple, use_unstable_features); match command { Command::Test => { @@ -138,7 +138,7 @@ pub fn main() { channel, sysroot_kind, &target_dir, - &cg_clif_build_dir, + &cg_clif_dylib, &host_triple, &target_triple, ); @@ -147,7 +147,7 @@ pub fn main() { channel, sysroot_kind, &target_dir, - &cg_clif_build_dir, + &cg_clif_dylib, &host_triple, &target_triple, ); @@ -157,7 +157,7 @@ pub fn main() { channel, sysroot_kind, &target_dir, - &cg_clif_build_dir, + &cg_clif_dylib, &host_triple, &target_triple, ); diff --git a/build_system/tests.rs b/build_system/tests.rs index 3f225b4efa2b1..d3296c6fda3dd 100644 --- a/build_system/tests.rs +++ b/build_system/tests.rs @@ -397,7 +397,7 @@ pub(crate) fn run_tests( channel: &str, sysroot_kind: SysrootKind, target_dir: &Path, - cg_clif_build_dir: &Path, + cg_clif_dylib: &Path, host_triple: &str, target_triple: &str, ) { @@ -408,7 +408,7 @@ pub(crate) fn run_tests( channel, SysrootKind::None, &target_dir, - cg_clif_build_dir, + cg_clif_dylib, &host_triple, &target_triple, ); @@ -427,7 +427,7 @@ pub(crate) fn run_tests( channel, sysroot_kind, &target_dir, - cg_clif_build_dir, + cg_clif_dylib, &host_triple, &target_triple, ); From 721668f13364f8d7b288b4dc6919bc2f9fdbdfb4 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Sun, 28 Aug 2022 17:14:47 +0000 Subject: [PATCH 39/98] Tiny cleanup --- build_system/tests.rs | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/build_system/tests.rs b/build_system/tests.rs index d3296c6fda3dd..e6348624c7bda 100644 --- a/build_system/tests.rs +++ b/build_system/tests.rs @@ -249,11 +249,7 @@ const EXTENDED_SYSROOT_SUITE: &[TestCase] = &[ bench_compile.arg("--prepare"); bench_compile.arg(format!("{:?}", runner.cargo_command(["clean"]))); - if cfg!(windows) { - bench_compile.arg("cmd /C \"set RUSTFLAGS= && cargo build\""); - } else { - bench_compile.arg("RUSTFLAGS='' cargo build"); - } + bench_compile.arg("cargo build"); bench_compile.arg(format!("{:?}", runner.cargo_command(["build"]))); spawn_and_wait(bench_compile); From c677cba06b69510585e7ce1f21523857679f08b8 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Sun, 28 Aug 2022 17:53:36 +0000 Subject: [PATCH 40/98] More uniform imports --- build_system/abi_checker.rs | 9 +++++---- build_system/config.rs | 3 ++- 2 files changed, 7 insertions(+), 5 deletions(-) diff --git a/build_system/abi_checker.rs b/build_system/abi_checker.rs index faff081745f8e..053198b699312 100644 --- a/build_system/abi_checker.rs +++ b/build_system/abi_checker.rs @@ -1,11 +1,12 @@ -use super::build_sysroot; -use super::config; -use super::utils::spawn_and_wait; -use build_system::SysrootKind; use std::env; use std::path::Path; use std::process::Command; +use super::build_sysroot; +use super::config; +use super::utils::spawn_and_wait; +use super::SysrootKind; + pub(crate) fn run( channel: &str, sysroot_kind: SysrootKind, diff --git a/build_system/config.rs b/build_system/config.rs index ef540cf1f822b..c31784e1097dc 100644 --- a/build_system/config.rs +++ b/build_system/config.rs @@ -1,4 +1,5 @@ -use std::{fs, process}; +use std::fs; +use std::process; fn load_config_file() -> Vec<(String, Option)> { fs::read_to_string("config.txt") From be305c2b1f4be31c66c3f646a85dc459d6ee5807 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Sun, 28 Aug 2022 16:38:09 +0000 Subject: [PATCH 41/98] Introduce cargo_command helper --- build_system/abi_checker.rs | 10 +--- build_system/build_backend.rs | 12 ++-- build_system/build_sysroot.rs | 5 +- build_system/prepare.rs | 5 +- build_system/tests.rs | 100 ++++++++++++++++------------------ build_system/utils.rs | 20 +++++++ 6 files changed, 81 insertions(+), 71 deletions(-) diff --git a/build_system/abi_checker.rs b/build_system/abi_checker.rs index 053198b699312..177b44d3141f1 100644 --- a/build_system/abi_checker.rs +++ b/build_system/abi_checker.rs @@ -1,10 +1,9 @@ use std::env; use std::path::Path; -use std::process::Command; use super::build_sysroot; use super::config; -use super::utils::spawn_and_wait; +use super::utils::{cargo_command, spawn_and_wait}; use super::SysrootKind; pub(crate) fn run( @@ -38,14 +37,11 @@ pub(crate) fn run( eprintln!("Running abi-checker"); let mut abi_checker_path = env::current_dir().unwrap(); abi_checker_path.push("abi-checker"); - env::set_current_dir(abi_checker_path.clone()).unwrap(); + env::set_current_dir(&abi_checker_path.clone()).unwrap(); let pairs = ["rustc_calls_cgclif", "cgclif_calls_rustc", "cgclif_calls_cc", "cc_calls_cgclif"]; - let mut cmd = Command::new("cargo"); - cmd.arg("run"); - cmd.arg("--target"); - cmd.arg(target_triple); + let mut cmd = cargo_command("cargo", "run", Some(target_triple), &abi_checker_path); cmd.arg("--"); cmd.arg("--pairs"); cmd.args(pairs); diff --git a/build_system/build_backend.rs b/build_system/build_backend.rs index d199d9906c342..cda468bcfa2df 100644 --- a/build_system/build_backend.rs +++ b/build_system/build_backend.rs @@ -1,17 +1,16 @@ use std::env; -use std::path::{Path, PathBuf}; -use std::process::Command; +use std::path::PathBuf; use super::rustc_info::get_file_name; -use super::utils::is_ci; +use super::utils::{cargo_command, is_ci}; pub(crate) fn build_backend( channel: &str, host_triple: &str, use_unstable_features: bool, ) -> PathBuf { - let mut cmd = Command::new("cargo"); - cmd.arg("build").arg("--target").arg(host_triple); + let source_dir = std::env::current_dir().unwrap(); + let mut cmd = cargo_command("cargo", "build", Some(host_triple), &source_dir); cmd.env("CARGO_BUILD_INCREMENTAL", "true"); // Force incr comp even in release mode @@ -42,7 +41,8 @@ pub(crate) fn build_backend( eprintln!("[BUILD] rustc_codegen_cranelift"); super::utils::spawn_and_wait(cmd); - Path::new("target") + source_dir + .join("target") .join(host_triple) .join(channel) .join(get_file_name("rustc_codegen_cranelift", "dylib")) diff --git a/build_system/build_sysroot.rs b/build_system/build_sysroot.rs index 5b18982fa7ef0..c2c81feb25a6b 100644 --- a/build_system/build_sysroot.rs +++ b/build_system/build_sysroot.rs @@ -3,7 +3,7 @@ use std::path::{Path, PathBuf}; use std::process::{self, Command}; use super::rustc_info::{get_file_name, get_rustc_version, get_wrapper_file_name}; -use super::utils::{spawn_and_wait, try_hard_link}; +use super::utils::{cargo_command, spawn_and_wait, try_hard_link}; use super::SysrootKind; pub(crate) fn build_sysroot( @@ -185,8 +185,7 @@ fn build_clif_sysroot_for_triple( } // Build sysroot - let mut build_cmd = Command::new("cargo"); - build_cmd.arg("build").arg("--target").arg(triple).current_dir("build_sysroot"); + let mut build_cmd = cargo_command("cargo", "build", Some(triple), Path::new("build_sysroot")); let mut rustflags = "-Zforce-unstable-if-unmarked -Cpanic=abort".to_string(); rustflags.push_str(&format!(" -Zcodegen-backend={}", cg_clif_dylib_path.to_str().unwrap())); if channel == "release" { diff --git a/build_system/prepare.rs b/build_system/prepare.rs index 9b89525395fc5..83a76d3591d68 100644 --- a/build_system/prepare.rs +++ b/build_system/prepare.rs @@ -5,7 +5,7 @@ use std::path::{Path, PathBuf}; use std::process::Command; use super::rustc_info::{get_file_name, get_rustc_path, get_rustc_version}; -use super::utils::{copy_dir_recursively, spawn_and_wait}; +use super::utils::{cargo_command, copy_dir_recursively, spawn_and_wait}; pub(crate) fn prepare() { prepare_sysroot(); @@ -52,8 +52,7 @@ pub(crate) fn prepare() { ); eprintln!("[LLVM BUILD] simple-raytracer"); - let mut build_cmd = Command::new("cargo"); - build_cmd.arg("build").env_remove("CARGO_TARGET_DIR").current_dir("simple-raytracer"); + let build_cmd = cargo_command("cargo", "build", None, Path::new("simple-raytracer")); spawn_and_wait(build_cmd); fs::copy( Path::new("simple-raytracer/target/debug").join(get_file_name("main", "bin")), diff --git a/build_system/tests.rs b/build_system/tests.rs index e6348624c7bda..3f0d461fbe6c3 100644 --- a/build_system/tests.rs +++ b/build_system/tests.rs @@ -1,7 +1,7 @@ use super::build_sysroot; use super::config; use super::rustc_info::get_wrapper_file_name; -use super::utils::{spawn_and_wait, spawn_and_wait_with_input}; +use super::utils::{cargo_command, spawn_and_wait, spawn_and_wait_with_input}; use build_system::SysrootKind; use std::env; use std::ffi::OsStr; @@ -218,20 +218,14 @@ const BASE_SYSROOT_SUITE: &[TestCase] = &[ const EXTENDED_SYSROOT_SUITE: &[TestCase] = &[ TestCase::new("test.rust-random/rand", &|runner| { runner.in_dir(["rand"], |runner| { - runner.run_cargo(["clean"]); + runner.run_cargo("clean", []); if runner.host_triple == runner.target_triple { eprintln!("[TEST] rust-random/rand"); - runner.run_cargo(["test", "--workspace"]); + runner.run_cargo("test", ["--workspace"]); } else { eprintln!("[AOT] rust-random/rand"); - runner.run_cargo([ - "build", - "--workspace", - "--target", - &runner.target_triple, - "--tests", - ]); + runner.run_cargo("build", ["--workspace", "--tests"]); } }); }), @@ -247,11 +241,19 @@ const EXTENDED_SYSROOT_SUITE: &[TestCase] = &[ bench_compile.arg("--warmup"); bench_compile.arg("1"); bench_compile.arg("--prepare"); - bench_compile.arg(format!("{:?}", runner.cargo_command(["clean"]))); + bench_compile.arg(format!("{:?}", runner.cargo_command("clean", []))); bench_compile.arg("cargo build"); - bench_compile.arg(format!("{:?}", runner.cargo_command(["build"]))); + let cargo_clif = runner + .root_dir + .clone() + .join("build") + .join(get_wrapper_file_name("cargo-clif", "bin")); + let mut clif_build_cmd = cargo_command(cargo_clif, "build", None, Path::new(".")); + clif_build_cmd.env("RUSTFLAGS", &runner.rust_flags); + bench_compile.arg(format!("{:?}", clif_build_cmd)); + spawn_and_wait(bench_compile); eprintln!("[BENCH RUN] ebobby/simple-raytracer"); @@ -265,51 +267,39 @@ const EXTENDED_SYSROOT_SUITE: &[TestCase] = &[ bench_run.arg(PathBuf::from("./raytracer_cg_clif")); spawn_and_wait(bench_run); } else { - runner.run_cargo(["clean"]); + runner.run_cargo("clean", []); eprintln!("[BENCH COMPILE] ebobby/simple-raytracer (skipped)"); eprintln!("[COMPILE] ebobby/simple-raytracer"); - runner.run_cargo(["build", "--target", &runner.target_triple]); + runner.run_cargo("build", []); eprintln!("[BENCH RUN] ebobby/simple-raytracer (skipped)"); } }); }), TestCase::new("test.libcore", &|runner| { runner.in_dir(["build_sysroot", "sysroot_src", "library", "core", "tests"], |runner| { - runner.run_cargo(["clean"]); + runner.run_cargo("clean", []); if runner.host_triple == runner.target_triple { - runner.run_cargo(["test"]); + runner.run_cargo("test", []); } else { eprintln!("Cross-Compiling: Not running tests"); - runner.run_cargo(["build", "--target", &runner.target_triple, "--tests"]); + runner.run_cargo("build", ["--tests"]); } }); }), TestCase::new("test.regex-shootout-regex-dna", &|runner| { runner.in_dir(["regex"], |runner| { - runner.run_cargo(["clean"]); + runner.run_cargo("clean", []); // newer aho_corasick versions throw a deprecation warning let lint_rust_flags = format!("{} --cap-lints warn", runner.rust_flags); - let mut build_cmd = runner.cargo_command([ - "build", - "--example", - "shootout-regex-dna", - "--target", - &runner.target_triple, - ]); + let mut build_cmd = runner.cargo_command("build", ["--example", "shootout-regex-dna"]); build_cmd.env("RUSTFLAGS", lint_rust_flags.clone()); spawn_and_wait(build_cmd); if runner.host_triple == runner.target_triple { - let mut run_cmd = runner.cargo_command([ - "run", - "--example", - "shootout-regex-dna", - "--target", - &runner.target_triple, - ]); + let mut run_cmd = runner.cargo_command("run", ["--example", "shootout-regex-dna"]); run_cmd.env("RUSTFLAGS", lint_rust_flags); let input = @@ -350,28 +340,30 @@ const EXTENDED_SYSROOT_SUITE: &[TestCase] = &[ }), TestCase::new("test.regex", &|runner| { runner.in_dir(["regex"], |runner| { - runner.run_cargo(["clean"]); + runner.run_cargo("clean", []); // newer aho_corasick versions throw a deprecation warning let lint_rust_flags = format!("{} --cap-lints warn", runner.rust_flags); if runner.host_triple == runner.target_triple { - let mut run_cmd = runner.cargo_command([ + let mut run_cmd = runner.cargo_command( "test", - "--tests", - "--", - "--exclude-should-panic", - "--test-threads", - "1", - "-Zunstable-options", - "-q", - ]); + [ + "--tests", + "--", + "--exclude-should-panic", + "--test-threads", + "1", + "-Zunstable-options", + "-q", + ], + ); run_cmd.env("RUSTFLAGS", lint_rust_flags); spawn_and_wait(run_cmd); } else { eprintln!("Cross-Compiling: Not running tests"); let mut build_cmd = - runner.cargo_command(["build", "--tests", "--target", &runner.target_triple]); + runner.cargo_command("build", ["--tests", "--target", &runner.target_triple]); build_cmd.env("RUSTFLAGS", lint_rust_flags.clone()); spawn_and_wait(build_cmd); } @@ -379,11 +371,11 @@ const EXTENDED_SYSROOT_SUITE: &[TestCase] = &[ }), TestCase::new("test.portable-simd", &|runner| { runner.in_dir(["portable-simd"], |runner| { - runner.run_cargo(["clean"]); - runner.run_cargo(["build", "--all-targets", "--target", &runner.target_triple]); + runner.run_cargo("clean", []); + runner.run_cargo("build", ["--all-targets", "--target", &runner.target_triple]); if runner.host_triple == runner.target_triple { - runner.run_cargo(["test", "-q"]); + runner.run_cargo("test", ["-q"]); } }); }), @@ -590,25 +582,29 @@ impl TestRunner { spawn_and_wait(cmd); } - fn cargo_command(&self, args: I) -> Command + fn cargo_command<'a, I>(&self, subcommand: &str, args: I) -> Command where - I: IntoIterator, - S: AsRef, + I: IntoIterator, { let mut cargo_clif = self.root_dir.clone(); cargo_clif.push("build"); cargo_clif.push(get_wrapper_file_name("cargo-clif", "bin")); - let mut cmd = Command::new(cargo_clif); + let mut cmd = cargo_command( + cargo_clif, + subcommand, + if subcommand == "clean" { None } else { Some(&self.target_triple) }, + Path::new("."), + ); cmd.args(args); cmd.env("RUSTFLAGS", &self.rust_flags); cmd } - fn run_cargo<'a, I>(&self, args: I) + fn run_cargo<'a, I>(&self, subcommand: &str, args: I) where I: IntoIterator, { - spawn_and_wait(self.cargo_command(args)); + spawn_and_wait(self.cargo_command(subcommand, args)); } } diff --git a/build_system/utils.rs b/build_system/utils.rs index bdf8f8ecd9970..4015a2beaba22 100644 --- a/build_system/utils.rs +++ b/build_system/utils.rs @@ -4,6 +4,26 @@ use std::io::Write; use std::path::Path; use std::process::{self, Command, Stdio}; +pub(crate) fn cargo_command( + cargo: impl AsRef, + subcommand: &str, + triple: Option<&str>, + source_dir: &Path, +) -> Command { + let mut cmd = Command::new(cargo.as_ref()); + cmd.arg(subcommand) + .arg("--manifest-path") + .arg(source_dir.join("Cargo.toml")) + .arg("--target-dir") + .arg(source_dir.join("target")); + + if let Some(triple) = triple { + cmd.arg("--target").arg(triple); + } + + cmd +} + #[track_caller] pub(crate) fn try_hard_link(src: impl AsRef, dst: impl AsRef) { let src = src.as_ref(); From a65c881aa3c3c065277375c592bea539ebaa3d4d Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Sun, 28 Aug 2022 17:41:36 +0000 Subject: [PATCH 42/98] Introduce hyperfine_command helper --- build_system/tests.rs | 33 +++++++++++++++------------------ build_system/utils.rs | 26 ++++++++++++++++++++++++++ 2 files changed, 41 insertions(+), 18 deletions(-) diff --git a/build_system/tests.rs b/build_system/tests.rs index 3f0d461fbe6c3..74042bc92183e 100644 --- a/build_system/tests.rs +++ b/build_system/tests.rs @@ -1,7 +1,7 @@ use super::build_sysroot; use super::config; use super::rustc_info::get_wrapper_file_name; -use super::utils::{cargo_command, spawn_and_wait, spawn_and_wait_with_input}; +use super::utils::{cargo_command, hyperfine_command, spawn_and_wait, spawn_and_wait_with_input}; use build_system::SysrootKind; use std::env; use std::ffi::OsStr; @@ -231,28 +231,23 @@ const EXTENDED_SYSROOT_SUITE: &[TestCase] = &[ }), TestCase::new("bench.simple-raytracer", &|runner| { runner.in_dir(["simple-raytracer"], |runner| { - let run_runs = env::var("RUN_RUNS").unwrap_or("10".to_string()); + let run_runs = env::var("RUN_RUNS").unwrap_or("10".to_string()).parse().unwrap(); if runner.host_triple == runner.target_triple { eprintln!("[BENCH COMPILE] ebobby/simple-raytracer"); - let mut bench_compile = Command::new("hyperfine"); - bench_compile.arg("--runs"); - bench_compile.arg(&run_runs); - bench_compile.arg("--warmup"); - bench_compile.arg("1"); - bench_compile.arg("--prepare"); - bench_compile.arg(format!("{:?}", runner.cargo_command("clean", []))); + let prepare = runner.cargo_command("clean", []); - bench_compile.arg("cargo build"); + let llvm_build_cmd = cargo_command("cargo", "build", None, Path::new(".")); let cargo_clif = runner .root_dir .clone() .join("build") .join(get_wrapper_file_name("cargo-clif", "bin")); - let mut clif_build_cmd = cargo_command(cargo_clif, "build", None, Path::new(".")); - clif_build_cmd.env("RUSTFLAGS", &runner.rust_flags); - bench_compile.arg(format!("{:?}", clif_build_cmd)); + let clif_build_cmd = cargo_command(cargo_clif, "build", None, Path::new(".")); + + let bench_compile = + hyperfine_command(1, run_runs, Some(prepare), llvm_build_cmd, clif_build_cmd); spawn_and_wait(bench_compile); @@ -260,11 +255,13 @@ const EXTENDED_SYSROOT_SUITE: &[TestCase] = &[ fs::copy(PathBuf::from("./target/debug/main"), PathBuf::from("raytracer_cg_clif")) .unwrap(); - let mut bench_run = Command::new("hyperfine"); - bench_run.arg("--runs"); - bench_run.arg(&run_runs); - bench_run.arg(PathBuf::from("./raytracer_cg_llvm")); - bench_run.arg(PathBuf::from("./raytracer_cg_clif")); + let bench_run = hyperfine_command( + 0, + run_runs, + None, + Command::new("./raytracer_cg_llvm"), + Command::new("./raytracer_cg_clif"), + ); spawn_and_wait(bench_run); } else { runner.run_cargo("clean", []); diff --git a/build_system/utils.rs b/build_system/utils.rs index 4015a2beaba22..48da64906e2a4 100644 --- a/build_system/utils.rs +++ b/build_system/utils.rs @@ -24,6 +24,32 @@ pub(crate) fn cargo_command( cmd } +pub(crate) fn hyperfine_command( + warmup: u64, + runs: u64, + prepare: Option, + a: Command, + b: Command, +) -> Command { + let mut bench = Command::new("hyperfine"); + + if warmup != 0 { + bench.arg("--warmup").arg(warmup.to_string()); + } + + if runs != 0 { + bench.arg("--runs").arg(runs.to_string()); + } + + if let Some(prepare) = prepare { + bench.arg("--prepare").arg(format!("{:?}", prepare)); + } + + bench.arg(format!("{:?}", a)).arg(format!("{:?}", b)); + + bench +} + #[track_caller] pub(crate) fn try_hard_link(src: impl AsRef, dst: impl AsRef) { let src = src.as_ref(); From 02219239525517322c6e90339db2c8ca234f097f Mon Sep 17 00:00:00 2001 From: Eric Holk Date: Tue, 30 Aug 2022 12:39:28 -0700 Subject: [PATCH 43/98] Make x.py check work --- src/base.rs | 4 ++++ src/value_and_place.rs | 2 +- 2 files changed, 5 insertions(+), 1 deletion(-) diff --git a/src/base.rs b/src/base.rs index 2aa11ac2eeaa6..399474d79e3b6 100644 --- a/src/base.rs +++ b/src/base.rs @@ -701,6 +701,10 @@ fn codegen_stmt<'tcx>( let operand = codegen_operand(fx, operand); operand.unsize_value(fx, lval); } + Rvalue::Cast(CastKind::DynStar, _, _) => { + // FIXME(dyn-star) + unimplemented!() + } Rvalue::Discriminant(place) => { let place = codegen_place(fx, place); let value = place.to_cvalue(fx); diff --git a/src/value_and_place.rs b/src/value_and_place.rs index 2ee98546c992a..d58b52851ac04 100644 --- a/src/value_and_place.rs +++ b/src/value_and_place.rs @@ -815,7 +815,7 @@ pub(crate) fn assert_assignable<'tcx>( ); // fn(&T) -> for<'l> fn(&'l T) is allowed } - (&ty::Dynamic(from_traits, _), &ty::Dynamic(to_traits, _)) => { + (&ty::Dynamic(from_traits, _, _from_kind), &ty::Dynamic(to_traits, _, _to_kind)) => { for (from, to) in from_traits.iter().zip(to_traits) { let from = fx.tcx.normalize_erasing_late_bound_regions(ParamEnv::reveal_all(), from); From da373e3ea83186c93f2902efac445a155807d5e6 Mon Sep 17 00:00:00 2001 From: b-naber Date: Mon, 27 Jun 2022 16:32:47 +0200 Subject: [PATCH 44/98] use ty::Unevaluated<'tcx, ()> in type system --- src/constant.rs | 19 +++++++++++++------ 1 file changed, 13 insertions(+), 6 deletions(-) diff --git a/src/constant.rs b/src/constant.rs index 0305341da784e..7bf578b6a4e67 100644 --- a/src/constant.rs +++ b/src/constant.rs @@ -124,11 +124,7 @@ pub(crate) fn codegen_constant<'tcx>( ) -> CValue<'tcx> { let const_ = match fx.monomorphize(constant.literal) { ConstantKind::Ty(ct) => ct, - ConstantKind::Val(val, ty) => return codegen_const_value(fx, val, ty), - }; - let const_val = match const_.kind() { - ConstKind::Value(valtree) => fx.tcx.valtree_to_const_val((const_.ty(), valtree)), - ConstKind::Unevaluated(ty::Unevaluated { def, substs, promoted }) + ConstantKind::Unevaluated(mir::Unevaluated { def, substs, promoted }) if fx.tcx.is_static(def.did) => { assert!(substs.is_empty()); @@ -136,7 +132,7 @@ pub(crate) fn codegen_constant<'tcx>( return codegen_static_ref(fx, def.did, fx.layout_of(const_.ty())).to_cvalue(fx); } - ConstKind::Unevaluated(unevaluated) => { + ConstantKind::Unevaluated(unevaluated) => { match fx.tcx.const_eval_resolve(ParamEnv::reveal_all(), unevaluated, None) { Ok(const_val) => const_val, Err(_) => { @@ -144,6 +140,17 @@ pub(crate) fn codegen_constant<'tcx>( } } } + ConstantKind::Val(val, ty) => return codegen_const_value(fx, val, ty), + }; + let const_val = match const_.kind() { + ConstKind::Value(valtree) => fx.tcx.valtree_to_const_val((const_.ty(), valtree)), + ConstKind::Unevaluated(ty::Unevaluated { def, substs, promoted }) + if fx.tcx.is_static(def.did) => + { + assert!(substs.is_empty()); + assert!(promoted.is_none()); + return codegen_static_ref(fx, def.did, fx.layout_of(const_.ty())).to_cvalue(fx); + } ConstKind::Param(_) | ConstKind::Infer(_) | ConstKind::Bound(_, _) From fa35afe8dca1e73169246101cba56b933a7ea132 Mon Sep 17 00:00:00 2001 From: b-naber Date: Thu, 30 Jun 2022 16:54:10 +0200 Subject: [PATCH 45/98] cranelift changes --- src/constant.rs | 108 ++++++++++++++++++++++++++---------------------- 1 file changed, 59 insertions(+), 49 deletions(-) diff --git a/src/constant.rs b/src/constant.rs index 7bf578b6a4e67..a04b38ae33f37 100644 --- a/src/constant.rs +++ b/src/constant.rs @@ -41,36 +41,30 @@ impl ConstantCx { pub(crate) fn check_constants(fx: &mut FunctionCx<'_, '_, '_>) -> bool { let mut all_constants_ok = true; for constant in &fx.mir.required_consts { - let const_ = match fx.monomorphize(constant.literal) { - ConstantKind::Ty(ct) => ct, + let unevaluated = match fx.monomorphize(constant.literal) { + ConstantKind::Ty(ct) => match ct.kind() { + ConstKind::Unevaluated(uv) => uv.expand(), + ConstKind::Value(_) => continue, + ConstKind::Param(_) + | ConstKind::Infer(_) + | ConstKind::Bound(_, _) + | ConstKind::Placeholder(_) + | ConstKind::Error(_) => unreachable!("{:?}", ct), + }, + ConstantKind::Unevaluated(uv, _) => uv, ConstantKind::Val(..) => continue, }; - match const_.kind() { - ConstKind::Value(_) => {} - ConstKind::Unevaluated(unevaluated) => { - if let Err(err) = - fx.tcx.const_eval_resolve(ParamEnv::reveal_all(), unevaluated, None) - { - all_constants_ok = false; - match err { - ErrorHandled::Reported(_) | ErrorHandled::Linted => { - fx.tcx.sess.span_err(constant.span, "erroneous constant encountered"); - } - ErrorHandled::TooGeneric => { - span_bug!( - constant.span, - "codegen encountered polymorphic constant: {:?}", - err - ); - } - } + + if let Err(err) = fx.tcx.const_eval_resolve(ParamEnv::reveal_all(), unevaluated, None) { + all_constants_ok = false; + match err { + ErrorHandled::Reported(_) | ErrorHandled::Linted => { + fx.tcx.sess.span_err(constant.span, "erroneous constant encountered"); + } + ErrorHandled::TooGeneric => { + span_bug!(constant.span, "codegen encountered polymorphic constant: {:?}", err); } } - ConstKind::Param(_) - | ConstKind::Infer(_) - | ConstKind::Bound(_, _) - | ConstKind::Placeholder(_) - | ConstKind::Error(_) => unreachable!("{:?}", const_), } } all_constants_ok @@ -122,43 +116,56 @@ pub(crate) fn codegen_constant<'tcx>( fx: &mut FunctionCx<'_, '_, 'tcx>, constant: &Constant<'tcx>, ) -> CValue<'tcx> { - let const_ = match fx.monomorphize(constant.literal) { - ConstantKind::Ty(ct) => ct, - ConstantKind::Unevaluated(mir::Unevaluated { def, substs, promoted }) + let (const_val, ty) = match fx.monomorphize(constant.literal) { + ConstantKind::Ty(const_) => match const_.kind() { + ConstKind::Value(valtree) => { + (fx.tcx.valtree_to_const_val((const_.ty(), valtree)), const_.ty()) + } + ConstKind::Unevaluated(ty::Unevaluated { def, substs, promoted }) + if fx.tcx.is_static(def.did) => + { + assert!(substs.is_empty()); + assert_eq!(promoted, ()); + return codegen_static_ref(fx, def.did, fx.layout_of(const_.ty())).to_cvalue(fx); + } + ConstKind::Unevaluated(unevaluated) => { + match fx.tcx.const_eval_resolve(ParamEnv::reveal_all(), unevaluated.expand(), None) + { + Ok(const_val) => (const_val, const_.ty()), + Err(_) => { + span_bug!( + constant.span, + "erroneous constant not captured by required_consts" + ); + } + } + } + ConstKind::Param(_) + | ConstKind::Infer(_) + | ConstKind::Bound(_, _) + | ConstKind::Placeholder(_) + | ConstKind::Error(_) => unreachable!("{:?}", const_), + }, + ConstantKind::Unevaluated(ty::Unevaluated { def, substs, promoted }, ty) if fx.tcx.is_static(def.did) => { assert!(substs.is_empty()); assert!(promoted.is_none()); - return codegen_static_ref(fx, def.did, fx.layout_of(const_.ty())).to_cvalue(fx); + return codegen_static_ref(fx, def.did, fx.layout_of(ty)).to_cvalue(fx); } - ConstantKind::Unevaluated(unevaluated) => { + ConstantKind::Unevaluated(unevaluated, ty) => { match fx.tcx.const_eval_resolve(ParamEnv::reveal_all(), unevaluated, None) { - Ok(const_val) => const_val, + Ok(const_val) => (const_val, ty), Err(_) => { span_bug!(constant.span, "erroneous constant not captured by required_consts"); } } } - ConstantKind::Val(val, ty) => return codegen_const_value(fx, val, ty), - }; - let const_val = match const_.kind() { - ConstKind::Value(valtree) => fx.tcx.valtree_to_const_val((const_.ty(), valtree)), - ConstKind::Unevaluated(ty::Unevaluated { def, substs, promoted }) - if fx.tcx.is_static(def.did) => - { - assert!(substs.is_empty()); - assert!(promoted.is_none()); - return codegen_static_ref(fx, def.did, fx.layout_of(const_.ty())).to_cvalue(fx); - } - ConstKind::Param(_) - | ConstKind::Infer(_) - | ConstKind::Bound(_, _) - | ConstKind::Placeholder(_) - | ConstKind::Error(_) => unreachable!("{:?}", const_), + ConstantKind::Val(val, ty) => (val, ty), }; - codegen_const_value(fx, const_val, const_.ty()) + codegen_const_value(fx, const_val, ty) } pub(crate) fn codegen_const_value<'tcx>( @@ -503,6 +510,9 @@ pub(crate) fn mir_operand_get_const_val<'tcx>( .eval_for_mir(fx.tcx, ParamEnv::reveal_all()) .try_to_value(fx.tcx), ConstantKind::Val(val, _) => Some(val), + ConstantKind::Unevaluated(uv, _) => { + fx.tcx.const_eval_resolve(ParamEnv::reveal_all(), uv, None).ok() + } }, // FIXME(rust-lang/rust#85105): Casts like `IMM8 as u32` result in the const being stored // inside a temporary before being passed to the intrinsic requiring the const argument. From 6d544a8a4c9ab5cd4b228532e2501980881801b7 Mon Sep 17 00:00:00 2001 From: Eric Holk Date: Tue, 30 Aug 2022 12:44:00 -0700 Subject: [PATCH 46/98] Address code review comments --- src/value_and_place.rs | 1 + 1 file changed, 1 insertion(+) diff --git a/src/value_and_place.rs b/src/value_and_place.rs index d58b52851ac04..cfaadca949107 100644 --- a/src/value_and_place.rs +++ b/src/value_and_place.rs @@ -816,6 +816,7 @@ pub(crate) fn assert_assignable<'tcx>( // fn(&T) -> for<'l> fn(&'l T) is allowed } (&ty::Dynamic(from_traits, _, _from_kind), &ty::Dynamic(to_traits, _, _to_kind)) => { + // FIXME(dyn-star): Do the right thing with DynKinds for (from, to) in from_traits.iter().zip(to_traits) { let from = fx.tcx.normalize_erasing_late_bound_regions(ParamEnv::reveal_all(), from); From a10dd1f340c425660557c042836da9e1e52e7453 Mon Sep 17 00:00:00 2001 From: b-naber Date: Wed, 14 Sep 2022 15:35:24 +0200 Subject: [PATCH 47/98] address review again --- src/constant.rs | 20 +------------------- 1 file changed, 1 insertion(+), 19 deletions(-) diff --git a/src/constant.rs b/src/constant.rs index a04b38ae33f37..bc34802fa7288 100644 --- a/src/constant.rs +++ b/src/constant.rs @@ -121,25 +121,7 @@ pub(crate) fn codegen_constant<'tcx>( ConstKind::Value(valtree) => { (fx.tcx.valtree_to_const_val((const_.ty(), valtree)), const_.ty()) } - ConstKind::Unevaluated(ty::Unevaluated { def, substs, promoted }) - if fx.tcx.is_static(def.did) => - { - assert!(substs.is_empty()); - assert_eq!(promoted, ()); - return codegen_static_ref(fx, def.did, fx.layout_of(const_.ty())).to_cvalue(fx); - } - ConstKind::Unevaluated(unevaluated) => { - match fx.tcx.const_eval_resolve(ParamEnv::reveal_all(), unevaluated.expand(), None) - { - Ok(const_val) => (const_val, const_.ty()), - Err(_) => { - span_bug!( - constant.span, - "erroneous constant not captured by required_consts" - ); - } - } - } + ConstKind::Unevaluated(_) => bug!("expected constant to be evaluated at this stage"), ConstKind::Param(_) | ConstKind::Infer(_) | ConstKind::Bound(_, _) From f68742a03cf460d8e319830acc6f371238d6bf13 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Thu, 15 Sep 2022 14:59:14 +0200 Subject: [PATCH 48/98] Rustup to rustc 1.65.0-nightly (750bd1a7f 2022-09-14) --- build_sysroot/Cargo.lock | 4 ++-- rust-toolchain | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/build_sysroot/Cargo.lock b/build_sysroot/Cargo.lock index 17338aeaadaa2..641891a95c4b2 100644 --- a/build_sysroot/Cargo.lock +++ b/build_sysroot/Cargo.lock @@ -301,9 +301,9 @@ dependencies = [ [[package]] name = "unicode-width" -version = "0.1.9" +version = "0.1.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3ed742d4ea2bd1176e236172c8429aaf54486e7ac098db29ffe6529e0ce50973" +checksum = "c0edd1e5b14653f783770bce4a4dabb4a5108a5370a5f5d8cfe8710c361f6c8b" dependencies = [ "compiler_builtins", "rustc-std-workspace-core", diff --git a/rust-toolchain b/rust-toolchain index 4a228e3f8a87e..ba03a47fac2e9 100644 --- a/rust-toolchain +++ b/rust-toolchain @@ -1,3 +1,3 @@ [toolchain] -channel = "nightly-2022-09-12" +channel = "nightly-2022-09-15" components = ["rust-src", "rustc-dev", "llvm-tools-preview"] From 879c86ff3088c70725dcbeed0430e497f970b8bd Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Thu, 15 Sep 2022 14:08:30 +0000 Subject: [PATCH 49/98] Implement dyn* support --- src/abi/mod.rs | 54 ++++++++++++++++++++++++++++++++++++++++-- src/base.rs | 6 ++--- src/unsize.rs | 16 +++++++++++++ src/value_and_place.rs | 4 ++++ src/vtable.rs | 26 +++++++++++++++----- 5 files changed, 95 insertions(+), 11 deletions(-) diff --git a/src/abi/mod.rs b/src/abi/mod.rs index 0497c2570e622..04e39954dd3cd 100644 --- a/src/abi/mod.rs +++ b/src/abi/mod.rs @@ -465,7 +465,7 @@ pub(crate) fn codegen_terminator_call<'tcx>( let sig = clif_sig_from_fn_abi(fx.tcx, fx.target_config.default_call_conv, &fn_abi); let sig = fx.bcx.import_signature(sig); - (CallTarget::Indirect(sig, method), Some(ptr)) + (CallTarget::Indirect(sig, method), Some(ptr.get_addr(fx))) } // Normal call @@ -560,7 +560,19 @@ pub(crate) fn codegen_drop<'tcx>( // we don't actually need to drop anything } else { match ty.kind() { - ty::Dynamic(..) => { + ty::Dynamic(_, _, ty::Dyn) => { + // IN THIS ARM, WE HAVE: + // ty = *mut (dyn Trait) + // which is: exists ( *mut T, Vtable ) + // args[0] args[1] + // + // args = ( Data, Vtable ) + // | + // v + // /-------\ + // | ... | + // \-------/ + // let (ptr, vtable) = drop_place.to_ptr_maybe_unsized(); let ptr = ptr.get_addr(fx); let drop_fn = crate::vtable::drop_fn_of_obj(fx, vtable.unwrap()); @@ -578,6 +590,44 @@ pub(crate) fn codegen_drop<'tcx>( let sig = fx.bcx.import_signature(sig); fx.bcx.ins().call_indirect(sig, drop_fn, &[ptr]); } + ty::Dynamic(_, _, ty::DynStar) => { + // IN THIS ARM, WE HAVE: + // ty = *mut (dyn* Trait) + // which is: *mut exists (T, Vtable) + // + // args = [ * ] + // | + // v + // ( Data, Vtable ) + // | + // v + // /-------\ + // | ... | + // \-------/ + // + // + // WE CAN CONVERT THIS INTO THE ABOVE LOGIC BY DOING + // + // data = &(*args[0]).0 // gives a pointer to Data above (really the same pointer) + // vtable = (*args[0]).1 // loads the vtable out + // (data, vtable) // an equivalent Rust `*mut dyn Trait` + // + // SO THEN WE CAN USE THE ABOVE CODE. + let dyn_star = drop_place.to_cvalue(fx); + let (data, vtable) = dyn_star.load_scalar_pair(fx); + let drop_fn = crate::vtable::drop_fn_of_obj(fx, vtable); + + let virtual_drop = Instance { + def: ty::InstanceDef::Virtual(drop_instance.def_id(), 0), + substs: drop_instance.substs, + }; + let fn_abi = + RevealAllLayoutCx(fx.tcx).fn_abi_of_instance(virtual_drop, ty::List::empty()); + + let sig = clif_sig_from_fn_abi(fx.tcx, fx.target_config.default_call_conv, &fn_abi); + let sig = fx.bcx.import_signature(sig); + fx.bcx.ins().call_indirect(sig, drop_fn, &[data]); + } _ => { assert!(!matches!(drop_instance.def, InstanceDef::Virtual(_, _))); diff --git a/src/base.rs b/src/base.rs index 399474d79e3b6..317aaa21c8e50 100644 --- a/src/base.rs +++ b/src/base.rs @@ -701,9 +701,9 @@ fn codegen_stmt<'tcx>( let operand = codegen_operand(fx, operand); operand.unsize_value(fx, lval); } - Rvalue::Cast(CastKind::DynStar, _, _) => { - // FIXME(dyn-star) - unimplemented!() + Rvalue::Cast(CastKind::DynStar, ref operand, _) => { + let operand = codegen_operand(fx, operand); + operand.coerce_dyn_star(fx, lval); } Rvalue::Discriminant(place) => { let place = codegen_place(fx, place); diff --git a/src/unsize.rs b/src/unsize.rs index dd9d891ddbdee..b194a7c8b0ddd 100644 --- a/src/unsize.rs +++ b/src/unsize.rs @@ -147,6 +147,22 @@ pub(crate) fn coerce_unsized_into<'tcx>( } } +pub(crate) fn coerce_dyn_star<'tcx>( + fx: &mut FunctionCx<'_, '_, 'tcx>, + src: CValue<'tcx>, + dst: CPlace<'tcx>, +) { + let data = src.load_scalar(fx); + + let vtable = if let ty::Dynamic(data, _, ty::DynStar) = dst.layout().ty.kind() { + crate::vtable::get_vtable(fx, src.layout().ty, data.principal()) + } else { + bug!("Only valid to do a DynStar cast into a DynStar type") + }; + + dst.write_cvalue(fx, CValue::by_val_pair(data, vtable, dst.layout())); +} + // Adapted from https://github.com/rust-lang/rust/blob/2a663555ddf36f6b041445894a8c175cd1bc718c/src/librustc_codegen_ssa/glue.rs pub(crate) fn size_and_align_of_dst<'tcx>( diff --git a/src/value_and_place.rs b/src/value_and_place.rs index cfaadca949107..91fb421a9ee1f 100644 --- a/src/value_and_place.rs +++ b/src/value_and_place.rs @@ -236,6 +236,10 @@ impl<'tcx> CValue<'tcx> { crate::unsize::coerce_unsized_into(fx, self, dest); } + pub(crate) fn coerce_dyn_star(self, fx: &mut FunctionCx<'_, '_, 'tcx>, dest: CPlace<'tcx>) { + crate::unsize::coerce_dyn_star(fx, self, dest); + } + /// If `ty` is signed, `const_val` must already be sign extended. pub(crate) fn const_val( fx: &mut FunctionCx<'_, '_, 'tcx>, diff --git a/src/vtable.rs b/src/vtable.rs index 36b3725ef42bc..f04fb82de8c81 100644 --- a/src/vtable.rs +++ b/src/vtable.rs @@ -45,12 +45,26 @@ pub(crate) fn get_ptr_and_method_ref<'tcx>( fx: &mut FunctionCx<'_, '_, 'tcx>, arg: CValue<'tcx>, idx: usize, -) -> (Value, Value) { - let (ptr, vtable) = if let Abi::ScalarPair(_, _) = arg.layout().abi { - arg.load_scalar_pair(fx) - } else { - let (ptr, vtable) = arg.try_to_ptr().unwrap(); - (ptr.get_addr(fx), vtable.unwrap()) +) -> (Pointer, Value) { + let (ptr, vtable) = 'block: { + if let ty::Ref(_, ty, _) = arg.layout().ty.kind() { + if ty.is_dyn_star() { + let inner_layout = fx.layout_of(arg.layout().ty.builtin_deref(true).unwrap().ty); + let dyn_star = CPlace::for_ptr(Pointer::new(arg.load_scalar(fx)), inner_layout); + let ptr = dyn_star.place_field(fx, mir::Field::new(0)).to_ptr(); + let vtable = + dyn_star.place_field(fx, mir::Field::new(1)).to_cvalue(fx).load_scalar(fx); + break 'block (ptr, vtable); + } + } + + if let Abi::ScalarPair(_, _) = arg.layout().abi { + let (ptr, vtable) = arg.load_scalar_pair(fx); + (Pointer::new(ptr), vtable) + } else { + let (ptr, vtable) = arg.try_to_ptr().unwrap(); + (ptr, vtable.unwrap()) + } }; let usize_size = fx.layout_of(fx.tcx.types.usize).size.bytes(); From b023e2f7d04d6f7707e4dd05ab133e56e9f4ff51 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Thu, 15 Sep 2022 16:05:27 +0000 Subject: [PATCH 50/98] Fix bundled static libraries --- src/archive.rs | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/archive.rs b/src/archive.rs index b4c7909617079..31d3d0e06156b 100644 --- a/src/archive.rs +++ b/src/archive.rs @@ -159,6 +159,8 @@ impl<'a> ArchiveBuilder<'a> for ArArchiveBuilder<'a> { let err = err.to_string(); if err == "Unknown file magic" { // Not an object file; skip it. + } else if object::read::archive::ArchiveFile::parse(&*data).is_ok() { + // Nested archive file; skip it. } else { sess.fatal(&format!( "error parsing `{}` during archive creation: {}", From d82b696594c39d5f463e4560b68d7a2d4e33b2f0 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Thu, 15 Sep 2022 16:14:29 +0000 Subject: [PATCH 51/98] Update for latests rustc test suite changes --- scripts/setup_rust_fork.sh | 4 ++++ scripts/test_rustc_tests.sh | 2 ++ 2 files changed, 6 insertions(+) diff --git a/scripts/setup_rust_fork.sh b/scripts/setup_rust_fork.sh index 6ae8b14f4c015..d6a37789599fe 100644 --- a/scripts/setup_rust_fork.sh +++ b/scripts/setup_rust_fork.sh @@ -68,3 +68,7 @@ popd # FIXME remove once inline asm is fully supported export RUSTFLAGS="$RUSTFLAGS --cfg=rustix_use_libc" + +# Allow the testsuite to use llvm tools +host_triple=$(rustc -vV | grep host | cut -d: -f2 | tr -d " ") +export LLVM_BIN_DIR="$(rustc --print sysroot)/lib/rustlib/$host_triple/bin" diff --git a/scripts/test_rustc_tests.sh b/scripts/test_rustc_tests.sh index 944787612d8bc..ace0cd76d81a5 100755 --- a/scripts/test_rustc_tests.sh +++ b/scripts/test_rustc_tests.sh @@ -116,6 +116,8 @@ rm src/test/ui/test-attrs/test-type.rs # TODO panic message on stderr. correct s # not sure if this is actually a bug in the test suite, but the symbol list shows the function without leading _ for some reason rm -r src/test/run-make/native-link-modifier-bundle +rm src/test/ui/stdio-is-blocking.rs # really slow with unoptimized libstd + 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,incremental} popd From d7c77313cb108b8a8fbeb61dffb74adcc36a82ca Mon Sep 17 00:00:00 2001 From: b-naber Date: Thu, 15 Sep 2022 22:27:41 +0200 Subject: [PATCH 52/98] nits --- src/constant.rs | 12 +----------- 1 file changed, 1 insertion(+), 11 deletions(-) diff --git a/src/constant.rs b/src/constant.rs index bc34802fa7288..6b4ed9b9d4053 100644 --- a/src/constant.rs +++ b/src/constant.rs @@ -117,17 +117,7 @@ pub(crate) fn codegen_constant<'tcx>( constant: &Constant<'tcx>, ) -> CValue<'tcx> { let (const_val, ty) = match fx.monomorphize(constant.literal) { - ConstantKind::Ty(const_) => match const_.kind() { - ConstKind::Value(valtree) => { - (fx.tcx.valtree_to_const_val((const_.ty(), valtree)), const_.ty()) - } - ConstKind::Unevaluated(_) => bug!("expected constant to be evaluated at this stage"), - ConstKind::Param(_) - | ConstKind::Infer(_) - | ConstKind::Bound(_, _) - | ConstKind::Placeholder(_) - | ConstKind::Error(_) => unreachable!("{:?}", const_), - }, + ConstantKind::Ty(const_) => unreachable!("{:?}", const_), ConstantKind::Unevaluated(ty::Unevaluated { def, substs, promoted }, ty) if fx.tcx.is_static(def.did) => { From 93af5f599922bd14c2156b26b277fa642cbceac5 Mon Sep 17 00:00:00 2001 From: Oli Scherer Date: Wed, 27 Jul 2022 11:58:34 +0000 Subject: [PATCH 53/98] Revert "Revert "Rollup merge of #98582 - oli-obk:unconstrained_opaque_type, r=estebank"" This reverts commit 4a742a691e7dd2522bad68b86fe2fd5a199d5561. --- src/base.rs | 1 + src/value_and_place.rs | 8 ++++++++ 2 files changed, 9 insertions(+) diff --git a/src/base.rs b/src/base.rs index 399474d79e3b6..11540d8008160 100644 --- a/src/base.rs +++ b/src/base.rs @@ -850,6 +850,7 @@ pub(crate) fn codegen_place<'tcx>( PlaceElem::Deref => { cplace = cplace.place_deref(fx); } + PlaceElem::OpaqueCast(ty) => cplace = cplace.place_opaque_cast(fx, ty), PlaceElem::Field(field, _ty) => { cplace = cplace.place_field(fx, field); } diff --git a/src/value_and_place.rs b/src/value_and_place.rs index cfaadca949107..3fa3e3657cb63 100644 --- a/src/value_and_place.rs +++ b/src/value_and_place.rs @@ -621,6 +621,14 @@ impl<'tcx> CPlace<'tcx> { } } + pub(crate) fn place_opaque_cast( + self, + fx: &mut FunctionCx<'_, '_, 'tcx>, + ty: Ty<'tcx>, + ) -> CPlace<'tcx> { + CPlace { inner: self.inner, layout: fx.layout_of(ty) } + } + pub(crate) fn place_field( self, fx: &mut FunctionCx<'_, '_, 'tcx>, From 3c5882018f7f686a5a0b3a631cad33503987e5aa Mon Sep 17 00:00:00 2001 From: b-naber Date: Mon, 19 Sep 2022 19:46:53 +0200 Subject: [PATCH 54/98] introduce mir::Unevaluated --- src/constant.rs | 13 ++----------- 1 file changed, 2 insertions(+), 11 deletions(-) diff --git a/src/constant.rs b/src/constant.rs index 6b4ed9b9d4053..aac64d854a6b5 100644 --- a/src/constant.rs +++ b/src/constant.rs @@ -5,7 +5,6 @@ use rustc_middle::middle::codegen_fn_attrs::CodegenFnAttrFlags; use rustc_middle::mir::interpret::{ read_target_uint, AllocId, ConstAllocation, ConstValue, ErrorHandled, GlobalAlloc, Scalar, }; -use rustc_middle::ty::ConstKind; use rustc_span::DUMMY_SP; use cranelift_codegen::ir::GlobalValueData; @@ -42,15 +41,7 @@ pub(crate) fn check_constants(fx: &mut FunctionCx<'_, '_, '_>) -> bool { let mut all_constants_ok = true; for constant in &fx.mir.required_consts { let unevaluated = match fx.monomorphize(constant.literal) { - ConstantKind::Ty(ct) => match ct.kind() { - ConstKind::Unevaluated(uv) => uv.expand(), - ConstKind::Value(_) => continue, - ConstKind::Param(_) - | ConstKind::Infer(_) - | ConstKind::Bound(_, _) - | ConstKind::Placeholder(_) - | ConstKind::Error(_) => unreachable!("{:?}", ct), - }, + ConstantKind::Ty(_) => unreachable!(), ConstantKind::Unevaluated(uv, _) => uv, ConstantKind::Val(..) => continue, }; @@ -118,7 +109,7 @@ pub(crate) fn codegen_constant<'tcx>( ) -> CValue<'tcx> { let (const_val, ty) = match fx.monomorphize(constant.literal) { ConstantKind::Ty(const_) => unreachable!("{:?}", const_), - ConstantKind::Unevaluated(ty::Unevaluated { def, substs, promoted }, ty) + ConstantKind::Unevaluated(mir::Unevaluated { def, substs, promoted }, ty) if fx.tcx.is_static(def.did) => { assert!(substs.is_empty()); From 7e250da20fd6ac20c554397bcb0e69bc6c235dac Mon Sep 17 00:00:00 2001 From: b-naber Date: Thu, 22 Sep 2022 12:34:23 +0200 Subject: [PATCH 55/98] rename Unevaluated to UnevaluatedConst --- src/constant.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/constant.rs b/src/constant.rs index aac64d854a6b5..e12805b093cc7 100644 --- a/src/constant.rs +++ b/src/constant.rs @@ -109,7 +109,7 @@ pub(crate) fn codegen_constant<'tcx>( ) -> CValue<'tcx> { let (const_val, ty) = match fx.monomorphize(constant.literal) { ConstantKind::Ty(const_) => unreachable!("{:?}", const_), - ConstantKind::Unevaluated(mir::Unevaluated { def, substs, promoted }, ty) + ConstantKind::Unevaluated(mir::UnevaluatedConst { def, substs, promoted }, ty) if fx.tcx.is_static(def.did) => { assert!(substs.is_empty()); From b3d3ba9928820465d6ca08e1068280006453d291 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Sun, 25 Sep 2022 14:11:30 +0200 Subject: [PATCH 56/98] Rustup to rustc 1.66.0-nightly (3f83906b3 2022-09-24) --- build_sysroot/Cargo.lock | 30 ++++++++++++++++++++---------- rust-toolchain | 2 +- 2 files changed, 21 insertions(+), 11 deletions(-) diff --git a/build_sysroot/Cargo.lock b/build_sysroot/Cargo.lock index 641891a95c4b2..d5a65c3b72173 100644 --- a/build_sysroot/Cargo.lock +++ b/build_sysroot/Cargo.lock @@ -54,11 +54,21 @@ dependencies = [ "rustc-std-workspace-core", ] +[[package]] +name = "cfg-if" +version = "1.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd" +dependencies = [ + "compiler_builtins", + "rustc-std-workspace-core", +] + [[package]] name = "compiler_builtins" -version = "0.1.79" +version = "0.1.80" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4f873ce2bd3550b0b565f878b3d04ea8253f4259dc3d20223af2e1ba86f5ecca" +checksum = "c3feb824e4dde07fb32acc53c8cc1f9e537bb4d7e0a331198000840979d410d3" dependencies = [ "rustc-std-workspace-core", ] @@ -135,9 +145,9 @@ dependencies = [ [[package]] name = "libc" -version = "0.2.132" +version = "0.2.133" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8371e4e5341c3a96db127eb2465ac681ced4c433e01dd0e938adbef26ba93ba5" +checksum = "c0f80d65747a3e43d1596c7c5492d95d5edddaabd45a7fcdb02b95f644164966" dependencies = [ "rustc-std-workspace-core", ] @@ -182,7 +192,7 @@ name = "panic_abort" version = "0.0.0" dependencies = [ "alloc", - "cfg-if", + "cfg-if 0.1.10", "compiler_builtins", "core", "libc", @@ -193,7 +203,7 @@ name = "panic_unwind" version = "0.0.0" dependencies = [ "alloc", - "cfg-if", + "cfg-if 0.1.10", "compiler_builtins", "core", "libc", @@ -245,7 +255,7 @@ version = "0.0.0" dependencies = [ "addr2line", "alloc", - "cfg-if", + "cfg-if 1.0.0", "compiler_builtins", "core", "dlmalloc", @@ -267,7 +277,7 @@ dependencies = [ name = "std_detect" version = "0.1.5" dependencies = [ - "cfg-if", + "cfg-if 1.0.0", "compiler_builtins", "libc", "rustc-std-workspace-alloc", @@ -289,7 +299,7 @@ dependencies = [ name = "test" version = "0.0.0" dependencies = [ - "cfg-if", + "cfg-if 0.1.10", "core", "getopts", "libc", @@ -315,7 +325,7 @@ name = "unwind" version = "0.0.0" dependencies = [ "cc", - "cfg-if", + "cfg-if 0.1.10", "compiler_builtins", "core", "libc", diff --git a/rust-toolchain b/rust-toolchain index ba03a47fac2e9..06e9106e685a4 100644 --- a/rust-toolchain +++ b/rust-toolchain @@ -1,3 +1,3 @@ [toolchain] -channel = "nightly-2022-09-15" +channel = "nightly-2022-09-25" components = ["rust-src", "rustc-dev", "llvm-tools-preview"] From 5ed4377677f071489ad24860ac2c6c3fac324921 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Sun, 25 Sep 2022 14:35:21 +0200 Subject: [PATCH 57/98] Fix ConstantKind::Ty codegen --- src/base.rs | 2 +- src/constant.rs | 74 ++++++++++++++++++++++--------------------------- 2 files changed, 34 insertions(+), 42 deletions(-) diff --git a/src/base.rs b/src/base.rs index de74a91dd8fbc..1aeb9ff25703d 100644 --- a/src/base.rs +++ b/src/base.rs @@ -917,7 +917,7 @@ pub(crate) fn codegen_operand<'tcx>( let cplace = codegen_place(fx, *place); cplace.to_cvalue(fx) } - Operand::Constant(const_) => crate::constant::codegen_constant(fx, const_), + Operand::Constant(const_) => crate::constant::codegen_constant_operand(fx, const_), } } diff --git a/src/constant.rs b/src/constant.rs index 9fbb08a9cb998..d1610b4005fa0 100644 --- a/src/constant.rs +++ b/src/constant.rs @@ -7,7 +7,6 @@ use rustc_middle::mir::interpret::{ }; use rustc_span::DUMMY_SP; -use cranelift_codegen::ir::GlobalValueData; use cranelift_module::*; use crate::prelude::*; @@ -81,53 +80,46 @@ pub(crate) fn codegen_tls_ref<'tcx>( CValue::by_val(tls_ptr, layout) } -fn codegen_static_ref<'tcx>( - fx: &mut FunctionCx<'_, '_, 'tcx>, - def_id: DefId, - layout: TyAndLayout<'tcx>, -) -> CPlace<'tcx> { - let data_id = data_id_for_static(fx.tcx, fx.module, def_id, false); - let local_data_id = fx.module.declare_data_in_func(data_id, &mut fx.bcx.func); - if fx.clif_comments.enabled() { - fx.add_comment(local_data_id, format!("{:?}", def_id)); - } - let global_ptr = fx.bcx.ins().global_value(fx.pointer_type, local_data_id); - assert!(!layout.is_unsized(), "unsized statics aren't supported"); - assert!( - matches!( - fx.bcx.func.global_values[local_data_id], - GlobalValueData::Symbol { tls: false, .. } - ), - "tls static referenced without Rvalue::ThreadLocalRef" - ); - CPlace::for_ptr(crate::pointer::Pointer::new(global_ptr), layout) -} - -pub(crate) fn codegen_constant<'tcx>( +pub(crate) fn eval_mir_constant<'tcx>( fx: &mut FunctionCx<'_, '_, 'tcx>, constant: &Constant<'tcx>, -) -> CValue<'tcx> { - let (const_val, ty) = match fx.monomorphize(constant.literal) { - ConstantKind::Ty(const_) => unreachable!("{:?}", const_), - ConstantKind::Unevaluated(mir::UnevaluatedConst { def, substs, promoted }, ty) +) -> (ConstValue<'tcx>, Ty<'tcx>) { + let constant_kind = fx.monomorphize(constant.literal); + let uv = match constant_kind { + ConstantKind::Ty(const_) => match const_.kind() { + ty::ConstKind::Unevaluated(uv) => uv.expand(), + ty::ConstKind::Value(val) => { + return (fx.tcx.valtree_to_const_val((const_.ty(), val)), const_.ty()); + } + err => span_bug!( + constant.span, + "encountered bad ConstKind after monomorphizing: {:?}", + err + ), + }, + ConstantKind::Unevaluated(mir::UnevaluatedConst { def, .. }, _) if fx.tcx.is_static(def.did) => { - assert!(substs.is_empty()); - assert!(promoted.is_none()); - - return codegen_static_ref(fx, def.did, fx.layout_of(ty)).to_cvalue(fx); - } - ConstantKind::Unevaluated(unevaluated, ty) => { - match fx.tcx.const_eval_resolve(ParamEnv::reveal_all(), unevaluated, None) { - Ok(const_val) => (const_val, ty), - Err(_) => { - span_bug!(constant.span, "erroneous constant not captured by required_consts"); - } - } + span_bug!(constant.span, "MIR constant refers to static"); } - ConstantKind::Val(val, ty) => (val, ty), + ConstantKind::Unevaluated(uv, _) => uv, + ConstantKind::Val(val, _) => return (val, constant_kind.ty()), }; + ( + fx.tcx.const_eval_resolve(ty::ParamEnv::reveal_all(), uv, None).unwrap_or_else(|_err| { + span_bug!(constant.span, "erroneous constant not captured by required_consts"); + }), + constant_kind.ty(), + ) +} + +pub(crate) fn codegen_constant_operand<'tcx>( + fx: &mut FunctionCx<'_, '_, 'tcx>, + constant: &Constant<'tcx>, +) -> CValue<'tcx> { + let (const_val, ty) = eval_mir_constant(fx, constant); + codegen_const_value(fx, const_val, ty) } From 241eae76e209b578b75b916e0e9a7d6ea24deb43 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Sun, 25 Sep 2022 14:44:51 +0200 Subject: [PATCH 58/98] Monomorphize ConstantKind::Unevaluated in mir_operand_get_const_val --- src/constant.rs | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) diff --git a/src/constant.rs b/src/constant.rs index d1610b4005fa0..da4a96c4acc84 100644 --- a/src/constant.rs +++ b/src/constant.rs @@ -459,14 +459,13 @@ pub(crate) fn mir_operand_get_const_val<'tcx>( operand: &Operand<'tcx>, ) -> Option> { match operand { - Operand::Constant(const_) => match const_.literal { - ConstantKind::Ty(const_) => fx - .monomorphize(const_) - .eval_for_mir(fx.tcx, ParamEnv::reveal_all()) - .try_to_value(fx.tcx), + Operand::Constant(const_) => match fx.monomorphize(const_.literal) { + ConstantKind::Ty(const_) => Some( + const_.eval_for_mir(fx.tcx, ParamEnv::reveal_all()).try_to_value(fx.tcx).unwrap(), + ), ConstantKind::Val(val, _) => Some(val), ConstantKind::Unevaluated(uv, _) => { - fx.tcx.const_eval_resolve(ParamEnv::reveal_all(), uv, None).ok() + Some(fx.tcx.const_eval_resolve(ParamEnv::reveal_all(), uv, None).unwrap()) } }, // FIXME(rust-lang/rust#85105): Casts like `IMM8 as u32` result in the const being stored From f82016891a26d7cd940f5e266c5fa24edee2f208 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Sun, 25 Sep 2022 14:58:33 +0200 Subject: [PATCH 59/98] Fix cpuid replacement shim --- src/inline_asm.rs | 22 ++++++++++++---------- 1 file changed, 12 insertions(+), 10 deletions(-) diff --git a/src/inline_asm.rs b/src/inline_asm.rs index 8b3d475cb1802..3fcc84d39295f 100644 --- a/src/inline_asm.rs +++ b/src/inline_asm.rs @@ -27,7 +27,7 @@ pub(crate) fn codegen_inline_asm<'tcx>( } // Used by stdarch - if template[0] == InlineAsmTemplatePiece::String("movq %rbx, ".to_string()) + if template[0] == InlineAsmTemplatePiece::String("mov ".to_string()) && matches!( template[1], InlineAsmTemplatePiece::Placeholder { @@ -36,24 +36,26 @@ pub(crate) fn codegen_inline_asm<'tcx>( span: _ } ) - && template[2] == InlineAsmTemplatePiece::String("\n".to_string()) - && template[3] == InlineAsmTemplatePiece::String("cpuid".to_string()) - && template[4] == InlineAsmTemplatePiece::String("\n".to_string()) - && template[5] == InlineAsmTemplatePiece::String("xchgq %rbx, ".to_string()) + && template[2] == InlineAsmTemplatePiece::String(", rbx".to_string()) + && template[3] == InlineAsmTemplatePiece::String("\n".to_string()) + && template[4] == InlineAsmTemplatePiece::String("cpuid".to_string()) + && template[5] == InlineAsmTemplatePiece::String("\n".to_string()) + && template[6] == InlineAsmTemplatePiece::String("xchg ".to_string()) && matches!( - template[6], + template[7], InlineAsmTemplatePiece::Placeholder { operand_idx: 0, modifier: Some('r'), span: _ } ) + && template[8] == InlineAsmTemplatePiece::String(", rbx".to_string()) { assert_eq!(operands.len(), 4); let (leaf, eax_place) = match operands[1] { InlineAsmOperand::InOut { reg: InlineAsmRegOrRegClass::Reg(InlineAsmReg::X86(X86InlineAsmReg::ax)), - late: true, + late: _, ref in_value, out_place: Some(out_place), } => ( @@ -68,7 +70,7 @@ pub(crate) fn codegen_inline_asm<'tcx>( InlineAsmRegOrRegClass::RegClass(InlineAsmRegClass::X86( X86InlineAsmRegClass::reg, )), - late: true, + late: _, place: Some(place), } => crate::base::codegen_place(fx, place), _ => unreachable!(), @@ -76,7 +78,7 @@ pub(crate) fn codegen_inline_asm<'tcx>( let (sub_leaf, ecx_place) = match operands[2] { InlineAsmOperand::InOut { reg: InlineAsmRegOrRegClass::Reg(InlineAsmReg::X86(X86InlineAsmReg::cx)), - late: true, + late: _, ref in_value, out_place: Some(out_place), } => ( @@ -88,7 +90,7 @@ pub(crate) fn codegen_inline_asm<'tcx>( let edx_place = match operands[3] { InlineAsmOperand::Out { reg: InlineAsmRegOrRegClass::Reg(InlineAsmReg::X86(X86InlineAsmReg::dx)), - late: true, + late: _, place: Some(place), } => crate::base::codegen_place(fx, place), _ => unreachable!(), From d422d506511d8665d16e1f396ef316dddb537ad0 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Sun, 25 Sep 2022 15:14:59 +0200 Subject: [PATCH 60/98] Pass --sysroot when building the new sysroot To avoid accidentally loading the original libcore --- build_system/build_sysroot.rs | 1 + 1 file changed, 1 insertion(+) diff --git a/build_system/build_sysroot.rs b/build_system/build_sysroot.rs index c2c81feb25a6b..856aecc49fd1c 100644 --- a/build_system/build_sysroot.rs +++ b/build_system/build_sysroot.rs @@ -188,6 +188,7 @@ fn build_clif_sysroot_for_triple( let mut build_cmd = cargo_command("cargo", "build", Some(triple), Path::new("build_sysroot")); let mut rustflags = "-Zforce-unstable-if-unmarked -Cpanic=abort".to_string(); rustflags.push_str(&format!(" -Zcodegen-backend={}", cg_clif_dylib_path.to_str().unwrap())); + rustflags.push_str(&format!(" --sysroot={}", target_dir.to_str().unwrap())); if channel == "release" { build_cmd.arg("--release"); rustflags.push_str(" -Zmir-opt-level=3"); From 94d52158c6ac7b1ce0350a334b28c9e3ccf00060 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Sun, 25 Sep 2022 15:16:45 +0200 Subject: [PATCH 61/98] Work around rust-lang/libc#2924 --- build_sysroot/Cargo.lock | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/build_sysroot/Cargo.lock b/build_sysroot/Cargo.lock index d5a65c3b72173..a8077feaaabac 100644 --- a/build_sysroot/Cargo.lock +++ b/build_sysroot/Cargo.lock @@ -145,9 +145,9 @@ dependencies = [ [[package]] name = "libc" -version = "0.2.133" +version = "0.2.132" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c0f80d65747a3e43d1596c7c5492d95d5edddaabd45a7fcdb02b95f644164966" +checksum = "8371e4e5341c3a96db127eb2465ac681ced4c433e01dd0e938adbef26ba93ba5" dependencies = [ "rustc-std-workspace-core", ] From 322ff0ba0589202df43f4749745c503529daacfc Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Sun, 25 Sep 2022 14:05:01 +0000 Subject: [PATCH 62/98] Work around rustbuild bug --- scripts/setup_rust_fork.sh | 15 +++++++++++++++ 1 file changed, 15 insertions(+) diff --git a/scripts/setup_rust_fork.sh b/scripts/setup_rust_fork.sh index d6a37789599fe..25103a2fd5036 100644 --- a/scripts/setup_rust_fork.sh +++ b/scripts/setup_rust_fork.sh @@ -27,6 +27,21 @@ index d95b5b7f17f..00b6f0e3635 100644 [dev-dependencies] rand = "0.7" rand_xorshift = "0.2" +diff --git a/src/bootstrap/config.rs b/src/bootstrap/config.rs +index a6333976f2a..c9a872e876c 100644 +--- a/src/bootstrap/config.rs ++++ b/src/bootstrap/config.rs +@@ -917,6 +917,10 @@ pub fn parse(args: &[String]) -> Config { + config.initial_cargo = config.out.join(config.build.triple).join("stage0/bin/cargo"); + } + ++ // Workaround for rustbuild bug ++ config.initial_rustc = PathBuf::from("$(pwd)/../build/rustc-clif"); ++ config.initial_cargo = PathBuf::from("$(rustup which cargo)"); ++ + // NOTE: it's important this comes *after* we set \`initial_rustc\` just above. + if config.dry_run { + let dir = config.out.join("tmp-dry-run"); diff --git a/src/tools/compiletest/src/runtest.rs b/src/tools/compiletest/src/runtest.rs index 8431aa7b818..a3ff7e68ce5 100644 --- a/src/tools/compiletest/src/runtest.rs From 887ca1fd2a5c027e0369435c5087a4ad269658d2 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Sun, 25 Sep 2022 14:06:07 +0000 Subject: [PATCH 63/98] Update rustc test suite failure list --- scripts/test_rustc_tests.sh | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/scripts/test_rustc_tests.sh b/scripts/test_rustc_tests.sh index ace0cd76d81a5..293dff1338644 100755 --- a/scripts/test_rustc_tests.sh +++ b/scripts/test_rustc_tests.sh @@ -30,9 +30,6 @@ rm src/test/incremental/issue-80691-bad-eval-cache.rs # -Cpanic=abort causes abo # requires compiling with -Cpanic=unwind 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/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 -r src/test/ui/macros/rfc-2011-nicer-assert-messages/ # vendor intrinsics @@ -67,6 +64,7 @@ rm src/test/ui/target-feature/missing-plusminus.rs # error not implemented rm src/test/ui/fn/dyn-fn-alignment.rs # wants a 256 byte alignment rm -r src/test/run-make/emit-named-files # requires full --emit support rm src/test/ui/abi/stack-probes.rs # stack probes not yet implemented +rm src/test/ui/simd/intrinsic/ptr-cast.rs # simd_expose_addr intrinsic unimplemented # optimization tests # ================== From 7dccb51fe367a21af01ce9095d4e06082dfba56d Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Mon, 26 Sep 2022 13:56:18 +0200 Subject: [PATCH 64/98] Abi-checker got renamed to abi-cafe --- .gitignore | 1 + build_system/{abi_checker.rs => abi_cafe.rs} | 18 +++++++++--------- build_system/mod.rs | 4 ++-- build_system/prepare.rs | 6 +++--- clean_all.sh | 2 +- config.txt | 2 +- ... 0001-abi-cafe-Disable-failing-tests.patch} | 2 +- 7 files changed, 18 insertions(+), 17 deletions(-) rename build_system/{abi_checker.rs => abi_cafe.rs} (67%) rename patches/{0001-abi-checker-Disable-failing-tests.patch => 0001-abi-cafe-Disable-failing-tests.patch} (96%) diff --git a/.gitignore b/.gitignore index 6fd3e4443de5c..9a4c54f08ca8c 100644 --- a/.gitignore +++ b/.gitignore @@ -19,4 +19,5 @@ perf.data.old /regex /simple-raytracer /portable-simd +/abi-cafe /abi-checker diff --git a/build_system/abi_checker.rs b/build_system/abi_cafe.rs similarity index 67% rename from build_system/abi_checker.rs rename to build_system/abi_cafe.rs index 177b44d3141f1..c2944ce62623a 100644 --- a/build_system/abi_checker.rs +++ b/build_system/abi_cafe.rs @@ -14,17 +14,17 @@ pub(crate) fn run( host_triple: &str, target_triple: &str, ) { - if !config::get_bool("testsuite.abi-checker") { - eprintln!("[SKIP] abi-checker"); + if !config::get_bool("testsuite.abi-cafe") { + eprintln!("[SKIP] abi-cafe"); return; } if host_triple != target_triple { - eprintln!("[SKIP] abi-checker (cross-compilation not supported)"); + eprintln!("[SKIP] abi-cafe (cross-compilation not supported)"); return; } - eprintln!("Building sysroot for abi-checker"); + eprintln!("Building sysroot for abi-cafe"); build_sysroot::build_sysroot( channel, sysroot_kind, @@ -34,14 +34,14 @@ pub(crate) fn run( target_triple, ); - eprintln!("Running abi-checker"); - let mut abi_checker_path = env::current_dir().unwrap(); - abi_checker_path.push("abi-checker"); - env::set_current_dir(&abi_checker_path.clone()).unwrap(); + eprintln!("Running abi-cafe"); + let mut abi_cafe_path = env::current_dir().unwrap(); + abi_cafe_path.push("abi-cafe"); + env::set_current_dir(&abi_cafe_path.clone()).unwrap(); let pairs = ["rustc_calls_cgclif", "cgclif_calls_rustc", "cgclif_calls_cc", "cc_calls_cgclif"]; - let mut cmd = cargo_command("cargo", "run", Some(target_triple), &abi_checker_path); + let mut cmd = cargo_command("cargo", "run", Some(target_triple), &abi_cafe_path); cmd.arg("--"); cmd.arg("--pairs"); cmd.args(pairs); diff --git a/build_system/mod.rs b/build_system/mod.rs index c665d1ef71c27..03c8f58c724ad 100644 --- a/build_system/mod.rs +++ b/build_system/mod.rs @@ -4,7 +4,7 @@ use std::process; use self::utils::is_ci; -mod abi_checker; +mod abi_cafe; mod build_backend; mod build_sysroot; mod config; @@ -143,7 +143,7 @@ pub fn main() { &target_triple, ); - abi_checker::run( + abi_cafe::run( channel, sysroot_kind, &target_dir, diff --git a/build_system/prepare.rs b/build_system/prepare.rs index 83a76d3591d68..3ad9f87e3186e 100644 --- a/build_system/prepare.rs +++ b/build_system/prepare.rs @@ -14,12 +14,12 @@ pub(crate) fn prepare() { Command::new("cargo").arg("install").arg("hyperfine").spawn().unwrap().wait().unwrap(); clone_repo_shallow_github( - "abi-checker", + "abi-cafe", "Gankra", - "abi-checker", + "abi-cafe", "4c6dc8c9c687e2b3a760ff2176ce236872b37212", ); - apply_patches("abi-checker", Path::new("abi-checker")); + apply_patches("abi-cafe", Path::new("abi-cafe")); clone_repo_shallow_github( "rand", diff --git a/clean_all.sh b/clean_all.sh index 62e52bd195800..0fd9b9455a3f1 100755 --- a/clean_all.sh +++ b/clean_all.sh @@ -3,4 +3,4 @@ set -e rm -rf build_sysroot/{sysroot_src/,target/,compiler-builtins/,rustc_version} rm -rf target/ build/ perf.data{,.old} y.bin -rm -rf rand/ regex/ simple-raytracer/ portable-simd/ abi-checker/ +rm -rf rand/ regex/ simple-raytracer/ portable-simd/ abi-checker/ abi-cafe/ diff --git a/config.txt b/config.txt index 2264d301d5920..0d539191b12f9 100644 --- a/config.txt +++ b/config.txt @@ -49,4 +49,4 @@ test.regex-shootout-regex-dna test.regex test.portable-simd -testsuite.abi-checker +testsuite.abi-cafe diff --git a/patches/0001-abi-checker-Disable-failing-tests.patch b/patches/0001-abi-cafe-Disable-failing-tests.patch similarity index 96% rename from patches/0001-abi-checker-Disable-failing-tests.patch rename to patches/0001-abi-cafe-Disable-failing-tests.patch index 526366a759876..511d2f536fda0 100644 --- a/patches/0001-abi-checker-Disable-failing-tests.patch +++ b/patches/0001-abi-cafe-Disable-failing-tests.patch @@ -1,7 +1,7 @@ From 1a315ba225577dbbd1f449d9609f16f984f68708 Mon Sep 17 00:00:00 2001 From: Afonso Bordado Date: Fri, 12 Aug 2022 22:51:58 +0000 -Subject: [PATCH] Disable abi-checker tests +Subject: [PATCH] Disable abi-cafe tests --- src/report.rs | 14 ++++++++++++++ From 72992c483c02974897aab5be3144befd896d5472 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Sun, 25 Sep 2022 15:49:44 +0000 Subject: [PATCH 65/98] Update to Cranelift 0.88.0 --- Cargo.lock | 58 +++++++++++++++++++++++++++++++++-------------------- Cargo.toml | 12 +++++------ src/base.rs | 4 +++- src/lib.rs | 4 ++-- 4 files changed, 47 insertions(+), 31 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index b4c607d482e53..c0f1dfd3e9d93 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -24,6 +24,12 @@ name = "ar" version = "0.8.0" source = "git+https://github.com/bjorn3/rust-ar.git?branch=do_not_remove_cg_clif_ranlib#de9ab0e56bf3a208381d342aa5b60f9ff2891648" +[[package]] +name = "arrayvec" +version = "0.7.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8da52d66c7071e2e3fa2a1e5c6d088fec47b593032b254f5e980de8ea54454d6" + [[package]] name = "autocfg" version = "1.1.0" @@ -36,6 +42,12 @@ version = "1.3.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "bef38d45163c2f1dde094a7dfd33ccf595c92905c8f8f4fdc18d06fb1037718a" +[[package]] +name = "bumpalo" +version = "3.11.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c1ad822118d20d2c234f427000d5acc36eabe1e29a348c89b63dd60b13f28e5d" + [[package]] name = "byteorder" version = "1.4.3" @@ -50,19 +62,21 @@ checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd" [[package]] name = "cranelift-bforest" -version = "0.87.0" +version = "0.88.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "93945adbccc8d731503d3038814a51e8317497c9e205411820348132fa01a358" +checksum = "b27bbd3e6c422cf6282b047bcdd51ecd9ca9f3497a3be0132ffa08e509b824b0" dependencies = [ "cranelift-entity", ] [[package]] name = "cranelift-codegen" -version = "0.87.0" +version = "0.88.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2b482acc9d0d0d1ad3288a90a8150ee648be3dce8dc8c8669ff026f72debdc31" +checksum = "872f5d4557a411b087bd731df6347c142ae1004e6467a144a7e33662e5715a01" dependencies = [ + "arrayvec", + "bumpalo", "cranelift-bforest", "cranelift-codegen-meta", "cranelift-codegen-shared", @@ -77,30 +91,30 @@ dependencies = [ [[package]] name = "cranelift-codegen-meta" -version = "0.87.0" +version = "0.88.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f9ec188d71e663192ef9048f204e410a7283b609942efc9fcc77da6d496edbb8" +checksum = "21b49fdebb29c62c1fc4da1eeebd609e9d530ecde24a9876def546275f73a244" dependencies = [ "cranelift-codegen-shared", ] [[package]] name = "cranelift-codegen-shared" -version = "0.87.0" +version = "0.88.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3ad794b1b1c2c7bd9f7b76cfe0f084eaf7753e55d56191c3f7d89e8fa4978b99" +checksum = "5fc0c091e2db055d4d7f6b7cec2d2ead286bcfaea3357c6a52c2a2613a8cb5ac" [[package]] name = "cranelift-entity" -version = "0.87.0" +version = "0.88.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "342da0d5056f4119d3c311c4aab2460ceb6ee6e127bb395b76dd2279a09ea7a5" +checksum = "354a9597be87996c9b278655e68b8447f65dd907256855ad773864edee8d985c" [[package]] name = "cranelift-frontend" -version = "0.87.0" +version = "0.88.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "dfff792f775b07d4d9cfe9f1c767ce755c6cbadda1bbd6db18a1c75ff9f7376a" +checksum = "0cd8dd3fb8b82c772f4172e87ae1677b971676fffa7c4e3398e3047e650a266b" dependencies = [ "cranelift-codegen", "log", @@ -110,15 +124,15 @@ dependencies = [ [[package]] name = "cranelift-isle" -version = "0.87.0" +version = "0.88.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8d51089478849f2ac8ef60a8a2d5346c8d4abfec0e45ac5b24530ef9f9499e1e" +checksum = "b82527802b1f7d8da288adc28f1dc97ea52943f5871c041213f7b5035ac698a7" [[package]] name = "cranelift-jit" -version = "0.87.0" +version = "0.88.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "095936e41720f86004b4c57ce88e6a13af28646bb3a6fb4afbebd5ae90c50029" +checksum = "54a6d007394ef18312fc6616fb99618844f13dff01edbbbc4a451c2b7cd5c8f4" dependencies = [ "anyhow", "cranelift-codegen", @@ -134,9 +148,9 @@ dependencies = [ [[package]] name = "cranelift-module" -version = "0.87.0" +version = "0.88.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "704a1aea4723d97eafe0fb7af110f6f6868b1ac95f5380bbc9adb2a3b8cf97e8" +checksum = "a106dd90ab4071f9e16b9fd3c2057d61c37f35af7c8f079c9ec59d6ede5b2cef" dependencies = [ "anyhow", "cranelift-codegen", @@ -144,9 +158,9 @@ dependencies = [ [[package]] name = "cranelift-native" -version = "0.87.0" +version = "0.88.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "885debe62f2078638d6585f54c9f05f5c2008f22ce5a2a9100ada785fc065dbd" +checksum = "c30ba8b910f1be023af0c39109cb28a8809734942a6b3eecbf2de8993052ea5e" dependencies = [ "cranelift-codegen", "libc", @@ -155,9 +169,9 @@ dependencies = [ [[package]] name = "cranelift-object" -version = "0.87.0" +version = "0.88.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "aac1310cf1081ae8eca916c92cd163b977c77cab6e831fa812273c26ff921816" +checksum = "506ac7a483c765a83795166ffe689f656afc0f4eb57fafa3f9e60b64bfa2caa6" dependencies = [ "anyhow", "cranelift-codegen", diff --git a/Cargo.toml b/Cargo.toml index 7a9e8f5d8e0c6..46fed4380e527 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -8,12 +8,12 @@ crate-type = ["dylib"] [dependencies] # These have to be in sync with each other -cranelift-codegen = { version = "0.87.0", features = ["unwind", "all-arch"] } -cranelift-frontend = "0.87.0" -cranelift-module = "0.87.0" -cranelift-native = "0.87.0" -cranelift-jit = { version = "0.87.0", optional = true } -cranelift-object = "0.87.0" +cranelift-codegen = { version = "0.88.0", features = ["unwind", "all-arch"] } +cranelift-frontend = "0.88.0" +cranelift-module = "0.88.0" +cranelift-native = "0.88.0" +cranelift-jit = { version = "0.88.0", optional = true } +cranelift-object = "0.88.0" target-lexicon = "0.12.0" gimli = { version = "0.26.0", default-features = false, features = ["write"]} object = { version = "0.29.0", default-features = false, features = ["std", "read_core", "write", "archive", "coff", "elf", "macho", "pe"] } diff --git a/src/base.rs b/src/base.rs index 1aeb9ff25703d..491525993fd1e 100644 --- a/src/base.rs +++ b/src/base.rs @@ -6,6 +6,8 @@ use rustc_middle::ty::adjustment::PointerCast; use rustc_middle::ty::layout::FnAbiOf; use rustc_middle::ty::print::with_no_trimmed_paths; +use cranelift_codegen::ir::UserFuncName; + use crate::constant::ConstantCx; use crate::debuginfo::FunctionDebugContext; use crate::prelude::*; @@ -64,7 +66,7 @@ pub(crate) fn codegen_fn<'tcx>( let mut func_ctx = FunctionBuilderContext::new(); let mut func = cached_func; func.clear(); - func.name = ExternalName::user(0, func_id.as_u32()); + func.name = UserFuncName::user(0, func_id.as_u32()); func.signature = sig; func.collect_debug_info(); diff --git a/src/lib.rs b/src/lib.rs index 913414e761821..74bd473653532 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -96,8 +96,8 @@ mod prelude { pub(crate) use cranelift_codegen::ir::function::Function; pub(crate) use cranelift_codegen::ir::types; pub(crate) use cranelift_codegen::ir::{ - AbiParam, Block, ExternalName, FuncRef, Inst, InstBuilder, MemFlags, Signature, SourceLoc, - StackSlot, StackSlotData, StackSlotKind, TrapCode, Type, Value, + AbiParam, Block, FuncRef, Inst, InstBuilder, MemFlags, Signature, SourceLoc, StackSlot, + StackSlotData, StackSlotKind, TrapCode, Type, Value, }; pub(crate) use cranelift_codegen::isa::{self, CallConv}; pub(crate) use cranelift_codegen::Context; From 0035f09c5a25d230b594374239a0c61301137946 Mon Sep 17 00:00:00 2001 From: Afonso Bordado Date: Sun, 21 Aug 2022 17:42:50 +0100 Subject: [PATCH 66/98] Avoid masking shift amounts Cranelift 0.87 now follows its own documentation regarding shift amounts, and implicitly masks them if the arch requires it. [0] [0]: https://github.com/bytecodealliance/wasmtime/commit/05089321740a07757dff0a285176b2651a49aae2 --- src/num.rs | 25 ++++++------------------- 1 file changed, 6 insertions(+), 19 deletions(-) diff --git a/src/num.rs b/src/num.rs index 4fadbf24d8a83..ecbab408ded97 100644 --- a/src/num.rs +++ b/src/num.rs @@ -150,18 +150,12 @@ pub(crate) fn codegen_int_binop<'tcx>( BinOp::BitXor => b.bxor(lhs, rhs), BinOp::BitAnd => b.band(lhs, rhs), BinOp::BitOr => b.bor(lhs, rhs), - BinOp::Shl => { - let lhs_ty = fx.bcx.func.dfg.value_type(lhs); - let actual_shift = fx.bcx.ins().band_imm(rhs, i64::from(lhs_ty.bits() - 1)); - fx.bcx.ins().ishl(lhs, actual_shift) - } + BinOp::Shl => b.ishl(lhs, rhs), BinOp::Shr => { - let lhs_ty = fx.bcx.func.dfg.value_type(lhs); - let actual_shift = fx.bcx.ins().band_imm(rhs, i64::from(lhs_ty.bits() - 1)); if signed { - fx.bcx.ins().sshr(lhs, actual_shift) + b.sshr(lhs, rhs) } else { - fx.bcx.ins().ushr(lhs, actual_shift) + b.ushr(lhs, rhs) } } // Compare binops handles by `codegen_binop`. @@ -279,22 +273,15 @@ pub(crate) fn codegen_checked_int_binop<'tcx>( } } BinOp::Shl => { - let lhs_ty = fx.bcx.func.dfg.value_type(lhs); - let masked_shift = fx.bcx.ins().band_imm(rhs, i64::from(lhs_ty.bits() - 1)); - let val = fx.bcx.ins().ishl(lhs, masked_shift); + let val = fx.bcx.ins().ishl(lhs, rhs); let ty = fx.bcx.func.dfg.value_type(val); let max_shift = i64::from(ty.bits()) - 1; let has_overflow = fx.bcx.ins().icmp_imm(IntCC::UnsignedGreaterThan, rhs, max_shift); (val, has_overflow) } BinOp::Shr => { - let lhs_ty = fx.bcx.func.dfg.value_type(lhs); - let masked_shift = fx.bcx.ins().band_imm(rhs, i64::from(lhs_ty.bits() - 1)); - let val = if !signed { - fx.bcx.ins().ushr(lhs, masked_shift) - } else { - fx.bcx.ins().sshr(lhs, masked_shift) - }; + let val = + if !signed { fx.bcx.ins().ushr(lhs, rhs) } else { fx.bcx.ins().sshr(lhs, rhs) }; let ty = fx.bcx.func.dfg.value_type(val); let max_shift = i64::from(ty.bits()) - 1; let has_overflow = fx.bcx.ins().icmp_imm(IntCC::UnsignedGreaterThan, rhs, max_shift); From f90bc3009ab7284772a7abc961fa746aaec5ffcd Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Sun, 25 Sep 2022 15:54:15 +0000 Subject: [PATCH 67/98] Enable stack probing on x86_64 Cranelift now supports inline stack probes on x86_64 --- src/lib.rs | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/src/lib.rs b/src/lib.rs index 74bd473653532..629d79d501240 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -251,7 +251,6 @@ fn build_isa(sess: &Session, backend_config: &BackendConfig) -> Box Box Date: Sun, 25 Sep 2022 16:01:43 +0000 Subject: [PATCH 68/98] Remove stabilized feature gate --- example/issue-91827-extern-types.rs | 1 - 1 file changed, 1 deletion(-) diff --git a/example/issue-91827-extern-types.rs b/example/issue-91827-extern-types.rs index 2ecc8b8238b18..039100696331b 100644 --- a/example/issue-91827-extern-types.rs +++ b/example/issue-91827-extern-types.rs @@ -5,7 +5,6 @@ // Test that we can handle unsized types with an extern type tail part. // Regression test for issue #91827. -#![feature(const_ptr_offset_from)] #![feature(extern_types)] use std::ptr::addr_of; From 88522158b2a7462418b89ddd7424502ee60535b4 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Mon, 26 Sep 2022 16:21:57 +0000 Subject: [PATCH 69/98] Re-enable structs abi-cafe test on AArch64 --- patches/0001-abi-cafe-Disable-failing-tests.patch | 9 +-------- 1 file changed, 1 insertion(+), 8 deletions(-) diff --git a/patches/0001-abi-cafe-Disable-failing-tests.patch b/patches/0001-abi-cafe-Disable-failing-tests.patch index 511d2f536fda0..a6bcade8eb857 100644 --- a/patches/0001-abi-cafe-Disable-failing-tests.patch +++ b/patches/0001-abi-cafe-Disable-failing-tests.patch @@ -11,7 +11,7 @@ diff --git a/src/report.rs b/src/report.rs index 7346f5e..8347762 100644 --- a/src/report.rs +++ b/src/report.rs -@@ -45,6 +45,20 @@ pub fn get_test_rules(test: &TestKey, caller: &dyn AbiImpl, callee: &dyn AbiImpl +@@ -45,6 +45,13 @@ pub fn get_test_rules(test: &TestKey, caller: &dyn AbiImpl, callee: &dyn AbiImpl // // THIS AREA RESERVED FOR VENDORS TO APPLY PATCHES @@ -21,13 +21,6 @@ index 7346f5e..8347762 100644 + result.run = Link; + result.check = Pass(Link); + } -+ -+ // structs is broken in the current release of cranelift for aarch64. -+ // It has been fixed for cranelift 0.88: https://github.com/bytecodealliance/wasmtime/pull/4634 -+ if cfg!(target_arch = "aarch64") && test.test_name == "structs" { -+ result.run = Link; -+ result.check = Pass(Link); -+ } + // END OF VENDOR RESERVED AREA // From ba56e8f313895eefc3e0f7de38c9cde3145b0c04 Mon Sep 17 00:00:00 2001 From: Afonso Bordado Date: Mon, 26 Sep 2022 09:45:00 +0100 Subject: [PATCH 70/98] Remove MSVC Check --- build_system/mod.rs | 11 +---------- 1 file changed, 1 insertion(+), 10 deletions(-) diff --git a/build_system/mod.rs b/build_system/mod.rs index 03c8f58c724ad..b25270d832ceb 100644 --- a/build_system/mod.rs +++ b/build_system/mod.rs @@ -122,16 +122,7 @@ pub fn main() { host_triple.clone() }; - if target_triple.ends_with("-msvc") { - eprintln!("The MSVC toolchain is not yet supported by rustc_codegen_cranelift."); - eprintln!("Switch to the MinGW toolchain for Windows support."); - eprintln!("Hint: You can use `rustup set default-host x86_64-pc-windows-gnu` to"); - eprintln!("set the global default target to MinGW"); - process::exit(1); - } - - let cg_clif_dylib = - build_backend::build_backend(channel, &host_triple, use_unstable_features); + let cg_clif_dylib = build_backend::build_backend(channel, &host_triple, use_unstable_features); match command { Command::Test => { tests::run_tests( From 481484c1410c360acd309ed3ba7fe214a6f61454 Mon Sep 17 00:00:00 2001 From: Afonso Bordado Date: Tue, 2 Aug 2022 08:31:50 +0100 Subject: [PATCH 71/98] Windows MinGW & MSVC Matrix CI --- .github/workflows/main.yml | 42 +++++++++++++++++++++++++++++--------- 1 file changed, 32 insertions(+), 10 deletions(-) diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index e8897e9ae8145..029e83f6aa4e4 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -122,10 +122,21 @@ jobs: name: cg_clif-${{ runner.os }}-cross-x86_64-mingw path: cg_clif.tar.xz - build_windows: - runs-on: windows-latest + windows: + runs-on: ${{ matrix.os }} timeout-minutes: 60 + strategy: + fail-fast: false + matrix: + include: + # Native Windows build with MSVC + - os: windows-latest + # cross-compile from Windows to Windows MinGW + - os: windows-latest + env: + TARGET_TRIPLE: x86_64-pc-windows-gnu + steps: - uses: actions/checkout@v3 @@ -149,29 +160,40 @@ jobs: # path: target # key: ${{ runner.os }}-cargo-build-target-${{ hashFiles('rust-toolchain', '**/Cargo.lock') }} + - name: Set MinGW as the default toolchain + if: matrix.env.TARGET_TRIPLE == 'x86_64-pc-windows-gnu' + run: rustup set default-host x86_64-pc-windows-gnu + - name: Prepare dependencies run: | git config --global user.email "user@example.com" git config --global user.name "User" git config --global core.autocrlf false - rustup set default-host x86_64-pc-windows-gnu rustc y.rs -o y.exe -g ./y.exe prepare + - name: Build without unstable features + env: + TARGET_TRIPLE: ${{ matrix.env.TARGET_TRIPLE }} + # This is the config rust-lang/rust uses for builds + run: ./y.rs build --no-unstable-features + - name: Build - #name: Test + run: ./y.rs build --sysroot none + + - name: Test run: | # Enable backtraces for easier debugging - #$Env:RUST_BACKTRACE=1 + $Env:RUST_BACKTRACE=1 # Reduce amount of benchmark runs as they are slow - #$Env:COMPILE_RUNS=2 - #$Env:RUN_RUNS=2 + $Env:COMPILE_RUNS=2 + $Env:RUN_RUNS=2 # Enable extra checks - #$Env:CG_CLIF_ENABLE_VERIFIER=1 + $Env:CG_CLIF_ENABLE_VERIFIER=1 - ./y.exe build + ./y.exe test - name: Package prebuilt cg_clif # don't use compression as xzip isn't supported by tar on windows and bzip2 hangs @@ -180,5 +202,5 @@ jobs: - name: Upload prebuilt cg_clif uses: actions/upload-artifact@v2 with: - name: cg_clif-${{ runner.os }} + name: cg_clif-${{ runner.os }}-${{ matrix.env.TARGET_TRIPLE }} path: cg_clif.tar From 1878ca61bcce43276fa723921b7a579482293ff0 Mon Sep 17 00:00:00 2001 From: Afonso Bordado Date: Mon, 26 Sep 2022 13:38:53 +0100 Subject: [PATCH 72/98] Disable JIT Tests for windows --- build_system/tests.rs | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/build_system/tests.rs b/build_system/tests.rs index 74042bc92183e..d4f393fc7ff92 100644 --- a/build_system/tests.rs +++ b/build_system/tests.rs @@ -450,7 +450,8 @@ impl TestRunner { out_dir.push("out"); let is_native = host_triple == target_triple; - let jit_supported = target_triple.contains("x86_64") && is_native; + let jit_supported = + target_triple.contains("x86_64") && is_native && !host_triple.contains("windows"); let mut rust_flags = env::var("RUSTFLAGS").ok().unwrap_or("".to_string()); let mut run_wrapper = Vec::new(); From 01d3e1a3ade98bbf636cf38289ed50c2d3d66ef0 Mon Sep 17 00:00:00 2001 From: Afonso Bordado Date: Mon, 26 Sep 2022 13:44:55 +0100 Subject: [PATCH 73/98] Disable failing windows CI tests --- .github/workflows/main.yml | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index 029e83f6aa4e4..91240cca8b489 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -192,6 +192,18 @@ jobs: # Enable extra checks $Env:CG_CLIF_ENABLE_VERIFIER=1 + + # WIP Disable some tests + + # This fails due to some weird argument handling by hyperfine, not an actual regression + # more of a build system issue + (Get-Content config.txt) -replace '(bench.simple-raytracer)', '# $1' | Out-File config.txt + + # This fails with a different output than expected + (Get-Content config.txt) -replace '(test.regex-shootout-regex-dna)', '# $1' | Out-File config.txt + + # This only fails on x86_64-pc-windows-gnu when run from a windows host + (Get-Content config.txt) -replace '(test.rust-random/rand)', '# $1' | Out-File config.txt ./y.exe test From 8072dec7a5f75861fc152310eb1bd6f171103835 Mon Sep 17 00:00:00 2001 From: Afonso Bordado Date: Mon, 26 Sep 2022 15:00:53 +0100 Subject: [PATCH 74/98] Drop abi cafe patch --- .../0001-abi-cafe-Disable-failing-tests.patch | 29 ------------------- 1 file changed, 29 deletions(-) delete mode 100644 patches/0001-abi-cafe-Disable-failing-tests.patch diff --git a/patches/0001-abi-cafe-Disable-failing-tests.patch b/patches/0001-abi-cafe-Disable-failing-tests.patch deleted file mode 100644 index a6bcade8eb857..0000000000000 --- a/patches/0001-abi-cafe-Disable-failing-tests.patch +++ /dev/null @@ -1,29 +0,0 @@ -From 1a315ba225577dbbd1f449d9609f16f984f68708 Mon Sep 17 00:00:00 2001 -From: Afonso Bordado -Date: Fri, 12 Aug 2022 22:51:58 +0000 -Subject: [PATCH] Disable abi-cafe tests - ---- - src/report.rs | 14 ++++++++++++++ - 1 file changed, 14 insertions(+) - -diff --git a/src/report.rs b/src/report.rs -index 7346f5e..8347762 100644 ---- a/src/report.rs -+++ b/src/report.rs -@@ -45,6 +45,13 @@ pub fn get_test_rules(test: &TestKey, caller: &dyn AbiImpl, callee: &dyn AbiImpl - // - // THIS AREA RESERVED FOR VENDORS TO APPLY PATCHES - -+ // Currently MSVC has some broken ABI issues. Furthermore, they cause -+ // a STATUS_ACCESS_VIOLATION, so we can't even run them. Ensure that they compile and link. -+ if cfg!(windows) && (test.test_name == "bool" || test.test_name == "ui128") { -+ result.run = Link; -+ result.check = Pass(Link); -+ } -+ - // END OF VENDOR RESERVED AREA - // - // --- -2.34.1 From 738dd2b70b6ab8366ae4620e5c0597c209e0235c Mon Sep 17 00:00:00 2001 From: Afonso Bordado Date: Tue, 27 Sep 2022 07:26:12 +0100 Subject: [PATCH 75/98] Windows CI Cache --- .github/workflows/main.yml | 38 +++++++++++++++++++------------------- 1 file changed, 19 insertions(+), 19 deletions(-) diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index 91240cca8b489..2d63881b7ab17 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -140,25 +140,25 @@ jobs: steps: - uses: actions/checkout@v3 - #- name: Cache cargo installed crates - # uses: actions/cache@v2 - # with: - # path: ~/.cargo/bin - # key: ${{ runner.os }}-cargo-installed-crates - - #- name: Cache cargo registry and index - # uses: actions/cache@v2 - # with: - # path: | - # ~/.cargo/registry - # ~/.cargo/git - # key: ${{ runner.os }}-cargo-registry-and-index-${{ hashFiles('**/Cargo.lock') }} - - #- name: Cache cargo target dir - # uses: actions/cache@v2 - # with: - # path: target - # key: ${{ runner.os }}-cargo-build-target-${{ hashFiles('rust-toolchain', '**/Cargo.lock') }} + - name: Cache cargo installed crates + uses: actions/cache@v2 + with: + path: ~/.cargo/bin + key: ${{ runner.os }}-${{ matrix.env.TARGET_TRIPLE }}-cargo-installed-crates + + - name: Cache cargo registry and index + uses: actions/cache@v2 + with: + path: | + ~/.cargo/registry + ~/.cargo/git + key: ${{ runner.os }}-${{ matrix.env.TARGET_TRIPLE }}-cargo-registry-and-index-${{ hashFiles('**/Cargo.lock') }} + + - name: Cache cargo target dir + uses: actions/cache@v2 + with: + path: target + key: ${{ runner.os }}-${{ matrix.env.TARGET_TRIPLE }}-cargo-build-target-${{ hashFiles('rust-toolchain', '**/Cargo.lock') }} - name: Set MinGW as the default toolchain if: matrix.env.TARGET_TRIPLE == 'x86_64-pc-windows-gnu' From cd8becbc03916b2c1db31ce1063c40f7d0d2b38e Mon Sep 17 00:00:00 2001 From: Afonso Bordado Date: Tue, 27 Sep 2022 07:38:54 +0100 Subject: [PATCH 76/98] Disable some ABI tests on MinGW --- ...e-some-test-on-x86_64-pc-windows-gnu.patch | 29 +++++++++++++++++++ 1 file changed, 29 insertions(+) create mode 100644 patches/0001-abi-cafe-Disable-some-test-on-x86_64-pc-windows-gnu.patch diff --git a/patches/0001-abi-cafe-Disable-some-test-on-x86_64-pc-windows-gnu.patch b/patches/0001-abi-cafe-Disable-some-test-on-x86_64-pc-windows-gnu.patch new file mode 100644 index 0000000000000..0e5e7cdfcdf1a --- /dev/null +++ b/patches/0001-abi-cafe-Disable-some-test-on-x86_64-pc-windows-gnu.patch @@ -0,0 +1,29 @@ +From 2b15fee2bb5fd14e34c7e17e44d99cb34f4c555d Mon Sep 17 00:00:00 2001 +From: Afonso Bordado +Date: Tue, 27 Sep 2022 07:55:17 +0100 +Subject: [PATCH] Disable some test on x86_64-pc-windows-gnu + +--- + src/report.rs | 6 ++++++ + 1 file changed, 6 insertions(+) + +diff --git a/src/report.rs b/src/report.rs +index eeec614..f582867 100644 +--- a/src/report.rs ++++ b/src/report.rs +@@ -48,6 +48,12 @@ pub fn get_test_rules(test: &TestKey, caller: &dyn AbiImpl, callee: &dyn AbiImpl + // + // THIS AREA RESERVED FOR VENDORS TO APPLY PATCHES + ++ // x86_64-pc-windows-gnu has some broken i128 tests that aren't disabled by default ++ if cfg!(all(target_os = "windows", target_env = "gnu")) && test.test_name == "ui128" { ++ result.run = Link; ++ result.check = Pass(Link); ++ } ++ + // END OF VENDOR RESERVED AREA + // + // +-- +2.30.1.windows.1 + From fb71d8abea5d2e512dd0bd3d9b3694d1421172cb Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Tue, 27 Sep 2022 08:31:22 +0000 Subject: [PATCH 77/98] Update to Cranelift 0.88.1 This fixes a regression of Atomic*::compare_exchange on AArch64 --- Cargo.lock | 44 ++++++++++++++++++++++---------------------- Cargo.toml | 12 ++++++------ 2 files changed, 28 insertions(+), 28 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index c0f1dfd3e9d93..3fa9d56cd01a3 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -62,18 +62,18 @@ checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd" [[package]] name = "cranelift-bforest" -version = "0.88.0" +version = "0.88.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b27bbd3e6c422cf6282b047bcdd51ecd9ca9f3497a3be0132ffa08e509b824b0" +checksum = "44409ccf2d0f663920cab563d2b79fcd6b2e9a2bcc6e929fef76c8f82ad6c17a" dependencies = [ "cranelift-entity", ] [[package]] name = "cranelift-codegen" -version = "0.88.0" +version = "0.88.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "872f5d4557a411b087bd731df6347c142ae1004e6467a144a7e33662e5715a01" +checksum = "98de2018ad96eb97f621f7d6b900a0cc661aec8d02ea4a50e56ecb48e5a2fcaf" dependencies = [ "arrayvec", "bumpalo", @@ -91,30 +91,30 @@ dependencies = [ [[package]] name = "cranelift-codegen-meta" -version = "0.88.0" +version = "0.88.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "21b49fdebb29c62c1fc4da1eeebd609e9d530ecde24a9876def546275f73a244" +checksum = "5287ce36e6c4758fbaf298bd1a8697ad97a4f2375a3d1b61142ea538db4877e5" dependencies = [ "cranelift-codegen-shared", ] [[package]] name = "cranelift-codegen-shared" -version = "0.88.0" +version = "0.88.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5fc0c091e2db055d4d7f6b7cec2d2ead286bcfaea3357c6a52c2a2613a8cb5ac" +checksum = "2855c24219e2f08827f3f4ffb2da92e134ae8d8ecc185b11ec8f9878cf5f588e" [[package]] name = "cranelift-entity" -version = "0.88.0" +version = "0.88.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "354a9597be87996c9b278655e68b8447f65dd907256855ad773864edee8d985c" +checksum = "0b65673279d75d34bf11af9660ae2dbd1c22e6d28f163f5c72f4e1dc56d56103" [[package]] name = "cranelift-frontend" -version = "0.88.0" +version = "0.88.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0cd8dd3fb8b82c772f4172e87ae1677b971676fffa7c4e3398e3047e650a266b" +checksum = "3ed2b3d7a4751163f6c4a349205ab1b7d9c00eecf19dcea48592ef1f7688eefc" dependencies = [ "cranelift-codegen", "log", @@ -124,15 +124,15 @@ dependencies = [ [[package]] name = "cranelift-isle" -version = "0.88.0" +version = "0.88.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b82527802b1f7d8da288adc28f1dc97ea52943f5871c041213f7b5035ac698a7" +checksum = "3be64cecea9d90105fc6a2ba2d003e98c867c1d6c4c86cc878f97ad9fb916293" [[package]] name = "cranelift-jit" -version = "0.88.0" +version = "0.88.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "54a6d007394ef18312fc6616fb99618844f13dff01edbbbc4a451c2b7cd5c8f4" +checksum = "f98ed42a70a0c9c388e34ec9477f57fc7300f541b1e5136a0e2ea02b1fac6015" dependencies = [ "anyhow", "cranelift-codegen", @@ -148,9 +148,9 @@ dependencies = [ [[package]] name = "cranelift-module" -version = "0.88.0" +version = "0.88.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a106dd90ab4071f9e16b9fd3c2057d61c37f35af7c8f079c9ec59d6ede5b2cef" +checksum = "d658ac7f156708bfccb647216cc8b9387469f50d352ba4ad80150541e4ae2d49" dependencies = [ "anyhow", "cranelift-codegen", @@ -158,9 +158,9 @@ dependencies = [ [[package]] name = "cranelift-native" -version = "0.88.0" +version = "0.88.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c30ba8b910f1be023af0c39109cb28a8809734942a6b3eecbf2de8993052ea5e" +checksum = "c4a03a6ac1b063e416ca4b93f6247978c991475e8271465340caa6f92f3c16a4" dependencies = [ "cranelift-codegen", "libc", @@ -169,9 +169,9 @@ dependencies = [ [[package]] name = "cranelift-object" -version = "0.88.0" +version = "0.88.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "506ac7a483c765a83795166ffe689f656afc0f4eb57fafa3f9e60b64bfa2caa6" +checksum = "eef0b4119b645b870a43a036d76c0ada3a076b1f82e8b8487659304c8b09049b" dependencies = [ "anyhow", "cranelift-codegen", diff --git a/Cargo.toml b/Cargo.toml index 46fed4380e527..09cf5b4a1edd8 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -8,12 +8,12 @@ crate-type = ["dylib"] [dependencies] # These have to be in sync with each other -cranelift-codegen = { version = "0.88.0", features = ["unwind", "all-arch"] } -cranelift-frontend = "0.88.0" -cranelift-module = "0.88.0" -cranelift-native = "0.88.0" -cranelift-jit = { version = "0.88.0", optional = true } -cranelift-object = "0.88.0" +cranelift-codegen = { version = "0.88.1", features = ["unwind", "all-arch"] } +cranelift-frontend = "0.88.1" +cranelift-module = "0.88.1" +cranelift-native = "0.88.1" +cranelift-jit = { version = "0.88.1", optional = true } +cranelift-object = "0.88.1" target-lexicon = "0.12.0" gimli = { version = "0.26.0", default-features = false, features = ["write"]} object = { version = "0.29.0", default-features = false, features = ["std", "read_core", "write", "archive", "coff", "elf", "macho", "pe"] } From e96badc97fde074e64c300c35d0acdd68cddc59b Mon Sep 17 00:00:00 2001 From: Afonso Bordado Date: Tue, 27 Sep 2022 08:15:41 +0100 Subject: [PATCH 78/98] Disable some rand tests on MinGW --- .github/workflows/main.yml | 3 -- ...001-rand-Disable-rand-tests-on-mingw.patch | 47 +++++++++++++++++++ 2 files changed, 47 insertions(+), 3 deletions(-) create mode 100644 patches/0001-rand-Disable-rand-tests-on-mingw.patch diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index 2d63881b7ab17..7f6cfd2ccc56f 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -201,9 +201,6 @@ jobs: # This fails with a different output than expected (Get-Content config.txt) -replace '(test.regex-shootout-regex-dna)', '# $1' | Out-File config.txt - - # This only fails on x86_64-pc-windows-gnu when run from a windows host - (Get-Content config.txt) -replace '(test.rust-random/rand)', '# $1' | Out-File config.txt ./y.exe test diff --git a/patches/0001-rand-Disable-rand-tests-on-mingw.patch b/patches/0001-rand-Disable-rand-tests-on-mingw.patch new file mode 100644 index 0000000000000..108f882408df1 --- /dev/null +++ b/patches/0001-rand-Disable-rand-tests-on-mingw.patch @@ -0,0 +1,47 @@ +From eea3bbaed34ab210868c324219a862a9d5f4681c Mon Sep 17 00:00:00 2001 +From: Afonso Bordado +Date: Tue, 27 Sep 2022 08:13:58 +0100 +Subject: [PATCH] Disable rand tests on mingw + +--- + rand_distr/src/pareto.rs | 2 ++ + rand_distr/tests/value_stability.rs | 4 ++++ + 2 files changed, 6 insertions(+) + +diff --git a/rand_distr/src/pareto.rs b/rand_distr/src/pareto.rs +index 217899ed9a..5f8e2c9bbb 100644 +--- a/rand_distr/src/pareto.rs ++++ b/rand_distr/src/pareto.rs +@@ -107,6 +107,8 @@ mod tests { + } + + #[test] ++ // This is broken on x86_64-pc-windows-gnu presumably due to a broken powf implementation ++ #[cfg(not(all(target_os = "windows", target_env = "gnu")))] + fn value_stability() { + fn test_samples>( + distr: D, zero: F, expected: &[F], +diff --git a/rand_distr/tests/value_stability.rs b/rand_distr/tests/value_stability.rs +index 192ba748b7..10c6ac24f6 100644 +--- a/rand_distr/tests/value_stability.rs ++++ b/rand_distr/tests/value_stability.rs +@@ -72,6 +72,8 @@ fn unit_disc_stability() { + } + + #[test] ++// This is broken on x86_64-pc-windows-gnu ++#[cfg(not(all(target_os = "windows", target_env = "gnu")))] + fn pareto_stability() { + test_samples(213, Pareto::new(1.0, 1.0).unwrap(), &[ + 1.0423688f32, 2.1235929, 4.132709, 1.4679428, +@@ -143,6 +145,8 @@ fn inverse_gaussian_stability() { + } + + #[test] ++// This is broken on x86_64-pc-windows-gnu ++#[cfg(not(all(target_os = "windows", target_env = "gnu")))] + fn gamma_stability() { + // Gamma has 3 cases: shape == 1, shape < 1, shape > 1 + test_samples(223, Gamma::new(1.0, 5.0).unwrap(), &[ +-- +2.30.1.windows.1 From a83ec3b6a451cd40f654f0606228564b9fa21a04 Mon Sep 17 00:00:00 2001 From: Afonso Bordado Date: Tue, 27 Sep 2022 12:26:23 +0100 Subject: [PATCH 79/98] Ignore rand tests --- ... 0003-rand-Disable-rand-tests-on-mingw.patch} | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) rename patches/{0001-rand-Disable-rand-tests-on-mingw.patch => 0003-rand-Disable-rand-tests-on-mingw.patch} (79%) diff --git a/patches/0001-rand-Disable-rand-tests-on-mingw.patch b/patches/0003-rand-Disable-rand-tests-on-mingw.patch similarity index 79% rename from patches/0001-rand-Disable-rand-tests-on-mingw.patch rename to patches/0003-rand-Disable-rand-tests-on-mingw.patch index 108f882408df1..d8775e2d022a0 100644 --- a/patches/0001-rand-Disable-rand-tests-on-mingw.patch +++ b/patches/0003-rand-Disable-rand-tests-on-mingw.patch @@ -1,4 +1,4 @@ -From eea3bbaed34ab210868c324219a862a9d5f4681c Mon Sep 17 00:00:00 2001 +From eec874c889b8d24e5ad50faded24288150f057b1 Mon Sep 17 00:00:00 2001 From: Afonso Bordado Date: Tue, 27 Sep 2022 08:13:58 +0100 Subject: [PATCH] Disable rand tests on mingw @@ -9,7 +9,7 @@ Subject: [PATCH] Disable rand tests on mingw 2 files changed, 6 insertions(+) diff --git a/rand_distr/src/pareto.rs b/rand_distr/src/pareto.rs -index 217899ed9a..5f8e2c9bbb 100644 +index 217899e..9cedeb7 100644 --- a/rand_distr/src/pareto.rs +++ b/rand_distr/src/pareto.rs @@ -107,6 +107,8 @@ mod tests { @@ -17,12 +17,12 @@ index 217899ed9a..5f8e2c9bbb 100644 #[test] + // This is broken on x86_64-pc-windows-gnu presumably due to a broken powf implementation -+ #[cfg(not(all(target_os = "windows", target_env = "gnu")))] ++ #[cfg_attr(all(target_os = "windows", target_env = "gnu"), ignore)] fn value_stability() { fn test_samples>( distr: D, zero: F, expected: &[F], diff --git a/rand_distr/tests/value_stability.rs b/rand_distr/tests/value_stability.rs -index 192ba748b7..10c6ac24f6 100644 +index 192ba74..0101ace 100644 --- a/rand_distr/tests/value_stability.rs +++ b/rand_distr/tests/value_stability.rs @@ -72,6 +72,8 @@ fn unit_disc_stability() { @@ -30,7 +30,7 @@ index 192ba748b7..10c6ac24f6 100644 #[test] +// This is broken on x86_64-pc-windows-gnu -+#[cfg(not(all(target_os = "windows", target_env = "gnu")))] ++#[cfg_attr(all(target_os = "windows", target_env = "gnu"), ignore)] fn pareto_stability() { test_samples(213, Pareto::new(1.0, 1.0).unwrap(), &[ 1.0423688f32, 2.1235929, 4.132709, 1.4679428, @@ -39,9 +39,9 @@ index 192ba748b7..10c6ac24f6 100644 #[test] +// This is broken on x86_64-pc-windows-gnu -+#[cfg(not(all(target_os = "windows", target_env = "gnu")))] ++#[cfg_attr(all(target_os = "windows", target_env = "gnu"), ignore)] fn gamma_stability() { // Gamma has 3 cases: shape == 1, shape < 1, shape > 1 test_samples(223, Gamma::new(1.0, 5.0).unwrap(), &[ --- -2.30.1.windows.1 +-- +2.25.1 From 4edf14520aaa7e2d506afa470d9b8b1f9999b8f8 Mon Sep 17 00:00:00 2001 From: Afonso Bordado Date: Tue, 27 Sep 2022 12:29:52 +0100 Subject: [PATCH 80/98] Use target triple artifact names --- .github/workflows/main.yml | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index 7f6cfd2ccc56f..5655f466d749f 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -29,7 +29,11 @@ jobs: matrix: include: - os: ubuntu-latest + env: + TARGET_TRIPLE: x86_64-unknown-linux-gnu - os: macos-latest + env: + TARGET_TRIPLE: x86_64-apple-darwin # cross-compile from Linux to Windows using mingw - os: ubuntu-latest env: @@ -112,7 +116,7 @@ jobs: if: matrix.env.TARGET_TRIPLE != 'x86_64-pc-windows-gnu' uses: actions/upload-artifact@v2 with: - name: cg_clif-${{ runner.os }} + name: ${{ matrix.env.TARGET_TRIPLE }} path: cg_clif.tar.xz - name: Upload prebuilt cg_clif (cross compile) @@ -132,6 +136,8 @@ jobs: include: # Native Windows build with MSVC - os: windows-latest + env: + TARGET_TRIPLE: x86_64-pc-windows-msvc # cross-compile from Windows to Windows MinGW - os: windows-latest env: @@ -211,5 +217,5 @@ jobs: - name: Upload prebuilt cg_clif uses: actions/upload-artifact@v2 with: - name: cg_clif-${{ runner.os }}-${{ matrix.env.TARGET_TRIPLE }} + name: ${{ matrix.env.TARGET_TRIPLE }} path: cg_clif.tar From 6909219a2945b9867250459e4722eae4ce359721 Mon Sep 17 00:00:00 2001 From: Afonso Bordado Date: Tue, 27 Sep 2022 12:42:27 +0100 Subject: [PATCH 81/98] Prefix artifact names with `cg_clif` Co-authored-by: bjorn3 <17426603+bjorn3@users.noreply.github.com> --- .github/workflows/main.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index 5655f466d749f..5061010c86cd3 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -116,7 +116,7 @@ jobs: if: matrix.env.TARGET_TRIPLE != 'x86_64-pc-windows-gnu' uses: actions/upload-artifact@v2 with: - name: ${{ matrix.env.TARGET_TRIPLE }} + name: cg_clif-${{ matrix.env.TARGET_TRIPLE }} path: cg_clif.tar.xz - name: Upload prebuilt cg_clif (cross compile) @@ -217,5 +217,5 @@ jobs: - name: Upload prebuilt cg_clif uses: actions/upload-artifact@v2 with: - name: ${{ matrix.env.TARGET_TRIPLE }} + name: cg_clif-${{ matrix.env.TARGET_TRIPLE }} path: cg_clif.tar From 102a577bb3ec92b8fddc155975d2d9980d25ecdc Mon Sep 17 00:00:00 2001 From: Urgau Date: Sat, 24 Sep 2022 12:34:56 +0200 Subject: [PATCH 82/98] Stabilize bench_black_box --- example/std_example.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/example/std_example.rs b/example/std_example.rs index 0b5b6cd55d720..ad108c34992e3 100644 --- a/example/std_example.rs +++ b/example/std_example.rs @@ -1,4 +1,4 @@ -#![feature(core_intrinsics, generators, generator_trait, is_sorted, bench_black_box)] +#![feature(core_intrinsics, generators, generator_trait, is_sorted)] #[cfg(target_arch = "x86_64")] use std::arch::x86_64::*; From 1d1827413f165d4b081253aa9b225a52a24d3c1d Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Wed, 5 Oct 2022 13:26:50 +0200 Subject: [PATCH 83/98] Rustup to rustc 1.66.0-nightly (01af5040f 2022-10-04) --- build_sysroot/Cargo.lock | 8 ++++---- example/mini_core.rs | 6 ++++++ rust-toolchain | 2 +- 3 files changed, 11 insertions(+), 5 deletions(-) diff --git a/build_sysroot/Cargo.lock b/build_sysroot/Cargo.lock index a8077feaaabac..683ec4940f9e9 100644 --- a/build_sysroot/Cargo.lock +++ b/build_sysroot/Cargo.lock @@ -66,9 +66,9 @@ dependencies = [ [[package]] name = "compiler_builtins" -version = "0.1.80" +version = "0.1.81" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c3feb824e4dde07fb32acc53c8cc1f9e537bb4d7e0a331198000840979d410d3" +checksum = "7927b44b9659f9a9af77eb0e6d98d8172ee5aec6924ed9360ae527cdd8551245" dependencies = [ "rustc-std-workspace-core", ] @@ -145,9 +145,9 @@ dependencies = [ [[package]] name = "libc" -version = "0.2.132" +version = "0.2.134" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8371e4e5341c3a96db127eb2465ac681ced4c433e01dd0e938adbef26ba93ba5" +checksum = "329c933548736bc49fd575ee68c89e8be4d260064184389a5b77517cddd99ffb" dependencies = [ "rustc-std-workspace-core", ] diff --git a/example/mini_core.rs b/example/mini_core.rs index 42f8aa50ba1a9..7f85b52f083a7 100644 --- a/example/mini_core.rs +++ b/example/mini_core.rs @@ -559,16 +559,22 @@ pub union MaybeUninit { pub mod intrinsics { extern "rust-intrinsic" { + #[rustc_safe_intrinsic] pub fn abort() -> !; + #[rustc_safe_intrinsic] pub fn size_of() -> usize; pub fn size_of_val(val: *const T) -> usize; + #[rustc_safe_intrinsic] pub fn min_align_of() -> usize; pub fn min_align_of_val(val: *const T) -> usize; pub fn copy(src: *const T, dst: *mut T, count: usize); pub fn transmute(e: T) -> U; pub fn ctlz_nonzero(x: T) -> T; + #[rustc_safe_intrinsic] pub fn needs_drop() -> bool; + #[rustc_safe_intrinsic] pub fn bitreverse(x: T) -> T; + #[rustc_safe_intrinsic] pub fn bswap(x: T) -> T; pub fn write_bytes(dst: *mut T, val: u8, count: usize); } diff --git a/rust-toolchain b/rust-toolchain index 06e9106e685a4..6799b9790840f 100644 --- a/rust-toolchain +++ b/rust-toolchain @@ -1,3 +1,3 @@ [toolchain] -channel = "nightly-2022-09-25" +channel = "nightly-2022-10-05" components = ["rust-src", "rustc-dev", "llvm-tools-preview"] From dae6a30d0b888a02e8b3a450510b8683f920cb16 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Wed, 5 Oct 2022 13:55:13 +0200 Subject: [PATCH 84/98] Remove workaround for rustbuild bug --- scripts/setup_rust_fork.sh | 15 --------------- 1 file changed, 15 deletions(-) diff --git a/scripts/setup_rust_fork.sh b/scripts/setup_rust_fork.sh index 25103a2fd5036..d6a37789599fe 100644 --- a/scripts/setup_rust_fork.sh +++ b/scripts/setup_rust_fork.sh @@ -27,21 +27,6 @@ index d95b5b7f17f..00b6f0e3635 100644 [dev-dependencies] rand = "0.7" rand_xorshift = "0.2" -diff --git a/src/bootstrap/config.rs b/src/bootstrap/config.rs -index a6333976f2a..c9a872e876c 100644 ---- a/src/bootstrap/config.rs -+++ b/src/bootstrap/config.rs -@@ -917,6 +917,10 @@ pub fn parse(args: &[String]) -> Config { - config.initial_cargo = config.out.join(config.build.triple).join("stage0/bin/cargo"); - } - -+ // Workaround for rustbuild bug -+ config.initial_rustc = PathBuf::from("$(pwd)/../build/rustc-clif"); -+ config.initial_cargo = PathBuf::from("$(rustup which cargo)"); -+ - // NOTE: it's important this comes *after* we set \`initial_rustc\` just above. - if config.dry_run { - let dir = config.out.join("tmp-dry-run"); diff --git a/src/tools/compiletest/src/runtest.rs b/src/tools/compiletest/src/runtest.rs index 8431aa7b818..a3ff7e68ce5 100644 --- a/src/tools/compiletest/src/runtest.rs From 187b76965a58dcb64b4ca6cd2513c517eda5ad67 Mon Sep 17 00:00:00 2001 From: ouz-a Date: Tue, 4 Oct 2022 21:39:43 +0300 Subject: [PATCH 85/98] Remove `mir::CastKind::Misc` --- src/base.rs | 7 ++++++- src/constant.rs | 11 ++++++++++- 2 files changed, 16 insertions(+), 2 deletions(-) diff --git a/src/base.rs b/src/base.rs index 11540d8008160..4303d63fe2131 100644 --- a/src/base.rs +++ b/src/base.rs @@ -633,7 +633,12 @@ fn codegen_stmt<'tcx>( lval.write_cvalue(fx, operand.cast_pointer_to(to_layout)); } Rvalue::Cast( - CastKind::Misc + CastKind::IntToInt + | CastKind::FloatToFloat + | CastKind::FloatToInt + | CastKind::IntToFloat + | CastKind::FnPtrToPtr + | CastKind::PtrToPtr | CastKind::PointerExposeAddress | CastKind::PointerFromExposedAddress, ref operand, diff --git a/src/constant.rs b/src/constant.rs index e12805b093cc7..c5f44bb847964 100644 --- a/src/constant.rs +++ b/src/constant.rs @@ -490,7 +490,16 @@ pub(crate) fn mir_operand_get_const_val<'tcx>( match &stmt.kind { StatementKind::Assign(local_and_rvalue) if &local_and_rvalue.0 == place => { match &local_and_rvalue.1 { - Rvalue::Cast(CastKind::Misc, operand, ty) => { + Rvalue::Cast( + CastKind::IntToInt + | CastKind::FloatToFloat + | CastKind::FloatToInt + | CastKind::IntToFloat + | CastKind::FnPtrToPtr + | CastKind::PtrToPtr, + operand, + ty, + ) => { if computed_const_val.is_some() { return None; // local assigned twice } From 69297f9c863f0e153d10447685b9a2cc34f60d57 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Tue, 11 Oct 2022 16:52:19 +0200 Subject: [PATCH 86/98] Rustup to rustc 1.66.0-nightly (a6b7274a4 2022-10-10) --- build_sysroot/Cargo.lock | 8 ++++---- rust-toolchain | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/build_sysroot/Cargo.lock b/build_sysroot/Cargo.lock index 683ec4940f9e9..f6a9cb67290c7 100644 --- a/build_sysroot/Cargo.lock +++ b/build_sysroot/Cargo.lock @@ -66,9 +66,9 @@ dependencies = [ [[package]] name = "compiler_builtins" -version = "0.1.81" +version = "0.1.82" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7927b44b9659f9a9af77eb0e6d98d8172ee5aec6924ed9360ae527cdd8551245" +checksum = "18cd7635fea7bb481ea543b392789844c1ad581299da70184c7175ce3af76603" dependencies = [ "rustc-std-workspace-core", ] @@ -145,9 +145,9 @@ dependencies = [ [[package]] name = "libc" -version = "0.2.134" +version = "0.2.135" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "329c933548736bc49fd575ee68c89e8be4d260064184389a5b77517cddd99ffb" +checksum = "68783febc7782c6c5cb401fbda4de5a9898be1762314da0bb2c10ced61f18b0c" dependencies = [ "rustc-std-workspace-core", ] diff --git a/rust-toolchain b/rust-toolchain index 6799b9790840f..b1e4e72751cfa 100644 --- a/rust-toolchain +++ b/rust-toolchain @@ -1,3 +1,3 @@ [toolchain] -channel = "nightly-2022-10-05" +channel = "nightly-2022-10-11" components = ["rust-src", "rustc-dev", "llvm-tools-preview"] From e1a7791fcb8f5f0f257f3c95241e723ea6abbdbc Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Thu, 13 Oct 2022 13:15:57 +0000 Subject: [PATCH 87/98] Update rust-analyzer.linkedProjects --- .vscode/settings.json | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/.vscode/settings.json b/.vscode/settings.json index d88309e412ed0..13301bf20a5ed 100644 --- a/.vscode/settings.json +++ b/.vscode/settings.json @@ -7,7 +7,7 @@ "rust-analyzer.cargo.features": ["unstable-features"], "rust-analyzer.linkedProjects": [ "./Cargo.toml", - //"./build_sysroot/sysroot_src/src/libstd/Cargo.toml", + //"./build_sysroot/sysroot_src/library/std/Cargo.toml", { "roots": [ "./example/mini_core.rs", @@ -36,10 +36,10 @@ ] }, { - "roots": ["./scripts/filter_profile.rs"], + "roots": ["./example/std_example.rs"], "crates": [ { - "root_module": "./scripts/filter_profile.rs", + "root_module": "./example/std_example.rs", "edition": "2018", "deps": [{ "crate": 1, "name": "std" }], "cfg": [], From f1dc206c4f87ba637200dc65d6c125534dcf13eb Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Mon, 12 Sep 2022 11:31:02 +0000 Subject: [PATCH 88/98] Introduce GitRepo type This will make it easier to move downloaded repos around --- build_system/prepare.rs | 132 +++++++++++++++++++++++++--------------- 1 file changed, 84 insertions(+), 48 deletions(-) diff --git a/build_system/prepare.rs b/build_system/prepare.rs index 3ad9f87e3186e..5c68d7ac97283 100644 --- a/build_system/prepare.rs +++ b/build_system/prepare.rs @@ -7,49 +7,45 @@ use std::process::Command; use super::rustc_info::{get_file_name, get_rustc_path, get_rustc_version}; use super::utils::{cargo_command, copy_dir_recursively, spawn_and_wait}; +pub(crate) const ABI_CAFE: GitRepo = GitRepo::github( + "Gankra", + "abi-cafe", + "4c6dc8c9c687e2b3a760ff2176ce236872b37212", + "abi-cafe", +); + +pub(crate) const RAND: GitRepo = + GitRepo::github("rust-random", "rand", "0f933f9c7176e53b2a3c7952ded484e1783f0bf1", "rand"); + +pub(crate) const REGEX: GitRepo = + GitRepo::github("rust-lang", "regex", "341f207c1071f7290e3f228c710817c280c8dca1", "regex"); + +pub(crate) const PORTABLE_SIMD: GitRepo = GitRepo::github( + "rust-lang", + "portable-simd", + "d5cd4a8112d958bd3a252327e0d069a6363249bd", + "portable-simd", +); + +pub(crate) const SIMPLE_RAYTRACER: GitRepo = GitRepo::github( + "ebobby", + "simple-raytracer", + "804a7a21b9e673a482797aa289a18ed480e4d813", + "", +); + pub(crate) fn prepare() { prepare_sysroot(); + // FIXME maybe install this only locally? eprintln!("[INSTALL] hyperfine"); Command::new("cargo").arg("install").arg("hyperfine").spawn().unwrap().wait().unwrap(); - clone_repo_shallow_github( - "abi-cafe", - "Gankra", - "abi-cafe", - "4c6dc8c9c687e2b3a760ff2176ce236872b37212", - ); - apply_patches("abi-cafe", Path::new("abi-cafe")); - - clone_repo_shallow_github( - "rand", - "rust-random", - "rand", - "0f933f9c7176e53b2a3c7952ded484e1783f0bf1", - ); - apply_patches("rand", Path::new("rand")); - - clone_repo_shallow_github( - "regex", - "rust-lang", - "regex", - "341f207c1071f7290e3f228c710817c280c8dca1", - ); - - clone_repo_shallow_github( - "portable-simd", - "rust-lang", - "portable-simd", - "d5cd4a8112d958bd3a252327e0d069a6363249bd", - ); - apply_patches("portable-simd", Path::new("portable-simd")); - - clone_repo_shallow_github( - "simple-raytracer", - "ebobby", - "simple-raytracer", - "804a7a21b9e673a482797aa289a18ed480e4d813", - ); + ABI_CAFE.fetch(); + RAND.fetch(); + REGEX.fetch(); + PORTABLE_SIMD.fetch(); + SIMPLE_RAYTRACER.fetch(); eprintln!("[LLVM BUILD] simple-raytracer"); let build_cmd = cargo_command("cargo", "build", None, Path::new("simple-raytracer")); @@ -88,38 +84,74 @@ fn prepare_sysroot() { apply_patches("sysroot", &sysroot_src); } +pub(crate) struct GitRepo { + url: GitRepoUrl, + rev: &'static str, + patch_name: &'static str, +} + +enum GitRepoUrl { + Github { user: &'static str, repo: &'static str }, +} + +impl GitRepo { + const fn github( + user: &'static str, + repo: &'static str, + rev: &'static str, + patch_name: &'static str, + ) -> GitRepo { + GitRepo { url: GitRepoUrl::Github { user, repo }, rev, patch_name } + } + + pub(crate) fn source_dir(&self) -> PathBuf { + match self.url { + GitRepoUrl::Github { user: _, repo } => PathBuf::from(format!("{}", repo)), + } + } + + fn fetch(&self) { + match self.url { + GitRepoUrl::Github { user, repo } => { + clone_repo_shallow_github(&self.source_dir(), user, repo, self.rev); + } + } + apply_patches(self.patch_name, &self.source_dir()); + } +} + #[allow(dead_code)] -fn clone_repo(target_dir: &str, repo: &str, rev: &str) { +fn clone_repo(download_dir: &Path, repo: &str, rev: &str) { eprintln!("[CLONE] {}", repo); // Ignore exit code as the repo may already have been checked out - Command::new("git").arg("clone").arg(repo).arg(target_dir).spawn().unwrap().wait().unwrap(); + Command::new("git").arg("clone").arg(repo).arg(&download_dir).spawn().unwrap().wait().unwrap(); let mut clean_cmd = Command::new("git"); - clean_cmd.arg("checkout").arg("--").arg(".").current_dir(target_dir); + clean_cmd.arg("checkout").arg("--").arg(".").current_dir(&download_dir); spawn_and_wait(clean_cmd); let mut checkout_cmd = Command::new("git"); - checkout_cmd.arg("checkout").arg("-q").arg(rev).current_dir(target_dir); + checkout_cmd.arg("checkout").arg("-q").arg(rev).current_dir(download_dir); spawn_and_wait(checkout_cmd); } -fn clone_repo_shallow_github(target_dir: &str, username: &str, repo: &str, rev: &str) { +fn clone_repo_shallow_github(download_dir: &Path, user: &str, repo: &str, rev: &str) { if cfg!(windows) { // Older windows doesn't have tar or curl by default. Fall back to using git. - clone_repo(target_dir, &format!("https://github.com/{}/{}.git", username, repo), rev); + clone_repo(download_dir, &format!("https://github.com/{}/{}.git", user, repo), rev); return; } - let archive_url = format!("https://github.com/{}/{}/archive/{}.tar.gz", username, repo, rev); + let archive_url = format!("https://github.com/{}/{}/archive/{}.tar.gz", user, repo, rev); let archive_file = format!("{}.tar.gz", rev); let archive_dir = format!("{}-{}", repo, rev); - eprintln!("[DOWNLOAD] {}/{} from {}", username, repo, archive_url); + eprintln!("[DOWNLOAD] {}/{} from {}", user, repo, archive_url); // Remove previous results if they exists let _ = std::fs::remove_file(&archive_file); let _ = std::fs::remove_dir_all(&archive_dir); - let _ = std::fs::remove_dir_all(target_dir); + let _ = std::fs::remove_dir_all(&download_dir); // Download zip archive let mut download_cmd = Command::new("curl"); @@ -132,9 +164,9 @@ fn clone_repo_shallow_github(target_dir: &str, username: &str, repo: &str, rev: spawn_and_wait(unpack_cmd); // Rename unpacked dir to the expected name - std::fs::rename(archive_dir, target_dir).unwrap(); + std::fs::rename(archive_dir, &download_dir).unwrap(); - init_git_repo(Path::new(target_dir)); + init_git_repo(&download_dir); // Cleanup std::fs::remove_file(archive_file).unwrap(); @@ -175,6 +207,10 @@ fn get_patches(source_dir: &Path, crate_name: &str) -> Vec { } fn apply_patches(crate_name: &str, target_dir: &Path) { + if crate_name == "" { + return; + } + for patch in get_patches(&std::env::current_dir().unwrap(), crate_name) { eprintln!( "[PATCH] {:?} <- {:?}", From 24198ce6b4937b52203f2b54e31c66b9932ee645 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Mon, 12 Sep 2022 13:13:42 +0000 Subject: [PATCH 89/98] Move all downloaded repos to the downloads/ dir --- .gitignore | 7 +----- build_system/abi_cafe.rs | 6 ++--- build_system/prepare.rs | 27 ++++++++++++++++------ build_system/tests.rs | 48 +++++++++++++++++++++------------------- clean_all.sh | 4 ++++ 5 files changed, 53 insertions(+), 39 deletions(-) diff --git a/.gitignore b/.gitignore index 9a4c54f08ca8c..fae09592c6ac0 100644 --- a/.gitignore +++ b/.gitignore @@ -15,9 +15,4 @@ perf.data.old /build_sysroot/compiler-builtins /build_sysroot/rustc_version /rust -/rand -/regex -/simple-raytracer -/portable-simd -/abi-cafe -/abi-checker +/download diff --git a/build_system/abi_cafe.rs b/build_system/abi_cafe.rs index c2944ce62623a..fae5b27163680 100644 --- a/build_system/abi_cafe.rs +++ b/build_system/abi_cafe.rs @@ -3,6 +3,7 @@ use std::path::Path; use super::build_sysroot; use super::config; +use super::prepare; use super::utils::{cargo_command, spawn_and_wait}; use super::SysrootKind; @@ -35,9 +36,8 @@ pub(crate) fn run( ); eprintln!("Running abi-cafe"); - let mut abi_cafe_path = env::current_dir().unwrap(); - abi_cafe_path.push("abi-cafe"); - env::set_current_dir(&abi_cafe_path.clone()).unwrap(); + let abi_cafe_path = prepare::ABI_CAFE.source_dir(); + env::set_current_dir(abi_cafe_path.clone()).unwrap(); let pairs = ["rustc_calls_cgclif", "cgclif_calls_rustc", "cgclif_calls_cc", "cc_calls_cgclif"]; diff --git a/build_system/prepare.rs b/build_system/prepare.rs index 5c68d7ac97283..f9ab8ae70412b 100644 --- a/build_system/prepare.rs +++ b/build_system/prepare.rs @@ -35,6 +35,11 @@ pub(crate) const SIMPLE_RAYTRACER: GitRepo = GitRepo::github( ); pub(crate) fn prepare() { + if Path::new("download").exists() { + std::fs::remove_dir_all(Path::new("download")).unwrap(); + } + std::fs::create_dir_all(Path::new("download")).unwrap(); + prepare_sysroot(); // FIXME maybe install this only locally? @@ -48,11 +53,15 @@ pub(crate) fn prepare() { SIMPLE_RAYTRACER.fetch(); eprintln!("[LLVM BUILD] simple-raytracer"); - let build_cmd = cargo_command("cargo", "build", None, Path::new("simple-raytracer")); + let build_cmd = cargo_command("cargo", "build", None, &SIMPLE_RAYTRACER.source_dir()); spawn_and_wait(build_cmd); fs::copy( - Path::new("simple-raytracer/target/debug").join(get_file_name("main", "bin")), - Path::new("simple-raytracer").join(get_file_name("raytracer_cg_llvm", "bin")), + SIMPLE_RAYTRACER + .source_dir() + .join("target") + .join("debug") + .join(get_file_name("main", "bin")), + SIMPLE_RAYTRACER.source_dir().join(get_file_name("raytracer_cg_llvm", "bin")), ) .unwrap(); } @@ -106,7 +115,9 @@ impl GitRepo { pub(crate) fn source_dir(&self) -> PathBuf { match self.url { - GitRepoUrl::Github { user: _, repo } => PathBuf::from(format!("{}", repo)), + GitRepoUrl::Github { user: _, repo } => { + std::env::current_dir().unwrap().join("download").join(repo) + } } } @@ -142,9 +153,11 @@ fn clone_repo_shallow_github(download_dir: &Path, user: &str, repo: &str, rev: & return; } + let downloads_dir = std::env::current_dir().unwrap().join("download"); + let archive_url = format!("https://github.com/{}/{}/archive/{}.tar.gz", user, repo, rev); - let archive_file = format!("{}.tar.gz", rev); - let archive_dir = format!("{}-{}", repo, rev); + let archive_file = downloads_dir.join(format!("{}.tar.gz", rev)); + let archive_dir = downloads_dir.join(format!("{}-{}", repo, rev)); eprintln!("[DOWNLOAD] {}/{} from {}", user, repo, archive_url); @@ -160,7 +173,7 @@ fn clone_repo_shallow_github(download_dir: &Path, user: &str, repo: &str, rev: & // Unpack tar archive let mut unpack_cmd = Command::new("tar"); - unpack_cmd.arg("xf").arg(&archive_file); + unpack_cmd.arg("xf").arg(&archive_file).current_dir(downloads_dir); spawn_and_wait(unpack_cmd); // Rename unpacked dir to the expected name diff --git a/build_system/tests.rs b/build_system/tests.rs index d4f393fc7ff92..a414b60f4e06b 100644 --- a/build_system/tests.rs +++ b/build_system/tests.rs @@ -1,5 +1,6 @@ use super::build_sysroot; use super::config; +use super::prepare; use super::rustc_info::get_wrapper_file_name; use super::utils::{cargo_command, hyperfine_command, spawn_and_wait, spawn_and_wait_with_input}; use build_system::SysrootKind; @@ -217,7 +218,7 @@ const BASE_SYSROOT_SUITE: &[TestCase] = &[ const EXTENDED_SYSROOT_SUITE: &[TestCase] = &[ TestCase::new("test.rust-random/rand", &|runner| { - runner.in_dir(["rand"], |runner| { + runner.in_dir(prepare::RAND.source_dir(), |runner| { runner.run_cargo("clean", []); if runner.host_triple == runner.target_triple { @@ -230,7 +231,7 @@ const EXTENDED_SYSROOT_SUITE: &[TestCase] = &[ }); }), TestCase::new("bench.simple-raytracer", &|runner| { - runner.in_dir(["simple-raytracer"], |runner| { + runner.in_dir(prepare::SIMPLE_RAYTRACER.source_dir(), |runner| { let run_runs = env::var("RUN_RUNS").unwrap_or("10".to_string()).parse().unwrap(); if runner.host_triple == runner.target_triple { @@ -273,19 +274,28 @@ const EXTENDED_SYSROOT_SUITE: &[TestCase] = &[ }); }), TestCase::new("test.libcore", &|runner| { - runner.in_dir(["build_sysroot", "sysroot_src", "library", "core", "tests"], |runner| { - runner.run_cargo("clean", []); + runner.in_dir( + std::env::current_dir() + .unwrap() + .join("build_sysroot") + .join("sysroot_src") + .join("library") + .join("core") + .join("tests"), + |runner| { + runner.run_cargo("clean", []); - if runner.host_triple == runner.target_triple { - runner.run_cargo("test", []); - } else { - eprintln!("Cross-Compiling: Not running tests"); - runner.run_cargo("build", ["--tests"]); - } - }); + if runner.host_triple == runner.target_triple { + runner.run_cargo("test", []); + } else { + eprintln!("Cross-Compiling: Not running tests"); + runner.run_cargo("build", ["--tests"]); + } + }, + ); }), TestCase::new("test.regex-shootout-regex-dna", &|runner| { - runner.in_dir(["regex"], |runner| { + runner.in_dir(prepare::REGEX.source_dir(), |runner| { runner.run_cargo("clean", []); // newer aho_corasick versions throw a deprecation warning @@ -336,7 +346,7 @@ const EXTENDED_SYSROOT_SUITE: &[TestCase] = &[ }); }), TestCase::new("test.regex", &|runner| { - runner.in_dir(["regex"], |runner| { + runner.in_dir(prepare::REGEX.source_dir(), |runner| { runner.run_cargo("clean", []); // newer aho_corasick versions throw a deprecation warning @@ -367,7 +377,7 @@ const EXTENDED_SYSROOT_SUITE: &[TestCase] = &[ }); }), TestCase::new("test.portable-simd", &|runner| { - runner.in_dir(["portable-simd"], |runner| { + runner.in_dir(prepare::PORTABLE_SIMD.source_dir(), |runner| { runner.run_cargo("clean", []); runner.run_cargo("build", ["--all-targets", "--target", &runner.target_triple]); @@ -506,16 +516,8 @@ impl TestRunner { } } - fn in_dir<'a, I, F>(&self, dir: I, callback: F) - where - I: IntoIterator, - F: FnOnce(&TestRunner), - { + fn in_dir(&self, new: impl AsRef, callback: impl FnOnce(&TestRunner)) { let current = env::current_dir().unwrap(); - let mut new = current.clone(); - for d in dir { - new.push(d); - } env::set_current_dir(new).unwrap(); callback(self); diff --git a/clean_all.sh b/clean_all.sh index 0fd9b9455a3f1..fedab2433aa05 100755 --- a/clean_all.sh +++ b/clean_all.sh @@ -3,4 +3,8 @@ set -e rm -rf build_sysroot/{sysroot_src/,target/,compiler-builtins/,rustc_version} rm -rf target/ build/ perf.data{,.old} y.bin +rm -rf download/ + +# Kept for now in case someone updates their checkout of cg_clif before running clean_all.sh +# FIXME remove at some point in the future rm -rf rand/ regex/ simple-raytracer/ portable-simd/ abi-checker/ abi-cafe/ From 54ee5ac0734a5c715558190fda9c61be2446d93a Mon Sep 17 00:00:00 2001 From: Rageking8 Date: Fri, 14 Oct 2022 00:25:34 +0800 Subject: [PATCH 90/98] more dupe word typos --- build_system/rustc_info.rs | 2 +- src/abi/pass_mode.rs | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/build_system/rustc_info.rs b/build_system/rustc_info.rs index 913b589afcc87..3c08b6fa3894d 100644 --- a/build_system/rustc_info.rs +++ b/build_system/rustc_info.rs @@ -65,7 +65,7 @@ pub(crate) fn get_file_name(crate_name: &str, crate_type: &str) -> String { } /// Similar to `get_file_name`, but converts any dashes (`-`) in the `crate_name` to -/// underscores (`_`). This is specially made for the the rustc and cargo wrappers +/// underscores (`_`). This is specially made for the rustc and cargo wrappers /// which have a dash in the name, and that is not allowed in a crate name. pub(crate) fn get_wrapper_file_name(crate_name: &str, crate_type: &str) -> String { let crate_name = crate_name.replace('-', "_"); diff --git a/src/abi/pass_mode.rs b/src/abi/pass_mode.rs index 96e25d3a8d4c9..e5ad31eb9484a 100644 --- a/src/abi/pass_mode.rs +++ b/src/abi/pass_mode.rs @@ -193,7 +193,7 @@ pub(super) fn from_casted_value<'tcx>( kind: StackSlotKind::ExplicitSlot, // FIXME Don't force the size to a multiple of 16 bytes once Cranelift gets a way to // specify stack slot alignment. - // Stack slot size may be bigger for for example `[u8; 3]` which is packed into an `i32`. + // Stack slot size may be bigger for example `[u8; 3]` which is packed into an `i32`. // It may also be smaller for example when the type is a wrapper around an integer with a // larger alignment than the integer. size: (std::cmp::max(abi_param_size, layout_size) + 15) / 16 * 16, From da770abea31e25514af65387ea93a755242610b7 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Fri, 21 Oct 2022 10:55:20 +0000 Subject: [PATCH 91/98] Update to Cranelift 0.89.0 --- Cargo.lock | 172 +++++++++++++++++++++++++++++++++++++++++++++-------- Cargo.toml | 12 ++-- 2 files changed, 154 insertions(+), 30 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 3fa9d56cd01a3..e55b04352a8fb 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -62,18 +62,18 @@ checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd" [[package]] name = "cranelift-bforest" -version = "0.88.1" +version = "0.89.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "44409ccf2d0f663920cab563d2b79fcd6b2e9a2bcc6e929fef76c8f82ad6c17a" +checksum = "be5e1ee4c22871d24a95196ea7047d58c1d978e46c88037d3d397b3b3e0af360" dependencies = [ "cranelift-entity", ] [[package]] name = "cranelift-codegen" -version = "0.88.1" +version = "0.89.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "98de2018ad96eb97f621f7d6b900a0cc661aec8d02ea4a50e56ecb48e5a2fcaf" +checksum = "70f600a52d59eed56a85f33750873b3b42d61e35ca777cd792369893f9e1f9dd" dependencies = [ "arrayvec", "bumpalo", @@ -91,30 +91,30 @@ dependencies = [ [[package]] name = "cranelift-codegen-meta" -version = "0.88.1" +version = "0.89.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5287ce36e6c4758fbaf298bd1a8697ad97a4f2375a3d1b61142ea538db4877e5" +checksum = "e8418218d0953d73e9b96e9d9ffec56145efa4f18988251530b5872ae4410563" dependencies = [ "cranelift-codegen-shared", ] [[package]] name = "cranelift-codegen-shared" -version = "0.88.1" +version = "0.89.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2855c24219e2f08827f3f4ffb2da92e134ae8d8ecc185b11ec8f9878cf5f588e" +checksum = "f01be0cfd40aba59153236ab4b99062131b5bbe6f9f3d4bcb238bd2f96ff5262" [[package]] name = "cranelift-entity" -version = "0.88.1" +version = "0.89.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0b65673279d75d34bf11af9660ae2dbd1c22e6d28f163f5c72f4e1dc56d56103" +checksum = "ddae4fec5d6859233ffa175b61d269443c473b3971a2c3e69008c8d3e83d5825" [[package]] name = "cranelift-frontend" -version = "0.88.1" +version = "0.89.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3ed2b3d7a4751163f6c4a349205ab1b7d9c00eecf19dcea48592ef1f7688eefc" +checksum = "f2cc3deb0df97748434cf9f7e404f1f5134f6a253fc9a6bca25c5cd6804c08d3" dependencies = [ "cranelift-codegen", "log", @@ -124,15 +124,18 @@ dependencies = [ [[package]] name = "cranelift-isle" -version = "0.88.1" +version = "0.89.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3be64cecea9d90105fc6a2ba2d003e98c867c1d6c4c86cc878f97ad9fb916293" +checksum = "fc3bb54287de9c36ba354eb849fefb77b5e73955058745fd08f12cfdfa181866" +dependencies = [ + "rayon", +] [[package]] name = "cranelift-jit" -version = "0.88.1" +version = "0.89.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f98ed42a70a0c9c388e34ec9477f57fc7300f541b1e5136a0e2ea02b1fac6015" +checksum = "e1122619a1f4f857afb3e2ba47bbc1e9c9ee7bce17c9e39f66999e38352773ad" dependencies = [ "anyhow", "cranelift-codegen", @@ -148,9 +151,9 @@ dependencies = [ [[package]] name = "cranelift-module" -version = "0.88.1" +version = "0.89.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d658ac7f156708bfccb647216cc8b9387469f50d352ba4ad80150541e4ae2d49" +checksum = "47605be4eb921bcf84d995a6594477db0790bf8442a6b187815e8e90fad82087" dependencies = [ "anyhow", "cranelift-codegen", @@ -158,9 +161,9 @@ dependencies = [ [[package]] name = "cranelift-native" -version = "0.88.1" +version = "0.89.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c4a03a6ac1b063e416ca4b93f6247978c991475e8271465340caa6f92f3c16a4" +checksum = "d8c2a4f2efdce1de1f94e74f12b3b4144e3bcafa6011338b87388325d72d2120" dependencies = [ "cranelift-codegen", "libc", @@ -169,9 +172,9 @@ dependencies = [ [[package]] name = "cranelift-object" -version = "0.88.1" +version = "0.89.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "eef0b4119b645b870a43a036d76c0ada3a076b1f82e8b8487659304c8b09049b" +checksum = "5696c434de314c4b3272e3d8eddb6a13b1e3a907788b484b1ec4d9f4e7d669dc" dependencies = [ "anyhow", "cranelift-codegen", @@ -190,6 +193,61 @@ dependencies = [ "cfg-if", ] +[[package]] +name = "crossbeam-channel" +version = "0.5.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c2dd04ddaf88237dc3b8d8f9a3c1004b506b54b3313403944054d23c0870c521" +dependencies = [ + "cfg-if", + "crossbeam-utils", +] + +[[package]] +name = "crossbeam-deque" +version = "0.8.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "715e8152b692bba2d374b53d4875445368fdf21a94751410af607a5ac677d1fc" +dependencies = [ + "cfg-if", + "crossbeam-epoch", + "crossbeam-utils", +] + +[[package]] +name = "crossbeam-epoch" +version = "0.9.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f916dfc5d356b0ed9dae65f1db9fc9770aa2851d2662b988ccf4fe3516e86348" +dependencies = [ + "autocfg", + "cfg-if", + "crossbeam-utils", + "memoffset", + "scopeguard", +] + +[[package]] +name = "crossbeam-utils" +version = "0.8.12" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "edbafec5fa1f196ca66527c1b12c2ec4745ca14b50f1ad8f9f6f720b55d11fac" +dependencies = [ + "cfg-if", +] + +[[package]] +name = "either" +version = "1.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "90e5c1c8368803113bf0c9584fc495a58b86dc8a29edbf8fe877d21d9507e797" + +[[package]] +name = "fallible-iterator" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4443176a9f2c162692bd3d352d745ef9413eec5782a80d8fd6f8a1ac692a07f7" + [[package]] name = "fxhash" version = "0.2.1" @@ -216,7 +274,9 @@ version = "0.26.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "22030e2c5a68ec659fde1e949a745124b48e6fa8b045b7ed5bd1fe4ccc5c4e5d" dependencies = [ + "fallible-iterator", "indexmap", + "stable_deref_trait", ] [[package]] @@ -228,6 +288,15 @@ dependencies = [ "ahash", ] +[[package]] +name = "hermit-abi" +version = "0.1.19" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "62b467343b94ba476dcb2500d242dadbb39557df889310ac77c5d99100aaac33" +dependencies = [ + "libc", +] + [[package]] name = "indexmap" version = "1.9.1" @@ -278,6 +347,25 @@ version = "2.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "2dffe52ecf27772e601905b7522cb4ef790d2cc203488bbd0e2fe85fcb74566d" +[[package]] +name = "memoffset" +version = "0.6.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5aa361d4faea93603064a027415f07bd8e1d5c88c9fbf68bf56a285428fd79ce" +dependencies = [ + "autocfg", +] + +[[package]] +name = "num_cpus" +version = "1.13.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "19e64526ebdee182341572e50e9ad03965aa510cd94427a4549448f285e957a1" +dependencies = [ + "hermit-abi", + "libc", +] + [[package]] name = "object" version = "0.29.0" @@ -296,11 +384,35 @@ version = "1.13.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "18a6dbe30758c9f83eb00cbea4ac95966305f5a7772f3f42ebfc7fc7eddbd8e1" +[[package]] +name = "rayon" +version = "1.5.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bd99e5772ead8baa5215278c9b15bf92087709e9c1b2d1f97cdb5a183c933a7d" +dependencies = [ + "autocfg", + "crossbeam-deque", + "either", + "rayon-core", +] + +[[package]] +name = "rayon-core" +version = "1.9.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "258bcdb5ac6dad48491bb2992db6b7cf74878b0384908af124823d118c99683f" +dependencies = [ + "crossbeam-channel", + "crossbeam-deque", + "crossbeam-utils", + "num_cpus", +] + [[package]] name = "regalloc2" -version = "0.3.2" +version = "0.4.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d43a209257d978ef079f3d446331d0f1794f5e0fc19b306a199983857833a779" +checksum = "69025b4a161879ba90719837c06621c3d73cffa147a000aeacf458f6a9572485" dependencies = [ "fxhash", "log", @@ -340,6 +452,12 @@ dependencies = [ "target-lexicon", ] +[[package]] +name = "scopeguard" +version = "1.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d29ab0c6d3fc0ee92fe66e2d99f700eab17a8d57d1c1d3b748380fb20baa78cd" + [[package]] name = "slice-group-by" version = "0.3.0" @@ -352,6 +470,12 @@ version = "1.9.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "2fd0db749597d91ff862fd1d55ea87f7855a744a8425a64695b6fca237d1dad1" +[[package]] +name = "stable_deref_trait" +version = "1.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a8f112729512f8e442d81f95a8a7ddf2b7c6b8a1a6f509a95864142b30cab2d3" + [[package]] name = "target-lexicon" version = "0.12.4" diff --git a/Cargo.toml b/Cargo.toml index 09cf5b4a1edd8..20b70ed2fb8bd 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -8,12 +8,12 @@ crate-type = ["dylib"] [dependencies] # These have to be in sync with each other -cranelift-codegen = { version = "0.88.1", features = ["unwind", "all-arch"] } -cranelift-frontend = "0.88.1" -cranelift-module = "0.88.1" -cranelift-native = "0.88.1" -cranelift-jit = { version = "0.88.1", optional = true } -cranelift-object = "0.88.1" +cranelift-codegen = { version = "0.89", features = ["unwind", "all-arch"] } +cranelift-frontend = "0.89" +cranelift-module = "0.89" +cranelift-native = "0.89" +cranelift-jit = { version = "0.89", optional = true } +cranelift-object = "0.89" target-lexicon = "0.12.0" gimli = { version = "0.26.0", default-features = false, features = ["write"]} object = { version = "0.29.0", default-features = false, features = ["std", "read_core", "write", "archive", "coff", "elf", "macho", "pe"] } From b1791eef6add9563c1b750e88ec02e681a9a4ad7 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Fri, 21 Oct 2022 10:58:33 +0000 Subject: [PATCH 92/98] Stop using a depracated function --- src/value_and_place.rs | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/value_and_place.rs b/src/value_and_place.rs index c9eb005e045d3..88d7fc2fce826 100644 --- a/src/value_and_place.rs +++ b/src/value_and_place.rs @@ -348,7 +348,7 @@ impl<'tcx> CPlace<'tcx> { local: Local, layout: TyAndLayout<'tcx>, ) -> CPlace<'tcx> { - let var = Variable::with_u32(fx.next_ssa_var); + let var = Variable::from_u32(fx.next_ssa_var); fx.next_ssa_var += 1; fx.bcx.declare_var(var, fx.clif_type(layout.ty).unwrap()); CPlace { inner: CPlaceInner::Var(local, var), layout } @@ -359,9 +359,9 @@ impl<'tcx> CPlace<'tcx> { local: Local, layout: TyAndLayout<'tcx>, ) -> CPlace<'tcx> { - let var1 = Variable::with_u32(fx.next_ssa_var); + let var1 = Variable::from_u32(fx.next_ssa_var); fx.next_ssa_var += 1; - let var2 = Variable::with_u32(fx.next_ssa_var); + let var2 = Variable::from_u32(fx.next_ssa_var); fx.next_ssa_var += 1; let (ty1, ty2) = fx.clif_pair_type(layout.ty).unwrap(); From 63e3df3d32546ab1b4a485b9a74dd91222b3039e Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Sun, 23 Oct 2022 13:50:51 +0200 Subject: [PATCH 93/98] Rustup to rustc 1.66.0-nightly (6e95b6da8 2022-10-22) --- rust-toolchain | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/rust-toolchain b/rust-toolchain index b1e4e72751cfa..c0a2e7a7883fc 100644 --- a/rust-toolchain +++ b/rust-toolchain @@ -1,3 +1,3 @@ [toolchain] -channel = "nightly-2022-10-11" +channel = "nightly-2022-10-23" components = ["rust-src", "rustc-dev", "llvm-tools-preview"] From 7a9abf5ab29bd91e1dc3d36ab1e46199e5413110 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Sun, 23 Oct 2022 14:14:35 +0200 Subject: [PATCH 94/98] Update rustc test suite failure list --- scripts/test_rustc_tests.sh | 2 -- 1 file changed, 2 deletions(-) diff --git a/scripts/test_rustc_tests.sh b/scripts/test_rustc_tests.sh index 293dff1338644..9b5db3cf81f0e 100755 --- a/scripts/test_rustc_tests.sh +++ b/scripts/test_rustc_tests.sh @@ -29,7 +29,6 @@ rm src/test/incremental/change_crate_dep_kind.rs rm src/test/incremental/issue-80691-bad-eval-cache.rs # -Cpanic=abort causes abort instead of exit(101) # requires compiling with -Cpanic=unwind -rm src/test/ui/test-attrs/test-fn-signature-verification-for-explicit-return-type.rs # "Cannot run dynamic test fn out-of-process" rm -r src/test/ui/macros/rfc-2011-nicer-assert-messages/ # vendor intrinsics @@ -108,7 +107,6 @@ rm src/test/ui/simd/intrinsic/generic-reduction-pass.rs # simd_reduce_add_unorde # bugs in the test suite # ====================== rm src/test/ui/backtrace.rs # TODO warning -rm src/test/ui/empty_global_asm.rs # TODO add needs-asm-support rm src/test/ui/simple_global_asm.rs # TODO add needs-asm-support rm src/test/ui/test-attrs/test-type.rs # TODO panic message on stderr. correct stdout # not sure if this is actually a bug in the test suite, but the symbol list shows the function without leading _ for some reason From 2470ad30e651dfd63ec6af90b83436eeafd6a3bd Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Sun, 23 Oct 2022 15:09:11 +0200 Subject: [PATCH 95/98] Allow dyn* upcasting --- src/unsize.rs | 34 ++++++++++++++++++++++++++++------ 1 file changed, 28 insertions(+), 6 deletions(-) diff --git a/src/unsize.rs b/src/unsize.rs index b194a7c8b0ddd..9c88f7dbcda33 100644 --- a/src/unsize.rs +++ b/src/unsize.rs @@ -25,7 +25,12 @@ pub(crate) fn unsized_info<'tcx>( .bcx .ins() .iconst(fx.pointer_type, len.eval_usize(fx.tcx, ParamEnv::reveal_all()) as i64), - (&ty::Dynamic(ref data_a, ..), &ty::Dynamic(ref data_b, ..)) => { + ( + &ty::Dynamic(ref data_a, _, src_dyn_kind), + &ty::Dynamic(ref data_b, _, target_dyn_kind), + ) => { + assert_eq!(src_dyn_kind, target_dyn_kind); + let old_info = old_info.expect("unsized_info: missing old info for trait upcasting coercion"); if data_a.principal_def_id() == data_b.principal_def_id() { @@ -101,6 +106,21 @@ fn unsize_ptr<'tcx>( } } +/// Coerces `src` to `dst_ty` which is guaranteed to be a `dyn*` type. +pub(crate) fn cast_to_dyn_star<'tcx>( + fx: &mut FunctionCx<'_, '_, 'tcx>, + src: Value, + src_ty_and_layout: TyAndLayout<'tcx>, + dst_ty: Ty<'tcx>, + old_info: Option, +) -> (Value, Value) { + assert!( + matches!(dst_ty.kind(), ty::Dynamic(_, _, ty::DynStar)), + "destination type must be a dyn*" + ); + (src, unsized_info(fx, src_ty_and_layout.ty, dst_ty, old_info)) +} + /// Coerce `src`, which is a reference to a value of type `src_ty`, /// to a value of type `dst_ty` and store the result in `dst` pub(crate) fn coerce_unsized_into<'tcx>( @@ -152,14 +172,16 @@ pub(crate) fn coerce_dyn_star<'tcx>( src: CValue<'tcx>, dst: CPlace<'tcx>, ) { - let data = src.load_scalar(fx); - - let vtable = if let ty::Dynamic(data, _, ty::DynStar) = dst.layout().ty.kind() { - crate::vtable::get_vtable(fx, src.layout().ty, data.principal()) + let (data, extra) = if let ty::Dynamic(_, _, ty::DynStar) = src.layout().ty.kind() { + let (data, vtable) = src.load_scalar_pair(fx); + (data, Some(vtable)) } else { - bug!("Only valid to do a DynStar cast into a DynStar type") + let data = src.load_scalar(fx); + (data, None) }; + let (data, vtable) = cast_to_dyn_star(fx, data, src.layout(), dst.layout().ty, extra); + dst.write_cvalue(fx, CValue::by_val_pair(data, vtable, dst.layout())); } From 342bac98072c7e8310167aaf26f19f0501a8f76c Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Sun, 23 Oct 2022 15:09:28 +0200 Subject: [PATCH 96/98] Fix drop for dyn* --- src/abi/mod.rs | 3 +-- src/value_and_place.rs | 44 ++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 45 insertions(+), 2 deletions(-) diff --git a/src/abi/mod.rs b/src/abi/mod.rs index 04e39954dd3cd..99059e788a074 100644 --- a/src/abi/mod.rs +++ b/src/abi/mod.rs @@ -613,8 +613,7 @@ pub(crate) fn codegen_drop<'tcx>( // (data, vtable) // an equivalent Rust `*mut dyn Trait` // // SO THEN WE CAN USE THE ABOVE CODE. - let dyn_star = drop_place.to_cvalue(fx); - let (data, vtable) = dyn_star.load_scalar_pair(fx); + let (data, vtable) = drop_place.to_cvalue(fx).dyn_star_force_data_on_stack(fx); let drop_fn = crate::vtable::drop_fn_of_obj(fx, vtable); let virtual_drop = Instance { diff --git a/src/value_and_place.rs b/src/value_and_place.rs index 88d7fc2fce826..75f968f3f4b8d 100644 --- a/src/value_and_place.rs +++ b/src/value_and_place.rs @@ -107,6 +107,50 @@ impl<'tcx> CValue<'tcx> { } } + // FIXME remove + // Forces the data value of a dyn* value to the stack and returns a pointer to it as well as the + // vtable pointer. + pub(crate) fn dyn_star_force_data_on_stack( + self, + fx: &mut FunctionCx<'_, '_, 'tcx>, + ) -> (Value, Value) { + assert!(self.1.ty.is_dyn_star()); + + match self.0 { + CValueInner::ByRef(ptr, None) => { + let (a_scalar, b_scalar) = match self.1.abi { + Abi::ScalarPair(a, b) => (a, b), + _ => unreachable!("dyn_star_force_data_on_stack({:?})", self), + }; + let b_offset = scalar_pair_calculate_b_offset(fx.tcx, a_scalar, b_scalar); + let clif_ty2 = scalar_to_clif_type(fx.tcx, b_scalar); + let mut flags = MemFlags::new(); + flags.set_notrap(); + let vtable = ptr.offset(fx, b_offset).load(fx, clif_ty2, flags); + (ptr.get_addr(fx), vtable) + } + CValueInner::ByValPair(data, vtable) => { + let stack_slot = fx.bcx.create_sized_stack_slot(StackSlotData { + kind: StackSlotKind::ExplicitSlot, + // FIXME Don't force the size to a multiple of 16 bytes once Cranelift gets a way to + // specify stack slot alignment. + size: (u32::try_from(fx.target_config.pointer_type().bytes()).unwrap() + 15) + / 16 + * 16, + }); + let data_ptr = Pointer::stack_slot(stack_slot); + let mut flags = MemFlags::new(); + flags.set_notrap(); + data_ptr.store(fx, data, flags); + + (data_ptr.get_addr(fx), vtable) + } + CValueInner::ByRef(_, Some(_)) | CValueInner::ByVal(_) => { + unreachable!("dyn_star_force_data_on_stack({:?})", self) + } + } + } + pub(crate) fn try_to_ptr(self) -> Option<(Pointer, Option)> { match self.0 { CValueInner::ByRef(ptr, meta) => Some((ptr, meta)), From b930e2d7227e8ca198e75fe81345e793b6cec164 Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Sun, 23 Oct 2022 16:16:50 +0200 Subject: [PATCH 97/98] Revert "Stop using a depracated function" This reverts commit b1791eef6add9563c1b750e88ec02e681a9a4ad7. --- src/value_and_place.rs | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/value_and_place.rs b/src/value_and_place.rs index 75f968f3f4b8d..c3dfbd37279f9 100644 --- a/src/value_and_place.rs +++ b/src/value_and_place.rs @@ -392,7 +392,7 @@ impl<'tcx> CPlace<'tcx> { local: Local, layout: TyAndLayout<'tcx>, ) -> CPlace<'tcx> { - let var = Variable::from_u32(fx.next_ssa_var); + let var = Variable::with_u32(fx.next_ssa_var); fx.next_ssa_var += 1; fx.bcx.declare_var(var, fx.clif_type(layout.ty).unwrap()); CPlace { inner: CPlaceInner::Var(local, var), layout } @@ -403,9 +403,9 @@ impl<'tcx> CPlace<'tcx> { local: Local, layout: TyAndLayout<'tcx>, ) -> CPlace<'tcx> { - let var1 = Variable::from_u32(fx.next_ssa_var); + let var1 = Variable::with_u32(fx.next_ssa_var); fx.next_ssa_var += 1; - let var2 = Variable::from_u32(fx.next_ssa_var); + let var2 = Variable::with_u32(fx.next_ssa_var); fx.next_ssa_var += 1; let (ty1, ty2) = fx.clif_pair_type(layout.ty).unwrap(); From 266e96785ab71834b917bf474f130a6d8fdecd4b Mon Sep 17 00:00:00 2001 From: bjorn3 <17426603+bjorn3@users.noreply.github.com> Date: Sun, 23 Oct 2022 16:14:08 +0200 Subject: [PATCH 98/98] Revert "Update to Cranelift 0.89.0" It added a lot of extra dependencies. I opened bytecodealliance/wasmtime#5101 to remove those dependencies again. This reverts commit da770abea31e25514af65387ea93a755242610b7. --- Cargo.lock | 172 ++++++++--------------------------------------------- Cargo.toml | 12 ++-- 2 files changed, 30 insertions(+), 154 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index e55b04352a8fb..3fa9d56cd01a3 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -62,18 +62,18 @@ checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd" [[package]] name = "cranelift-bforest" -version = "0.89.0" +version = "0.88.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "be5e1ee4c22871d24a95196ea7047d58c1d978e46c88037d3d397b3b3e0af360" +checksum = "44409ccf2d0f663920cab563d2b79fcd6b2e9a2bcc6e929fef76c8f82ad6c17a" dependencies = [ "cranelift-entity", ] [[package]] name = "cranelift-codegen" -version = "0.89.0" +version = "0.88.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "70f600a52d59eed56a85f33750873b3b42d61e35ca777cd792369893f9e1f9dd" +checksum = "98de2018ad96eb97f621f7d6b900a0cc661aec8d02ea4a50e56ecb48e5a2fcaf" dependencies = [ "arrayvec", "bumpalo", @@ -91,30 +91,30 @@ dependencies = [ [[package]] name = "cranelift-codegen-meta" -version = "0.89.0" +version = "0.88.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e8418218d0953d73e9b96e9d9ffec56145efa4f18988251530b5872ae4410563" +checksum = "5287ce36e6c4758fbaf298bd1a8697ad97a4f2375a3d1b61142ea538db4877e5" dependencies = [ "cranelift-codegen-shared", ] [[package]] name = "cranelift-codegen-shared" -version = "0.89.0" +version = "0.88.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f01be0cfd40aba59153236ab4b99062131b5bbe6f9f3d4bcb238bd2f96ff5262" +checksum = "2855c24219e2f08827f3f4ffb2da92e134ae8d8ecc185b11ec8f9878cf5f588e" [[package]] name = "cranelift-entity" -version = "0.89.0" +version = "0.88.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ddae4fec5d6859233ffa175b61d269443c473b3971a2c3e69008c8d3e83d5825" +checksum = "0b65673279d75d34bf11af9660ae2dbd1c22e6d28f163f5c72f4e1dc56d56103" [[package]] name = "cranelift-frontend" -version = "0.89.0" +version = "0.88.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f2cc3deb0df97748434cf9f7e404f1f5134f6a253fc9a6bca25c5cd6804c08d3" +checksum = "3ed2b3d7a4751163f6c4a349205ab1b7d9c00eecf19dcea48592ef1f7688eefc" dependencies = [ "cranelift-codegen", "log", @@ -124,18 +124,15 @@ dependencies = [ [[package]] name = "cranelift-isle" -version = "0.89.0" +version = "0.88.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fc3bb54287de9c36ba354eb849fefb77b5e73955058745fd08f12cfdfa181866" -dependencies = [ - "rayon", -] +checksum = "3be64cecea9d90105fc6a2ba2d003e98c867c1d6c4c86cc878f97ad9fb916293" [[package]] name = "cranelift-jit" -version = "0.89.0" +version = "0.88.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e1122619a1f4f857afb3e2ba47bbc1e9c9ee7bce17c9e39f66999e38352773ad" +checksum = "f98ed42a70a0c9c388e34ec9477f57fc7300f541b1e5136a0e2ea02b1fac6015" dependencies = [ "anyhow", "cranelift-codegen", @@ -151,9 +148,9 @@ dependencies = [ [[package]] name = "cranelift-module" -version = "0.89.0" +version = "0.88.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "47605be4eb921bcf84d995a6594477db0790bf8442a6b187815e8e90fad82087" +checksum = "d658ac7f156708bfccb647216cc8b9387469f50d352ba4ad80150541e4ae2d49" dependencies = [ "anyhow", "cranelift-codegen", @@ -161,9 +158,9 @@ dependencies = [ [[package]] name = "cranelift-native" -version = "0.89.0" +version = "0.88.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d8c2a4f2efdce1de1f94e74f12b3b4144e3bcafa6011338b87388325d72d2120" +checksum = "c4a03a6ac1b063e416ca4b93f6247978c991475e8271465340caa6f92f3c16a4" dependencies = [ "cranelift-codegen", "libc", @@ -172,9 +169,9 @@ dependencies = [ [[package]] name = "cranelift-object" -version = "0.89.0" +version = "0.88.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5696c434de314c4b3272e3d8eddb6a13b1e3a907788b484b1ec4d9f4e7d669dc" +checksum = "eef0b4119b645b870a43a036d76c0ada3a076b1f82e8b8487659304c8b09049b" dependencies = [ "anyhow", "cranelift-codegen", @@ -193,61 +190,6 @@ dependencies = [ "cfg-if", ] -[[package]] -name = "crossbeam-channel" -version = "0.5.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c2dd04ddaf88237dc3b8d8f9a3c1004b506b54b3313403944054d23c0870c521" -dependencies = [ - "cfg-if", - "crossbeam-utils", -] - -[[package]] -name = "crossbeam-deque" -version = "0.8.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "715e8152b692bba2d374b53d4875445368fdf21a94751410af607a5ac677d1fc" -dependencies = [ - "cfg-if", - "crossbeam-epoch", - "crossbeam-utils", -] - -[[package]] -name = "crossbeam-epoch" -version = "0.9.11" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f916dfc5d356b0ed9dae65f1db9fc9770aa2851d2662b988ccf4fe3516e86348" -dependencies = [ - "autocfg", - "cfg-if", - "crossbeam-utils", - "memoffset", - "scopeguard", -] - -[[package]] -name = "crossbeam-utils" -version = "0.8.12" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "edbafec5fa1f196ca66527c1b12c2ec4745ca14b50f1ad8f9f6f720b55d11fac" -dependencies = [ - "cfg-if", -] - -[[package]] -name = "either" -version = "1.8.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "90e5c1c8368803113bf0c9584fc495a58b86dc8a29edbf8fe877d21d9507e797" - -[[package]] -name = "fallible-iterator" -version = "0.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4443176a9f2c162692bd3d352d745ef9413eec5782a80d8fd6f8a1ac692a07f7" - [[package]] name = "fxhash" version = "0.2.1" @@ -274,9 +216,7 @@ version = "0.26.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "22030e2c5a68ec659fde1e949a745124b48e6fa8b045b7ed5bd1fe4ccc5c4e5d" dependencies = [ - "fallible-iterator", "indexmap", - "stable_deref_trait", ] [[package]] @@ -288,15 +228,6 @@ dependencies = [ "ahash", ] -[[package]] -name = "hermit-abi" -version = "0.1.19" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "62b467343b94ba476dcb2500d242dadbb39557df889310ac77c5d99100aaac33" -dependencies = [ - "libc", -] - [[package]] name = "indexmap" version = "1.9.1" @@ -347,25 +278,6 @@ version = "2.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "2dffe52ecf27772e601905b7522cb4ef790d2cc203488bbd0e2fe85fcb74566d" -[[package]] -name = "memoffset" -version = "0.6.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5aa361d4faea93603064a027415f07bd8e1d5c88c9fbf68bf56a285428fd79ce" -dependencies = [ - "autocfg", -] - -[[package]] -name = "num_cpus" -version = "1.13.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "19e64526ebdee182341572e50e9ad03965aa510cd94427a4549448f285e957a1" -dependencies = [ - "hermit-abi", - "libc", -] - [[package]] name = "object" version = "0.29.0" @@ -384,35 +296,11 @@ version = "1.13.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "18a6dbe30758c9f83eb00cbea4ac95966305f5a7772f3f42ebfc7fc7eddbd8e1" -[[package]] -name = "rayon" -version = "1.5.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bd99e5772ead8baa5215278c9b15bf92087709e9c1b2d1f97cdb5a183c933a7d" -dependencies = [ - "autocfg", - "crossbeam-deque", - "either", - "rayon-core", -] - -[[package]] -name = "rayon-core" -version = "1.9.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "258bcdb5ac6dad48491bb2992db6b7cf74878b0384908af124823d118c99683f" -dependencies = [ - "crossbeam-channel", - "crossbeam-deque", - "crossbeam-utils", - "num_cpus", -] - [[package]] name = "regalloc2" -version = "0.4.1" +version = "0.3.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "69025b4a161879ba90719837c06621c3d73cffa147a000aeacf458f6a9572485" +checksum = "d43a209257d978ef079f3d446331d0f1794f5e0fc19b306a199983857833a779" dependencies = [ "fxhash", "log", @@ -452,12 +340,6 @@ dependencies = [ "target-lexicon", ] -[[package]] -name = "scopeguard" -version = "1.1.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d29ab0c6d3fc0ee92fe66e2d99f700eab17a8d57d1c1d3b748380fb20baa78cd" - [[package]] name = "slice-group-by" version = "0.3.0" @@ -470,12 +352,6 @@ version = "1.9.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "2fd0db749597d91ff862fd1d55ea87f7855a744a8425a64695b6fca237d1dad1" -[[package]] -name = "stable_deref_trait" -version = "1.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a8f112729512f8e442d81f95a8a7ddf2b7c6b8a1a6f509a95864142b30cab2d3" - [[package]] name = "target-lexicon" version = "0.12.4" diff --git a/Cargo.toml b/Cargo.toml index 20b70ed2fb8bd..09cf5b4a1edd8 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -8,12 +8,12 @@ crate-type = ["dylib"] [dependencies] # These have to be in sync with each other -cranelift-codegen = { version = "0.89", features = ["unwind", "all-arch"] } -cranelift-frontend = "0.89" -cranelift-module = "0.89" -cranelift-native = "0.89" -cranelift-jit = { version = "0.89", optional = true } -cranelift-object = "0.89" +cranelift-codegen = { version = "0.88.1", features = ["unwind", "all-arch"] } +cranelift-frontend = "0.88.1" +cranelift-module = "0.88.1" +cranelift-native = "0.88.1" +cranelift-jit = { version = "0.88.1", optional = true } +cranelift-object = "0.88.1" target-lexicon = "0.12.0" gimli = { version = "0.26.0", default-features = false, features = ["write"]} object = { version = "0.29.0", default-features = false, features = ["std", "read_core", "write", "archive", "coff", "elf", "macho", "pe"] }