Skip to content

Commit 05812df

Browse files
cjgillotcompiler-errors
authored andcommitted
Handle generic parameters.
1 parent cdf7807 commit 05812df

File tree

25 files changed

+170
-223
lines changed

25 files changed

+170
-223
lines changed

compiler/rustc_ast_lowering/src/lib.rs

+40-80
Original file line numberDiff line numberDiff line change
@@ -252,11 +252,10 @@ enum ImplTraitContext {
252252
ReturnPositionOpaqueTy {
253253
/// Origin: Either OpaqueTyOrigin::FnReturn or OpaqueTyOrigin::AsyncFn,
254254
origin: hir::OpaqueTyOrigin,
255+
in_trait: bool,
255256
},
256257
/// Impl trait in type aliases.
257258
TypeAliasesOpaqueTy,
258-
/// Return-position `impl Trait` in trait definition
259-
InTrait,
260259
/// `impl Trait` is not accepted in this position.
261260
Disallowed(ImplTraitPosition),
262261
}
@@ -1343,24 +1342,26 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
13431342
TyKind::ImplTrait(def_node_id, ref bounds) => {
13441343
let span = t.span;
13451344
match itctx {
1346-
ImplTraitContext::ReturnPositionOpaqueTy { origin } => {
1347-
self.lower_opaque_impl_trait(span, *origin, def_node_id, bounds, itctx)
1348-
}
1345+
ImplTraitContext::ReturnPositionOpaqueTy { origin, in_trait } => self
1346+
.lower_opaque_impl_trait(
1347+
span,
1348+
*origin,
1349+
def_node_id,
1350+
bounds,
1351+
*in_trait,
1352+
itctx,
1353+
),
13491354
ImplTraitContext::TypeAliasesOpaqueTy => {
13501355
let mut nested_itctx = ImplTraitContext::TypeAliasesOpaqueTy;
13511356
self.lower_opaque_impl_trait(
13521357
span,
13531358
hir::OpaqueTyOrigin::TyAlias,
13541359
def_node_id,
13551360
bounds,
1356-
&mut nested_itctx,
1361+
false,
1362+
nested_itctx,
13571363
)
13581364
}
1359-
ImplTraitContext::InTrait => {
1360-
self.lower_impl_trait_in_trait(span, def_node_id, |lctx| {
1361-
lctx.lower_param_bounds(bounds, ImplTraitContext::InTrait)
1362-
})
1363-
}
13641365
ImplTraitContext::Universal => {
13651366
let span = t.span;
13661367
let ident = Ident::from_str_and_span(&pprust::ty_to_string(t), span);
@@ -1430,6 +1431,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
14301431
origin: hir::OpaqueTyOrigin,
14311432
opaque_ty_node_id: NodeId,
14321433
bounds: &GenericBounds,
1434+
in_trait: bool,
14331435
itctx: &mut ImplTraitContext,
14341436
) -> hir::TyKind<'hir> {
14351437
// Make sure we know that some funky desugaring has been going on here.
@@ -1518,6 +1520,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
15181520
}),
15191521
bounds: hir_bounds,
15201522
origin,
1523+
in_trait,
15211524
};
15221525
debug!(?opaque_ty_item);
15231526

@@ -1544,30 +1547,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
15441547
debug!(?lifetimes);
15451548

15461549
// `impl Trait` now just becomes `Foo<'a, 'b, ..>`.
1547-
hir::TyKind::OpaqueDef(hir::ItemId { def_id: opaque_ty_def_id }, lifetimes)
1548-
}
1549-
1550-
#[instrument(level = "debug", skip(self, lower_bounds))]
1551-
fn lower_impl_trait_in_trait(
1552-
&mut self,
1553-
span: Span,
1554-
opaque_ty_node_id: NodeId,
1555-
lower_bounds: impl FnOnce(&mut Self) -> hir::GenericBounds<'hir>,
1556-
) -> hir::TyKind<'hir> {
1557-
let opaque_ty_def_id = self.local_def_id(opaque_ty_node_id);
1558-
self.with_hir_id_owner(opaque_ty_node_id, |lctx| {
1559-
let hir_bounds = lower_bounds(lctx);
1560-
let rpitit_placeholder = hir::ImplTraitPlaceholder { bounds: hir_bounds };
1561-
let rpitit_item = hir::Item {
1562-
def_id: opaque_ty_def_id,
1563-
ident: Ident::empty(),
1564-
kind: hir::ItemKind::ImplTraitPlaceholder(rpitit_placeholder),
1565-
span: lctx.lower_span(span),
1566-
vis_span: lctx.lower_span(span.shrink_to_lo()),
1567-
};
1568-
hir::OwnerNode::Item(lctx.arena.alloc(rpitit_item))
1569-
});
1570-
hir::TyKind::ImplTraitInTrait(hir::ItemId { def_id: opaque_ty_def_id })
1550+
hir::TyKind::OpaqueDef(hir::ItemId { def_id: opaque_ty_def_id }, lifetimes, in_trait)
15711551
}
15721552

15731553
/// Registers a new opaque type with the proper `NodeId`s and
@@ -1728,30 +1708,28 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
17281708
)
17291709
.emit();
17301710
}
1731-
self.lower_async_fn_ret_ty_in_trait(
1711+
self.lower_async_fn_ret_ty(
17321712
&decl.output,
17331713
fn_node_id.expect("`make_ret_async` but no `fn_def_id`"),
17341714
ret_id,
1715+
true,
17351716
)
17361717
}
17371718
_ => {
17381719
if !kind.impl_trait_return_allowed(self.tcx) {
1739-
if kind == FnDeclKind::Impl {
1740-
self.tcx
1741-
.sess
1742-
.create_feature_err(
1743-
TraitFnAsync { fn_span, span },
1744-
sym::return_position_impl_trait_in_trait,
1745-
)
1746-
.emit();
1747-
} else {
1748-
self.tcx.sess.emit_err(TraitFnAsync { fn_span, span });
1749-
}
1720+
self.tcx
1721+
.sess
1722+
.create_feature_err(
1723+
TraitFnAsync { fn_span, span },
1724+
sym::return_position_impl_trait_in_trait,
1725+
)
1726+
.emit();
17501727
}
17511728
self.lower_async_fn_ret_ty(
17521729
&decl.output,
17531730
fn_node_id.expect("`make_ret_async` but no `fn_def_id`"),
17541731
ret_id,
1732+
false,
17551733
)
17561734
}
17571735
}
@@ -1763,10 +1741,15 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
17631741
let fn_def_id = self.local_def_id(fn_node_id);
17641742
ImplTraitContext::ReturnPositionOpaqueTy {
17651743
origin: hir::OpaqueTyOrigin::FnReturn(fn_def_id),
1744+
in_trait: false,
17661745
}
17671746
}
1768-
Some(_) if kind.impl_trait_in_trait_allowed(self.tcx) => {
1769-
ImplTraitContext::InTrait
1747+
Some(fn_node_id) if kind.impl_trait_in_trait_allowed(self.tcx) => {
1748+
let fn_def_id = self.local_def_id(fn_node_id);
1749+
ImplTraitContext::ReturnPositionOpaqueTy {
1750+
origin: hir::OpaqueTyOrigin::FnReturn(fn_def_id),
1751+
in_trait: true,
1752+
}
17701753
}
17711754
_ => ImplTraitContext::Disallowed(match kind {
17721755
FnDeclKind::Fn | FnDeclKind::Inherent => {
@@ -1829,6 +1812,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
18291812
output: &FnRetTy,
18301813
fn_node_id: NodeId,
18311814
opaque_ty_node_id: NodeId,
1815+
in_trait: bool,
18321816
) -> hir::FnRetTy<'hir> {
18331817
let span = output.span();
18341818

@@ -1960,6 +1944,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
19601944
span,
19611945
ImplTraitContext::ReturnPositionOpaqueTy {
19621946
origin: hir::OpaqueTyOrigin::FnReturn(fn_def_id),
1947+
in_trait,
19631948
},
19641949
);
19651950

@@ -1999,6 +1984,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
19991984
}),
20001985
bounds: arena_vec![this; future_bound],
20011986
origin: hir::OpaqueTyOrigin::AsyncFn(fn_def_id),
1987+
in_trait,
20021988
};
20031989

20041990
trace!("exist ty from async fn def id: {:#?}", opaque_ty_def_id);
@@ -2043,41 +2029,15 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
20432029
// Foo = impl Trait` is, internally, created as a child of the
20442030
// async fn, so the *type parameters* are inherited. It's
20452031
// only the lifetime parameters that we must supply.
2046-
let opaque_ty_ref =
2047-
hir::TyKind::OpaqueDef(hir::ItemId { def_id: opaque_ty_def_id }, generic_args);
2032+
let opaque_ty_ref = hir::TyKind::OpaqueDef(
2033+
hir::ItemId { def_id: opaque_ty_def_id },
2034+
generic_args,
2035+
in_trait,
2036+
);
20482037
let opaque_ty = self.ty(opaque_ty_span, opaque_ty_ref);
20492038
hir::FnRetTy::Return(self.arena.alloc(opaque_ty))
20502039
}
20512040

2052-
// Transforms `-> T` for `async fn` into `-> OpaqueTy { .. }`
2053-
// combined with the following definition of `OpaqueTy`:
2054-
//
2055-
// type OpaqueTy<generics_from_parent_fn> = impl Future<Output = T>;
2056-
//
2057-
// `output`: unlowered output type (`T` in `-> T`)
2058-
// `fn_def_id`: `DefId` of the parent function (used to create child impl trait definition)
2059-
// `opaque_ty_node_id`: `NodeId` of the opaque `impl Trait` type that should be created
2060-
#[instrument(level = "debug", skip(self))]
2061-
fn lower_async_fn_ret_ty_in_trait(
2062-
&mut self,
2063-
output: &FnRetTy,
2064-
fn_node_id: NodeId,
2065-
opaque_ty_node_id: NodeId,
2066-
) -> hir::FnRetTy<'hir> {
2067-
let kind = self.lower_impl_trait_in_trait(output.span(), opaque_ty_node_id, |lctx| {
2068-
let bound = lctx.lower_async_fn_output_type_to_future_bound(
2069-
output,
2070-
output.span(),
2071-
ImplTraitContext::InTrait,
2072-
);
2073-
arena_vec![lctx; bound]
2074-
});
2075-
2076-
let opaque_ty_span = self.mark_span_with_reason(DesugaringKind::Async, output.span(), None);
2077-
let opaque_ty = self.ty(opaque_ty_span, kind);
2078-
hir::FnRetTy::Return(self.arena.alloc(opaque_ty))
2079-
}
2080-
20812041
/// Transforms `-> T` into `Future<Output = T>`.
20822042
fn lower_async_fn_output_type_to_future_bound(
20832043
&mut self,

compiler/rustc_borrowck/src/diagnostics/region_name.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -772,7 +772,7 @@ impl<'tcx> MirBorrowckCtxt<'_, 'tcx> {
772772
fn get_future_inner_return_ty(&self, hir_ty: &'tcx hir::Ty<'tcx>) -> &'tcx hir::Ty<'tcx> {
773773
let hir = self.infcx.tcx.hir();
774774

775-
let hir::TyKind::OpaqueDef(id, _) = hir_ty.kind else {
775+
let hir::TyKind::OpaqueDef(id, _, _) = hir_ty.kind else {
776776
span_bug!(
777777
hir_ty.span,
778778
"lowered return type of async fn is not OpaqueDef: {:?}",

compiler/rustc_hir/src/hir.rs

+4-15
Original file line numberDiff line numberDiff line change
@@ -2505,6 +2505,7 @@ pub struct OpaqueTy<'hir> {
25052505
pub generics: &'hir Generics<'hir>,
25062506
pub bounds: GenericBounds<'hir>,
25072507
pub origin: OpaqueTyOrigin,
2508+
pub in_trait: bool,
25082509
}
25092510

25102511
/// From whence the opaque type came.
@@ -2518,12 +2519,6 @@ pub enum OpaqueTyOrigin {
25182519
TyAlias,
25192520
}
25202521

2521-
/// Placeholder representation of an `impl Trait` in a trait. Since this never gets lowered into a `ty::Opaque` of its own, we just keep this as
2522-
#[derive(Debug, HashStable_Generic)]
2523-
pub struct ImplTraitPlaceholder<'hir> {
2524-
pub bounds: GenericBounds<'hir>,
2525-
}
2526-
25272522
/// The various kinds of types recognized by the compiler.
25282523
#[derive(Debug, HashStable_Generic)]
25292524
pub enum TyKind<'hir> {
@@ -2550,12 +2545,9 @@ pub enum TyKind<'hir> {
25502545
///
25512546
/// The generic argument list contains the lifetimes (and in the future
25522547
/// possibly parameters) that are actually bound on the `impl Trait`.
2553-
OpaqueDef(ItemId, &'hir [GenericArg<'hir>]),
2554-
/// A type that represents an `impl Trait` in a trait function. This is
2555-
/// not an opaque type, since it acts more like an associated type than
2556-
/// an opaque, and since it needs no generics since it inherits those
2557-
/// from the item's parent.
2558-
ImplTraitInTrait(ItemId),
2548+
///
2549+
/// The last parameter specifies whether this opaque appears in a trait definition.
2550+
OpaqueDef(ItemId, &'hir [GenericArg<'hir>], bool),
25592551
/// A trait object type `Bound1 + Bound2 + Bound3`
25602552
/// where `Bound` is a trait or a lifetime.
25612553
TraitObject(&'hir [PolyTraitRef<'hir>], &'hir Lifetime, TraitObjectSyntax),
@@ -3011,8 +3003,6 @@ pub enum ItemKind<'hir> {
30113003
TyAlias(&'hir Ty<'hir>, &'hir Generics<'hir>),
30123004
/// An opaque `impl Trait` type alias, e.g., `type Foo = impl Bar;`.
30133005
OpaqueTy(OpaqueTy<'hir>),
3014-
/// An `impl Trait` in a trait
3015-
ImplTraitPlaceholder(ImplTraitPlaceholder<'hir>),
30163006
/// An enum definition, e.g., `enum Foo<A, B> {C<A>, D<B>}`.
30173007
Enum(EnumDef<'hir>, &'hir Generics<'hir>),
30183008
/// A struct definition, e.g., `struct Foo<A> {x: A}`.
@@ -3081,7 +3071,6 @@ impl ItemKind<'_> {
30813071
ItemKind::Trait(..) => "trait",
30823072
ItemKind::TraitAlias(..) => "trait alias",
30833073
ItemKind::Impl(..) => "implementation",
3084-
ItemKind::ImplTraitPlaceholder(..) => "opaque type in trait",
30853074
}
30863075
}
30873076
}

compiler/rustc_hir/src/intravisit.rs

+1-8
Original file line numberDiff line numberDiff line change
@@ -562,10 +562,6 @@ pub fn walk_item<'v, V: Visitor<'v>>(visitor: &mut V, item: &'v Item<'v>) {
562562
walk_generics(visitor, generics);
563563
walk_list!(visitor, visit_param_bound, bounds);
564564
}
565-
ItemKind::ImplTraitPlaceholder(ImplTraitPlaceholder { bounds }) => {
566-
visitor.visit_id(item.hir_id());
567-
walk_list!(visitor, visit_param_bound, bounds);
568-
}
569565
ItemKind::Enum(ref enum_definition, ref generics) => {
570566
visitor.visit_generics(generics);
571567
// `visit_enum_def()` takes care of visiting the `Item`'s `HirId`.
@@ -674,13 +670,10 @@ pub fn walk_ty<'v, V: Visitor<'v>>(visitor: &mut V, typ: &'v Ty<'v>) {
674670
TyKind::Path(ref qpath) => {
675671
visitor.visit_qpath(qpath, typ.hir_id, typ.span);
676672
}
677-
TyKind::OpaqueDef(item_id, lifetimes) => {
673+
TyKind::OpaqueDef(item_id, lifetimes, _in_trait) => {
678674
visitor.visit_nested_item(item_id);
679675
walk_list!(visitor, visit_generic_arg, lifetimes);
680676
}
681-
TyKind::ImplTraitInTrait(item_id) => {
682-
visitor.visit_nested_item(item_id);
683-
}
684677
TyKind::Array(ref ty, ref length) => {
685678
visitor.visit_ty(ty);
686679
visitor.visit_array_length(length)

compiler/rustc_hir/src/target.rs

+7-2
Original file line numberDiff line numberDiff line change
@@ -80,8 +80,13 @@ impl Target {
8080
ItemKind::ForeignMod { .. } => Target::ForeignMod,
8181
ItemKind::GlobalAsm(..) => Target::GlobalAsm,
8282
ItemKind::TyAlias(..) => Target::TyAlias,
83-
ItemKind::OpaqueTy(..) => Target::OpaqueTy,
84-
ItemKind::ImplTraitPlaceholder(..) => Target::ImplTraitPlaceholder,
83+
ItemKind::OpaqueTy(ref opaque) => {
84+
if opaque.in_trait {
85+
Target::ImplTraitPlaceholder
86+
} else {
87+
Target::OpaqueTy
88+
}
89+
}
8590
ItemKind::Enum(..) => Target::Enum,
8691
ItemKind::Struct(..) => Target::Struct,
8792
ItemKind::Union(..) => Target::Union,

compiler/rustc_hir_pretty/src/lib.rs

-4
Original file line numberDiff line numberDiff line change
@@ -327,7 +327,6 @@ impl<'a> State<'a> {
327327
self.print_ty_fn(f.abi, f.unsafety, f.decl, None, f.generic_params, f.param_names);
328328
}
329329
hir::TyKind::OpaqueDef(..) => self.word("/*impl Trait*/"),
330-
hir::TyKind::ImplTraitInTrait(..) => self.word("/*impl Trait*/"),
331330
hir::TyKind::Path(ref qpath) => self.print_qpath(qpath, false),
332331
hir::TyKind::TraitObject(bounds, ref lifetime, syntax) => {
333332
if syntax == ast::TraitObjectSyntax::Dyn {
@@ -609,9 +608,6 @@ impl<'a> State<'a> {
609608
state.print_bounds("= impl", real_bounds);
610609
});
611610
}
612-
hir::ItemKind::ImplTraitPlaceholder(..) => {
613-
unreachable!("FIXME(RPITIT): I don't think this ever gets called here...");
614-
}
615611
hir::ItemKind::Enum(ref enum_definition, params) => {
616612
self.print_enum_def(enum_definition, params, item.ident.name, item.span);
617613
}

compiler/rustc_infer/src/infer/error_reporting/nice_region_error/static_impl_trait.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -300,7 +300,7 @@ pub fn suggest_new_region_bound(
300300
continue;
301301
}
302302
match fn_return.kind {
303-
TyKind::OpaqueDef(item_id, _) => {
303+
TyKind::OpaqueDef(item_id, _, _) => {
304304
let item = tcx.hir().item(item_id);
305305
let ItemKind::OpaqueTy(opaque) = &item.kind else {
306306
return;

compiler/rustc_metadata/src/rmeta/encoder.rs

-3
Original file line numberDiff line numberDiff line change
@@ -1500,9 +1500,6 @@ impl<'a, 'tcx> EncodeContext<'a, 'tcx> {
15001500
hir::ItemKind::OpaqueTy(..) => {
15011501
self.encode_explicit_item_bounds(def_id);
15021502
}
1503-
hir::ItemKind::ImplTraitPlaceholder(..) => {
1504-
self.encode_explicit_item_bounds(def_id);
1505-
}
15061503
hir::ItemKind::Enum(..) => {
15071504
let adt_def = self.tcx.adt_def(def_id);
15081505
record!(self.tables.repr_options[def_id] <- adt_def.repr());

0 commit comments

Comments
 (0)