Skip to content
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

Implement Return Type Notation (RTN)'s path form in where clauses #129629

Merged
merged 7 commits into from
Sep 22, 2024
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Next Next commit
Resolve self type alias in impl for RTN
  • Loading branch information
compiler-errors committed Sep 21, 2024
commit af24d0b66081bebc881769145385f5baeeed390d
26 changes: 25 additions & 1 deletion compiler/rustc_hir_analysis/src/collect/resolve_bound_vars.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1910,6 +1910,7 @@ impl<'a, 'tcx> BoundVarContext<'a, 'tcx> {
// from the generics of the parameter's definition, since we want
// to be able to resolve an RTN path on a nested body (e.g. method
// inside an impl) using the where clauses on the method.
// FIXME(return_type_notation): Think of some better way of doing this.
let Some(generics) = self.tcx.hir_owner_node(hir_id.owner).generics()
else {
return;
Expand Down Expand Up @@ -1948,7 +1949,30 @@ impl<'a, 'tcx> BoundVarContext<'a, 'tcx> {
};
(bound_vars, assoc_item.def_id, item_segment)
}
Res::SelfTyAlias { is_trait_impl: true, .. } => todo!(),
// If we have a self type alias (in an impl), try to resolve an
// associated item from one of the supertraits of the impl's trait.
Res::SelfTyAlias { alias_to: impl_def_id, is_trait_impl: true, .. } => {
let hir::ItemKind::Impl(hir::Impl { of_trait: Some(trait_ref), .. }) = self
.tcx
.hir_node_by_def_id(impl_def_id.expect_local())
.expect_item()
.kind
else {
return;
};
let Some(trait_def_id) = trait_ref.trait_def_id() else {
return;
};
let Some((bound_vars, assoc_item)) = BoundVarContext::supertrait_hrtb_vars(
self.tcx,
trait_def_id,
item_segment.ident,
ty::AssocKind::Fn,
) else {
return;
};
(bound_vars, assoc_item.def_id, item_segment)
}
_ => return,
}
}
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
//@ check-pass

#![feature(return_type_notation)]
//~^ WARN the feature `return_type_notation` is incomplete

trait Trait {
fn method() -> impl Sized;
}

fn is_send(_: impl Send) {}

struct W<T>(T);

impl<T> W<T> {
fn test()
where
T: Trait,
T::method(..): Send,
{
is_send(T::method());
}
}

fn main() {}
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
warning: the feature `return_type_notation` is incomplete and may not be safe to use and/or cause compiler crashes
--> $DIR/path-constrained-in-method.rs:3:12
|
LL | #![feature(return_type_notation)]
| ^^^^^^^^^^^^^^^^^^^^
|
= note: see issue #109417 <https://github.com/rust-lang/rust/issues/109417> for more information
= note: `#[warn(incomplete_features)]` on by default

warning: 1 warning emitted

Original file line number Diff line number Diff line change
Expand Up @@ -13,4 +13,15 @@ trait Bar: Foo {
Self::method(..): Send;
}

fn is_send(_: impl Send) {}

impl<T: Foo> Bar for T {
fn other()
where
Self::method(..): Send,
{
is_send(Self::method());
}
}

fn main() {}