-
Notifications
You must be signed in to change notification settings - Fork 12.9k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
trait alias infrastructure #45047
trait alias infrastructure #45047
Changes from all commits
d4a2826
f1c4a92
46dc7c5
1b6ad1e
2eefc9d
63f1c24
4029a01
4f0b4f2
435fe5b
aaeae4c
834674f
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -390,12 +390,18 @@ impl PatternSource { | |
} | ||
} | ||
|
||
#[derive(Copy, Clone, PartialEq, Eq, Debug)] | ||
enum AliasPossibility { | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I'll be the first to admit this is a bad name. |
||
No, | ||
Maybe, | ||
} | ||
|
||
#[derive(Copy, Clone, PartialEq, Eq, Debug)] | ||
enum PathSource<'a> { | ||
// Type paths `Path`. | ||
Type, | ||
// Trait paths in bounds or impls. | ||
Trait, | ||
Trait(AliasPossibility), | ||
// Expression paths `path`, with optional parent context. | ||
Expr(Option<&'a Expr>), | ||
// Paths in path patterns `Path`. | ||
|
@@ -415,7 +421,7 @@ enum PathSource<'a> { | |
impl<'a> PathSource<'a> { | ||
fn namespace(self) -> Namespace { | ||
match self { | ||
PathSource::Type | PathSource::Trait | PathSource::Struct | | ||
PathSource::Type | PathSource::Trait(_) | PathSource::Struct | | ||
PathSource::Visibility | PathSource::ImportPrefix => TypeNS, | ||
PathSource::Expr(..) | PathSource::Pat | PathSource::TupleStruct => ValueNS, | ||
PathSource::TraitItem(ns) => ns, | ||
|
@@ -427,23 +433,23 @@ impl<'a> PathSource<'a> { | |
PathSource::Visibility | PathSource::ImportPrefix => true, | ||
PathSource::Type | PathSource::Expr(..) | PathSource::Pat | | ||
PathSource::Struct | PathSource::TupleStruct | | ||
PathSource::Trait | PathSource::TraitItem(..) => false, | ||
PathSource::Trait(_) | PathSource::TraitItem(..) => false, | ||
} | ||
} | ||
|
||
fn defer_to_typeck(self) -> bool { | ||
match self { | ||
PathSource::Type | PathSource::Expr(..) | PathSource::Pat | | ||
PathSource::Struct | PathSource::TupleStruct => true, | ||
PathSource::Trait | PathSource::TraitItem(..) | | ||
PathSource::Trait(_) | PathSource::TraitItem(..) | | ||
PathSource::Visibility | PathSource::ImportPrefix => false, | ||
} | ||
} | ||
|
||
fn descr_expected(self) -> &'static str { | ||
match self { | ||
PathSource::Type => "type", | ||
PathSource::Trait => "trait", | ||
PathSource::Trait(_) => "trait", | ||
PathSource::Pat => "unit struct/variant or constant", | ||
PathSource::Struct => "struct, variant or union type", | ||
PathSource::TupleStruct => "tuple struct/variant", | ||
|
@@ -472,10 +478,15 @@ impl<'a> PathSource<'a> { | |
Def::TyForeign(..) => true, | ||
_ => false, | ||
}, | ||
PathSource::Trait => match def { | ||
PathSource::Trait(AliasPossibility::No) => match def { | ||
Def::Trait(..) => true, | ||
_ => false, | ||
}, | ||
PathSource::Trait(AliasPossibility::Maybe) => match def { | ||
Def::Trait(..) => true, | ||
Def::TraitAlias(..) => true, | ||
_ => false, | ||
}, | ||
PathSource::Expr(..) => match def { | ||
Def::StructCtor(_, CtorKind::Const) | Def::StructCtor(_, CtorKind::Fn) | | ||
Def::VariantCtor(_, CtorKind::Const) | Def::VariantCtor(_, CtorKind::Fn) | | ||
|
@@ -530,8 +541,8 @@ impl<'a> PathSource<'a> { | |
__diagnostic_used!(E0577); | ||
__diagnostic_used!(E0578); | ||
match (self, has_unexpected_resolution) { | ||
(PathSource::Trait, true) => "E0404", | ||
(PathSource::Trait, false) => "E0405", | ||
(PathSource::Trait(_), true) => "E0404", | ||
(PathSource::Trait(_), false) => "E0405", | ||
(PathSource::Type, true) => "E0573", | ||
(PathSource::Type, false) => "E0412", | ||
(PathSource::Struct, true) => "E0574", | ||
|
@@ -693,7 +704,7 @@ impl<'a, 'tcx> Visitor<'tcx> for Resolver<'a> { | |
tref: &'tcx ast::PolyTraitRef, | ||
m: &'tcx ast::TraitBoundModifier) { | ||
self.smart_resolve_path(tref.trait_ref.ref_id, None, | ||
&tref.trait_ref.path, PathSource::Trait); | ||
&tref.trait_ref.path, PathSource::Trait(AliasPossibility::Maybe)); | ||
visit::walk_poly_trait_ref(self, tref, m); | ||
} | ||
fn visit_variant(&mut self, | ||
|
@@ -1935,6 +1946,17 @@ impl<'a> Resolver<'a> { | |
}); | ||
} | ||
|
||
ItemKind::TraitAlias(ref generics, ref bounds) => { | ||
// Create a new rib for the trait-wide type parameters. | ||
self.with_type_parameter_rib(HasTypeParameters(generics, ItemRibKind), |this| { | ||
let local_def_id = this.definitions.local_def_id(item.id); | ||
this.with_self_rib(Def::SelfTy(Some(local_def_id), None), |this| { | ||
this.visit_generics(generics); | ||
walk_list!(this, visit_ty_param_bound, bounds); | ||
}); | ||
}); | ||
} | ||
|
||
ItemKind::Mod(_) | ItemKind::ForeignMod(_) => { | ||
self.with_scope(item.id, |this| { | ||
visit::walk_item(this, item); | ||
|
@@ -2083,7 +2105,7 @@ impl<'a> Resolver<'a> { | |
&path, | ||
trait_ref.path.span, | ||
trait_ref.path.segments.last().unwrap().span, | ||
PathSource::Trait) | ||
PathSource::Trait(AliasPossibility::No)) | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This function There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. OK, I guess this was tacitly endorsed, so I'll add comments in a future commit. |
||
.base_def(); | ||
if def != Def::Err { | ||
new_id = Some(def.def_id()); | ||
|
@@ -2635,7 +2657,7 @@ impl<'a> Resolver<'a> { | |
err.span_label(span, format!("did you mean `{}!(...)`?", path_str)); | ||
return (err, candidates); | ||
} | ||
(Def::TyAlias(..), PathSource::Trait) => { | ||
(Def::TyAlias(..), PathSource::Trait(_)) => { | ||
err.span_label(span, "type aliases cannot be used for traits"); | ||
return (err, candidates); | ||
} | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
yeah, you used to have to say
trait Foo for ?Sized
, but now that's the default (and you have to writetrait Foo: Sized
)There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I would assume that
TraitBoundModifier::Maybe
in this context is illegal, right? i.e.,trait Foo = ?Sized
is kind of nonsense.There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Agreed.