1
Fork 0

Fix const-generics ICE related to binding

This commit is contained in:
Yuki Okushi 2021-07-02 08:02:11 +09:00
parent ce331ee6ee
commit 242ac57015
No known key found for this signature in database
GPG key ID: DABA5B072961C18A
5 changed files with 150 additions and 1 deletions

View file

@ -115,7 +115,14 @@ fn resolve_associated_item<'tcx>(
); );
let trait_ref = ty::TraitRef::from_method(tcx, trait_id, rcvr_substs); let trait_ref = ty::TraitRef::from_method(tcx, trait_id, rcvr_substs);
let vtbl = tcx.codegen_fulfill_obligation((param_env, ty::Binder::bind(trait_ref, tcx)))?; let vtbl = if trait_item.kind == ty::AssocKind::Const {
let bound_vars = tcx
.mk_bound_variable_kinds(std::iter::once(ty::BoundVariableKind::Region(ty::BrAnon(0))));
let bind = ty::Binder::bind_with_vars(trait_ref, bound_vars);
tcx.codegen_fulfill_obligation((param_env, bind))?
} else {
tcx.codegen_fulfill_obligation((param_env, ty::Binder::bind(trait_ref, tcx)))?
};
// Now that we know which impl is being used, we can dispatch to // Now that we know which impl is being used, we can dispatch to
// the actual function: // the actual function:

View file

@ -0,0 +1,38 @@
#![feature(const_generics, const_evaluatable_checked)]
#![allow(incomplete_features)]
trait TensorDimension {
const DIM: usize;
}
trait TensorSize: TensorDimension {
fn size(&self) -> [usize; Self::DIM];
}
trait Broadcastable: TensorSize + Sized {
type Element;
fn lazy_updim<const NEWDIM: usize>(&self, size: [usize; NEWDIM]) {}
}
struct BMap<'a, R, T: Broadcastable, F: Fn(T::Element) -> R, const DIM: usize> {
reference: &'a T,
closure: F,
}
impl<'a, R, T: Broadcastable, F: Fn(T::Element) -> R, const DIM: usize> TensorDimension
for BMap<'a, R, T, F, DIM>
{
const DIM: usize = DIM;
}
impl<'a, R, T: Broadcastable, F: Fn(T::Element) -> R, const DIM: usize> TensorSize
for BMap<'a, R, T, F, DIM>
{
fn size(&self) -> [usize; DIM] {
//~^ ERROR: method not compatible with trait [E0308]
self.reference.size()
//~^ ERROR: unconstrained generic constant
//~| ERROR: mismatched types
}
}
fn main() {}

View file

@ -0,0 +1,29 @@
error[E0308]: method not compatible with trait
--> $DIR/issue-83765.rs:30:5
|
LL | fn size(&self) -> [usize; DIM] {
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected `Self::DIM`, found `DIM`
|
= note: expected type `Self::DIM`
found type `DIM`
error: unconstrained generic constant
--> $DIR/issue-83765.rs:32:24
|
LL | self.reference.size()
| ^^^^
|
= help: try adding a `where` bound using this expression: `where [(); Self::DIM]:`
error[E0308]: mismatched types
--> $DIR/issue-83765.rs:32:9
|
LL | self.reference.size()
| ^^^^^^^^^^^^^^^^^^^^^ expected `DIM`, found `Self::DIM`
|
= note: expected type `DIM`
found type `Self::DIM`
error: aborting due to 3 previous errors
For more information about this error, try `rustc --explain E0308`.

View file

@ -0,0 +1,31 @@
#![feature(const_generics, const_fn_trait_bound, const_evaluatable_checked)]
#![allow(incomplete_features)]
trait _Contains<T> {
const does_contain: bool;
}
trait Contains<T, const Satisfied: bool> {}
trait Delegates<T> {}
impl<T, U> Delegates<U> for T where T: Contains<U, true> {}
const fn contains<A, B>() -> bool
where
A: _Contains<B>,
{
A::does_contain
}
impl<T, U> Contains<T, { contains::<T, U>() }> for U where T: _Contains<U> {}
fn writes_to_path<C>(cap: &C) {
writes_to_specific_path(&cap);
//~^ ERROR: the trait bound `(): _Contains<&C>` is not satisfied [E0277]
//~| ERROR: unconstrained generic constant
}
fn writes_to_specific_path<C: Delegates<()>>(cap: &C) {}
fn main() {}

View file

@ -0,0 +1,44 @@
error[E0277]: the trait bound `(): _Contains<&C>` is not satisfied
--> $DIR/issue-85848.rs:24:5
|
LL | writes_to_specific_path(&cap);
| ^^^^^^^^^^^^^^^^^^^^^^^ the trait `_Contains<&C>` is not implemented for `()`
...
LL | fn writes_to_specific_path<C: Delegates<()>>(cap: &C) {}
| ------------- required by this bound in `writes_to_specific_path`
|
note: required because of the requirements on the impl of `Contains<(), true>` for `&C`
--> $DIR/issue-85848.rs:21:12
|
LL | impl<T, U> Contains<T, { contains::<T, U>() }> for U where T: _Contains<U> {}
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ^
note: required because of the requirements on the impl of `Delegates<()>` for `&C`
--> $DIR/issue-85848.rs:12:12
|
LL | impl<T, U> Delegates<U> for T where T: Contains<U, true> {}
| ^^^^^^^^^^^^ ^
error: unconstrained generic constant
--> $DIR/issue-85848.rs:24:5
|
LL | writes_to_specific_path(&cap);
| ^^^^^^^^^^^^^^^^^^^^^^^
...
LL | fn writes_to_specific_path<C: Delegates<()>>(cap: &C) {}
| ------------- required by this bound in `writes_to_specific_path`
|
= help: try adding a `where` bound using this expression: `where [(); { contains::<T, U>() }]:`
note: required because of the requirements on the impl of `Contains<(), true>` for `&C`
--> $DIR/issue-85848.rs:21:12
|
LL | impl<T, U> Contains<T, { contains::<T, U>() }> for U where T: _Contains<U> {}
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ^
note: required because of the requirements on the impl of `Delegates<()>` for `&C`
--> $DIR/issue-85848.rs:12:12
|
LL | impl<T, U> Delegates<U> for T where T: Contains<U, true> {}
| ^^^^^^^^^^^^ ^
error: aborting due to 2 previous errors
For more information about this error, try `rustc --explain E0277`.