Skip to content

Commit c0e0d8f

Browse files
committed
Require the constness query to only be invoked on things that can have constness
1 parent 3d0bf68 commit c0e0d8f

File tree

6 files changed

+66
-13
lines changed

6 files changed

+66
-13
lines changed

Diff for: compiler/rustc_const_eval/src/const_eval/fn_queries.rs

+5-4
Original file line numberDiff line numberDiff line change
@@ -18,9 +18,7 @@ fn constness(tcx: TyCtxt<'_>, def_id: LocalDefId) -> hir::Constness {
1818
let node = tcx.hir_node_by_def_id(def_id);
1919

2020
match node {
21-
hir::Node::Ctor(_)
22-
| hir::Node::AnonConst(_)
23-
| hir::Node::ConstBlock(_)
21+
hir::Node::Ctor(hir::VariantData::Tuple(..))
2422
| hir::Node::ImplItem(hir::ImplItem { kind: hir::ImplItemKind::Const(..), .. }) => {
2523
hir::Constness::Const
2624
}
@@ -41,7 +39,10 @@ fn constness(tcx: TyCtxt<'_>, def_id: LocalDefId) -> hir::Constness {
4139
let is_const = is_parent_const_impl_raw(tcx, def_id);
4240
if is_const { hir::Constness::Const } else { hir::Constness::NotConst }
4341
} else {
44-
hir::Constness::NotConst
42+
tcx.dcx().span_bug(
43+
tcx.def_span(def_id),
44+
format!("should not be requesting the constness of items that can't be const: {node:#?}: {:?}", tcx.def_kind(def_id))
45+
)
4546
}
4647
}
4748
}

Diff for: compiler/rustc_hir/src/hir.rs

+1-3
Original file line numberDiff line numberDiff line change
@@ -4044,9 +4044,7 @@ impl<'hir> Node<'hir> {
40444044
_ => None,
40454045
},
40464046
Node::TraitItem(ti) => match ti.kind {
4047-
TraitItemKind::Fn(ref sig, TraitFn::Provided(_)) => {
4048-
Some(FnKind::Method(ti.ident, sig))
4049-
}
4047+
TraitItemKind::Fn(ref sig, _) => Some(FnKind::Method(ti.ident, sig)),
40504048
_ => None,
40514049
},
40524050
Node::ImplItem(ii) => match ii.kind {

Diff for: compiler/rustc_metadata/src/rmeta/encoder.rs

+3-2
Original file line numberDiff line numberDiff line change
@@ -1268,8 +1268,7 @@ fn should_encode_constness(def_kind: DefKind) -> bool {
12681268
| DefKind::AssocFn
12691269
| DefKind::Closure
12701270
| DefKind::Impl { of_trait: true }
1271-
| DefKind::Variant
1272-
| DefKind::Ctor(..) => true,
1271+
| DefKind::Ctor(_, CtorKind::Fn) => true,
12731272

12741273
DefKind::Struct
12751274
| DefKind::Union
@@ -1296,6 +1295,8 @@ fn should_encode_constness(def_kind: DefKind) -> bool {
12961295
| DefKind::LifetimeParam
12971296
| DefKind::GlobalAsm
12981297
| DefKind::ExternCrate
1298+
| DefKind::Ctor(_, CtorKind::Const)
1299+
| DefKind::Variant
12991300
| DefKind::SyntheticCoroutineBody => false,
13001301
}
13011302
}

Diff for: compiler/rustc_middle/src/query/mod.rs

+3-1
Original file line numberDiff line numberDiff line change
@@ -746,7 +746,9 @@ rustc_queries! {
746746
desc { |tcx| "computing drop-check constraints for `{}`", tcx.def_path_str(key) }
747747
}
748748

749-
/// Returns `true` if this is a const fn / const impl.
749+
/// Returns the constness of functions and impls.
750+
///
751+
/// Will ICE if used on things that are always const or never const.
750752
///
751753
/// **Do not call this function manually.** It is only meant to cache the base data for the
752754
/// higher-level functions. Consider using `is_const_fn` or `is_const_trait_impl` instead.

Diff for: compiler/rustc_middle/src/ty/mod.rs

+12-2
Original file line numberDiff line numberDiff line change
@@ -2014,7 +2014,17 @@ impl<'tcx> TyCtxt<'tcx> {
20142014
self.constness(def_id) == hir::Constness::Const
20152015
}
20162016
DefKind::Trait => self.is_const_trait(def_id),
2017-
DefKind::AssocTy | DefKind::AssocFn => {
2017+
DefKind::AssocTy => {
2018+
let parent_def_id = self.parent(def_id);
2019+
match self.def_kind(parent_def_id) {
2020+
DefKind::Impl { of_trait: false } => false,
2021+
DefKind::Impl { of_trait: true } | DefKind::Trait => {
2022+
self.is_conditionally_const(parent_def_id)
2023+
}
2024+
_ => bug!("unexpected parent item of associated type: {parent_def_id:?}"),
2025+
}
2026+
}
2027+
DefKind::AssocFn => {
20182028
let parent_def_id = self.parent(def_id);
20192029
match self.def_kind(parent_def_id) {
20202030
DefKind::Impl { of_trait: false } => {
@@ -2023,7 +2033,7 @@ impl<'tcx> TyCtxt<'tcx> {
20232033
DefKind::Impl { of_trait: true } | DefKind::Trait => {
20242034
self.is_conditionally_const(parent_def_id)
20252035
}
2026-
_ => bug!("unexpected parent item of associated item: {parent_def_id:?}"),
2036+
_ => bug!("unexpected parent item of associated fn: {parent_def_id:?}"),
20272037
}
20282038
}
20292039
DefKind::OpaqueTy => match self.opaque_ty_origin(def_id) {

Diff for: src/tools/clippy/clippy_lints/src/manual_float_methods.rs

+42-1
Original file line numberDiff line numberDiff line change
@@ -6,8 +6,11 @@ use clippy_utils::source::SpanRangeExt;
66
use clippy_utils::{is_from_proc_macro, path_to_local};
77
use rustc_errors::Applicability;
88
use rustc_hir::{BinOpKind, Constness, Expr, ExprKind};
9+
use rustc_hir::def::DefKind;
10+
use rustc_hir::def_id::DefId;
911
use rustc_lint::{LateContext, LateLintPass, Lint, LintContext};
1012
use rustc_middle::lint::in_external_macro;
13+
use rustc_middle::ty::TyCtxt;
1114
use rustc_session::impl_lint_pass;
1215

1316
declare_clippy_lint! {
@@ -94,6 +97,44 @@ impl ManualFloatMethods {
9497
}
9598
}
9699

100+
fn is_not_const(tcx: TyCtxt<'_>, def_id: DefId) -> bool {
101+
match tcx.def_kind(def_id) {
102+
DefKind::Mod
103+
| DefKind::Struct
104+
| DefKind::Union
105+
| DefKind::Enum
106+
| DefKind::Variant
107+
| DefKind::Trait
108+
| DefKind::TyAlias
109+
| DefKind::ForeignTy
110+
| DefKind::TraitAlias
111+
| DefKind::AssocTy
112+
| DefKind::Macro(..)
113+
| DefKind::Field
114+
| DefKind::LifetimeParam
115+
| DefKind::ExternCrate
116+
| DefKind::Use
117+
| DefKind::ForeignMod
118+
| DefKind::GlobalAsm
119+
| DefKind::Impl { .. }
120+
| DefKind::OpaqueTy
121+
| DefKind::SyntheticCoroutineBody
122+
| DefKind::TyParam => true,
123+
124+
DefKind::AnonConst
125+
| DefKind::InlineConst
126+
| DefKind::Const
127+
| DefKind::ConstParam
128+
| DefKind::Static { .. }
129+
| DefKind::Ctor(..)
130+
| DefKind::AssocConst => false,
131+
132+
DefKind::Fn
133+
| DefKind::AssocFn
134+
| DefKind::Closure => tcx.constness(def_id) == Constness::NotConst,
135+
}
136+
}
137+
97138
impl<'tcx> LateLintPass<'tcx> for ManualFloatMethods {
98139
fn check_expr(&mut self, cx: &LateContext<'tcx>, expr: &'tcx Expr<'tcx>) {
99140
if let ExprKind::Binary(kind, lhs, rhs) = expr.kind
@@ -105,7 +146,7 @@ impl<'tcx> LateLintPass<'tcx> for ManualFloatMethods {
105146
&& exprs.iter_mut().partition_in_place(|i| path_to_local(i).is_some()) == 2
106147
&& !in_external_macro(cx.sess(), expr.span)
107148
&& (
108-
matches!(cx.tcx.constness(cx.tcx.hir().enclosing_body_owner(expr.hir_id)), Constness::NotConst)
149+
is_not_const(cx.tcx, cx.tcx.hir().enclosing_body_owner(expr.hir_id).into())
109150
|| self.msrv.meets(msrvs::CONST_FLOAT_CLASSIFY)
110151
)
111152
&& let [first, second, const_1, const_2] = exprs

0 commit comments

Comments
 (0)