Skip to content

Commit 569d7e3

Browse files
committed
Auto merge of #128456 - Oneirical:clantestine-operations, r=jieyouxu
Migrate `reproducible-build` `run-make` test to rmake Part of #121876 and the associated [Google Summer of Code project](https://blog.rust-lang.org/2024/05/01/gsoc-2024-selected-projects.html). This will likely fail. Locally, rustc errors with `linker 'linker' not found` on line 36 while the file exists according to the dir-debug statement before it. If this gets fixed and the test passes, further developments may include: - [x] There may be some leftovers from each test - `test_in_tmpdir` may therefore be required. - [ ] Try jobs on all ignored architectures. - [x] A potential refactor with a struct and a custom function like #128410 so this isn't just a huge stream of `rfs` and `rustc`. This is a little bit harder to do in this test considering the variability present in each test case. // try-job: x86_64-msvc // windows jobs passed in a prior run // try-job: x86_64-mingw // try-job: i686-msvc // try-job: i686-mingw try-job: aarch64-apple try-job: aarch64-gnu try-job: armhf-gnu try-job: test-various try-job: dist-various-1
2 parents a73bc4a + e752410 commit 569d7e3

File tree

3 files changed

+240
-141
lines changed

3 files changed

+240
-141
lines changed

Diff for: src/tools/tidy/src/allowed_run_make_makefiles.txt

-1
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,6 @@ run-make/jobserver-error/Makefile
88
run-make/libs-through-symlinks/Makefile
99
run-make/libtest-thread-limit/Makefile
1010
run-make/macos-deployment-target/Makefile
11-
run-make/reproducible-build/Makefile
1211
run-make/split-debuginfo/Makefile
1312
run-make/symbol-mangling-hashed/Makefile
1413
run-make/translation/Makefile

Diff for: tests/run-make/reproducible-build/Makefile

-140
This file was deleted.

Diff for: tests/run-make/reproducible-build/rmake.rs

+240
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,240 @@
1+
// This test case makes sure that two identical invocations of the compiler
2+
// (i.e. same code base, same compile-flags, same compiler-versions, etc.)
3+
// produce the same output. In the past, symbol names of monomorphized functions
4+
// were not deterministic (which we want to avoid).
5+
//
6+
// The test tries to exercise as many different paths into symbol name
7+
// generation as possible:
8+
//
9+
// - regular functions
10+
// - generic functions
11+
// - methods
12+
// - statics
13+
// - closures
14+
// - enum variant constructors
15+
// - tuple struct constructors
16+
// - drop glue
17+
// - FnOnce adapters
18+
// - Trait object shims
19+
// - Fn Pointer shims
20+
// See https://github.com/rust-lang/rust/pull/32293
21+
// Tracking Issue: https://github.com/rust-lang/rust/issues/129080
22+
23+
use run_make_support::{
24+
bin_name, cwd, diff, is_darwin, is_windows, rfs, run_in_tmpdir, rust_lib_name, rustc,
25+
};
26+
27+
fn main() {
28+
// Smoke tests. Simple flags, build should be reproducible.
29+
eprintln!("smoke_test => None");
30+
smoke_test(None);
31+
eprintln!("smoke_test => SmokeFlag::Debug");
32+
smoke_test(Some(SmokeFlag::Debug));
33+
eprintln!("smoke_test => SmokeFlag::Opt");
34+
smoke_test(Some(SmokeFlag::Opt));
35+
36+
// Builds should be reproducible even through custom library search paths
37+
// or remap path prefixes.
38+
eprintln!("paths_test => PathsFlag::Link");
39+
paths_test(PathsFlag::Link);
40+
eprintln!("paths_test => PathsFlag::Remap");
41+
paths_test(PathsFlag::Remap);
42+
43+
// Builds should be reproducible even if each build is done in a different directory,
44+
// with both --remap-path-prefix and -Z remap-cwd-prefix.
45+
46+
// FIXME(Oneirical): Building with crate type set to `bin` AND having -Cdebuginfo=2
47+
// (or `-g`, the shorthand form) enabled will cause reproducibility failures.
48+
// See https://github.com/rust-lang/rust/issues/89911
49+
50+
if !is_darwin() && !is_windows() {
51+
// FIXME(Oneirical): Bin builds are not reproducible on non-Linux targets.
52+
eprintln!("diff_dir_test => Bin, Path");
53+
diff_dir_test(CrateType::Bin, RemapType::Path);
54+
}
55+
56+
eprintln!("diff_dir_test => Rlib, Path");
57+
diff_dir_test(CrateType::Rlib, RemapType::Path);
58+
59+
// FIXME(Oneirical): This specific case would fail on Linux, should -Cdebuginfo=2
60+
// be added.
61+
// FIXME(Oneirical): Bin builds are not reproducible on non-Linux targets.
62+
// See https://github.com/rust-lang/rust/issues/89911
63+
if !is_darwin() && !is_windows() {
64+
eprintln!("diff_dir_test => Bin, Cwd false");
65+
diff_dir_test(CrateType::Bin, RemapType::Cwd { is_empty: false });
66+
}
67+
68+
eprintln!("diff_dir_test => Rlib, Cwd false");
69+
diff_dir_test(CrateType::Rlib, RemapType::Cwd { is_empty: false });
70+
eprintln!("diff_dir_test => Rlib, Cwd true");
71+
diff_dir_test(CrateType::Rlib, RemapType::Cwd { is_empty: true });
72+
73+
eprintln!("final extern test");
74+
// Builds should be reproducible when using the --extern flag.
75+
run_in_tmpdir(|| {
76+
rustc().input("reproducible-build-aux.rs").run();
77+
rustc()
78+
.input("reproducible-build.rs")
79+
.crate_type("rlib")
80+
.extern_("reproducible_build_aux", rust_lib_name("reproducible_build_aux"))
81+
.run();
82+
rfs::copy(rust_lib_name("reproducible_build"), rust_lib_name("foo"));
83+
rfs::copy(rust_lib_name("reproducible_build_aux"), rust_lib_name("bar"));
84+
rustc()
85+
.input("reproducible-build.rs")
86+
.crate_type("rlib")
87+
.extern_("reproducible_build_aux", rust_lib_name("bar"))
88+
.run();
89+
assert!(rfs::read(rust_lib_name("foo")) == rfs::read(rust_lib_name("reproducible_build")))
90+
});
91+
}
92+
93+
#[track_caller]
94+
fn smoke_test(flag: Option<SmokeFlag>) {
95+
run_in_tmpdir(|| {
96+
rustc().input("linker.rs").opt().run();
97+
rustc().input("reproducible-build-aux.rs").run();
98+
let mut compiler1 = rustc();
99+
let mut compiler2 = rustc();
100+
if let Some(flag) = flag {
101+
match flag {
102+
SmokeFlag::Debug => {
103+
compiler1.arg("-g");
104+
compiler2.arg("-g");
105+
}
106+
SmokeFlag::Opt => {
107+
compiler1.opt();
108+
compiler2.opt();
109+
}
110+
};
111+
};
112+
compiler1
113+
.input("reproducible-build.rs")
114+
.linker(&cwd().join(bin_name("linker")).display().to_string())
115+
.run();
116+
compiler2
117+
.input("reproducible-build.rs")
118+
.linker(&cwd().join(bin_name("linker")).display().to_string())
119+
.run();
120+
diff().actual_file("linker-arguments1").expected_file("linker-arguments2").run();
121+
});
122+
}
123+
124+
#[track_caller]
125+
fn paths_test(flag: PathsFlag) {
126+
run_in_tmpdir(|| {
127+
rustc().input("reproducible-build-aux.rs").run();
128+
let mut compiler1 = rustc();
129+
let mut compiler2 = rustc();
130+
match flag {
131+
PathsFlag::Link => {
132+
compiler1.library_search_path("a");
133+
compiler2.library_search_path("b");
134+
}
135+
PathsFlag::Remap => {
136+
compiler1.arg("--remap-path-prefix=/a=/c");
137+
compiler2.arg("--remap-path-prefix=/b=/c");
138+
}
139+
}
140+
compiler1.input("reproducible-build.rs").crate_type("rlib").run();
141+
rfs::rename(rust_lib_name("reproducible_build"), rust_lib_name("foo"));
142+
compiler2.input("reproducible-build.rs").crate_type("rlib").run();
143+
assert!(rfs::read(rust_lib_name("foo")) == rfs::read(rust_lib_name("reproducible_build")))
144+
});
145+
}
146+
147+
#[track_caller]
148+
fn diff_dir_test(crate_type: CrateType, remap_type: RemapType) {
149+
run_in_tmpdir(|| {
150+
let base_dir = cwd();
151+
rustc().input("reproducible-build-aux.rs").run();
152+
rfs::create_dir("test");
153+
rfs::copy("reproducible-build.rs", "test/reproducible-build.rs");
154+
let mut compiler1 = rustc();
155+
let mut compiler2 = rustc();
156+
match crate_type {
157+
CrateType::Bin => {
158+
compiler1.crate_type("bin");
159+
compiler2.crate_type("bin");
160+
}
161+
CrateType::Rlib => {
162+
compiler1.crate_type("rlib");
163+
compiler2.crate_type("rlib");
164+
}
165+
}
166+
match remap_type {
167+
RemapType::Path => {
168+
compiler1.arg(&format!("--remap-path-prefix={}=/b", cwd().display()));
169+
compiler2
170+
.arg(format!("--remap-path-prefix={}=/b", base_dir.join("test").display()));
171+
}
172+
RemapType::Cwd { is_empty } => {
173+
// FIXME(Oneirical): Building with crate type set to `bin` AND having -Cdebuginfo=2
174+
// (or `-g`, the shorthand form) enabled will cause reproducibility failures
175+
// for multiple platforms.
176+
// See https://github.com/rust-lang/rust/issues/89911
177+
// FIXME(#129117): Windows rlib + `-Cdebuginfo=2` + `-Z remap-cwd-prefix=.` seems
178+
// to be unreproducible.
179+
if !matches!(crate_type, CrateType::Bin) && !is_windows() {
180+
compiler1.arg("-Cdebuginfo=2");
181+
compiler2.arg("-Cdebuginfo=2");
182+
}
183+
if is_empty {
184+
compiler1.arg("-Zremap-cwd-prefix=");
185+
compiler2.arg("-Zremap-cwd-prefix=");
186+
} else {
187+
compiler1.arg("-Zremap-cwd-prefix=.");
188+
compiler2.arg("-Zremap-cwd-prefix=.");
189+
}
190+
}
191+
}
192+
compiler1.input("reproducible-build.rs").run();
193+
match crate_type {
194+
CrateType::Bin => {
195+
rfs::rename(bin_name("reproducible-build"), bin_name("foo"));
196+
}
197+
CrateType::Rlib => {
198+
rfs::rename(rust_lib_name("reproducible_build"), rust_lib_name("foo"));
199+
}
200+
}
201+
std::env::set_current_dir("test").unwrap();
202+
compiler2
203+
.input("reproducible-build.rs")
204+
.library_search_path(&base_dir)
205+
.out_dir(&base_dir)
206+
.run();
207+
std::env::set_current_dir(&base_dir).unwrap();
208+
match crate_type {
209+
CrateType::Bin => {
210+
assert!(rfs::read(bin_name("reproducible-build")) == rfs::read(bin_name("foo")));
211+
}
212+
CrateType::Rlib => {
213+
assert!(
214+
rfs::read(rust_lib_name("foo"))
215+
== rfs::read(rust_lib_name("reproducible_build"))
216+
);
217+
}
218+
}
219+
});
220+
}
221+
222+
enum SmokeFlag {
223+
Debug,
224+
Opt,
225+
}
226+
227+
enum PathsFlag {
228+
Link,
229+
Remap,
230+
}
231+
232+
enum CrateType {
233+
Bin,
234+
Rlib,
235+
}
236+
237+
enum RemapType {
238+
Path,
239+
Cwd { is_empty: bool },
240+
}

0 commit comments

Comments
 (0)