about summary refs log tree commit diff
path: root/compiler/rustc_attr/src
diff options
context:
space:
mode:
authorbors <bors@rust-lang.org>2022-07-14 13:42:09 +0000
committerbors <bors@rust-lang.org>2022-07-14 13:42:09 +0000
commit24699bcbadff59693a89a5184afed87f6416cdea (patch)
treed982a08c704d13e4ace62c79465e57dd4a6d6f38 /compiler/rustc_attr/src
parentf1a8854f9be2e5cad764d630a53d26c7b72f8162 (diff)
parent3e2c5b5f751c3375c2ce4a2d2f54e4d8499e454d (diff)
downloadrust-24699bcbadff59693a89a5184afed87f6416cdea.tar.gz
rust-24699bcbadff59693a89a5184afed87f6416cdea.zip
Auto merge of #95956 - yaahc:stable-in-unstable, r=cjgillot
Support unstable moves via stable in unstable items

part of https://rust-lang.zulipchat.com/#narrow/stream/131828-t-compiler/topic/moving.20items.20to.20core.20unstably and a blocker of https://github.com/rust-lang/rust/pull/90328.

The libs-api team needs the ability to move an already stable item to a new location unstably, in this case for Error in core. Otherwise these changes are insta-stable making them much harder to merge.

This PR attempts to solve the problem by checking the stability of path segments as well as the last item in the path itself, which is currently the only thing checked.
Diffstat (limited to 'compiler/rustc_attr/src')
-rw-r--r--compiler/rustc_attr/src/builtin.rs29
1 files changed, 27 insertions, 2 deletions
diff --git a/compiler/rustc_attr/src/builtin.rs b/compiler/rustc_attr/src/builtin.rs
index 6673d75d99d..dcfbecedfe8 100644
--- a/compiler/rustc_attr/src/builtin.rs
+++ b/compiler/rustc_attr/src/builtin.rs
@@ -137,7 +137,7 @@ impl ConstStability {
 pub enum StabilityLevel {
     // Reason for the current stability level and the relevant rust-lang issue
     Unstable { reason: Option<Symbol>, issue: Option<NonZeroU32>, is_soft: bool },
-    Stable { since: Symbol },
+    Stable { since: Symbol, allowed_through_unstable_modules: bool },
 }
 
 impl StabilityLevel {
@@ -172,6 +172,7 @@ where
     let mut stab: Option<(Stability, Span)> = None;
     let mut const_stab: Option<(ConstStability, Span)> = None;
     let mut promotable = false;
+    let mut allowed_through_unstable_modules = false;
 
     let diagnostic = &sess.parse_sess.span_diagnostic;
 
@@ -182,6 +183,7 @@ where
             sym::unstable,
             sym::stable,
             sym::rustc_promotable,
+            sym::rustc_allowed_through_unstable_modules,
         ]
         .iter()
         .any(|&s| attr.has_name(s))
@@ -193,6 +195,8 @@ where
 
         if attr.has_name(sym::rustc_promotable) {
             promotable = true;
+        } else if attr.has_name(sym::rustc_allowed_through_unstable_modules) {
+            allowed_through_unstable_modules = true;
         }
         // attributes with data
         else if let Some(MetaItem { kind: MetaItemKind::List(ref metas), .. }) = meta {
@@ -406,7 +410,7 @@ where
 
                     match (feature, since) {
                         (Some(feature), Some(since)) => {
-                            let level = Stable { since };
+                            let level = Stable { since, allowed_through_unstable_modules: false };
                             if sym::stable == meta_name {
                                 stab = Some((Stability { level, feature }, attr.span));
                             } else {
@@ -447,6 +451,27 @@ where
         }
     }
 
+    if allowed_through_unstable_modules {
+        if let Some((
+            Stability {
+                level: StabilityLevel::Stable { ref mut allowed_through_unstable_modules, .. },
+                ..
+            },
+            _,
+        )) = stab
+        {
+            *allowed_through_unstable_modules = true;
+        } else {
+            struct_span_err!(
+                diagnostic,
+                item_sp,
+                E0789,
+                "`rustc_allowed_through_unstable_modules` attribute must be paired with a `stable` attribute"
+            )
+            .emit();
+        }
+    }
+
     (stab, const_stab)
 }