about summary refs log tree commit diff
path: root/compiler/rustc_codegen_ssa
diff options
context:
space:
mode:
authorJonathan Brouwer <jonathantbrouwer@gmail.com>2025-06-22 12:14:38 +0200
committerJonathan Brouwer <jonathantbrouwer@gmail.com>2025-06-22 22:17:04 +0200
commit2084831cd54eb603fec6cd85ebd9d1426b09f628 (patch)
tree54d0aff88295539e999e2d99e612761f137a973a /compiler/rustc_codegen_ssa
parent111e9bc64bbdce14122e3676978f2ceefa5bff1a (diff)
downloadrust-2084831cd54eb603fec6cd85ebd9d1426b09f628.tar.gz
rust-2084831cd54eb603fec6cd85ebd9d1426b09f628.zip
Port `#[no_mangle]` to new attribute parsing infrastructure
Signed-off-by: Jonathan Brouwer <jonathantbrouwer@gmail.com>
Diffstat (limited to 'compiler/rustc_codegen_ssa')
-rw-r--r--compiler/rustc_codegen_ssa/messages.ftl2
-rw-r--r--compiler/rustc_codegen_ssa/src/codegen_attrs.rs48
-rw-r--r--compiler/rustc_codegen_ssa/src/errors.rs8
3 files changed, 34 insertions, 24 deletions
diff --git a/compiler/rustc_codegen_ssa/messages.ftl b/compiler/rustc_codegen_ssa/messages.ftl
index 2bd8644e0d7..b2e86414d90 100644
--- a/compiler/rustc_codegen_ssa/messages.ftl
+++ b/compiler/rustc_codegen_ssa/messages.ftl
@@ -221,6 +221,8 @@ codegen_ssa_multiple_main_functions = entry symbol `main` declared multiple time
 
 codegen_ssa_no_field = no field `{$name}`
 
+codegen_ssa_no_mangle_nameless = `#[no_mangle]` cannot be used on {$definition} as it has no name
+
 codegen_ssa_no_module_named =
     no module named `{$user_path}` (mangled: {$cgu_name}). available modules: {$cgu_names}
 
diff --git a/compiler/rustc_codegen_ssa/src/codegen_attrs.rs b/compiler/rustc_codegen_ssa/src/codegen_attrs.rs
index 39818be5bde..b554ccfac50 100644
--- a/compiler/rustc_codegen_ssa/src/codegen_attrs.rs
+++ b/compiler/rustc_codegen_ssa/src/codegen_attrs.rs
@@ -23,6 +23,7 @@ use rustc_span::{Ident, Span, sym};
 use rustc_target::spec::SanitizerSet;
 
 use crate::errors;
+use crate::errors::NoMangleNameless;
 use crate::target_features::{
     check_target_feature_trait_unsafe, check_tied_features, from_target_feature_attr,
 };
@@ -87,7 +88,6 @@ fn codegen_fn_attrs(tcx: TyCtxt<'_>, did: LocalDefId) -> CodegenFnAttrs {
     let mut link_ordinal_span = None;
     let mut no_sanitize_span = None;
     let mut mixed_export_name_no_mangle_lint_state = MixedExportNameAndNoMangleState::default();
-    let mut no_mangle_span = None;
 
     for attr in attrs.iter() {
         // In some cases, attribute are only valid on functions, but it's the `check_attr`
@@ -122,6 +122,25 @@ fn codegen_fn_attrs(tcx: TyCtxt<'_>, did: LocalDefId) -> CodegenFnAttrs {
                 }
                 AttributeKind::Cold(_) => codegen_fn_attrs.flags |= CodegenFnAttrFlags::COLD,
                 AttributeKind::Align { align, .. } => codegen_fn_attrs.alignment = Some(*align),
+                AttributeKind::NoMangle(attr_span) => {
+                    if tcx.opt_item_name(did.to_def_id()).is_some() {
+                        codegen_fn_attrs.flags |= CodegenFnAttrFlags::NO_MANGLE;
+                        mixed_export_name_no_mangle_lint_state.track_no_mangle(
+                            *attr_span,
+                            tcx.local_def_id_to_hir_id(did),
+                            attr,
+                        );
+                    } else {
+                        tcx.dcx().emit_err(NoMangleNameless {
+                            span: *attr_span,
+                            definition: format!(
+                                "{} {}",
+                                tcx.def_descr_article(did.to_def_id()),
+                                tcx.def_descr(did.to_def_id())
+                            ),
+                        });
+                    }
+                }
                 _ => {}
             }
         }
@@ -141,28 +160,6 @@ fn codegen_fn_attrs(tcx: TyCtxt<'_>, did: LocalDefId) -> CodegenFnAttrs {
                 codegen_fn_attrs.flags |= CodegenFnAttrFlags::ALLOCATOR_ZEROED
             }
             sym::naked => codegen_fn_attrs.flags |= CodegenFnAttrFlags::NAKED,
-            sym::no_mangle => {
-                no_mangle_span = Some(attr.span());
-                if tcx.opt_item_name(did.to_def_id()).is_some() {
-                    codegen_fn_attrs.flags |= CodegenFnAttrFlags::NO_MANGLE;
-                    mixed_export_name_no_mangle_lint_state.track_no_mangle(
-                        attr.span(),
-                        tcx.local_def_id_to_hir_id(did),
-                        attr,
-                    );
-                } else {
-                    tcx.dcx()
-                        .struct_span_err(
-                            attr.span(),
-                            format!(
-                                "`#[no_mangle]` cannot be used on {} {} as it has no name",
-                                tcx.def_descr_article(did.to_def_id()),
-                                tcx.def_descr(did.to_def_id()),
-                            ),
-                        )
-                        .emit();
-                }
-            }
             sym::rustc_std_internal_symbol => {
                 codegen_fn_attrs.flags |= CodegenFnAttrFlags::RUSTC_STD_INTERNAL_SYMBOL
             }
@@ -544,12 +541,15 @@ fn codegen_fn_attrs(tcx: TyCtxt<'_>, did: LocalDefId) -> CodegenFnAttrs {
     if codegen_fn_attrs.flags.contains(CodegenFnAttrFlags::RUSTC_STD_INTERNAL_SYMBOL)
         && codegen_fn_attrs.flags.contains(CodegenFnAttrFlags::NO_MANGLE)
     {
+        let no_mangle_span =
+            find_attr!(attrs, AttributeKind::NoMangle(no_mangle_span) => *no_mangle_span)
+                .unwrap_or_default();
         let lang_item =
             lang_items::extract(attrs).map_or(None, |(name, _span)| LangItem::from_name(name));
         let mut err = tcx
             .dcx()
             .struct_span_err(
-                no_mangle_span.unwrap_or_default(),
+                no_mangle_span,
                 "`#[no_mangle]` cannot be used on internal language items",
             )
             .with_note("Rustc requires this item to have a specific mangled name.")
diff --git a/compiler/rustc_codegen_ssa/src/errors.rs b/compiler/rustc_codegen_ssa/src/errors.rs
index 72e71b97a17..caac0f83f9d 100644
--- a/compiler/rustc_codegen_ssa/src/errors.rs
+++ b/compiler/rustc_codegen_ssa/src/errors.rs
@@ -1310,3 +1310,11 @@ impl<G: EmissionGuarantee> Diagnostic<'_, G> for TargetFeatureDisableOrEnable<'_
         diag
     }
 }
+
+#[derive(Diagnostic)]
+#[diag(codegen_ssa_no_mangle_nameless)]
+pub(crate) struct NoMangleNameless {
+    #[primary_span]
+    pub span: Span,
+    pub definition: String,
+}