Skip to content

Commit 2733313

Browse files
committed
abstract merge-base commit logic
Signed-off-by: onur-ozkan <[email protected]>
1 parent 51917e2 commit 2733313

File tree

4 files changed

+57
-42
lines changed

4 files changed

+57
-42
lines changed

src/bootstrap/src/core/build_steps/llvm.rs

+14-22
Original file line numberDiff line numberDiff line change
@@ -20,13 +20,13 @@ use crate::core::builder::{Builder, RunConfig, ShouldRun, Step};
2020
use crate::core::config::{Config, TargetSelection};
2121
use crate::utils::channel;
2222
use crate::utils::helpers::{
23-
self, exe, get_clang_cl_resource_dir, output, t, unhashed_basename, up_to_date,
23+
self, exe, get_clang_cl_resource_dir, get_closest_merge_base_commit, output, t,
24+
unhashed_basename, up_to_date,
2425
};
2526
use crate::{generate_smart_stamp_hash, CLang, GitRepo, Kind};
2627

2728
use crate::utils::exec::BootstrapCommand;
2829
use build_helper::ci::CiEnv;
29-
use build_helper::git::get_git_merge_base;
3030

3131
#[derive(Clone)]
3232
pub struct LlvmResult {
@@ -153,26 +153,18 @@ pub fn prebuilt_llvm_config(builder: &Builder<'_>, target: TargetSelection) -> L
153153
/// This retrieves the LLVM sha we *want* to use, according to git history.
154154
pub(crate) fn detect_llvm_sha(config: &Config, is_git: bool) -> String {
155155
let llvm_sha = if is_git {
156-
// We proceed in 2 steps. First we get the closest commit that is actually upstream. Then we
157-
// walk back further to the last bors merge commit that actually changed LLVM. The first
158-
// step will fail on CI because only the `auto` branch exists; we just fall back to `HEAD`
159-
// in that case.
160-
let closest_upstream = get_git_merge_base(&config.git_config(), Some(&config.src))
161-
.unwrap_or_else(|_| "HEAD".into());
162-
let mut rev_list = helpers::git(Some(&config.src));
163-
rev_list.args(&[
164-
PathBuf::from("rev-list"),
165-
format!("--author={}", config.stage0_metadata.config.git_merge_commit_email).into(),
166-
"-n1".into(),
167-
"--first-parent".into(),
168-
closest_upstream.into(),
169-
"--".into(),
170-
config.src.join("src/llvm-project"),
171-
config.src.join("src/bootstrap/download-ci-llvm-stamp"),
172-
// the LLVM shared object file is named `LLVM-12-rust-{version}-nightly`
173-
config.src.join("src/version"),
174-
]);
175-
output(&mut rev_list.command).trim().to_owned()
156+
get_closest_merge_base_commit(
157+
Some(&config.src),
158+
&config.git_config(),
159+
&config.stage0_metadata.config.git_merge_commit_email,
160+
&[
161+
config.src.join("src/llvm-project"),
162+
config.src.join("src/bootstrap/download-ci-llvm-stamp"),
163+
// the LLVM shared object file is named `LLVM-12-rust-{version}-nightly`
164+
config.src.join("src/version"),
165+
],
166+
)
167+
.unwrap()
176168
} else if let Some(info) = channel::read_commit_info_file(&config.src) {
177169
info.sha.trim().to_owned()
178170
} else {

src/bootstrap/src/core/config/config.rs

+18-19
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,7 @@ use crate::core::build_steps::llvm;
2020
use crate::core::config::flags::{Color, Flags, Warnings};
2121
use crate::utils::cache::{Interned, INTERNER};
2222
use crate::utils::channel::{self, GitInfo};
23-
use crate::utils::helpers::{self, exe, output, t};
23+
use crate::utils::helpers::{self, exe, get_closest_merge_base_commit, output, t};
2424
use build_helper::exit;
2525
use serde::{Deserialize, Deserializer};
2626
use serde_derive::Deserialize;
@@ -2455,14 +2455,14 @@ impl Config {
24552455

24562456
// Look for a version to compare to based on the current commit.
24572457
// Only commits merged by bors will have CI artifacts.
2458-
let merge_base = output(
2459-
&mut helpers::git(Some(&self.src))
2460-
.arg("rev-list")
2461-
.arg(format!("--author={}", self.stage0_metadata.config.git_merge_commit_email))
2462-
.args(["-n1", "--first-parent", "HEAD"])
2463-
.command,
2464-
);
2465-
let commit = merge_base.trim_end();
2458+
let commit = get_closest_merge_base_commit(
2459+
Some(&self.src),
2460+
&self.git_config(),
2461+
&self.stage0_metadata.config.git_merge_commit_email,
2462+
&[],
2463+
)
2464+
.unwrap();
2465+
24662466
if commit.is_empty() {
24672467
println!("ERROR: could not find commit hash for downloading rustc");
24682468
println!("HELP: maybe your repository history is too shallow?");
@@ -2473,7 +2473,7 @@ impl Config {
24732473

24742474
// Warn if there were changes to the compiler or standard library since the ancestor commit.
24752475
let has_changes = !t!(helpers::git(Some(&self.src))
2476-
.args(["diff-index", "--quiet", commit, "--", &compiler, &library])
2476+
.args(["diff-index", "--quiet", &commit, "--", &compiler, &library])
24772477
.command
24782478
.status())
24792479
.success();
@@ -2553,14 +2553,13 @@ impl Config {
25532553

25542554
// Look for a version to compare to based on the current commit.
25552555
// Only commits merged by bors will have CI artifacts.
2556-
let merge_base = output(
2557-
&mut helpers::git(Some(&self.src))
2558-
.arg("rev-list")
2559-
.arg(format!("--author={}", self.stage0_metadata.config.git_merge_commit_email))
2560-
.args(["-n1", "--first-parent", "HEAD"])
2561-
.command,
2562-
);
2563-
let commit = merge_base.trim_end();
2556+
let commit = get_closest_merge_base_commit(
2557+
Some(&self.src),
2558+
&self.git_config(),
2559+
&self.stage0_metadata.config.git_merge_commit_email,
2560+
&[],
2561+
)
2562+
.unwrap();
25642563
if commit.is_empty() {
25652564
println!("error: could not find commit hash for downloading components from CI");
25662565
println!("help: maybe your repository history is too shallow?");
@@ -2571,7 +2570,7 @@ impl Config {
25712570

25722571
// Warn if there were changes to the compiler or standard library since the ancestor commit.
25732572
let mut git = helpers::git(Some(&self.src));
2574-
git.args(["diff-index", "--quiet", commit, "--"]);
2573+
git.args(["diff-index", "--quiet", &commit, "--"]);
25752574

25762575
for path in modified_paths {
25772576
git.arg(format!("{top_level}/{path}"));

src/bootstrap/src/utils/helpers.rs

+24
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
//! Simple things like testing the various filesystem operations here and there,
44
//! not a lot of interesting happenings here unfortunately.
55
6+
use build_helper::git::{get_git_merge_base, output_result, GitConfig};
67
use build_helper::util::fail;
78
use std::env;
89
use std::ffi::OsStr;
@@ -520,3 +521,26 @@ pub fn git(source_dir: Option<&Path>) -> BootstrapCommand {
520521

521522
git
522523
}
524+
525+
/// Returns the closest commit available from upstream for the given `author` and `target_paths`.
526+
///
527+
/// If it fails to find the commit from upstream using `git merge-base`, fallbacks to HEAD.
528+
pub fn get_closest_merge_base_commit(
529+
source_dir: Option<&Path>,
530+
config: &GitConfig<'_>,
531+
author: &str,
532+
target_paths: &[PathBuf],
533+
) -> Result<String, String> {
534+
let merge_base = get_git_merge_base(config, source_dir).unwrap_or_else(|_| "HEAD".into());
535+
536+
let mut git = git(source_dir);
537+
538+
git.arg(Path::new("rev-list"));
539+
git.args([&format!("--author={author}"), "-n1", "--first-parent", &merge_base]);
540+
if !target_paths.is_empty() {
541+
git.arg("--");
542+
git.args(target_paths);
543+
}
544+
545+
Ok(output_result(&mut git.command)?.trim().to_owned())
546+
}

src/tools/build_helper/src/git.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@ pub struct GitConfig<'a> {
77
}
88

99
/// Runs a command and returns the output
10-
fn output_result(cmd: &mut Command) -> Result<String, String> {
10+
pub fn output_result(cmd: &mut Command) -> Result<String, String> {
1111
let output = match cmd.stderr(Stdio::inherit()).output() {
1212
Ok(status) => status,
1313
Err(e) => return Err(format!("failed to run command: {:?}: {}", cmd, e)),

0 commit comments

Comments
 (0)