Skip to content

Commit c2fbe40

Browse files
committed
Auto merge of rust-lang#122483 - matthiaskrgr:rollup-n07dsh5, r=matthiaskrgr
Rollup of 9 pull requests Successful merges: - rust-lang#104353 (Add CStr::bytes iterator) - rust-lang#119676 (rustdoc-search: search types by higher-order functions) - rust-lang#120699 (Document `TRACK_DIAGNOSTIC` calls.) - rust-lang#121899 (Document how removing a type's field can be bad and what to do instead) - rust-lang#122405 (Add methods to create StableMIR constant) - rust-lang#122416 (Various style improvements to `rustc_lint::levels`) - rust-lang#122421 (Improve `Step` docs) - rust-lang#122440 (const-eval: organize and extend tests for required-consts) - rust-lang#122461 (fix unsoundness in Step::forward_unchecked for signed integers) Failed merges: - rust-lang#122397 (Various cleanups around the const eval query providers) r? `@ghost` `@rustbot` modify labels: rollup
2 parents e69f14b + 75dc99b commit c2fbe40

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

46 files changed

+2227
-447
lines changed

compiler/rustc_errors/src/emitter.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -2086,7 +2086,7 @@ impl HumanEmitter {
20862086
}
20872087
if !self.short_message {
20882088
for child in children {
2089-
assert!(child.level.can_be_top_or_sub().1);
2089+
assert!(child.level.can_be_subdiag());
20902090
let span = &child.span;
20912091
if let Err(err) = self.emit_messages_default_inner(
20922092
span,

compiler/rustc_errors/src/lib.rs

+92-70
Original file line numberDiff line numberDiff line change
@@ -526,12 +526,15 @@ pub enum StashKey {
526526
UndeterminedMacroResolution,
527527
}
528528

529-
fn default_track_diagnostic(diag: DiagInner, f: &mut dyn FnMut(DiagInner)) {
529+
fn default_track_diagnostic<R>(diag: DiagInner, f: &mut dyn FnMut(DiagInner) -> R) -> R {
530530
(*f)(diag)
531531
}
532532

533-
pub static TRACK_DIAGNOSTIC: AtomicRef<fn(DiagInner, &mut dyn FnMut(DiagInner))> =
534-
AtomicRef::new(&(default_track_diagnostic as _));
533+
/// Diagnostics emitted by `DiagCtxtInner::emit_diagnostic` are passed through this function. Used
534+
/// for tracking by incremental, to replay diagnostics as necessary.
535+
pub static TRACK_DIAGNOSTIC: AtomicRef<
536+
fn(DiagInner, &mut dyn FnMut(DiagInner) -> Option<ErrorGuaranteed>) -> Option<ErrorGuaranteed>,
537+
> = AtomicRef::new(&(default_track_diagnostic as _));
535538

536539
#[derive(Copy, Clone, Default)]
537540
pub struct DiagCtxtFlags {
@@ -1422,74 +1425,103 @@ impl DiagCtxtInner {
14221425

14231426
// Return value is only `Some` if the level is `Error` or `DelayedBug`.
14241427
fn emit_diagnostic(&mut self, mut diagnostic: DiagInner) -> Option<ErrorGuaranteed> {
1425-
assert!(diagnostic.level.can_be_top_or_sub().0);
1426-
1427-
if let Some(expectation_id) = diagnostic.level.get_expectation_id() {
1428-
// The `LintExpectationId` can be stable or unstable depending on when it was created.
1429-
// Diagnostics created before the definition of `HirId`s are unstable and can not yet
1430-
// be stored. Instead, they are buffered until the `LintExpectationId` is replaced by
1431-
// a stable one by the `LintLevelsBuilder`.
1432-
if let LintExpectationId::Unstable { .. } = expectation_id {
1433-
self.unstable_expect_diagnostics.push(diagnostic);
1434-
return None;
1435-
}
1436-
self.suppressed_expected_diag = true;
1437-
self.fulfilled_expectations.insert(expectation_id.normalize());
1438-
}
1439-
14401428
if diagnostic.has_future_breakage() {
14411429
// Future breakages aren't emitted if they're `Level::Allow`,
14421430
// but they still need to be constructed and stashed below,
14431431
// so they'll trigger the must_produce_diag check.
1444-
self.suppressed_expected_diag = true;
1432+
assert!(matches!(diagnostic.level, Error | Warning | Allow));
14451433
self.future_breakage_diagnostics.push(diagnostic.clone());
14461434
}
14471435

1448-
// Note that because this comes before the `match` below,
1449-
// `-Zeagerly-emit-delayed-bugs` continues to work even after we've
1450-
// issued an error and stopped recording new delayed bugs.
1451-
if diagnostic.level == DelayedBug && self.flags.eagerly_emit_delayed_bugs {
1452-
diagnostic.level = Error;
1453-
}
1454-
1436+
// We call TRACK_DIAGNOSTIC with an empty closure for the cases that
1437+
// return early *and* have some kind of side-effect, except where
1438+
// noted.
14551439
match diagnostic.level {
1456-
// This must come after the possible promotion of `DelayedBug` to
1457-
// `Error` above.
1458-
Fatal | Error if self.treat_next_err_as_bug() => {
1459-
diagnostic.level = Bug;
1440+
Bug => {}
1441+
Fatal | Error => {
1442+
if self.treat_next_err_as_bug() {
1443+
// `Fatal` and `Error` can be promoted to `Bug`.
1444+
diagnostic.level = Bug;
1445+
}
14601446
}
14611447
DelayedBug => {
1462-
// If we have already emitted at least one error, we don't need
1463-
// to record the delayed bug, because it'll never be used.
1464-
return if let Some(guar) = self.has_errors() {
1465-
Some(guar)
1448+
// Note that because we check these conditions first,
1449+
// `-Zeagerly-emit-delayed-bugs` and `-Ztreat-err-as-bug`
1450+
// continue to work even after we've issued an error and
1451+
// stopped recording new delayed bugs.
1452+
if self.flags.eagerly_emit_delayed_bugs {
1453+
// `DelayedBug` can be promoted to `Error` or `Bug`.
1454+
if self.treat_next_err_as_bug() {
1455+
diagnostic.level = Bug;
1456+
} else {
1457+
diagnostic.level = Error;
1458+
}
14661459
} else {
1467-
let backtrace = std::backtrace::Backtrace::capture();
1468-
// This `unchecked_error_guaranteed` is valid. It is where the
1469-
// `ErrorGuaranteed` for delayed bugs originates. See
1470-
// `DiagCtxtInner::drop`.
1471-
#[allow(deprecated)]
1472-
let guar = ErrorGuaranteed::unchecked_error_guaranteed();
1473-
self.delayed_bugs
1474-
.push((DelayedDiagInner::with_backtrace(diagnostic, backtrace), guar));
1475-
Some(guar)
1476-
};
1460+
// If we have already emitted at least one error, we don't need
1461+
// to record the delayed bug, because it'll never be used.
1462+
return if let Some(guar) = self.has_errors() {
1463+
Some(guar)
1464+
} else {
1465+
// No `TRACK_DIAGNOSTIC` call is needed, because the
1466+
// incremental session is deleted if there is a delayed
1467+
// bug. This also saves us from cloning the diagnostic.
1468+
let backtrace = std::backtrace::Backtrace::capture();
1469+
// This `unchecked_error_guaranteed` is valid. It is where the
1470+
// `ErrorGuaranteed` for delayed bugs originates. See
1471+
// `DiagCtxtInner::drop`.
1472+
#[allow(deprecated)]
1473+
let guar = ErrorGuaranteed::unchecked_error_guaranteed();
1474+
self.delayed_bugs
1475+
.push((DelayedDiagInner::with_backtrace(diagnostic, backtrace), guar));
1476+
Some(guar)
1477+
};
1478+
}
1479+
}
1480+
ForceWarning(None) => {} // `ForceWarning(Some(...))` is below, with `Expect`
1481+
Warning => {
1482+
if !self.flags.can_emit_warnings {
1483+
// We are not emitting warnings.
1484+
if diagnostic.has_future_breakage() {
1485+
// The side-effect is at the top of this method.
1486+
TRACK_DIAGNOSTIC(diagnostic, &mut |_| None);
1487+
}
1488+
return None;
1489+
}
14771490
}
1478-
Warning if !self.flags.can_emit_warnings => {
1491+
Note | Help | FailureNote => {}
1492+
OnceNote | OnceHelp => panic!("bad level: {:?}", diagnostic.level),
1493+
Allow => {
1494+
// Nothing emitted for allowed lints.
14791495
if diagnostic.has_future_breakage() {
1480-
(*TRACK_DIAGNOSTIC)(diagnostic, &mut |_| {});
1496+
// The side-effect is at the top of this method.
1497+
TRACK_DIAGNOSTIC(diagnostic, &mut |_| None);
1498+
self.suppressed_expected_diag = true;
14811499
}
14821500
return None;
14831501
}
1484-
Allow | Expect(_) => {
1485-
(*TRACK_DIAGNOSTIC)(diagnostic, &mut |_| {});
1486-
return None;
1502+
Expect(expect_id) | ForceWarning(Some(expect_id)) => {
1503+
// Diagnostics created before the definition of `HirId`s are
1504+
// unstable and can not yet be stored. Instead, they are
1505+
// buffered until the `LintExpectationId` is replaced by a
1506+
// stable one by the `LintLevelsBuilder`.
1507+
if let LintExpectationId::Unstable { .. } = expect_id {
1508+
// We don't call TRACK_DIAGNOSTIC because we wait for the
1509+
// unstable ID to be updated, whereupon the diagnostic will
1510+
// be passed into this method again.
1511+
self.unstable_expect_diagnostics.push(diagnostic);
1512+
return None;
1513+
}
1514+
self.fulfilled_expectations.insert(expect_id.normalize());
1515+
if let Expect(_) = diagnostic.level {
1516+
// Nothing emitted here for expected lints.
1517+
TRACK_DIAGNOSTIC(diagnostic, &mut |_| None);
1518+
self.suppressed_expected_diag = true;
1519+
return None;
1520+
}
14871521
}
1488-
_ => {}
14891522
}
14901523

1491-
let mut guaranteed = None;
1492-
(*TRACK_DIAGNOSTIC)(diagnostic, &mut |mut diagnostic| {
1524+
TRACK_DIAGNOSTIC(diagnostic, &mut |mut diagnostic| {
14931525
if let Some(code) = diagnostic.code {
14941526
self.emitted_diagnostic_codes.insert(code);
14951527
}
@@ -1552,17 +1584,17 @@ impl DiagCtxtInner {
15521584
// `ErrorGuaranteed` for errors and lint errors originates.
15531585
#[allow(deprecated)]
15541586
let guar = ErrorGuaranteed::unchecked_error_guaranteed();
1555-
guaranteed = Some(guar);
15561587
if is_lint {
15571588
self.lint_err_guars.push(guar);
15581589
} else {
15591590
self.err_guars.push(guar);
15601591
}
15611592
self.panic_if_treat_err_as_bug();
1593+
Some(guar)
1594+
} else {
1595+
None
15621596
}
1563-
});
1564-
1565-
guaranteed
1597+
})
15661598
}
15671599

15681600
fn treat_err_as_bug(&self) -> bool {
@@ -1863,23 +1895,13 @@ impl Level {
18631895
matches!(*self, FailureNote)
18641896
}
18651897

1866-
pub fn get_expectation_id(&self) -> Option<LintExpectationId> {
1867-
match self {
1868-
Expect(id) | ForceWarning(Some(id)) => Some(*id),
1869-
_ => None,
1870-
}
1871-
}
1872-
1873-
// Can this level be used in a top-level diagnostic message and/or a
1874-
// subdiagnostic message?
1875-
fn can_be_top_or_sub(&self) -> (bool, bool) {
1898+
// Can this level be used in a subdiagnostic message?
1899+
fn can_be_subdiag(&self) -> bool {
18761900
match self {
18771901
Bug | DelayedBug | Fatal | Error | ForceWarning(_) | FailureNote | Allow
1878-
| Expect(_) => (true, false),
1879-
1880-
Warning | Note | Help => (true, true),
1902+
| Expect(_) => false,
18811903

1882-
OnceNote | OnceHelp => (false, true),
1904+
Warning | Note | Help | OnceNote | OnceHelp => true,
18831905
}
18841906
}
18851907
}

compiler/rustc_interface/src/callbacks.rs

+5-5
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,7 @@ fn track_span_parent(def_id: rustc_span::def_id::LocalDefId) {
2929
/// This is a callback from `rustc_errors` as it cannot access the implicit state
3030
/// in `rustc_middle` otherwise. It is used when diagnostic messages are
3131
/// emitted and stores them in the current query, if there is one.
32-
fn track_diagnostic(diagnostic: DiagInner, f: &mut dyn FnMut(DiagInner)) {
32+
fn track_diagnostic<R>(diagnostic: DiagInner, f: &mut dyn FnMut(DiagInner) -> R) -> R {
3333
tls::with_context_opt(|icx| {
3434
if let Some(icx) = icx {
3535
if let Some(diagnostics) = icx.diagnostics {
@@ -38,11 +38,11 @@ fn track_diagnostic(diagnostic: DiagInner, f: &mut dyn FnMut(DiagInner)) {
3838

3939
// Diagnostics are tracked, we can ignore the dependency.
4040
let icx = tls::ImplicitCtxt { task_deps: TaskDepsRef::Ignore, ..icx.clone() };
41-
return tls::enter_context(&icx, move || (*f)(diagnostic));
41+
tls::enter_context(&icx, move || (*f)(diagnostic))
42+
} else {
43+
// In any other case, invoke diagnostics anyway.
44+
(*f)(diagnostic)
4245
}
43-
44-
// In any other case, invoke diagnostics anyway.
45-
(*f)(diagnostic);
4646
})
4747
}
4848

0 commit comments

Comments
 (0)