]> git.lizzy.rs Git - rust.git/blobdiff - compiler/rustc_ast_passes/src/feature_gate.rs
Add a new ABI to support cmse_nonsecure_call
[rust.git] / compiler / rustc_ast_passes / src / feature_gate.rs
index 6a9d6d2ed121eabad7d4405414c866b44a65e449..62d0721c35fb1edd9f94ab33cbda8ac1d57c8185 100644 (file)
 use tracing::debug;
 
 macro_rules! gate_feature_fn {
+    ($visitor: expr, $has_feature: expr, $span: expr, $name: expr, $explain: expr, $help: expr) => {{
+        let (visitor, has_feature, span, name, explain, help) =
+            (&*$visitor, $has_feature, $span, $name, $explain, $help);
+        let has_feature: bool = has_feature(visitor.features);
+        debug!("gate_feature(feature = {:?}, span = {:?}); has? {}", name, span, has_feature);
+        if !has_feature && !span.allows_unstable($name) {
+            feature_err_issue(&visitor.sess.parse_sess, name, span, GateIssue::Language, explain)
+                .help(help)
+                .emit();
+        }
+    }};
     ($visitor: expr, $has_feature: expr, $span: expr, $name: expr, $explain: expr) => {{
         let (visitor, has_feature, span, name, explain) =
             (&*$visitor, $has_feature, $span, $name, $explain);
@@ -27,6 +38,9 @@ macro_rules! gate_feature_fn {
 }
 
 macro_rules! gate_feature_post {
+    ($visitor: expr, $feature: ident, $span: expr, $explain: expr, $help: expr) => {
+        gate_feature_fn!($visitor, |x: &Features| x.$feature, $span, sym::$feature, $explain, $help)
+    };
     ($visitor: expr, $feature: ident, $span: expr, $explain: expr) => {
         gate_feature_fn!($visitor, |x: &Features| x.$feature, $span, sym::$feature, $explain)
     };
@@ -142,6 +156,14 @@ fn check_abi(&self, abi: ast::StrLit) {
                     "efiapi ABI is experimental and subject to change"
                 );
             }
+            "C-cmse-nonsecure-call" => {
+                gate_feature_post!(
+                    &self,
+                    abi_c_cmse_nonsecure_call,
+                    span,
+                    "C-cmse-nonsecure-call ABI is experimental and subject to change"
+                );
+            }
             abi => self
                 .sess
                 .parse_sess
@@ -356,7 +378,7 @@ fn visit_item(&mut self, i: &'a ast::Item) {
                     gate_feature_post!(
                         &self,
                         negative_impls,
-                        span.to(of_trait.as_ref().map(|t| t.path.span).unwrap_or(span)),
+                        span.to(of_trait.as_ref().map_or(span, |t| t.path.span)),
                         "negative trait bounds are not yet fully implemented; \
                          use marker types for now"
                     );
@@ -597,6 +619,13 @@ pub fn check_crate(krate: &ast::Crate, sess: &Session) {
 
     let spans = sess.parse_sess.gated_spans.spans.borrow();
     macro_rules! gate_all {
+        ($gate:ident, $msg:literal, $help:literal) => {
+            if let Some(spans) = spans.get(&sym::$gate) {
+                for span in spans {
+                    gate_feature_post!(&visitor, $gate, *span, $msg, $help);
+                }
+            }
+        };
         ($gate:ident, $msg:literal) => {
             if let Some(spans) = spans.get(&sym::$gate) {
                 for span in spans {
@@ -607,7 +636,11 @@ macro_rules! gate_all {
     }
     gate_all!(if_let_guard, "`if let` guards are experimental");
     gate_all!(let_chains, "`let` expressions in this position are experimental");
-    gate_all!(async_closure, "async closures are unstable");
+    gate_all!(
+        async_closure,
+        "async closures are unstable",
+        "to use an async block, remove the `||`: `async {`"
+    );
     gate_all!(generators, "yield syntax is experimental");
     gate_all!(or_patterns, "or-patterns syntax is experimental");
     gate_all!(raw_ref_op, "raw address of syntax is experimental");
@@ -619,6 +652,10 @@ macro_rules! gate_all {
         extended_key_value_attributes,
         "arbitrary expressions in key-value attributes are unstable"
     );
+    gate_all!(
+        const_generics_defaults,
+        "default values for const generic parameters are experimental"
+    );
     if sess.parse_sess.span_diagnostic.err_count() == 0 {
         // Errors for `destructuring_assignment` can get quite noisy, especially where `_` is
         // involved, so we only emit errors where there are no other parsing errors.