about summary refs log tree commit diff
path: root/src
diff options
context:
space:
mode:
authorVadim Petrochenkov <vadim.petrochenkov@gmail.com>2015-11-23 13:36:49 +0300
committerVadim Petrochenkov <vadim.petrochenkov@gmail.com>2015-12-18 04:12:31 +0300
commita09246ad34ee83b5c8be9af836d7b0aa06d4aabe (patch)
tree7e4738ab281c48a21cf5f3ff8591290b8f434052 /src
parentf8ae31f60123584b3c40521177bb703022faa8c8 (diff)
downloadrust-a09246ad34ee83b5c8be9af836d7b0aa06d4aabe.tar.gz
rust-a09246ad34ee83b5c8be9af836d7b0aa06d4aabe.zip
Approximate type aliases as public when determining impl publicity
Diffstat (limited to 'src')
-rw-r--r--src/librustc_privacy/lib.rs10
-rw-r--r--src/test/compile-fail/lint-visible-private-types.rs19
2 files changed, 29 insertions, 0 deletions
diff --git a/src/librustc_privacy/lib.rs b/src/librustc_privacy/lib.rs
index 46074423917..a4c9874e74d 100644
--- a/src/librustc_privacy/lib.rs
+++ b/src/librustc_privacy/lib.rs
@@ -1128,11 +1128,21 @@ impl<'a, 'tcx: 'a, 'v> Visitor<'v> for SearchInterfaceForPrivateItemsVisitor<'a,
                 def::DefPrimTy(..) | def::DefSelfTy(..) | def::DefTyParam(..) => {
                     // Public
                 }
+                def::DefAssociatedTy(..) if self.is_quiet => {
+                    // Conservatively approximate the whole type alias as public without
+                    // recursing into its components when determining impl publicity.
+                    return
+                }
                 def::DefStruct(def_id) | def::DefTy(def_id, _) |
                 def::DefTrait(def_id) | def::DefAssociatedTy(def_id, _) => {
                     // Non-local means public, local needs to be checked
                     if let Some(node_id) = self.tcx.map.as_local_node_id(def_id) {
                         if let Some(ast_map::NodeItem(ref item)) = self.tcx.map.find(node_id) {
+                            if let (&hir::ItemTy(..), true) = (&item.node, self.is_quiet) {
+                                // Conservatively approximate the whole type alias as public without
+                                // recursing into its components when determining impl publicity.
+                                return
+                            }
                             if item.vis != hir::Public {
                                 if !self.is_quiet {
                                     span_err!(self.tcx.sess, ty.span, E0446,
diff --git a/src/test/compile-fail/lint-visible-private-types.rs b/src/test/compile-fail/lint-visible-private-types.rs
index f43c17c3854..89be4d9789d 100644
--- a/src/test/compile-fail/lint-visible-private-types.rs
+++ b/src/test/compile-fail/lint-visible-private-types.rs
@@ -121,3 +121,22 @@ impl<T: ParamTrait<Private<isize>>>  //~ ERROR private type in public interface
      ParamTrait<T> for Public<i8> {
     fn foo() -> T { panic!() }
 }
+
+type PrivAlias = Public<i8>;
+
+trait PrivTrait2 {
+    type Alias;
+}
+impl PrivTrait2 for Private<isize> {
+    type Alias = Public<u8>;
+}
+
+impl PubTrait for PrivAlias {
+    fn bar(&self) -> Private<isize> { panic!() } //~ ERROR private type in public interface
+    fn baz() -> Private<isize> { panic!() } //~ ERROR private type in public interface
+}
+
+impl PubTrait for <Private<isize> as PrivTrait2>::Alias {
+    fn bar(&self) -> Private<isize> { panic!() } //~ ERROR private type in public interface
+    fn baz() -> Private<isize> { panic!() } //~ ERROR private type in public interface
+}