Skip to content
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.

Commit 3ded370

Browse files
committedMar 13, 2025
type privacy: Check constructor types in tuple struct patterns
1 parent a2aba05 commit 3ded370

File tree

3 files changed

+95
-0
lines changed

3 files changed

+95
-0
lines changed
 

‎compiler/rustc_privacy/src/lib.rs

+21
Original file line numberDiff line numberDiff line change
@@ -1302,6 +1302,27 @@ impl<'tcx> Visitor<'tcx> for TypePrivacyVisitor<'tcx> {
13021302
return;
13031303
}
13041304

1305+
match pattern.kind {
1306+
hir::PatKind::TupleStruct(qpath, ..) => {
1307+
// Tuple struct constructors have to be checked specially.
1308+
self.span = qpath.span();
1309+
let def_id = match qpath {
1310+
hir::QPath::Resolved(_, path) => path.res.opt_def_id(),
1311+
hir::QPath::TypeRelative(..) | hir::QPath::LangItem(..) => self
1312+
.maybe_typeck_results
1313+
.unwrap_or_else(|| span_bug!(self.span, "`hir::Pat` outside of a body"))
1314+
.type_dependent_def_id(pattern.hir_id),
1315+
};
1316+
1317+
if let Some(def_id) = def_id {
1318+
if self.visit(self.tcx.type_of(def_id).instantiate_identity()).is_break() {
1319+
return;
1320+
}
1321+
}
1322+
}
1323+
_ => {}
1324+
}
1325+
13051326
intravisit::walk_pat(self, pattern);
13061327
}
13071328

Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
mod m {
2+
struct Priv;
3+
4+
#[allow(private_interfaces)]
5+
pub struct PubStruct(pub Priv);
6+
pub enum PubEnum {
7+
#[allow(private_interfaces)]
8+
Variant(Priv),
9+
}
10+
11+
impl PubStruct {
12+
pub fn new() -> PubStruct {
13+
PubStruct(Priv)
14+
}
15+
}
16+
impl PubEnum {
17+
pub fn new() -> PubEnum {
18+
PubEnum::Variant(Priv)
19+
}
20+
}
21+
}
22+
23+
fn main() {
24+
match m::PubStruct::new() {
25+
m::PubStruct(_) => {} //~ ERROR type `Priv` is private
26+
m::PubStruct(..) => {} //~ ERROR type `Priv` is private
27+
}
28+
29+
match m::PubEnum::new() {
30+
m::PubEnum::Variant(_) => {} //~ ERROR type `Priv` is private
31+
m::PubEnum::Variant(..) => {} //~ ERROR type `Priv` is private
32+
}
33+
34+
let _ = m::PubStruct; //~ ERROR type `Priv` is private
35+
let _ = m::PubEnum::Variant; //~ ERROR type `Priv` is private
36+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,38 @@
1+
error: type `Priv` is private
2+
--> $DIR/private-in-public-tuple-struct-pat.rs:25:9
3+
|
4+
LL | m::PubStruct(_) => {}
5+
| ^^^^^^^^^^^^ private type
6+
7+
error: type `Priv` is private
8+
--> $DIR/private-in-public-tuple-struct-pat.rs:26:9
9+
|
10+
LL | m::PubStruct(..) => {}
11+
| ^^^^^^^^^^^^ private type
12+
13+
error: type `Priv` is private
14+
--> $DIR/private-in-public-tuple-struct-pat.rs:30:9
15+
|
16+
LL | m::PubEnum::Variant(_) => {}
17+
| ^^^^^^^^^^^^^^^^^^^ private type
18+
19+
error: type `Priv` is private
20+
--> $DIR/private-in-public-tuple-struct-pat.rs:31:9
21+
|
22+
LL | m::PubEnum::Variant(..) => {}
23+
| ^^^^^^^^^^^^^^^^^^^ private type
24+
25+
error: type `Priv` is private
26+
--> $DIR/private-in-public-tuple-struct-pat.rs:34:13
27+
|
28+
LL | let _ = m::PubStruct;
29+
| ^^^^^^^^^^^^ private type
30+
31+
error: type `Priv` is private
32+
--> $DIR/private-in-public-tuple-struct-pat.rs:35:13
33+
|
34+
LL | let _ = m::PubEnum::Variant;
35+
| ^^^^^^^^^^^^^^^^^^^ private type
36+
37+
error: aborting due to 6 previous errors
38+

0 commit comments

Comments
 (0)
Failed to load comments.