diff options
| -rw-r--r-- | compiler/rustc_hir_typeck/src/lib.rs | 6 | ||||
| -rw-r--r-- | compiler/rustc_interface/src/passes.rs | 1 | ||||
| -rw-r--r-- | compiler/rustc_middle/src/hooks/mod.rs | 5 | ||||
| -rw-r--r-- | compiler/rustc_middle/src/query/mod.rs | 4 | ||||
| -rw-r--r-- | compiler/rustc_passes/src/lib.rs | 2 | ||||
| -rw-r--r-- | compiler/rustc_passes/src/naked_functions.rs | 39 |
6 files changed, 19 insertions, 38 deletions
diff --git a/compiler/rustc_hir_typeck/src/lib.rs b/compiler/rustc_hir_typeck/src/lib.rs index 5a814822163..30651534d7b 100644 --- a/compiler/rustc_hir_typeck/src/lib.rs +++ b/compiler/rustc_hir_typeck/src/lib.rs @@ -55,8 +55,8 @@ use rustc_middle::query::Providers; use rustc_middle::ty::{self, Ty, TyCtxt}; use rustc_middle::{bug, span_bug}; use rustc_session::config; -use rustc_span::Span; use rustc_span::def_id::LocalDefId; +use rustc_span::{Span, sym}; use tracing::{debug, instrument}; use typeck_root_ctxt::TypeckRootCtxt; @@ -170,6 +170,10 @@ fn typeck_with_inspect<'tcx>( .map(|(idx, ty)| fcx.normalize(arg_span(idx), ty)), ); + if tcx.has_attr(def_id, sym::naked) { + tcx.typeck_naked_fn(def_id, body); + } + check_fn(&mut fcx, fn_sig, None, decl, def_id, body, tcx.features().unsized_fn_params()); } else { let expected_type = if let Some(infer_ty) = infer_type_if_missing(&fcx, node) { diff --git a/compiler/rustc_interface/src/passes.rs b/compiler/rustc_interface/src/passes.rs index 75d92ae7a2e..696f4b493f2 100644 --- a/compiler/rustc_interface/src/passes.rs +++ b/compiler/rustc_interface/src/passes.rs @@ -960,7 +960,6 @@ fn run_required_analyses(tcx: TyCtxt<'_>) { tcx.par_hir_for_each_module(|module| { tcx.ensure_ok().check_mod_loops(module); tcx.ensure_ok().check_mod_attrs(module); - tcx.ensure_ok().check_mod_naked_functions(module); tcx.ensure_ok().check_mod_unstable_api_usage(module); }); }, diff --git a/compiler/rustc_middle/src/hooks/mod.rs b/compiler/rustc_middle/src/hooks/mod.rs index c5ce6efcb81..12110c36044 100644 --- a/compiler/rustc_middle/src/hooks/mod.rs +++ b/compiler/rustc_middle/src/hooks/mod.rs @@ -102,6 +102,11 @@ declare_hooks! { /// Ensure the given scalar is valid for the given type. /// This checks non-recursive runtime validity. hook validate_scalar_in_layout(scalar: crate::ty::ScalarInt, ty: Ty<'tcx>) -> bool; + + /// Naked fns can only have trivial binding patterns in arguments, + /// may not actually use those arguments, and the body must consist of just + /// a single asm statement. + hook typeck_naked_fn(def_id: LocalDefId, body: &'tcx rustc_hir::Body<'tcx>) -> (); } #[cold] diff --git a/compiler/rustc_middle/src/query/mod.rs b/compiler/rustc_middle/src/query/mod.rs index 279033ee072..bb0b0a41d5a 100644 --- a/compiler/rustc_middle/src/query/mod.rs +++ b/compiler/rustc_middle/src/query/mod.rs @@ -1119,10 +1119,6 @@ rustc_queries! { desc { |tcx| "checking loops in {}", describe_as_module(key, tcx) } } - query check_mod_naked_functions(key: LocalModDefId) { - desc { |tcx| "checking naked functions in {}", describe_as_module(key, tcx) } - } - query check_mod_privacy(key: LocalModDefId) { desc { |tcx| "checking privacy in {}", describe_as_module(key.to_local_def_id(), tcx) } } diff --git a/compiler/rustc_passes/src/lib.rs b/compiler/rustc_passes/src/lib.rs index f9445485f60..aa4c56846c5 100644 --- a/compiler/rustc_passes/src/lib.rs +++ b/compiler/rustc_passes/src/lib.rs @@ -14,7 +14,7 @@ #![feature(try_blocks)] // tidy-alphabetical-end -use rustc_middle::query::Providers; +use rustc_middle::util::Providers; pub mod abi_test; mod check_attr; diff --git a/compiler/rustc_passes/src/naked_functions.rs b/compiler/rustc_passes/src/naked_functions.rs index e9e88424bcc..4397a323dfc 100644 --- a/compiler/rustc_passes/src/naked_functions.rs +++ b/compiler/rustc_passes/src/naked_functions.rs @@ -1,13 +1,12 @@ //! Checks validity of naked functions. use rustc_hir as hir; -use rustc_hir::def::DefKind; -use rustc_hir::def_id::{LocalDefId, LocalModDefId}; +use rustc_hir::def_id::LocalDefId; use rustc_hir::intravisit::Visitor; use rustc_hir::{ExprKind, HirIdSet, StmtKind}; -use rustc_middle::query::Providers; use rustc_middle::span_bug; use rustc_middle::ty::TyCtxt; +use rustc_middle::util::Providers; use rustc_span::{Span, sym}; use crate::errors::{ @@ -15,36 +14,14 @@ use crate::errors::{ }; pub(crate) fn provide(providers: &mut Providers) { - *providers = Providers { check_mod_naked_functions, ..*providers }; + providers.hooks.typeck_naked_fn = typeck_naked_fn; } -fn check_mod_naked_functions(tcx: TyCtxt<'_>, module_def_id: LocalModDefId) { - let items = tcx.hir_module_items(module_def_id); - for def_id in items.definitions() { - if !matches!(tcx.def_kind(def_id), DefKind::Fn | DefKind::AssocFn) { - continue; - } - - let body = match tcx.hir_node_by_def_id(def_id) { - hir::Node::Item(hir::Item { - kind: hir::ItemKind::Fn { body: body_id, .. }, .. - }) - | hir::Node::TraitItem(hir::TraitItem { - kind: hir::TraitItemKind::Fn(_, hir::TraitFn::Provided(body_id)), - .. - }) - | hir::Node::ImplItem(hir::ImplItem { - kind: hir::ImplItemKind::Fn(_, body_id), .. - }) => tcx.hir_body(*body_id), - _ => continue, - }; - - if tcx.has_attr(def_id, sym::naked) { - check_no_patterns(tcx, body.params); - check_no_parameters_use(tcx, body); - check_asm(tcx, def_id, body); - } - } +fn typeck_naked_fn<'tcx>(tcx: TyCtxt<'tcx>, def_id: LocalDefId, body: &'tcx hir::Body<'tcx>) { + debug_assert!(tcx.has_attr(def_id, sym::naked)); + check_no_patterns(tcx, body.params); + check_no_parameters_use(tcx, body); + check_asm(tcx, def_id, body); } /// Checks that parameters don't use patterns. Mirrors the checks for function declarations. |
