about summary refs log tree commit diff
path: root/src/librustc/middle
diff options
context:
space:
mode:
authorbors <bors@rust-lang.org>2017-01-05 21:58:45 +0000
committerbors <bors@rust-lang.org>2017-01-05 21:58:45 +0000
commit42bed7238534b50178cb2bd275f1153d67cc3ece (patch)
treec200dc71f1158faf3cb3c21a3b3eb2589174e163 /src/librustc/middle
parentea2d41e31fb865ee57278f8acb78aacd75933856 (diff)
parentab8e92514cc273477e63c089ea6f38b0adba5ddd (diff)
downloadrust-42bed7238534b50178cb2bd275f1153d67cc3ece.tar.gz
rust-42bed7238534b50178cb2bd275f1153d67cc3ece.zip
Auto merge of #38689 - pnkfelix:dont-check-stability-on-private-items, r=nikomatsakis
Dont check stability for items that are not pub to universe.

Dont check stability for items that are not pub to universe.

In other words, skip it for private and even `pub(restricted)` items, because stability checks are only relevant to things visible in other crates.

Fix #38412.
Diffstat (limited to 'src/librustc/middle')
-rw-r--r--src/librustc/middle/stability.rs37
1 files changed, 36 insertions, 1 deletions
diff --git a/src/librustc/middle/stability.rs b/src/librustc/middle/stability.rs
index f45e86f2f4b..e6c9d2c36d0 100644
--- a/src/librustc/middle/stability.rs
+++ b/src/librustc/middle/stability.rs
@@ -18,7 +18,7 @@ use hir::map as hir_map;
 use lint;
 use hir::def::Def;
 use hir::def_id::{CrateNum, CRATE_DEF_INDEX, DefId, DefIndex, LOCAL_CRATE};
-use ty::TyCtxt;
+use ty::{self, TyCtxt};
 use middle::privacy::AccessLevels;
 use syntax::symbol::Symbol;
 use syntax_pos::{Span, DUMMY_SP};
@@ -432,6 +432,36 @@ struct Checker<'a, 'tcx: 'a> {
 }
 
 impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> {
+    // (See issue #38412)
+    fn skip_stability_check_due_to_privacy(self, def_id: DefId) -> bool {
+        let visibility = {
+            // Check if `def_id` is a trait method.
+            match self.sess.cstore.associated_item(def_id) {
+                Some(ty::AssociatedItem { container: ty::TraitContainer(trait_def_id), .. }) => {
+                    // Trait methods do not declare visibility (even
+                    // for visibility info in cstore). Use containing
+                    // trait instead, so methods of pub traits are
+                    // themselves considered pub.
+                    self.sess.cstore.visibility(trait_def_id)
+                }
+                _ => {
+                    // Otherwise, cstore info works directly.
+                    self.sess.cstore.visibility(def_id)
+                }
+            }
+        };
+
+        match visibility {
+            // must check stability for pub items.
+            ty::Visibility::Public => false,
+
+            // these are not visible outside crate; therefore
+            // stability markers are irrelevant, if even present.
+            ty::Visibility::Restricted(..) |
+            ty::Visibility::Invisible => true,
+        }
+    }
+
     pub fn check_stability(self, def_id: DefId, id: NodeId, span: Span) {
         if self.sess.codemap().span_allows_unstable(span) {
             debug!("stability: \
@@ -492,6 +522,11 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> {
             self.stability.borrow_mut().used_features.insert(feature.clone(), level.clone());
         }
 
+        // Issue 38412: private items lack stability markers.
+        if self.skip_stability_check_due_to_privacy(def_id) {
+            return
+        }
+
         match stability {
             Some(&Stability { level: attr::Unstable {ref reason, issue}, ref feature, .. }) => {
                 if !self.stability.borrow().active_features.contains(feature) {