summary refs log tree commit diff
path: root/compiler/rustc_mir_transform
diff options
context:
space:
mode:
authorclubby789 <jamie@hill-daniel.co.uk>2024-11-11 16:36:00 +0000
committerclubby789 <jamie@hill-daniel.co.uk>2024-11-12 13:28:05 +0000
commit94371d5a8cf3c0480a744e4727837e9d7b2281b0 (patch)
tree8f567a69fcc3504a6887efd78c8bd37eb0c718a9 /compiler/rustc_mir_transform
parent2a9cc8f4d6aee54ecf1882bfaa690165b52d66f2 (diff)
downloadrust-94371d5a8cf3c0480a744e4727837e9d7b2281b0.tar.gz
rust-94371d5a8cf3c0480a744e4727837e9d7b2281b0.zip
Validate and test `-Zmir-enable-passes`
Diffstat (limited to 'compiler/rustc_mir_transform')
-rw-r--r--compiler/rustc_mir_transform/messages.ftl2
-rw-r--r--compiler/rustc_mir_transform/src/errors.rs6
-rw-r--r--compiler/rustc_mir_transform/src/lib.rs1
-rw-r--r--compiler/rustc_mir_transform/src/pass_manager.rs24
4 files changed, 28 insertions, 5 deletions
diff --git a/compiler/rustc_mir_transform/messages.ftl b/compiler/rustc_mir_transform/messages.ftl
index c8992b8b834..9bbfae17fd9 100644
--- a/compiler/rustc_mir_transform/messages.ftl
+++ b/compiler/rustc_mir_transform/messages.ftl
@@ -34,3 +34,5 @@ mir_transform_undefined_transmute = pointers cannot be transmuted to integers du
     .note = at compile-time, pointers do not have an integer value
     .note2 = avoiding this restriction via `union` or raw pointers leads to compile-time undefined behavior
     .help = for more information, see https://doc.rust-lang.org/std/mem/fn.transmute.html
+
+mir_transform_unknown_pass_name = MIR pass `{$name}` is unknown and will be ignored
diff --git a/compiler/rustc_mir_transform/src/errors.rs b/compiler/rustc_mir_transform/src/errors.rs
index 8b309147c64..2d9eeddea2e 100644
--- a/compiler/rustc_mir_transform/src/errors.rs
+++ b/compiler/rustc_mir_transform/src/errors.rs
@@ -38,6 +38,12 @@ pub(crate) struct UnalignedPackedRef {
     pub span: Span,
 }
 
+#[derive(Diagnostic)]
+#[diag(mir_transform_unknown_pass_name)]
+pub(crate) struct UnknownPassName<'a> {
+    pub(crate) name: &'a str,
+}
+
 pub(crate) struct AssertLint<P> {
     pub span: Span,
     pub assert_kind: AssertKind<P>,
diff --git a/compiler/rustc_mir_transform/src/lib.rs b/compiler/rustc_mir_transform/src/lib.rs
index 66ac3d30ca4..68904c65252 100644
--- a/compiler/rustc_mir_transform/src/lib.rs
+++ b/compiler/rustc_mir_transform/src/lib.rs
@@ -90,7 +90,6 @@ macro_rules! declare_passes {
             )+
         )*
 
-        #[cfg(debug_assertions)]
         static PASS_NAMES: LazyLock<Vec<String>> = LazyLock::new(|| vec![
             // Fake marker pass
             "PreCodegen".to_string(),
diff --git a/compiler/rustc_mir_transform/src/pass_manager.rs b/compiler/rustc_mir_transform/src/pass_manager.rs
index 37c9f5b4c21..bc960ae0f56 100644
--- a/compiler/rustc_mir_transform/src/pass_manager.rs
+++ b/compiler/rustc_mir_transform/src/pass_manager.rs
@@ -8,7 +8,7 @@ use rustc_session::Session;
 use tracing::trace;
 
 use crate::lint::lint_body;
-use crate::validate;
+use crate::{errors, validate};
 
 thread_local! {
     static PASS_NAMES: RefCell<FxHashMap<&'static str, &'static str>> = {
@@ -198,13 +198,29 @@ fn run_passes_inner<'tcx>(
     let overridden_passes = &tcx.sess.opts.unstable_opts.mir_enable_passes;
     trace!(?overridden_passes);
 
+    let named_passes: FxIndexSet<_> =
+        overridden_passes.iter().map(|(name, _)| name.as_str()).collect();
+    let known_passes: FxIndexSet<_> = crate::PASS_NAMES.iter().map(|p| p.as_str()).collect();
+
+    for &name in named_passes.difference(&known_passes) {
+        tcx.dcx().emit_warn(errors::UnknownPassName { name });
+    }
+
+    // Verify that no passes are missing from the `declare_passes` invocation
     #[cfg(debug_assertions)]
+    #[allow(rustc::diagnostic_outside_of_impl)]
+    #[allow(rustc::untranslatable_diagnostic)]
     {
         let used_passes: FxIndexSet<_> = passes.iter().map(|p| p.name()).collect();
-        let known_passes: FxIndexSet<_> = crate::PASS_NAMES.iter().map(|p| p.as_str()).collect();
 
-        for &name in used_passes.difference(&known_passes) {
-            tcx.dcx().bug(format!("pass `{name}` is not declared in `PASS_NAMES`"));
+        let undeclared = used_passes.difference(&known_passes).collect::<Vec<_>>();
+        if let Some((name, rest)) = undeclared.split_first() {
+            let mut err =
+                tcx.dcx().struct_bug(format!("pass `{name}` is not declared in `PASS_NAMES`"));
+            for name in rest {
+                err.note(format!("pass `{name}` is also not declared in `PASS_NAMES`"));
+            }
+            err.emit();
         }
     }