Skip to content

allow opaques to be defined by trait queries, again #113690

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

Merged
merged 1 commit into from
Jul 19, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
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
11 changes: 6 additions & 5 deletions compiler/rustc_trait_selection/src/infer.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
use crate::traits::query::evaluate_obligation::InferCtxtExt as _;
use crate::traits::{self, ObligationCtxt};
use crate::traits::{self, DefiningAnchor, ObligationCtxt};

use rustc_hir::def_id::DefId;
use rustc_hir::lang_items::LangItem;
Expand Down Expand Up @@ -80,7 +80,7 @@ impl<'tcx> InferCtxtExt<'tcx> for InferCtxt<'tcx> {

pub trait InferCtxtBuilderExt<'tcx> {
fn enter_canonical_trait_query<K, R>(
&mut self,
self,
canonical_key: &Canonical<'tcx, K>,
operation: impl FnOnce(&ObligationCtxt<'_, 'tcx>, K) -> Result<R, NoSolution>,
) -> Result<CanonicalQueryResponse<'tcx, R>, NoSolution>
Expand Down Expand Up @@ -108,7 +108,7 @@ impl<'tcx> InferCtxtBuilderExt<'tcx> for InferCtxtBuilder<'tcx> {
/// have `'tcx` be free on this function so that we can talk about
/// `K: TypeFoldable<TyCtxt<'tcx>>`.)
fn enter_canonical_trait_query<K, R>(
&mut self,
self,
canonical_key: &Canonical<'tcx, K>,
operation: impl FnOnce(&ObligationCtxt<'_, 'tcx>, K) -> Result<R, NoSolution>,
) -> Result<CanonicalQueryResponse<'tcx, R>, NoSolution>
Expand All @@ -117,8 +117,9 @@ impl<'tcx> InferCtxtBuilderExt<'tcx> for InferCtxtBuilder<'tcx> {
R: Debug + TypeFoldable<TyCtxt<'tcx>>,
Canonical<'tcx, QueryResponse<'tcx, R>>: ArenaAllocatable<'tcx>,
{
let (infcx, key, canonical_inference_vars) =
self.build_with_canonical(DUMMY_SP, canonical_key);
let (infcx, key, canonical_inference_vars) = self
.with_opaque_type_inference(DefiningAnchor::Bubble)
.build_with_canonical(DUMMY_SP, canonical_key);
let ocx = ObligationCtxt::new(&infcx);
let value = operation(&ocx, key)?;
ocx.make_canonicalized_query_response(canonical_inference_vars, value)
Expand Down
12 changes: 12 additions & 0 deletions tests/ui/impl-trait/defined-by-trait-resolution.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
//! The trait query `foo: Fn() -> u8` is a valid defining use of RPIT.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Could you add revision to this test and the other one demonstrating what it does in the new solver?

// revisions: current next
//[next] compile-flags: -Ztrait-solver=next

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

(I expect it to pass in the new solver too)


// build-pass

fn returns_u8(_: impl Fn() -> u8) {}

pub fn foo() -> impl Sized {
returns_u8(foo);
0u8
}

fn main() {}
19 changes: 19 additions & 0 deletions tests/ui/type-alias-impl-trait/defined-by-user-annotation.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
// User type annotation in fn bodies is a a valid defining site for opaque types.
// check-pass
#![feature(type_alias_impl_trait)]

trait Equate { type Proj; }
impl<T> Equate for T { type Proj = T; }

trait Indirect { type Ty; }
impl<A, B: Equate<Proj = A>> Indirect for (A, B) { type Ty = (); }

type Opq = impl Sized;
fn define_1(_: Opq) {
let _ = None::<<(Opq, u8) as Indirect>::Ty>;
}
fn define_2() -> Opq {
0u8
}

fn main() {}