Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Always evaluate free constants and statics, even if previous errors occurred #121087

Merged
merged 1 commit into from
Feb 20, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -249,7 +249,7 @@ impl<'mir, 'tcx> Checker<'mir, 'tcx> {
let secondary_errors = mem::take(&mut self.secondary_errors);
if self.error_emitted.is_none() {
for error in secondary_errors {
error.emit();
self.error_emitted = Some(error.emit());
Comment on lines 249 to +252
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@RalfJung found the issue that caused us to const eval even though there were const qualif errors 🙈

}
} else {
assert!(self.tcx.dcx().has_errors().is_some());
Expand Down
11 changes: 11 additions & 0 deletions compiler/rustc_hir_analysis/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -198,6 +198,17 @@ pub fn check_crate(tcx: TyCtxt<'_>) -> Result<(), ErrorGuaranteed> {
collect::test_opaque_hidden_types(tcx)?;
}

// Make sure we evaluate all static and (non-associated) const items, even if unused.
// If any of these fail to evaluate, we do not want this crate to pass compilation.
tcx.hir().par_body_owners(|item_def_id| {
oli-obk marked this conversation as resolved.
Show resolved Hide resolved
let def_kind = tcx.def_kind(item_def_id);
match def_kind {
DefKind::Static(_) => tcx.ensure().eval_static_initializer(item_def_id),
DefKind::Const => tcx.ensure().const_eval_poly(item_def_id.into()),
_ => (),
}
});

// Freeze definitions as we don't add new ones at this point. This improves performance by
// allowing lock-free access to them.
tcx.untracked().definitions.freeze();
Expand Down
26 changes: 0 additions & 26 deletions compiler/rustc_lint/src/builtin.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1542,32 +1542,6 @@ impl<'tcx> LateLintPass<'tcx> for TypeAliasBounds {
}
}

declare_lint_pass!(
/// Lint constants that are erroneous.
/// Without this lint, we might not get any diagnostic if the constant is
/// unused within this crate, even though downstream crates can't use it
/// without producing an error.
UnusedBrokenConst => []
);

impl<'tcx> LateLintPass<'tcx> for UnusedBrokenConst {
fn check_item(&mut self, cx: &LateContext<'_>, it: &hir::Item<'_>) {
match it.kind {
hir::ItemKind::Const(_, _, body_id) => {
let def_id = cx.tcx.hir().body_owner_def_id(body_id).to_def_id();
// trigger the query once for all constants since that will already report the errors
// FIXME(generic_const_items): Does this work properly with generic const items?
cx.tcx.ensure().const_eval_poly(def_id);
}
hir::ItemKind::Static(_, _, body_id) => {
let def_id = cx.tcx.hir().body_owner_def_id(body_id).to_def_id();
cx.tcx.ensure().eval_static_initializer(def_id);
}
_ => {}
}
}
}

oli-obk marked this conversation as resolved.
Show resolved Hide resolved
declare_lint! {
/// The `trivial_bounds` lint detects trait bounds that don't depend on
/// any type parameters.
Expand Down
2 changes: 0 additions & 2 deletions compiler/rustc_lint/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -213,8 +213,6 @@ late_lint_methods!(
ExplicitOutlivesRequirements: ExplicitOutlivesRequirements,
InvalidValue: InvalidValue,
DerefNullPtr: DerefNullPtr,
// May Depend on constants elsewhere
UnusedBrokenConst: UnusedBrokenConst,
UnstableFeatures: UnstableFeatures,
UngatedAsyncFnTrackCaller: UngatedAsyncFnTrackCaller,
ArrayIntoIter: ArrayIntoIter::default(),
Expand Down
5 changes: 0 additions & 5 deletions src/tools/clippy/tests/ui-toml/suppress_lint_in_const/test.rs
Original file line number Diff line number Diff line change
Expand Up @@ -13,8 +13,6 @@

const ARR: [i32; 2] = [1, 2];
const REF: &i32 = &ARR[idx()]; // Ok, should not produce stderr, since `suppress-restriction-lint-in-const` is set true.
const REF_ERR: &i32 = &ARR[idx4()]; // Ok, let rustc handle const contexts.
//~^ ERROR: failed

const fn idx() -> usize {
1
Expand All @@ -35,9 +33,6 @@ fn main() {
x[const { idx() }]; // Ok, should not produce stderr.
x[const { idx4() }]; // Ok, let rustc's `unconditional_panic` lint handle `usize` indexing on arrays.
const { &ARR[idx()] }; // Ok, should not produce stderr, since `suppress-restriction-lint-in-const` is set true.
const { &ARR[idx4()] }; // Ok, should not produce stderr, since `suppress-restriction-lint-in-const` is set true.
//
//~^^ ERROR: failed

let y = &x;
y[0]; // Ok, referencing shouldn't affect this lint. See the issue 6021
Expand Down
33 changes: 7 additions & 26 deletions src/tools/clippy/tests/ui-toml/suppress_lint_in_const/test.stderr
Original file line number Diff line number Diff line change
@@ -1,17 +1,5 @@
error[E0080]: evaluation of `main::{constant#3}` failed
--> $DIR/test.rs:38:14
|
LL | const { &ARR[idx4()] }; // Ok, should not produce stderr, since `suppress-restriction-lint-in-const` is set true.
| ^^^^^^^^^^^ index out of bounds: the length is 2 but the index is 4

note: erroneous constant encountered
--> $DIR/test.rs:38:5
|
LL | const { &ARR[idx4()] }; // Ok, should not produce stderr, since `suppress-restriction-lint-in-const` is set true.
| ^^^^^^^^^^^^^^^^^^^^^^

error: indexing may panic
--> $DIR/test.rs:29:5
--> $DIR/test.rs:27:5
|
LL | x[index];
| ^^^^^^^^
Expand All @@ -21,51 +9,44 @@ LL | x[index];
= help: to override `-D warnings` add `#[allow(clippy::indexing_slicing)]`

error: indexing may panic
--> $DIR/test.rs:47:5
--> $DIR/test.rs:42:5
|
LL | v[0];
| ^^^^
|
= help: consider using `.get(n)` or `.get_mut(n)` instead

error: indexing may panic
--> $DIR/test.rs:48:5
--> $DIR/test.rs:43:5
|
LL | v[10];
| ^^^^^
|
= help: consider using `.get(n)` or `.get_mut(n)` instead

error: indexing may panic
--> $DIR/test.rs:49:5
--> $DIR/test.rs:44:5
|
LL | v[1 << 3];
| ^^^^^^^^^
|
= help: consider using `.get(n)` or `.get_mut(n)` instead

error: indexing may panic
--> $DIR/test.rs:55:5
--> $DIR/test.rs:50:5
|
LL | v[N];
| ^^^^
|
= help: consider using `.get(n)` or `.get_mut(n)` instead

error: indexing may panic
--> $DIR/test.rs:56:5
--> $DIR/test.rs:51:5
|
LL | v[M];
| ^^^^
|
= help: consider using `.get(n)` or `.get_mut(n)` instead

error[E0080]: evaluation of constant value failed
--> $DIR/test.rs:16:24
|
LL | const REF_ERR: &i32 = &ARR[idx4()]; // Ok, let rustc handle const contexts.
| ^^^^^^^^^^^ index out of bounds: the length is 2 but the index is 4

error: aborting due to 8 previous errors
error: aborting due to 6 previous errors

For more information about this error, try `rustc --explain E0080`.
2 changes: 0 additions & 2 deletions src/tools/clippy/tests/ui/indexing_slicing_index.rs
Original file line number Diff line number Diff line change
Expand Up @@ -13,8 +13,6 @@
const ARR: [i32; 2] = [1, 2];
const REF: &i32 = &ARR[idx()]; // This should be linted, since `suppress-restriction-lint-in-const` default is false.
//~^ ERROR: indexing may panic
const REF_ERR: &i32 = &ARR[idx4()]; // Ok, let rustc handle const contexts.
//~^ ERROR: indexing may panic

const fn idx() -> usize {
1
Expand Down
47 changes: 16 additions & 31 deletions src/tools/clippy/tests/ui/indexing_slicing_index.stderr
Original file line number Diff line number Diff line change
Expand Up @@ -9,37 +9,28 @@ LL | const REF: &i32 = &ARR[idx()]; // This should be linted, since `suppress-re
= note: `-D clippy::indexing-slicing` implied by `-D warnings`
= help: to override `-D warnings` add `#[allow(clippy::indexing_slicing)]`

error: indexing may panic
--> $DIR/indexing_slicing_index.rs:16:24
|
LL | const REF_ERR: &i32 = &ARR[idx4()]; // Ok, let rustc handle const contexts.
| ^^^^^^^^^^^
|
= help: consider using `.get(n)` or `.get_mut(n)` instead
= note: the suggestion might not be applicable in constant blocks

error[E0080]: evaluation of `main::{constant#3}` failed
--> $DIR/indexing_slicing_index.rs:48:14
--> $DIR/indexing_slicing_index.rs:46:14
|
LL | const { &ARR[idx4()] };
| ^^^^^^^^^^^ index out of bounds: the length is 2 but the index is 4

note: erroneous constant encountered
--> $DIR/indexing_slicing_index.rs:48:5
--> $DIR/indexing_slicing_index.rs:46:5
|
LL | const { &ARR[idx4()] };
| ^^^^^^^^^^^^^^^^^^^^^^

error: indexing may panic
--> $DIR/indexing_slicing_index.rs:29:5
--> $DIR/indexing_slicing_index.rs:27:5
|
LL | x[index];
| ^^^^^^^^
|
= help: consider using `.get(n)` or `.get_mut(n)` instead

error: index is out of bounds
--> $DIR/indexing_slicing_index.rs:32:5
--> $DIR/indexing_slicing_index.rs:30:5
|
LL | x[4];
| ^^^^
Expand All @@ -48,13 +39,13 @@ LL | x[4];
= help: to override `-D warnings` add `#[allow(clippy::out_of_bounds_indexing)]`

error: index is out of bounds
--> $DIR/indexing_slicing_index.rs:34:5
--> $DIR/indexing_slicing_index.rs:32:5
|
LL | x[1 << 3];
| ^^^^^^^^^

error: indexing may panic
--> $DIR/indexing_slicing_index.rs:45:14
--> $DIR/indexing_slicing_index.rs:43:14
|
LL | const { &ARR[idx()] };
| ^^^^^^^^^^
Expand All @@ -63,7 +54,7 @@ LL | const { &ARR[idx()] };
= note: the suggestion might not be applicable in constant blocks

error: indexing may panic
--> $DIR/indexing_slicing_index.rs:48:14
--> $DIR/indexing_slicing_index.rs:46:14
|
LL | const { &ARR[idx4()] };
| ^^^^^^^^^^^
Expand All @@ -72,69 +63,63 @@ LL | const { &ARR[idx4()] };
= note: the suggestion might not be applicable in constant blocks

error: index is out of bounds
--> $DIR/indexing_slicing_index.rs:55:5
--> $DIR/indexing_slicing_index.rs:53:5
|
LL | y[4];
| ^^^^

error: indexing may panic
--> $DIR/indexing_slicing_index.rs:58:5
--> $DIR/indexing_slicing_index.rs:56:5
|
LL | v[0];
| ^^^^
|
= help: consider using `.get(n)` or `.get_mut(n)` instead

error: indexing may panic
--> $DIR/indexing_slicing_index.rs:60:5
--> $DIR/indexing_slicing_index.rs:58:5
|
LL | v[10];
| ^^^^^
|
= help: consider using `.get(n)` or `.get_mut(n)` instead

error: indexing may panic
--> $DIR/indexing_slicing_index.rs:62:5
--> $DIR/indexing_slicing_index.rs:60:5
|
LL | v[1 << 3];
| ^^^^^^^^^
|
= help: consider using `.get(n)` or `.get_mut(n)` instead

error: index is out of bounds
--> $DIR/indexing_slicing_index.rs:70:5
--> $DIR/indexing_slicing_index.rs:68:5
|
LL | x[N];
| ^^^^

error: indexing may panic
--> $DIR/indexing_slicing_index.rs:73:5
--> $DIR/indexing_slicing_index.rs:71:5
|
LL | v[N];
| ^^^^
|
= help: consider using `.get(n)` or `.get_mut(n)` instead

error: indexing may panic
--> $DIR/indexing_slicing_index.rs:75:5
--> $DIR/indexing_slicing_index.rs:73:5
|
LL | v[M];
| ^^^^
|
= help: consider using `.get(n)` or `.get_mut(n)` instead

error: index is out of bounds
--> $DIR/indexing_slicing_index.rs:79:13
--> $DIR/indexing_slicing_index.rs:77:13
|
LL | let _ = x[4];
| ^^^^

error[E0080]: evaluation of constant value failed
--> $DIR/indexing_slicing_index.rs:16:24
|
LL | const REF_ERR: &i32 = &ARR[idx4()]; // Ok, let rustc handle const contexts.
| ^^^^^^^^^^^ index out of bounds: the length is 2 but the index is 4

error: aborting due to 17 previous errors
error: aborting due to 15 previous errors

For more information about this error, try `rustc --explain E0080`.
2 changes: 1 addition & 1 deletion tests/mir-opt/dataflow-const-prop/enum.rs
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ fn statics() {

static RC: &E = &E::V2(4);

// CHECK: [[t:_.*]] = const {alloc2: &&E};
// CHECK: [[t:_.*]] = const {alloc5: &&E};
// CHECK: [[e2]] = (*[[t]]);
let e2 = RC;

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,12 +4,12 @@ trait Foo {
const BAR: u32;
}

const IMPL_REF_BAR: u32 = GlobalImplRef::BAR;
const IMPL_REF_BAR: u32 = GlobalImplRef::BAR; //~ ERROR E0391

struct GlobalImplRef;

impl GlobalImplRef {
const BAR: u32 = IMPL_REF_BAR; //~ ERROR E0391
const BAR: u32 = IMPL_REF_BAR;
}

fn main() {}
Original file line number Diff line number Diff line change
@@ -1,14 +1,9 @@
error[E0391]: cycle detected when elaborating drops for `<impl at $DIR/issue-24949-assoc-const-static-recursion-impl.rs:11:1: 11:19>::BAR`
--> $DIR/issue-24949-assoc-const-static-recursion-impl.rs:12:22
|
LL | const BAR: u32 = IMPL_REF_BAR;
| ^^^^^^^^^^^^
|
note: ...which requires simplifying constant for the type system `IMPL_REF_BAR`...
error[E0391]: cycle detected when simplifying constant for the type system `IMPL_REF_BAR`
--> $DIR/issue-24949-assoc-const-static-recursion-impl.rs:7:1
|
LL | const IMPL_REF_BAR: u32 = GlobalImplRef::BAR;
| ^^^^^^^^^^^^^^^^^^^^^^^
|
note: ...which requires const-evaluating + checking `IMPL_REF_BAR`...
--> $DIR/issue-24949-assoc-const-static-recursion-impl.rs:7:27
|
Expand All @@ -29,7 +24,12 @@ note: ...which requires caching mir of `<impl at $DIR/issue-24949-assoc-const-st
|
LL | const BAR: u32 = IMPL_REF_BAR;
| ^^^^^^^^^^^^^^
= note: ...which again requires elaborating drops for `<impl at $DIR/issue-24949-assoc-const-static-recursion-impl.rs:11:1: 11:19>::BAR`, completing the cycle
note: ...which requires elaborating drops for `<impl at $DIR/issue-24949-assoc-const-static-recursion-impl.rs:11:1: 11:19>::BAR`...
--> $DIR/issue-24949-assoc-const-static-recursion-impl.rs:12:22
|
LL | const BAR: u32 = IMPL_REF_BAR;
| ^^^^^^^^^^^^
= note: ...which again requires simplifying constant for the type system `IMPL_REF_BAR`, completing the cycle
= note: cycle used when running analysis passes on this crate
= note: see https://rustc-dev-guide.rust-lang.org/overview.html#queries and https://rustc-dev-guide.rust-lang.org/query.html for more information

Expand Down
Loading
Loading