mirror of
https://github.com/rust-lang/rust.git
synced 2024-11-28 17:53:56 +00:00
Auto merge of #92257 - fee1-dead:fix_env_further_bounds, r=oli-obk
normalize env constness for nested obligations Closes #92230.
This commit is contained in:
commit
f8abed9ed4
@ -8,6 +8,7 @@
|
|||||||
//! https://rustc-dev-guide.rust-lang.org/traits/resolution.html#confirmation
|
//! https://rustc-dev-guide.rust-lang.org/traits/resolution.html#confirmation
|
||||||
use rustc_data_structures::stack::ensure_sufficient_stack;
|
use rustc_data_structures::stack::ensure_sufficient_stack;
|
||||||
use rustc_hir::lang_items::LangItem;
|
use rustc_hir::lang_items::LangItem;
|
||||||
|
use rustc_hir::Constness;
|
||||||
use rustc_index::bit_set::GrowableBitSet;
|
use rustc_index::bit_set::GrowableBitSet;
|
||||||
use rustc_infer::infer::InferOk;
|
use rustc_infer::infer::InferOk;
|
||||||
use rustc_infer::infer::LateBoundRegionConversionTime::HigherRankedType;
|
use rustc_infer::infer::LateBoundRegionConversionTime::HigherRankedType;
|
||||||
@ -51,6 +52,38 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
|
|||||||
obligation: &TraitObligation<'tcx>,
|
obligation: &TraitObligation<'tcx>,
|
||||||
candidate: SelectionCandidate<'tcx>,
|
candidate: SelectionCandidate<'tcx>,
|
||||||
) -> Result<Selection<'tcx>, SelectionError<'tcx>> {
|
) -> Result<Selection<'tcx>, SelectionError<'tcx>> {
|
||||||
|
let mut obligation = obligation;
|
||||||
|
let new_obligation;
|
||||||
|
|
||||||
|
// HACK(const_trait_impl): the surrounding environment is remapped to a non-const context
|
||||||
|
// because nested obligations might be actually `~const` then (incorrectly) requiring
|
||||||
|
// const impls. for example:
|
||||||
|
// ```
|
||||||
|
// pub trait Super {}
|
||||||
|
// pub trait Sub: Super {}
|
||||||
|
//
|
||||||
|
// impl<A> const Super for &A where A: ~const Super {}
|
||||||
|
// impl<A> const Sub for &A where A: ~const Sub {}
|
||||||
|
// ```
|
||||||
|
//
|
||||||
|
// The procedure to check the code above without the remapping code is as follows:
|
||||||
|
// ```
|
||||||
|
// CheckWf(impl const Sub for &A where A: ~const Sub) // <- const env
|
||||||
|
// CheckPredicate(&A: Super)
|
||||||
|
// CheckPredicate(A: ~const Super) // <- still const env, failure
|
||||||
|
// ```
|
||||||
|
if obligation.param_env.constness() == Constness::Const
|
||||||
|
&& obligation.predicate.skip_binder().constness == ty::BoundConstness::NotConst
|
||||||
|
{
|
||||||
|
new_obligation = TraitObligation {
|
||||||
|
cause: obligation.cause.clone(),
|
||||||
|
param_env: obligation.param_env.without_const(),
|
||||||
|
..*obligation
|
||||||
|
};
|
||||||
|
|
||||||
|
obligation = &new_obligation;
|
||||||
|
}
|
||||||
|
|
||||||
match candidate {
|
match candidate {
|
||||||
BuiltinCandidate { has_nested } => {
|
BuiltinCandidate { has_nested } => {
|
||||||
let data = self.confirm_builtin_candidate(obligation, has_nested);
|
let data = self.confirm_builtin_candidate(obligation, has_nested);
|
||||||
|
@ -0,0 +1,14 @@
|
|||||||
|
// Regression test for #92230.
|
||||||
|
//
|
||||||
|
// check-pass
|
||||||
|
|
||||||
|
#![feature(const_fn_trait_bound)]
|
||||||
|
#![feature(const_trait_impl)]
|
||||||
|
|
||||||
|
pub trait Super {}
|
||||||
|
pub trait Sub: Super {}
|
||||||
|
|
||||||
|
impl<A> const Super for &A where A: ~const Super {}
|
||||||
|
impl<A> const Sub for &A where A: ~const Sub {}
|
||||||
|
|
||||||
|
fn main() {}
|
@ -4,6 +4,7 @@ pub static Y: &'static X = {
|
|||||||
const Y: &'static [u8] = b"";
|
const Y: &'static [u8] = b"";
|
||||||
&X(*Y)
|
&X(*Y)
|
||||||
//~^ ERROR E0277
|
//~^ ERROR E0277
|
||||||
|
//~| ERROR E0277
|
||||||
};
|
};
|
||||||
|
|
||||||
fn main() {}
|
fn main() {}
|
||||||
|
@ -8,6 +8,20 @@ LL | &X(*Y)
|
|||||||
= note: all function arguments must have a statically known size
|
= note: all function arguments must have a statically known size
|
||||||
= help: unsized fn params are gated as an unstable feature
|
= help: unsized fn params are gated as an unstable feature
|
||||||
|
|
||||||
error: aborting due to previous error
|
error[E0277]: the size for values of type `[u8]` cannot be known at compilation time
|
||||||
|
--> $DIR/issue-30355.rs:5:6
|
||||||
|
|
|
||||||
|
LL | &X(*Y)
|
||||||
|
| ^ doesn't have a size known at compile-time
|
||||||
|
|
|
||||||
|
= help: within `X`, the trait `Sized` is not implemented for `[u8]`
|
||||||
|
note: required because it appears within the type `X`
|
||||||
|
--> $DIR/issue-30355.rs:1:12
|
||||||
|
|
|
||||||
|
LL | pub struct X([u8]);
|
||||||
|
| ^
|
||||||
|
= note: the return type of a function must have a statically known size
|
||||||
|
|
||||||
|
error: aborting due to 2 previous errors
|
||||||
|
|
||||||
For more information about this error, try `rustc --explain E0277`.
|
For more information about this error, try `rustc --explain E0277`.
|
||||||
|
Loading…
Reference in New Issue
Block a user