Rollup merge of #119705 - fmease:tilde-const-assoc-fns-trait-impls, r=compiler-errors

Support `~const` in associated functions in trait impls

Fixes #119700.
This commit is contained in:
Matthias Krüger 2024-01-08 00:38:35 +01:00 committed by GitHub
commit 39b3ef17a1
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 65 additions and 30 deletions

View File

@ -12,6 +12,7 @@ use rustc_hir::def::{DefKind, Res};
use rustc_hir::def_id::{LocalDefId, CRATE_DEF_ID}; use rustc_hir::def_id::{LocalDefId, CRATE_DEF_ID};
use rustc_hir::PredicateOrigin; use rustc_hir::PredicateOrigin;
use rustc_index::{Idx, IndexSlice, IndexVec}; use rustc_index::{Idx, IndexSlice, IndexVec};
use rustc_middle::span_bug;
use rustc_middle::ty::{ResolverAstLowering, TyCtxt}; use rustc_middle::ty::{ResolverAstLowering, TyCtxt};
use rustc_span::edit_distance::find_best_match_for_name; use rustc_span::edit_distance::find_best_match_for_name;
use rustc_span::symbol::{kw, sym, Ident}; use rustc_span::symbol::{kw, sym, Ident};
@ -576,23 +577,25 @@ impl<'hir> LoweringContext<'_, 'hir> {
// This is used to track which lifetimes have already been defined, // This is used to track which lifetimes have already been defined,
// and which need to be replicated when lowering an async fn. // and which need to be replicated when lowering an async fn.
match parent_hir.node().expect_item().kind { let generics = match parent_hir.node().expect_item().kind {
hir::ItemKind::Impl(impl_) => { hir::ItemKind::Impl(impl_) => {
self.is_in_trait_impl = impl_.of_trait.is_some(); self.is_in_trait_impl = impl_.of_trait.is_some();
&impl_.generics
} }
hir::ItemKind::Trait(_, _, generics, _, _) if self.tcx.features().effects => { hir::ItemKind::Trait(_, _, generics, _, _) => generics,
self.host_param_id = generics kind => {
.params span_bug!(item.span, "assoc item has unexpected kind of parent: {}", kind.descr())
.iter()
.find(|param| {
matches!(
param.kind,
hir::GenericParamKind::Const { is_host_effect: true, .. }
)
})
.map(|param| param.def_id);
} }
_ => {} };
if self.tcx.features().effects {
self.host_param_id = generics
.params
.iter()
.find(|param| {
matches!(param.kind, hir::GenericParamKind::Const { is_host_effect: true, .. })
})
.map(|param| param.def_id);
} }
match ctxt { match ctxt {

View File

@ -1,27 +1,30 @@
error[E0277]: can't compare `impl PartialEq + Destruct + Copy` with `impl PartialEq + Destruct + Copy` error[E0277]: can't compare `()` with `()`
--> $DIR/const-impl-trait.rs:28:17 --> $DIR/const-impl-trait.rs:35:17
| |
LL | fn huh() -> impl ~const PartialEq + ~const Destruct + Copy { LL | assert!(cmp(&()));
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ no implementation for `impl PartialEq + Destruct + Copy == impl PartialEq + Destruct + Copy` | --- ^^^ no implementation for `() == ()`
| |
| required by a bound introduced by this call
| |
= help: the trait `~const PartialEq` is not implemented for `impl PartialEq + Destruct + Copy` = help: the trait `const PartialEq` is not implemented for `()`
note: required by a bound in `Foo::{opaque#0}` = help: the trait `PartialEq` is implemented for `()`
--> $DIR/const-impl-trait.rs:24:22 note: required by a bound in `cmp`
--> $DIR/const-impl-trait.rs:12:23
| |
LL | fn huh() -> impl ~const PartialEq + ~const Destruct + Copy; LL | const fn cmp(a: &impl ~const PartialEq) -> bool {
| ^^^^^^^^^^^^^^^^ required by this bound in `Foo::{opaque#0}` | ^^^^^^^^^^^^^^^^ required by this bound in `cmp`
error[E0277]: can't drop `impl PartialEq + Destruct + Copy` error[E0277]: can't compare `&impl ~const PartialEq` with `&impl ~const PartialEq`
--> $DIR/const-impl-trait.rs:28:17 --> $DIR/const-impl-trait.rs:13:7
| |
LL | fn huh() -> impl ~const PartialEq + ~const Destruct + Copy { LL | a == a
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `~const Destruct` is not implemented for `impl PartialEq + Destruct + Copy` | ^^ no implementation for `&impl ~const PartialEq == &impl ~const PartialEq`
| |
note: required by a bound in `Foo::{opaque#0}` = help: the trait `~const PartialEq<&impl ~const PartialEq>` is not implemented for `&impl ~const PartialEq`
--> $DIR/const-impl-trait.rs:24:41 help: consider dereferencing both sides of the expression
| |
LL | fn huh() -> impl ~const PartialEq + ~const Destruct + Copy; LL | *a == *a
| ^^^^^^^^^^^^^^^ required by this bound in `Foo::{opaque#0}` | + +
error: aborting due to 2 previous errors error: aborting due to 2 previous errors

View File

@ -0,0 +1,29 @@
// Regression test for issue #119700.
// check-pass
#![feature(const_trait_impl, effects)]
#[const_trait]
trait Main {
fn compute<T: ~const Aux>() -> u32;
}
impl const Main for () {
fn compute<T: ~const Aux>() -> u32 {
T::generate()
}
}
#[const_trait]
trait Aux {
fn generate() -> u32;
}
impl const Aux for () {
fn generate() -> u32 { 1024 }
}
fn main() {
const _: u32 = <()>::compute::<()>();
let _ = <()>::compute::<()>();
}