Skip to content

Commit

Permalink
Rollup merge of rust-lang#65579 - skinny121:resolve_const_vars, r=varkor
Browse files Browse the repository at this point in the history
Changed `resolve_type_vars_with_obligations` to also resolve const inference variables

Fixes rust-lang#65380
r? @varkor
  • Loading branch information
JohnTitor authored Oct 20, 2019
2 parents 6d6ead4 + 9cefcd3 commit df117c2
Show file tree
Hide file tree
Showing 10 changed files with 37 additions and 34 deletions.
6 changes: 3 additions & 3 deletions src/librustc/infer/resolve.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
use super::{InferCtxt, FixupError, FixupResult, Span};
use super::type_variable::{TypeVariableOrigin, TypeVariableOriginKind};
use crate::mir::interpret::ConstValue;
use crate::ty::{self, Ty, Const, TyCtxt, TypeFoldable, InferConst, TypeFlags};
use crate::ty::{self, Ty, Const, TyCtxt, TypeFoldable, InferConst};
use crate::ty::fold::{TypeFolder, TypeVisitor};

///////////////////////////////////////////////////////////////////////////
Expand Down Expand Up @@ -29,7 +29,7 @@ impl<'a, 'tcx> TypeFolder<'tcx> for OpportunisticVarResolver<'a, 'tcx> {
}

fn fold_ty(&mut self, t: Ty<'tcx>) -> Ty<'tcx> {
if !t.has_infer_types() {
if !t.has_infer_types() && !t.has_infer_consts() {
t // micro-optimize -- if there is nothing in this type that this fold affects...
} else {
let t = self.infcx.shallow_resolve(t);
Expand All @@ -38,7 +38,7 @@ impl<'a, 'tcx> TypeFolder<'tcx> for OpportunisticVarResolver<'a, 'tcx> {
}

fn fold_const(&mut self, ct: &'tcx Const<'tcx>) -> &'tcx Const<'tcx> {
if !ct.has_type_flags(TypeFlags::HAS_CT_INFER) {
if !ct.has_infer_consts() {
ct // micro-optimize -- if there is nothing in this const that this fold affects...
} else {
let ct = self.infcx.shallow_resolve(ct);
Expand Down
3 changes: 3 additions & 0 deletions src/librustc/ty/fold.rs
Original file line number Diff line number Diff line change
Expand Up @@ -88,6 +88,9 @@ pub trait TypeFoldable<'tcx>: fmt::Debug + Clone {
fn has_infer_types(&self) -> bool {
self.has_type_flags(TypeFlags::HAS_TY_INFER)
}
fn has_infer_consts(&self) -> bool {
self.has_type_flags(TypeFlags::HAS_CT_INFER)
}
fn has_local_value(&self) -> bool {
self.has_type_flags(TypeFlags::KEEP_IN_LOCAL_TCX)
}
Expand Down
10 changes: 5 additions & 5 deletions src/librustc_typeck/check/coercion.rs
Original file line number Diff line number Diff line change
Expand Up @@ -811,7 +811,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
target: Ty<'tcx>,
allow_two_phase: AllowTwoPhase,
) -> RelateResult<'tcx, Ty<'tcx>> {
let source = self.resolve_type_vars_with_obligations(expr_ty);
let source = self.resolve_vars_with_obligations(expr_ty);
debug!("coercion::try({:?}: {:?} -> {:?})", expr, source, target);

let cause = self.cause(expr.span, ObligationCauseCode::ExprAssignable);
Expand All @@ -829,7 +829,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {

/// Same as `try_coerce()`, but without side-effects.
pub fn can_coerce(&self, expr_ty: Ty<'tcx>, target: Ty<'tcx>) -> bool {
let source = self.resolve_type_vars_with_obligations(expr_ty);
let source = self.resolve_vars_with_obligations(expr_ty);
debug!("coercion::can({:?} -> {:?})", source, target);

let cause = self.cause(syntax_pos::DUMMY_SP, ObligationCauseCode::ExprAssignable);
Expand All @@ -853,8 +853,8 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
-> RelateResult<'tcx, Ty<'tcx>>
where E: AsCoercionSite
{
let prev_ty = self.resolve_type_vars_with_obligations(prev_ty);
let new_ty = self.resolve_type_vars_with_obligations(new_ty);
let prev_ty = self.resolve_vars_with_obligations(prev_ty);
let new_ty = self.resolve_vars_with_obligations(new_ty);
debug!("coercion::try_find_coercion_lub({:?}, {:?})", prev_ty, new_ty);

// Special-case that coercion alone cannot handle:
Expand Down Expand Up @@ -1333,7 +1333,7 @@ impl<'tcx, 'exprs, E: AsCoercionSite> CoerceMany<'tcx, 'exprs, E> {
err.span_label(return_sp, "expected because this return type...");
err.span_label( *sp, format!(
"...is found to be `{}` here",
fcx.resolve_type_vars_with_obligations(expected),
fcx.resolve_vars_with_obligations(expected),
));
}
err
Expand Down
4 changes: 2 additions & 2 deletions src/librustc_typeck/check/demand.rs
Original file line number Diff line number Diff line change
Expand Up @@ -108,7 +108,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
expected: Ty<'tcx>,
allow_two_phase: AllowTwoPhase)
-> (Ty<'tcx>, Option<DiagnosticBuilder<'tcx>>) {
let expected = self.resolve_type_vars_with_obligations(expected);
let expected = self.resolve_vars_with_obligations(expected);

let e = match self.try_coerce(expr, checked_ty, expected, allow_two_phase) {
Ok(ty) => return (ty, None),
Expand All @@ -117,7 +117,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {

let expr = expr.peel_drop_temps();
let cause = self.misc(expr.span);
let expr_ty = self.resolve_type_vars_with_obligations(checked_ty);
let expr_ty = self.resolve_vars_with_obligations(checked_ty);
let mut err = self.report_mismatched_types(&cause, expected, expr_ty, e);

if self.is_assign_to_bool(expr, expected) {
Expand Down
2 changes: 1 addition & 1 deletion src/librustc_typeck/check/expr.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1010,7 +1010,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
expr: &'tcx hir::Expr,
) -> Ty<'tcx> {
let flds = expected.only_has_type(self).and_then(|ty| {
let ty = self.resolve_type_vars_with_obligations(ty);
let ty = self.resolve_vars_with_obligations(ty);
match ty.kind {
ty::Tuple(ref flds) => Some(&flds[..]),
_ => None
Expand Down
2 changes: 1 addition & 1 deletion src/librustc_typeck/check/method/suggest.rs
Original file line number Diff line number Diff line change
Expand Up @@ -919,7 +919,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
// This occurs for UFCS desugaring of `T::method`, where there is no
// receiver expression for the method call, and thus no autoderef.
if let SelfSource::QPath(_) = source {
return is_local(self.resolve_type_vars_with_obligations(rcvr_ty));
return is_local(self.resolve_vars_with_obligations(rcvr_ty));
}

self.autoderef(span, rcvr_ty).any(|(ty, _)| is_local(ty))
Expand Down
22 changes: 11 additions & 11 deletions src/librustc_typeck/check/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2440,23 +2440,23 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
self.cause(span, ObligationCauseCode::MiscObligation)
}

/// Resolves type variables in `ty` if possible. Unlike the infcx
/// Resolves type and const variables in `ty` if possible. Unlike the infcx
/// version (resolve_vars_if_possible), this version will
/// also select obligations if it seems useful, in an effort
/// to get more type information.
fn resolve_type_vars_with_obligations(&self, mut ty: Ty<'tcx>) -> Ty<'tcx> {
debug!("resolve_type_vars_with_obligations(ty={:?})", ty);
fn resolve_vars_with_obligations(&self, mut ty: Ty<'tcx>) -> Ty<'tcx> {
debug!("resolve_vars_with_obligations(ty={:?})", ty);

// No Infer()? Nothing needs doing.
if !ty.has_infer_types() {
debug!("resolve_type_vars_with_obligations: ty={:?}", ty);
if !ty.has_infer_types() && !ty.has_infer_consts() {
debug!("resolve_vars_with_obligations: ty={:?}", ty);
return ty;
}

// If `ty` is a type variable, see whether we already know what it is.
ty = self.resolve_vars_if_possible(&ty);
if !ty.has_infer_types() {
debug!("resolve_type_vars_with_obligations: ty={:?}", ty);
if !ty.has_infer_types() && !ty.has_infer_consts() {
debug!("resolve_vars_with_obligations: ty={:?}", ty);
return ty;
}

Expand All @@ -2467,7 +2467,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
self.select_obligations_where_possible(false, |_| {});
ty = self.resolve_vars_if_possible(&ty);

debug!("resolve_type_vars_with_obligations: ty={:?}", ty);
debug!("resolve_vars_with_obligations: ty={:?}", ty);
ty
}

Expand Down Expand Up @@ -3668,7 +3668,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
formal_ret: Ty<'tcx>,
formal_args: &[Ty<'tcx>])
-> Vec<Ty<'tcx>> {
let formal_ret = self.resolve_type_vars_with_obligations(formal_ret);
let formal_ret = self.resolve_vars_with_obligations(formal_ret);
let ret_ty = match expected_ret.only_has_type(self) {
Some(ret) => ret,
None => return Vec::new()
Expand Down Expand Up @@ -4517,7 +4517,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
err.span_suggestion(
span,
"try adding a return type",
format!("-> {} ", self.resolve_type_vars_with_obligations(found)),
format!("-> {} ", self.resolve_vars_with_obligations(found)),
Applicability::MachineApplicable);
true
}
Expand Down Expand Up @@ -4993,7 +4993,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
// If no resolution is possible, then an error is reported.
// Numeric inference variables may be left unresolved.
pub fn structurally_resolved_type(&self, sp: Span, ty: Ty<'tcx>) -> Ty<'tcx> {
let ty = self.resolve_type_vars_with_obligations(ty);
let ty = self.resolve_vars_with_obligations(ty);
if !ty.is_ty_var() {
ty
} else {
Expand Down
4 changes: 2 additions & 2 deletions src/librustc_typeck/check/op.rs
Original file line number Diff line number Diff line change
Expand Up @@ -179,7 +179,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
self.check_expr_with_needs(lhs_expr, Needs::MutPlace)
}
};
let lhs_ty = self.resolve_type_vars_with_obligations(lhs_ty);
let lhs_ty = self.resolve_vars_with_obligations(lhs_ty);

// N.B., as we have not yet type-checked the RHS, we don't have the
// type at hand. Make a variable to represent it. The whole reason
Expand All @@ -196,7 +196,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {

// see `NB` above
let rhs_ty = self.check_expr_coercable_to_type(rhs_expr, rhs_ty_var);
let rhs_ty = self.resolve_type_vars_with_obligations(rhs_ty);
let rhs_ty = self.resolve_vars_with_obligations(rhs_ty);

let return_ty = match result {
Ok(method) => {
Expand Down
2 changes: 1 addition & 1 deletion src/librustc_typeck/check/pat.rs
Original file line number Diff line number Diff line change
Expand Up @@ -251,7 +251,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
expected: Ty<'tcx>,
mut def_bm: BindingMode,
) -> (Ty<'tcx>, BindingMode) {
let mut expected = self.resolve_type_vars_with_obligations(&expected);
let mut expected = self.resolve_vars_with_obligations(&expected);

// Peel off as many `&` or `&mut` from the scrutinee type as possible. For example,
// for `match &&&mut Some(5)` the loop runs three times, aborting when it reaches
Expand Down
Original file line number Diff line number Diff line change
@@ -1,20 +1,20 @@
error[E0308]: mismatched types
--> $DIR/const-argument-cross-crate-mismatch.rs:6:41
--> $DIR/const-argument-cross-crate-mismatch.rs:6:67
|
LL | let _ = const_generic_lib::function(const_generic_lib::Struct([0u8, 1u8]));
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected `3usize`, found `2usize`
| ^^^^^^^^^^ expected an array with a fixed size of 3 elements, found one with 2 elements
|
= note: expected type `const_generic_lib::Struct<3usize>`
found type `const_generic_lib::Struct<_: usize>`
= note: expected type `[u8; 3]`
found type `[u8; 2]`

error[E0308]: mismatched types
--> $DIR/const-argument-cross-crate-mismatch.rs:8:39
--> $DIR/const-argument-cross-crate-mismatch.rs:8:65
|
LL | let _: const_generic_lib::Alias = const_generic_lib::Struct([0u8, 1u8, 2u8]);
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected `2usize`, found `3usize`
| ^^^^^^^^^^^^^^^ expected an array with a fixed size of 2 elements, found one with 3 elements
|
= note: expected type `const_generic_lib::Struct<2usize>`
found type `const_generic_lib::Struct<_: usize>`
= note: expected type `[u8; 2]`
found type `[u8; 3]`

error: aborting due to 2 previous errors

Expand Down

0 comments on commit df117c2

Please sign in to comment.