Skip to content

Commit 9906de2

Browse files
committed
Make build compiler explicit in check::Rustc and check::Std
1 parent 50e5599 commit 9906de2

File tree

3 files changed

+87
-73
lines changed

3 files changed

+87
-73
lines changed

src/bootstrap/src/core/build_steps/check.rs

Lines changed: 56 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,7 @@
11
//! Implementation of compiling the compiler and standard library, in "check"-based modes.
22
3+
use build_helper::exit;
4+
35
use crate::core::build_steps::compile::{
46
add_to_sysroot, run_cargo, rustc_cargo, rustc_cargo_env, std_cargo, std_crates_for_run_make,
57
};
@@ -9,10 +11,12 @@ use crate::core::builder::{
911
};
1012
use crate::core::config::TargetSelection;
1113
use crate::utils::build_stamp::{self, BuildStamp};
12-
use crate::{Mode, Subcommand};
14+
use crate::{Compiler, Mode, Subcommand};
1315

1416
#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1517
pub struct Std {
18+
/// Compiler that will check this std.
19+
pub build_compiler: Compiler,
1620
pub target: TargetSelection,
1721
/// Whether to build only a subset of crates.
1822
///
@@ -25,8 +29,8 @@ pub struct Std {
2529
impl Std {
2630
const CRATE_OR_DEPS: &[&str] = &["sysroot", "coretests", "alloctests"];
2731

28-
pub fn new(target: TargetSelection) -> Self {
29-
Self { target, crates: vec![] }
32+
pub fn new(build_compiler: Compiler, target: TargetSelection) -> Self {
33+
Self { build_compiler, target, crates: vec![] }
3034
}
3135
}
3236

@@ -45,7 +49,11 @@ impl Step for Std {
4549

4650
fn make_run(run: RunConfig<'_>) {
4751
let crates = std_crates_for_run_make(&run);
48-
run.builder.ensure(Std { target: run.target, crates });
52+
run.builder.ensure(Std {
53+
build_compiler: run.builder.compiler(run.builder.top_stage, run.target),
54+
target: run.target,
55+
crates,
56+
});
4957
}
5058

5159
fn run(self, builder: &Builder<'_>) {
@@ -56,9 +64,9 @@ impl Step for Std {
5664
return;
5765
}
5866

59-
let stage = builder.top_stage;
67+
let build_compiler = self.build_compiler;
68+
let stage = build_compiler.stage;
6069
let target = self.target;
61-
let build_compiler = builder.compiler(stage, builder.config.host_target);
6270

6371
let mut cargo = builder::Cargo::new(
6472
builder,
@@ -69,7 +77,7 @@ impl Step for Std {
6977
Kind::Check,
7078
);
7179

72-
std_cargo(builder, target, build_compiler.stage, &mut cargo);
80+
std_cargo(builder, target, stage, &mut cargo);
7381
if matches!(builder.config.cmd, Subcommand::Fix) {
7482
// By default, cargo tries to fix all targets. Tell it not to fix tests until we've added `test` to the sysroot.
7583
cargo.arg("--lib");
@@ -126,12 +134,21 @@ impl Step for Std {
126134
}
127135

128136
fn metadata(&self) -> Option<StepMetadata> {
129-
Some(StepMetadata::check("std", self.target))
137+
Some(StepMetadata::check("std", self.target).built_by(self.build_compiler))
130138
}
131139
}
132140

141+
fn default_compiler_for_checking_rustc(builder: &Builder<'_>) -> Compiler {
142+
// When checking the stage N compiler, we want to do it with the stage N-1 compiler,
143+
builder.compiler(builder.top_stage - 1, builder.config.host_target)
144+
}
145+
146+
/// Checks rustc using `build_compiler` and copies the built
147+
/// .rmeta files into the sysroot of `build_copoiler`.
133148
#[derive(Debug, Clone, PartialEq, Eq, Hash)]
134149
pub struct Rustc {
150+
/// Compiler that will check this rustc.
151+
pub build_compiler: Compiler,
135152
pub target: TargetSelection,
136153
/// Whether to build only a subset of crates.
137154
///
@@ -142,13 +159,13 @@ pub struct Rustc {
142159
}
143160

144161
impl Rustc {
145-
pub fn new(target: TargetSelection, builder: &Builder<'_>) -> Self {
162+
pub fn new(builder: &Builder<'_>, build_compiler: Compiler, target: TargetSelection) -> Self {
146163
let crates = builder
147164
.in_tree_crates("rustc-main", Some(target))
148165
.into_iter()
149166
.map(|krate| krate.name.to_string())
150167
.collect();
151-
Self { target, crates }
168+
Self { build_compiler, target, crates }
152169
}
153170
}
154171

@@ -163,40 +180,46 @@ impl Step for Rustc {
163180

164181
fn make_run(run: RunConfig<'_>) {
165182
let crates = run.make_run_crates(Alias::Compiler);
166-
run.builder.ensure(Rustc { target: run.target, crates });
183+
run.builder.ensure(Rustc {
184+
target: run.target,
185+
build_compiler: default_compiler_for_checking_rustc(run.builder),
186+
crates,
187+
});
167188
}
168189

169-
/// Builds the compiler.
190+
/// Check the compiler.
170191
///
171-
/// This will build the compiler for a particular stage of the build using
192+
/// This will check the compiler for a particular stage of the build using
172193
/// the `compiler` targeting the `target` architecture. The artifacts
173194
/// created will also be linked into the sysroot directory.
174195
fn run(self, builder: &Builder<'_>) {
175-
let compiler = builder.compiler(builder.top_stage, builder.config.host_target);
196+
if builder.top_stage < 2 && builder.config.host_target != self.target {
197+
eprintln!("Cannot do a cross-compilation check on stage 1, use stage 2");
198+
exit!(1);
199+
}
200+
201+
let build_compiler = self.build_compiler;
176202
let target = self.target;
177203

178-
if compiler.stage != 0 {
179-
// If we're not in stage 0, then we won't have a std from the beta
180-
// compiler around. That means we need to make sure there's one in
181-
// the sysroot for the compiler to find. Otherwise, we're going to
182-
// fail when building crates that need to generate code (e.g., build
183-
// scripts and their dependencies).
184-
builder.std(compiler, compiler.host);
185-
builder.std(compiler, target);
186-
} else {
187-
builder.ensure(Std::new(target));
188-
}
204+
// Build host std for compiling build scripts
205+
builder.std(build_compiler, build_compiler.host);
206+
207+
// Build target std so that the checked rustc can link to it during the check
208+
// FIXME: maybe we can a way to only do a check of std here?
209+
// But for that we would have to copy the stdlib rmetas to the sysroot of the build
210+
// compiler, which conflicts with std rlibs, if we also build std.
211+
builder.std(build_compiler, target);
189212

190213
let mut cargo = builder::Cargo::new(
191214
builder,
192-
compiler,
215+
build_compiler,
193216
Mode::Rustc,
194217
SourceType::InTree,
195218
target,
196219
Kind::Check,
197220
);
198221

199-
rustc_cargo(builder, &mut cargo, target, &compiler, &self.crates);
222+
rustc_cargo(builder, &mut cargo, target, &build_compiler, &self.crates);
200223

201224
// Explicitly pass -p for all compiler crates -- this will force cargo
202225
// to also check the tests/benches/examples for these crates, rather
@@ -211,17 +234,18 @@ impl Step for Rustc {
211234
None,
212235
);
213236

214-
let stamp = build_stamp::librustc_stamp(builder, compiler, target).with_prefix("check");
237+
let stamp =
238+
build_stamp::librustc_stamp(builder, build_compiler, target).with_prefix("check");
215239

216240
run_cargo(builder, cargo, builder.config.free_args.clone(), &stamp, vec![], true, false);
217241

218-
let libdir = builder.sysroot_target_libdir(compiler, target);
219-
let hostdir = builder.sysroot_target_libdir(compiler, compiler.host);
242+
let libdir = builder.sysroot_target_libdir(build_compiler, target);
243+
let hostdir = builder.sysroot_target_libdir(build_compiler, build_compiler.host);
220244
add_to_sysroot(builder, &libdir, &hostdir, &stamp);
221245
}
222246

223247
fn metadata(&self) -> Option<StepMetadata> {
224-
Some(StepMetadata::check("rustc", self.target))
248+
Some(StepMetadata::check("rustc", self.target).built_by(self.build_compiler))
225249
}
226250
}
227251

@@ -462,7 +486,7 @@ fn run_tool_check_step(
462486
let display_name = path.rsplit('/').next().unwrap();
463487
let compiler = builder.compiler(builder.top_stage, builder.config.host_target);
464488

465-
builder.ensure(Rustc::new(target, builder));
489+
builder.ensure(Rustc::new(builder, compiler, target));
466490

467491
let mut cargo = prepare_tool_cargo(
468492
builder,

src/bootstrap/src/core/build_steps/clippy.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -215,7 +215,7 @@ impl Step for Rustc {
215215
builder.std(compiler, compiler.host);
216216
builder.std(compiler, target);
217217
} else {
218-
builder.ensure(check::Std::new(target));
218+
builder.ensure(check::Std::new(compiler, target));
219219
}
220220
}
221221

@@ -287,7 +287,7 @@ macro_rules! lint_any {
287287
let target = self.target;
288288

289289
if !builder.download_rustc() {
290-
builder.ensure(check::Rustc::new(target, builder));
290+
builder.ensure(check::Rustc::new(builder, compiler, target));
291291
};
292292

293293
let cargo = prepare_tool_cargo(

src/bootstrap/src/core/builder/tests.rs

Lines changed: 29 additions & 39 deletions
Original file line numberDiff line numberDiff line change
@@ -1240,24 +1240,21 @@ mod snapshot {
12401240
ctx.config("check")
12411241
.path("compiler")
12421242
.render_steps(), @r"
1243-
[check] std <host>
12441243
[build] llvm <host>
1245-
[check] rustc <host>
1246-
[check] cranelift <host>
1247-
[check] gcc <host>
1244+
[check] rustc 0 <host> -> rustc 1 <host>
12481245
");
12491246

12501247
insta::assert_snapshot!(
12511248
ctx.config("check")
12521249
.path("rustc")
12531250
.render_steps(), @r"
1254-
[check] std <host>
12551251
[build] llvm <host>
1256-
[check] rustc <host>
1252+
[check] rustc 0 <host> -> rustc 1 <host>
12571253
");
12581254
}
12591255

12601256
#[test]
1257+
#[should_panic]
12611258
fn check_compiler_stage_0() {
12621259
let ctx = TestCtx::new();
12631260
ctx.config("check").path("compiler").stage(0).run();
@@ -1272,11 +1269,7 @@ mod snapshot {
12721269
.stage(1)
12731270
.render_steps(), @r"
12741271
[build] llvm <host>
1275-
[build] rustc 0 <host> -> rustc 1 <host>
1276-
[build] rustc 1 <host> -> std 1 <host>
1277-
[check] rustc <host>
1278-
[check] cranelift <host>
1279-
[check] gcc <host>
1272+
[check] rustc 0 <host> -> rustc 1 <host>
12801273
");
12811274
}
12821275

@@ -1291,11 +1284,7 @@ mod snapshot {
12911284
[build] llvm <host>
12921285
[build] rustc 0 <host> -> rustc 1 <host>
12931286
[build] rustc 1 <host> -> std 1 <host>
1294-
[build] rustc 1 <host> -> rustc 2 <host>
1295-
[build] rustc 2 <host> -> std 2 <host>
1296-
[check] rustc <host>
1297-
[check] cranelift <host>
1298-
[check] gcc <host>
1287+
[check] rustc 1 <host> -> rustc 2 <host>
12991288
");
13001289
}
13011290

@@ -1311,23 +1300,24 @@ mod snapshot {
13111300
[build] llvm <host>
13121301
[build] rustc 0 <host> -> rustc 1 <host>
13131302
[build] rustc 1 <host> -> std 1 <host>
1303+
[build] rustc 1 <host> -> std 1 <target1>
1304+
[build] llvm <target1>
1305+
[check] rustc 1 <host> -> rustc 2 <target1>
1306+
[check] rustc 1 <host> -> Rustdoc 2 <target1>
1307+
[check] rustc 1 <host> -> cranelift 2 <target1>
1308+
[check] rustc 1 <host> -> gcc 2 <target1>
1309+
[check] rustc 1 <host> -> Clippy 2 <target1>
1310+
[check] rustc 1 <host> -> Miri 2 <target1>
1311+
[check] rustc 1 <host> -> CargoMiri 2 <target1>
1312+
[check] rustc 0 <host> -> MiroptTestTools 1 <target1>
1313+
[check] rustc 1 <host> -> Rustfmt 2 <target1>
1314+
[check] rustc 1 <host> -> rust-analyzer 2 <target1>
13141315
[build] rustc 1 <host> -> rustc 2 <host>
13151316
[build] rustc 2 <host> -> std 2 <host>
1316-
[build] rustc 1 <host> -> std 1 <target1>
13171317
[build] rustc 2 <host> -> std 2 <target1>
1318-
[check] rustc <target1>
1319-
[check] Rustdoc <target1>
1320-
[check] cranelift <target1>
1321-
[check] gcc <target1>
1322-
[check] Clippy <target1>
1323-
[check] Miri <target1>
1324-
[check] CargoMiri <target1>
1325-
[check] MiroptTestTools <target1>
1326-
[check] Rustfmt <target1>
1327-
[check] rust-analyzer <target1>
1328-
[check] TestFloatParse <target1>
1329-
[check] FeaturesStatusDump <target1>
1330-
[check] std <target1>
1318+
[check] rustc 2 <host> -> TestFloatParse 3 <target1>
1319+
[check] rustc 0 <host> -> FeaturesStatusDump 1 <target1>
1320+
[check] rustc 2 <host> -> std 2 <target1>
13311321
");
13321322
}
13331323

@@ -1340,11 +1330,12 @@ mod snapshot {
13401330
.render_steps(), @r"
13411331
[build] llvm <host>
13421332
[build] rustc 0 <host> -> rustc 1 <host>
1343-
[check] std <host>
1333+
[check] rustc 1 <host> -> std 1 <host>
13441334
");
13451335
}
13461336

13471337
#[test]
1338+
#[should_panic]
13481339
fn check_library_stage_0() {
13491340
let ctx = TestCtx::new();
13501341
ctx.config("check").path("library").stage(0).run();
@@ -1360,7 +1351,7 @@ mod snapshot {
13601351
.render_steps(), @r"
13611352
[build] llvm <host>
13621353
[build] rustc 0 <host> -> rustc 1 <host>
1363-
[check] std <host>
1354+
[check] rustc 1 <host> -> std 1 <host>
13641355
");
13651356
}
13661357

@@ -1376,7 +1367,7 @@ mod snapshot {
13761367
[build] rustc 0 <host> -> rustc 1 <host>
13771368
[build] rustc 1 <host> -> std 1 <host>
13781369
[build] rustc 1 <host> -> rustc 2 <host>
1379-
[check] std <host>
1370+
[check] rustc 2 <host> -> std 2 <host>
13801371
");
13811372
}
13821373

@@ -1402,14 +1393,15 @@ mod snapshot {
14021393
ctx.config("check")
14031394
.path("miri")
14041395
.render_steps(), @r"
1405-
[check] std <host>
14061396
[build] llvm <host>
1407-
[check] rustc <host>
1397+
[build] rustc 0 <host> -> rustc 1 <host>
1398+
[check] rustc 0 <host> -> rustc 1 <host>
14081399
[check] Miri <host>
14091400
");
14101401
}
14111402

14121403
#[test]
1404+
#[should_panic]
14131405
fn check_miri_stage_0() {
14141406
let ctx = TestCtx::new();
14151407
ctx.config("check").path("miri").stage(0).run();
@@ -1425,8 +1417,7 @@ mod snapshot {
14251417
.render_steps(), @r"
14261418
[build] llvm <host>
14271419
[build] rustc 0 <host> -> rustc 1 <host>
1428-
[build] rustc 1 <host> -> std 1 <host>
1429-
[check] rustc <host>
1420+
[check] rustc 0 <host> -> rustc 1 <host>
14301421
[check] Miri <host>
14311422
");
14321423
}
@@ -1443,8 +1434,7 @@ mod snapshot {
14431434
[build] rustc 0 <host> -> rustc 1 <host>
14441435
[build] rustc 1 <host> -> std 1 <host>
14451436
[build] rustc 1 <host> -> rustc 2 <host>
1446-
[build] rustc 2 <host> -> std 2 <host>
1447-
[check] rustc <host>
1437+
[check] rustc 1 <host> -> rustc 2 <host>
14481438
[check] Miri <host>
14491439
");
14501440
}

0 commit comments

Comments
 (0)