Skip to content

Commit acd245b

Browse files
committed
Fix Clippy staging for compiler
1 parent 0e97526 commit acd245b

File tree

5 files changed

+87
-56
lines changed

5 files changed

+87
-56
lines changed

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

Lines changed: 1 addition & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -30,10 +30,6 @@ pub struct Std {
3030

3131
impl Std {
3232
const CRATE_OR_DEPS: &[&str] = &["sysroot", "coretests", "alloctests"];
33-
34-
pub fn new(build_compiler: Compiler, target: TargetSelection) -> Self {
35-
Self { build_compiler, target, crates: vec![] }
36-
}
3733
}
3834

3935
impl Step for Std {
@@ -232,7 +228,7 @@ impl Step for Rustc {
232228
}
233229

234230
/// Prepares a compiler that will check something with the given `mode`.
235-
fn prepare_compiler_for_check(
231+
pub fn prepare_compiler_for_check(
236232
builder: &Builder<'_>,
237233
target: TargetSelection,
238234
mode: Mode,

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

Lines changed: 49 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,27 @@
11
//! Implementation of running clippy on the compiler, standard library and various tools.
2+
//!
3+
//! This serves a double purpose:
4+
//! - The first is to run Clippy itself on in-tree code, in order to test and dogfood it.
5+
//! - The second is to actually lint the in-tree codebase on CI, with a hard-coded set of rules,
6+
//! which is performed by the `x clippy ci` command.
7+
//!
8+
//! In order to prepare a build compiler for running clippy, use the
9+
//! `check::prepare_compiler_for_check` function. That prepares a compiler and a standard library
10+
//! for running Clippy. The second part (actually building Clippy) is performed inside
11+
//! [Builder::cargo_clippy_cmd]. It would be nice if this was more explicit, and we actually had
12+
//! to pass a prebuilt Clippy from the outside when running `cargo clippy`, but that would be
13+
//! (as usual) a massive undertaking/refactoring.
214
315
use super::check;
416
use super::compile::{run_cargo, rustc_cargo, std_cargo};
517
use super::tool::{RustcPrivateCompilers, SourceType, prepare_tool_cargo};
618
use crate::builder::{Builder, ShouldRun};
19+
use crate::core::build_steps::check::prepare_compiler_for_check;
720
use crate::core::build_steps::compile::std_crates_for_run_make;
821
use crate::core::builder;
922
use crate::core::builder::{Alias, Kind, RunConfig, Step, StepMetadata, crate_description};
1023
use crate::utils::build_stamp::{self, BuildStamp};
11-
use crate::{Mode, Subcommand, TargetSelection};
24+
use crate::{Compiler, Mode, Subcommand, TargetSelection};
1225

1326
/// Disable the most spammy clippy lints
1427
const IGNORED_RULES_FOR_STD_AND_RUSTC: &[&str] = &[
@@ -179,14 +192,35 @@ impl Step for Std {
179192
}
180193
}
181194

195+
/// Lints the compiler.
196+
///
197+
/// This will build Clippy with the `build_compiler` and use it to lint
198+
/// in-tree rustc.
182199
#[derive(Debug, Clone, PartialEq, Eq, Hash)]
183200
pub struct Rustc {
184-
pub target: TargetSelection,
201+
build_compiler: Compiler,
202+
target: TargetSelection,
185203
config: LintConfig,
186204
/// Whether to lint only a subset of crates.
187205
crates: Vec<String>,
188206
}
189207

208+
impl Rustc {
209+
fn new(
210+
builder: &Builder<'_>,
211+
target: TargetSelection,
212+
config: LintConfig,
213+
crates: Vec<String>,
214+
) -> Self {
215+
Self {
216+
build_compiler: prepare_compiler_for_check(builder, target, Mode::Rustc),
217+
target,
218+
config,
219+
crates,
220+
}
221+
}
222+
}
223+
190224
impl Step for Rustc {
191225
type Output = ();
192226
const ONLY_HOSTS: bool = true;
@@ -197,43 +231,26 @@ impl Step for Rustc {
197231
}
198232

199233
fn make_run(run: RunConfig<'_>) {
234+
let builder = run.builder;
200235
let crates = run.make_run_crates(Alias::Compiler);
201236
let config = LintConfig::new(run.builder);
202-
run.builder.ensure(Rustc { target: run.target, config, crates });
237+
run.builder.ensure(Rustc::new(builder, run.target, config, crates));
203238
}
204239

205-
/// Lints the compiler.
206-
///
207-
/// This will lint the compiler for a particular stage of the build using
208-
/// the `compiler` targeting the `target` architecture.
209240
fn run(self, builder: &Builder<'_>) {
210-
let compiler = builder.compiler(builder.top_stage, builder.config.host_target);
241+
let build_compiler = self.build_compiler;
211242
let target = self.target;
212243

213-
if !builder.download_rustc() {
214-
if compiler.stage != 0 {
215-
// If we're not in stage 0, then we won't have a std from the beta
216-
// compiler around. That means we need to make sure there's one in
217-
// the sysroot for the compiler to find. Otherwise, we're going to
218-
// fail when building crates that need to generate code (e.g., build
219-
// scripts and their dependencies).
220-
builder.std(compiler, compiler.host);
221-
builder.std(compiler, target);
222-
} else {
223-
builder.ensure(check::Std::new(compiler, target));
224-
}
225-
}
226-
227244
let mut cargo = builder::Cargo::new(
228245
builder,
229-
compiler,
246+
build_compiler,
230247
Mode::Rustc,
231248
SourceType::InTree,
232249
target,
233250
Kind::Clippy,
234251
);
235252

236-
rustc_cargo(builder, &mut cargo, target, &compiler, &self.crates);
253+
rustc_cargo(builder, &mut cargo, target, &self.build_compiler, &self.crates);
237254

238255
// Explicitly pass -p for all compiler crates -- this will force cargo
239256
// to also lint the tests/benches/examples for these crates, rather
@@ -249,15 +266,15 @@ impl Step for Rustc {
249266
builder,
250267
cargo,
251268
lint_args(builder, &self.config, IGNORED_RULES_FOR_STD_AND_RUSTC),
252-
&build_stamp::librustc_stamp(builder, compiler, target),
269+
&build_stamp::librustc_stamp(builder, build_compiler, target),
253270
vec![],
254271
true,
255272
false,
256273
);
257274
}
258275

259276
fn metadata(&self) -> Option<StepMetadata> {
260-
Some(StepMetadata::clippy("rustc", self.target))
277+
Some(StepMetadata::clippy("rustc", self.target).built_by(self.build_compiler))
261278
}
262279
}
263280

@@ -515,11 +532,12 @@ impl Step for CI {
515532
],
516533
forbid: vec![],
517534
};
518-
builder.ensure(Rustc {
519-
target: self.target,
520-
config: self.config.merge(&compiler_clippy_cfg),
521-
crates: vec![],
522-
});
535+
builder.ensure(Rustc::new(
536+
builder,
537+
self.target,
538+
self.config.merge(&compiler_clippy_cfg),
539+
vec![],
540+
));
523541

524542
let rustc_codegen_gcc = LintConfig {
525543
allow: vec![],

src/bootstrap/src/core/builder/mod.rs

Lines changed: 10 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1556,8 +1556,10 @@ You have to build a stage1 compiler for `{}` first, and then use it to build a s
15561556
self.ensure(tool::Rustdoc { target_compiler })
15571557
}
15581558

1559-
pub fn cargo_clippy_cmd(&self, run_compiler: Compiler) -> BootstrapCommand {
1560-
if run_compiler.stage == 0 {
1559+
/// Create a Cargo command for running Clippy.
1560+
/// The used Clippy is (or in the case of stage 0, already was) built using `build_compiler`.
1561+
pub fn cargo_clippy_cmd(&self, build_compiler: Compiler) -> BootstrapCommand {
1562+
if build_compiler.stage == 0 {
15611563
let cargo_clippy = self
15621564
.config
15631565
.initial_cargo_clippy
@@ -1569,15 +1571,16 @@ You have to build a stage1 compiler for `{}` first, and then use it to build a s
15691571
return cmd;
15701572
}
15711573

1572-
// FIXME: double check that `run_compiler`'s stage is what we want to use
1573-
let compilers =
1574-
RustcPrivateCompilers::new(self, run_compiler.stage, self.build.host_target);
1575-
assert_eq!(run_compiler, compilers.target_compiler());
1574+
let compilers = RustcPrivateCompilers::from_build_compiler(
1575+
self,
1576+
build_compiler,
1577+
self.build.host_target,
1578+
);
15761579

15771580
let _ = self.ensure(tool::Clippy::from_compilers(compilers));
15781581
let cargo_clippy = self.ensure(tool::CargoClippy::from_compilers(compilers));
15791582
let mut dylib_path = helpers::dylib_path();
1580-
dylib_path.insert(0, self.sysroot(run_compiler).join("lib"));
1583+
dylib_path.insert(0, self.sysroot(build_compiler).join("lib"));
15811584

15821585
let mut cmd = command(cargo_clippy.tool_path);
15831586
cmd.env(helpers::dylib_path_var(), env::join_paths(&dylib_path).unwrap());

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

Lines changed: 24 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -2076,12 +2076,13 @@ mod snapshot {
20762076
[build] llvm <host>
20772077
[build] rustc 0 <host> -> rustc 1 <host>
20782078
[check] rustc 1 <host> -> rustc 2 <host>
2079-
[build] rustc 0 <host> -> clippy-driver 1 <host>
2080-
[build] rustc 0 <host> -> cargo-clippy 1 <host>
2079+
[build] rustc 1 <host> -> std 1 <host>
2080+
[build] rustc 1 <host> -> rustc 2 <host>
2081+
[build] rustc 1 <host> -> clippy-driver 2 <host>
2082+
[build] rustc 1 <host> -> cargo-clippy 2 <host>
20812083
[clippy] bootstrap <host>
20822084
[clippy] std <host>
2083-
[build] rustc 1 <host> -> std 1 <host>
2084-
[clippy] rustc <host>
2085+
[clippy] rustc 0 <host> -> rustc 1 <host>
20852086
[clippy] rustc 0 <host> -> rustc_codegen_gcc 1 <host>
20862087
");
20872088
}
@@ -2099,17 +2100,30 @@ mod snapshot {
20992100
[build] rustc 1 <host> -> std 1 <host>
21002101
[build] rustc 1 <host> -> rustc 2 <host>
21012102
[check] rustc 2 <host> -> rustc 3 <host>
2102-
[build] rustc 1 <host> -> clippy-driver 2 <host>
2103-
[build] rustc 1 <host> -> cargo-clippy 2 <host>
2103+
[build] rustc 2 <host> -> std 2 <host>
2104+
[build] rustc 2 <host> -> rustc 3 <host>
2105+
[build] rustc 2 <host> -> clippy-driver 3 <host>
2106+
[build] rustc 2 <host> -> cargo-clippy 3 <host>
21042107
[clippy] bootstrap <host>
21052108
[clippy] std <host>
2106-
[build] rustc 2 <host> -> std 2 <host>
2107-
[clippy] rustc <host>
2108-
[build] rustc 0 <host> -> clippy-driver 1 <host>
2109-
[build] rustc 0 <host> -> cargo-clippy 1 <host>
2109+
[build] rustc 1 <host> -> clippy-driver 2 <host>
2110+
[build] rustc 1 <host> -> cargo-clippy 2 <host>
2111+
[clippy] rustc 1 <host> -> rustc 2 <host>
21102112
[clippy] rustc 1 <host> -> rustc_codegen_gcc 2 <host>
21112113
");
21122114
}
2115+
2116+
#[test]
2117+
fn clippy_compiler() {
2118+
let ctx = TestCtx::new();
2119+
insta::assert_snapshot!(
2120+
ctx.config("clippy")
2121+
.path("compiler")
2122+
.render_steps(), @r"
2123+
[build] llvm <host>
2124+
[clippy] rustc 0 <host> -> rustc 1 <host>
2125+
");
2126+
}
21132127
}
21142128

21152129
struct ExecutedSteps {

src/bootstrap/src/utils/build_stamp.rs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -146,13 +146,13 @@ pub fn libstd_stamp(
146146
}
147147

148148
/// Cargo's output path for librustc in a given stage, compiled by a particular
149-
/// compiler for the specified target.
149+
/// `build_compiler` for the specified target.
150150
pub fn librustc_stamp(
151151
builder: &Builder<'_>,
152-
compiler: Compiler,
152+
build_compiler: Compiler,
153153
target: TargetSelection,
154154
) -> BuildStamp {
155-
BuildStamp::new(&builder.cargo_out(compiler, Mode::Rustc, target)).with_prefix("librustc")
155+
BuildStamp::new(&builder.cargo_out(build_compiler, Mode::Rustc, target)).with_prefix("librustc")
156156
}
157157

158158
/// Computes a hash representing the state of a repository/submodule and additional input.

0 commit comments

Comments
 (0)