Skip to content

Commit

Permalink
use precompiled rustdoc with CI rustc
Browse files Browse the repository at this point in the history
When CI rustc is enabled and rustdoc sources are unchanged, we can use
the precompiled rustdoc from the CI rustc's sysroot. This speeds up
bootstrapping quite a lot by avoiding unnecessary rustdoc compilation.

Signed-off-by: onur-ozkan <work@onurozkan.dev>
  • Loading branch information
onur-ozkan committed Jul 20, 2024
1 parent 2b5a982 commit 0636293
Showing 1 changed file with 53 additions and 6 deletions.
59 changes: 53 additions & 6 deletions src/bootstrap/src/core/build_steps/tool.rs
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ use crate::core::builder::{Builder, Cargo as CargoCommand, RunConfig, ShouldRun,
use crate::core::config::TargetSelection;
use crate::utils::channel::GitInfo;
use crate::utils::exec::{command, BootstrapCommand};
use crate::utils::helpers::{add_dylib_path, exe, t};
use crate::utils::helpers::{add_dylib_path, exe, get_closest_merge_base_commit, git, t};
use crate::Compiler;
use crate::Mode;
use crate::{gha, Kind};
Expand Down Expand Up @@ -554,6 +554,57 @@ impl Step for Rustdoc {
}
let target = target_compiler.host;

let bin_rustdoc = || {
let sysroot = builder.sysroot(target_compiler);
let bindir = sysroot.join("bin");
t!(fs::create_dir_all(&bindir));
let bin_rustdoc = bindir.join(exe("rustdoc", target_compiler.host));
let _ = fs::remove_file(&bin_rustdoc);
bin_rustdoc
};

// If CI rustc is enabled and we haven't modified the rustdoc sources,
// use the precompiled rustdoc from CI rustc's sysroot to speed up bootstrapping.
if builder.download_rustc()
&& target_compiler.stage > 0
&& builder.rust_info().is_managed_git_subrepository()
{
let commit = get_closest_merge_base_commit(
Some(&builder.config.src),
&builder.config.git_config(),
&builder.config.stage0_metadata.config.git_merge_commit_email,
&[],
)
.unwrap();

let librustdoc_src = builder.config.src.join("src/librustdoc");
let rustdoc_src = builder.config.src.join("src/tools/rustdoc");

// FIXME: The change detection logic here is quite similar to `Config::download_ci_rustc_commit`.
// It would be better to unify them.
let has_changes = !git(Some(&builder.config.src))
.allow_failure()
.run_always()
.args(["diff-index", "--quiet", &commit])
.arg("--")
.arg(librustdoc_src)
.arg(rustdoc_src)
.run(builder)
.is_success();

if !has_changes {
let precompiled_rustdoc = builder
.config
.ci_rustc_dir()
.join("bin")
.join(exe("rustdoc", target_compiler.host));

let bin_rustdoc = bin_rustdoc();
builder.copy_link(&precompiled_rustdoc, &bin_rustdoc);
return bin_rustdoc;
}
}

let build_compiler = if builder.download_rustc() && target_compiler.stage == 1 {
// We already have the stage 1 compiler, we don't need to cut the stage.
builder.compiler(target_compiler.stage, builder.config.build)
Expand Down Expand Up @@ -614,11 +665,7 @@ impl Step for Rustdoc {

// don't create a stage0-sysroot/bin directory.
if target_compiler.stage > 0 {
let sysroot = builder.sysroot(target_compiler);
let bindir = sysroot.join("bin");
t!(fs::create_dir_all(&bindir));
let bin_rustdoc = bindir.join(exe("rustdoc", target_compiler.host));
let _ = fs::remove_file(&bin_rustdoc);
let bin_rustdoc = bin_rustdoc();
builder.copy_link(&tool_rustdoc, &bin_rustdoc);
bin_rustdoc
} else {
Expand Down

0 comments on commit 0636293

Please sign in to comment.