Inherited use constness and assoc change predicate
This commit is contained in:
parent
d356cd10f7
commit
7e6db83b14
@ -255,7 +255,7 @@ checksum = "81a18687293a1546b67c246452202bbbf143d239cb43494cc163da14979082da"
|
||||
|
||||
[[package]]
|
||||
name = "cargo"
|
||||
version = "0.57.0"
|
||||
version = "0.56.0"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"atty",
|
||||
@ -388,7 +388,7 @@ dependencies = [
|
||||
|
||||
[[package]]
|
||||
name = "cargo-util"
|
||||
version = "0.1.1"
|
||||
version = "0.1.0"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"core-foundation",
|
||||
|
@ -16,6 +16,15 @@ pub enum AssocItemContainer {
|
||||
}
|
||||
|
||||
impl AssocItemContainer {
|
||||
/// Asserts that this is the `DefId` of an associated item declared
|
||||
/// in an impl, and returns the trait `DefId`.
|
||||
pub fn assert_impl(&self) -> DefId {
|
||||
match *self {
|
||||
ImplContainer(id) => id,
|
||||
_ => bug!("associated item has wrong container type: {:?}", self),
|
||||
}
|
||||
}
|
||||
|
||||
/// Asserts that this is the `DefId` of an associated item declared
|
||||
/// in a trait, and returns the trait `DefId`.
|
||||
pub fn assert_trait(&self) -> DefId {
|
||||
|
@ -1292,7 +1292,24 @@ pub fn check_type_bounds<'tcx>(
|
||||
};
|
||||
|
||||
tcx.infer_ctxt().enter(move |infcx| {
|
||||
let inh = Inherited::new(infcx, impl_ty.def_id.expect_local());
|
||||
// if the item is inside a const impl, we transform the predicates to be const.
|
||||
let constness = tcx.impl_constness(impl_ty.container.assert_impl());
|
||||
let pred_map = match constness {
|
||||
hir::Constness::NotConst => |p, _| p,
|
||||
hir::Constness::Const => |p: ty::Predicate<'tcx>, tcx: TyCtxt<'tcx>| {
|
||||
p.kind()
|
||||
.map_bound(|kind| match kind {
|
||||
ty::PredicateKind::Trait(mut tp) => {
|
||||
tp.constness = hir::Constness::Const;
|
||||
ty::PredicateKind::Trait(tp)
|
||||
}
|
||||
kind => kind,
|
||||
})
|
||||
.to_predicate(tcx)
|
||||
},
|
||||
};
|
||||
|
||||
let inh = Inherited::with_constness(infcx, impl_ty.def_id.expect_local(), constness);
|
||||
let infcx = &inh.infcx;
|
||||
let mut selcx = traits::SelectionContext::new(&infcx);
|
||||
|
||||
@ -1310,7 +1327,7 @@ pub fn check_type_bounds<'tcx>(
|
||||
.explicit_item_bounds(trait_ty.def_id)
|
||||
.iter()
|
||||
.map(|&(bound, span)| {
|
||||
let concrete_ty_bound = bound.subst(tcx, rebased_substs);
|
||||
let concrete_ty_bound = pred_map(bound.subst(tcx, rebased_substs), tcx);
|
||||
debug!("check_type_bounds: concrete_ty_bound = {:?}", concrete_ty_bound);
|
||||
|
||||
traits::Obligation::new(mk_cause(span), param_env, concrete_ty_bound)
|
||||
@ -1328,7 +1345,10 @@ pub fn check_type_bounds<'tcx>(
|
||||
debug!("compare_projection_bounds: normalized predicate = {:?}", normalized_predicate);
|
||||
obligation.predicate = normalized_predicate;
|
||||
|
||||
inh.register_predicates(obligations);
|
||||
inh.register_predicates(obligations.into_iter().map(|mut o| {
|
||||
o.predicate = pred_map(o.predicate, tcx);
|
||||
o
|
||||
}));
|
||||
inh.register_predicate(obligation);
|
||||
}
|
||||
|
||||
|
@ -52,6 +52,9 @@ pub struct Inherited<'a, 'tcx> {
|
||||
pub(super) deferred_generator_interiors:
|
||||
RefCell<Vec<(hir::BodyId, Ty<'tcx>, hir::GeneratorKind)>>,
|
||||
|
||||
/// Reports whether this is in a const context.
|
||||
pub(super) constness: hir::Constness,
|
||||
|
||||
pub(super) body_id: Option<hir::BodyId>,
|
||||
}
|
||||
|
||||
@ -93,6 +96,12 @@ impl<'tcx> InheritedBuilder<'tcx> {
|
||||
|
||||
impl Inherited<'a, 'tcx> {
|
||||
pub(super) fn new(infcx: InferCtxt<'a, 'tcx>, def_id: LocalDefId) -> Self {
|
||||
let tcx = infcx.tcx;
|
||||
let item_id = tcx.hir().local_def_id_to_hir_id(def_id);
|
||||
Self::with_constness(infcx, def_id, tcx.hir().get(item_id).constness())
|
||||
}
|
||||
|
||||
pub(super) fn with_constness(infcx: InferCtxt<'a, 'tcx>, def_id: LocalDefId, constness: hir::Constness) -> Self {
|
||||
let tcx = infcx.tcx;
|
||||
let item_id = tcx.hir().local_def_id_to_hir_id(def_id);
|
||||
let body_id = tcx.hir().maybe_body_owned_by(item_id);
|
||||
@ -108,12 +117,29 @@ impl Inherited<'a, 'tcx> {
|
||||
deferred_call_resolutions: RefCell::new(Default::default()),
|
||||
deferred_cast_checks: RefCell::new(Vec::new()),
|
||||
deferred_generator_interiors: RefCell::new(Vec::new()),
|
||||
constness,
|
||||
body_id,
|
||||
}
|
||||
}
|
||||
|
||||
pub(super) fn register_predicate(&self, obligation: traits::PredicateObligation<'tcx>) {
|
||||
#[instrument(level = "debug", skip(self))]
|
||||
fn transform_predicate(&self, p: &mut ty::Predicate<'tcx>) {
|
||||
// Don't transform non-const bounds into const bounds,
|
||||
// but transform const bounds to non-const when we are
|
||||
// not in a const context.
|
||||
if let hir::Constness::NotConst = self.constness {
|
||||
let kind = p.kind();
|
||||
if let ty::PredicateKind::Trait(pred) = kind.as_ref().skip_binder() {
|
||||
let mut pred = *pred;
|
||||
pred.constness = hir::Constness::NotConst;
|
||||
*p = kind.rebind(ty::PredicateKind::Trait(pred)).to_predicate(self.tcx);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub(super) fn register_predicate(&self, mut obligation: traits::PredicateObligation<'tcx>) {
|
||||
debug!("register_predicate({:?})", obligation);
|
||||
self.transform_predicate(&mut obligation.predicate);
|
||||
if obligation.has_escaping_bound_vars() {
|
||||
span_bug!(obligation.cause.span, "escaping bound vars in predicate {:?}", obligation);
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user