Skip to content

Commit 781ebbe

Browse files
committed
Auto merge of #115898 - onur-ozkan:config-change-tracking, r=Mark-Simulacrum
bootstrap major change detection implementation The use of `changelog-seen` and `bootstrap/CHANGELOG.md` has not been functional in any way for many years. We often do major/breaking changes but never update the changelog file or the `changelog-seen`. This is an alternative method for tracking major or breaking changes and informing developers when such changes occur. Example output when bootstrap detects a major change: ![image](https://github.com/rust-lang/rust/assets/39852038/ee802dfa-a02b-488b-a433-f853ce079b8a)
2 parents 1578329 + 7d3dcd9 commit 781ebbe

File tree

16 files changed

+109
-113
lines changed

16 files changed

+109
-113
lines changed

compiler/rustc_codegen_cranelift/scripts/setup_rust_fork.sh

+1-1
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,7 @@ index d95b5b7f17f..00b6f0e3635 100644
3131
EOF
3232

3333
cat > config.toml <<EOF
34-
changelog-seen = 2
34+
change-id = 115898
3535
3636
[llvm]
3737
ninja = false

compiler/rustc_codegen_gcc/test.sh

+1-1
Original file line numberDiff line numberDiff line change
@@ -214,7 +214,7 @@ function setup_rustc() {
214214
rm config.toml || true
215215

216216
cat > config.toml <<EOF
217-
changelog-seen = 2
217+
change-id = 115898
218218
219219
[rust]
220220
codegen-backends = []

config.example.toml

+12-5
Original file line numberDiff line numberDiff line change
@@ -19,11 +19,18 @@
1919
# Note that this has no default value (x.py uses the defaults in `config.example.toml`).
2020
#profile = <none>
2121

22-
# Keeps track of the last version of `x.py` used.
23-
# If `changelog-seen` does not match the version that is currently running,
24-
# `x.py` will prompt you to update it and to read the changelog.
25-
# See `src/bootstrap/CHANGELOG.md` for more information.
26-
changelog-seen = 2
22+
# Keeps track of major changes made to this configuration.
23+
#
24+
# This value also represents ID of the PR that caused major changes. Meaning,
25+
# you can visit github.com/rust-lang/rust/pull/{change-id} to check for more details.
26+
#
27+
# A 'major change' includes any of the following
28+
# - A new option
29+
# - A change in the default values
30+
#
31+
# If `change-id` does not match the version that is currently running,
32+
# `x.py` will prompt you to update it and check the related PR for more details.
33+
change-id = 115898
2734

2835
# =============================================================================
2936
# Tweaking how LLVM is compiled

src/bootstrap/CHANGELOG.md

-71
This file was deleted.

src/bootstrap/README.md

+9-5
Original file line numberDiff line numberDiff line change
@@ -181,23 +181,27 @@ Some general areas that you may be interested in modifying are:
181181
`Config` struct.
182182
* Adding a sanity check? Take a look at `bootstrap/sanity.rs`.
183183

184-
If you make a major change, please remember to:
184+
If you make a major change on bootstrap configuration, please remember to:
185185

186-
+ Update `VERSION` in `src/bootstrap/main.rs`.
187-
* Update `changelog-seen = N` in `config.example.toml`.
188-
* Add an entry in `src/bootstrap/CHANGELOG.md`.
186+
+ Update `CONFIG_CHANGE_HISTORY` in `src/bootstrap/lib.rs`.
187+
* Update `change-id = {pull-request-id}` in `config.example.toml`.
189188

190189
A 'major change' includes
191190

192191
* A new option or
193192
* A change in the default options.
194193

195194
Changes that do not affect contributors to the compiler or users
196-
building rustc from source don't need an update to `VERSION`.
195+
building rustc from source don't need an update to `CONFIG_CHANGE_HISTORY`.
197196

198197
If you have any questions, feel free to reach out on the `#t-infra/bootstrap` channel
199198
at [Rust Bootstrap Zulip server][rust-bootstrap-zulip]. When you encounter bugs,
200199
please file issues on the [Rust issue tracker][rust-issue-tracker].
201200

202201
[rust-bootstrap-zulip]: https://rust-lang.zulipchat.com/#narrow/stream/t-infra.2Fbootstrap
203202
[rust-issue-tracker]: https://github.com/rust-lang/rust/issues
203+
204+
## Changelog
205+
206+
Because we do not release bootstrap with versions, we also do not maintain CHANGELOG files. To
207+
review the changes made to bootstrap, simply run `git log --no-merges --oneline -- src/bootstrap`.

src/bootstrap/bin/main.rs

+28-13
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@ use std::{env, fs};
1313

1414
#[cfg(all(any(unix, windows), not(target_os = "solaris")))]
1515
use bootstrap::t;
16-
use bootstrap::{Build, Config, Subcommand, VERSION};
16+
use bootstrap::{find_recent_config_change_ids, Build, Config, Subcommand, CONFIG_CHANGE_HISTORY};
1717

1818
fn main() {
1919
let args = env::args().skip(1).collect::<Vec<_>>();
@@ -42,7 +42,7 @@ fn main() {
4242
}
4343
err => {
4444
drop(err);
45-
println!("warning: build directory locked by process {pid}, waiting for lock");
45+
println!("WARNING: build directory locked by process {pid}, waiting for lock");
4646
let mut lock = t!(build_lock.write());
4747
t!(lock.write(&process::id().to_string().as_ref()));
4848
lock
@@ -51,7 +51,7 @@ fn main() {
5151
}
5252

5353
#[cfg(any(not(any(unix, windows)), target_os = "solaris"))]
54-
println!("warning: file locking not supported for target, not locking build directory");
54+
println!("WARNING: file locking not supported for target, not locking build directory");
5555

5656
// check_version warnings are not printed during setup
5757
let changelog_suggestion =
@@ -61,7 +61,7 @@ fn main() {
6161
// changelog warning, not the `x.py setup` message.
6262
let suggest_setup = config.config.is_none() && !matches!(config.cmd, Subcommand::Setup { .. });
6363
if suggest_setup {
64-
println!("warning: you have not made a `config.toml`");
64+
println!("WARNING: you have not made a `config.toml`");
6565
println!(
6666
"help: consider running `./x.py setup` or copying `config.example.toml` by running \
6767
`cp config.example.toml config.toml`"
@@ -74,7 +74,7 @@ fn main() {
7474
Build::new(config).build();
7575

7676
if suggest_setup {
77-
println!("warning: you have not made a `config.toml`");
77+
println!("WARNING: you have not made a `config.toml`");
7878
println!(
7979
"help: consider running `./x.py setup` or copying `config.example.toml` by running \
8080
`cp config.example.toml config.toml`"
@@ -91,7 +91,7 @@ fn main() {
9191
contents.contains("https://github.com/rust-lang/rust/issues/77620#issuecomment-705144570")
9292
}) {
9393
println!(
94-
"warning: You have the pre-push script installed to .git/hooks/pre-commit. \
94+
"WARNING: You have the pre-push script installed to .git/hooks/pre-commit. \
9595
Consider moving it to .git/hooks/pre-push instead, which runs less often."
9696
);
9797
}
@@ -104,19 +104,34 @@ fn main() {
104104
fn check_version(config: &Config) -> Option<String> {
105105
let mut msg = String::new();
106106

107-
let suggestion = if let Some(seen) = config.changelog_seen {
108-
if seen != VERSION {
109-
msg.push_str("warning: there have been changes to x.py since you last updated.\n");
110-
format!("update `config.toml` to use `changelog-seen = {VERSION}` instead")
107+
if config.changelog_seen.is_some() {
108+
msg.push_str("WARNING: The use of `changelog-seen` is deprecated. Please refer to `change-id` option in `config.example.toml` instead.\n");
109+
}
110+
111+
let latest_config_id = CONFIG_CHANGE_HISTORY.last().unwrap();
112+
let suggestion = if let Some(id) = config.change_id {
113+
if &id != latest_config_id {
114+
msg.push_str("WARNING: there have been changes to x.py since you last updated.\n");
115+
let change_links: Vec<String> = find_recent_config_change_ids(id)
116+
.iter()
117+
.map(|id| format!("https://github.com/rust-lang/rust/pull/{id}"))
118+
.collect();
119+
if !change_links.is_empty() {
120+
msg.push_str("To see more detail about these changes, visit the following PRs:\n");
121+
for link in change_links {
122+
msg.push_str(&format!(" - {link}\n"));
123+
}
124+
}
125+
msg.push_str("WARNING: there have been changes to x.py since you last updated.\n");
126+
format!("update `config.toml` to use `change-id = {latest_config_id}` instead")
111127
} else {
112128
return None;
113129
}
114130
} else {
115-
msg.push_str("warning: x.py has made several changes recently you may want to look at\n");
116-
format!("add `changelog-seen = {VERSION}` at the top of `config.toml`")
131+
msg.push_str("WARNING: The `change-id` is missing in the `config.toml`. This means that you will not be able to track the major changes made to the bootstrap configurations.\n");
132+
format!("add `change-id = {latest_config_id}` at the top of `config.toml`")
117133
};
118134

119-
msg.push_str("help: consider looking at the changes in `src/bootstrap/CHANGELOG.md`\n");
120135
msg.push_str("note: to silence this warning, ");
121136
msg.push_str(&suggestion);
122137

src/bootstrap/bootstrap_test.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -103,7 +103,7 @@ class GenerateAndParseConfig(unittest.TestCase):
103103
"""Test that we can serialize and deserialize a config.toml file"""
104104
def test_no_args(self):
105105
build = serialize_and_parse([])
106-
self.assertEqual(build.get_toml("changelog-seen"), '2')
106+
self.assertEqual(build.get_toml("change-id"), '115898')
107107
self.assertEqual(build.get_toml("profile"), 'dist')
108108
self.assertIsNone(build.get_toml("llvm.download-ci-llvm"))
109109

src/bootstrap/config.rs

+17-3
Original file line numberDiff line numberDiff line change
@@ -112,7 +112,8 @@ impl Display for DebuginfoLevel {
112112
/// `config.example.toml`.
113113
#[derive(Default, Clone)]
114114
pub struct Config {
115-
pub changelog_seen: Option<usize>,
115+
pub changelog_seen: Option<usize>, // FIXME: Deprecated field. Remove it at 2024.
116+
pub change_id: Option<usize>,
116117
pub ccache: Option<String>,
117118
/// Call Build::ninja() instead of this.
118119
pub ninja_in_file: bool,
@@ -546,7 +547,8 @@ impl Target {
546547
#[derive(Deserialize, Default)]
547548
#[serde(deny_unknown_fields, rename_all = "kebab-case")]
548549
struct TomlConfig {
549-
changelog_seen: Option<usize>,
550+
changelog_seen: Option<usize>, // FIXME: Deprecated field. Remove it at 2024.
551+
change_id: Option<usize>,
550552
build: Option<Build>,
551553
install: Option<Install>,
552554
llvm: Option<Llvm>,
@@ -574,7 +576,17 @@ trait Merge {
574576
impl Merge for TomlConfig {
575577
fn merge(
576578
&mut self,
577-
TomlConfig { build, install, llvm, rust, dist, target, profile: _, changelog_seen }: Self,
579+
TomlConfig {
580+
build,
581+
install,
582+
llvm,
583+
rust,
584+
dist,
585+
target,
586+
profile: _,
587+
changelog_seen,
588+
change_id,
589+
}: Self,
578590
replace: ReplaceOpt,
579591
) {
580592
fn do_merge<T: Merge>(x: &mut Option<T>, y: Option<T>, replace: ReplaceOpt) {
@@ -587,6 +599,7 @@ impl Merge for TomlConfig {
587599
}
588600
}
589601
self.changelog_seen.merge(changelog_seen, replace);
602+
self.change_id.merge(change_id, replace);
590603
do_merge(&mut self.build, build, replace);
591604
do_merge(&mut self.install, install, replace);
592605
do_merge(&mut self.llvm, llvm, replace);
@@ -1242,6 +1255,7 @@ impl Config {
12421255
toml.merge(override_toml, ReplaceOpt::Override);
12431256

12441257
config.changelog_seen = toml.changelog_seen;
1258+
config.change_id = toml.change_id;
12451259

12461260
let build = toml.build.unwrap_or_default();
12471261
if let Some(file_build) = build.build {

src/bootstrap/config/tests.rs

+6-6
Original file line numberDiff line numberDiff line change
@@ -102,7 +102,7 @@ fn override_toml() {
102102
&[
103103
"check".to_owned(),
104104
"--config=/does/not/exist".to_owned(),
105-
"--set=changelog-seen=1".to_owned(),
105+
"--set=change-id=1".to_owned(),
106106
"--set=rust.lto=fat".to_owned(),
107107
"--set=rust.deny-warnings=false".to_owned(),
108108
"--set=build.gdb=\"bar\"".to_owned(),
@@ -112,7 +112,7 @@ fn override_toml() {
112112
|&_| {
113113
toml::from_str(
114114
r#"
115-
changelog-seen = 0
115+
change-id = 0
116116
[rust]
117117
lto = "off"
118118
deny-warnings = true
@@ -129,7 +129,7 @@ build-config = {}
129129
.unwrap()
130130
},
131131
);
132-
assert_eq!(config.changelog_seen, Some(1), "setting top-level value");
132+
assert_eq!(config.change_id, Some(1), "setting top-level value");
133133
assert_eq!(
134134
config.rust_lto,
135135
crate::config::RustcLto::Fat,
@@ -156,10 +156,10 @@ fn override_toml_duplicate() {
156156
&[
157157
"check".to_owned(),
158158
"--config=/does/not/exist".to_owned(),
159-
"--set=changelog-seen=1".to_owned(),
160-
"--set=changelog-seen=2".to_owned(),
159+
"--set=change-id=1".to_owned(),
160+
"--set=change-id=2".to_owned(),
161161
],
162-
|&_| toml::from_str("changelog-seen = 0").unwrap(),
162+
|&_| toml::from_str("change-id = 0").unwrap(),
163163
);
164164
}
165165

src/bootstrap/lib.rs

+22-1
Original file line numberDiff line numberDiff line change
@@ -112,7 +112,15 @@ const LLVM_TOOLS: &[&str] = &[
112112
/// LLD file names for all flavors.
113113
const LLD_FILE_NAMES: &[&str] = &["ld.lld", "ld64.lld", "lld-link", "wasm-ld"];
114114

115-
pub const VERSION: usize = 2;
115+
/// Keeps track of major changes made to the bootstrap configuration.
116+
///
117+
/// These values also represent the IDs of the PRs that caused major changes.
118+
/// You can visit `https://github.com/rust-lang/rust/pull/{any-id-from-the-list}` to
119+
/// check for more details regarding each change.
120+
///
121+
/// If you make any major changes (such as adding new values or changing default values), please
122+
/// ensure that the associated PR ID is added to the end of this list.
123+
pub const CONFIG_CHANGE_HISTORY: &[usize] = &[115898];
116124

117125
/// Extra --check-cfg to add when building
118126
/// (Mode restriction, config name, config values (if any))
@@ -1844,3 +1852,16 @@ fn envify(s: &str) -> String {
18441852
.flat_map(|c| c.to_uppercase())
18451853
.collect()
18461854
}
1855+
1856+
pub fn find_recent_config_change_ids(current_id: usize) -> Vec<usize> {
1857+
let index = CONFIG_CHANGE_HISTORY
1858+
.iter()
1859+
.position(|&id| id == current_id)
1860+
.expect(&format!("Value `{}` was not found in `CONFIG_CHANGE_HISTORY`.", current_id));
1861+
1862+
CONFIG_CHANGE_HISTORY
1863+
.iter()
1864+
.skip(index + 1) // Skip the current_id and IDs before it
1865+
.cloned()
1866+
.collect()
1867+
}

0 commit comments

Comments
 (0)