Split UserTypeAnnotation to have a kind
This commit is contained in:
parent
4a204bebdf
commit
1da411e750
13 changed files with 60 additions and 36 deletions
|
@ -275,7 +275,7 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
|
|||
user_ty: ty::UserType<'tcx>,
|
||||
span: Span,
|
||||
) {
|
||||
let ty::UserType::Ty(user_ty) = user_ty else { bug!() };
|
||||
let ty::UserTypeKind::Ty(user_ty) = user_ty.kind else { bug!() };
|
||||
|
||||
// A fast path for a common case with closure input/output types.
|
||||
if let ty::Infer(_) = user_ty.kind() {
|
||||
|
|
|
@ -110,7 +110,7 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
|
|||
) {
|
||||
self.ascribe_user_type_skip_wf(
|
||||
arg_decl.ty,
|
||||
ty::UserType::Ty(user_ty),
|
||||
ty::UserType::new(ty::UserTypeKind::Ty(user_ty)),
|
||||
arg_decl.source_info.span,
|
||||
);
|
||||
}
|
||||
|
@ -119,7 +119,7 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
|
|||
let output_decl = &body.local_decls[RETURN_PLACE];
|
||||
self.ascribe_user_type_skip_wf(
|
||||
output_decl.ty,
|
||||
ty::UserType::Ty(user_provided_sig.output()),
|
||||
ty::UserType::new(ty::UserTypeKind::Ty(user_provided_sig.output())),
|
||||
output_decl.source_info.span,
|
||||
);
|
||||
}
|
||||
|
|
|
@ -31,7 +31,7 @@ use rustc_middle::ty::visit::TypeVisitableExt;
|
|||
use rustc_middle::ty::{
|
||||
self, Binder, CanonicalUserTypeAnnotation, CanonicalUserTypeAnnotations, CoroutineArgsExt,
|
||||
Dynamic, GenericArgsRef, OpaqueHiddenType, OpaqueTypeKey, RegionVid, Ty, TyCtxt, UserArgs,
|
||||
UserType, UserTypeAnnotationIndex,
|
||||
UserTypeAnnotationIndex,
|
||||
};
|
||||
use rustc_middle::{bug, span_bug};
|
||||
use rustc_mir_dataflow::ResultsCursor;
|
||||
|
@ -370,7 +370,10 @@ impl<'a, 'b, 'tcx> Visitor<'tcx> for TypeVerifier<'a, 'b, 'tcx> {
|
|||
} else {
|
||||
self.cx.ascribe_user_type(
|
||||
constant.const_.ty(),
|
||||
UserType::TypeOf(uv.def, UserArgs { args: uv.args, user_self_ty: None }),
|
||||
ty::UserType::new(ty::UserTypeKind::TypeOf(uv.def, UserArgs {
|
||||
args: uv.args,
|
||||
user_self_ty: None,
|
||||
})),
|
||||
locations.span(self.cx.body),
|
||||
);
|
||||
}
|
||||
|
@ -991,9 +994,10 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
|
|||
for user_annotation in self.user_type_annotations {
|
||||
let CanonicalUserTypeAnnotation { span, ref user_ty, inferred_ty } = *user_annotation;
|
||||
let annotation = self.instantiate_canonical(span, user_ty);
|
||||
if let ty::UserType::TypeOf(def, args) = annotation
|
||||
if let ty::UserTypeKind::TypeOf(def, args) = annotation.kind
|
||||
&& let DefKind::InlineConst = tcx.def_kind(def)
|
||||
{
|
||||
// TODO:
|
||||
self.check_inline_const(inferred_ty, def.expect_local(), args, span);
|
||||
} else {
|
||||
self.ascribe_user_type(inferred_ty, annotation, span);
|
||||
|
|
|
@ -25,7 +25,7 @@ use rustc_middle::ty::fold::TypeFoldable;
|
|||
use rustc_middle::ty::visit::{TypeVisitable, TypeVisitableExt};
|
||||
use rustc_middle::ty::{
|
||||
self, AdtKind, CanonicalUserType, GenericArgKind, GenericArgsRef, GenericParamDefKind,
|
||||
IsIdentity, Ty, TyCtxt, UserArgs, UserSelfTy, UserType,
|
||||
IsIdentity, Ty, TyCtxt, UserArgs, UserSelfTy,
|
||||
};
|
||||
use rustc_middle::{bug, span_bug};
|
||||
use rustc_session::lint;
|
||||
|
@ -216,11 +216,9 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
|
|||
debug!("fcx {}", self.tag());
|
||||
|
||||
if Self::can_contain_user_lifetime_bounds((args, user_self_ty)) {
|
||||
let canonicalized =
|
||||
self.canonicalize_user_type_annotation(UserType::TypeOf(def_id, UserArgs {
|
||||
args,
|
||||
user_self_ty,
|
||||
}));
|
||||
let canonicalized = self.canonicalize_user_type_annotation(ty::UserType::new(
|
||||
ty::UserTypeKind::TypeOf(def_id, UserArgs { args, user_self_ty }),
|
||||
));
|
||||
debug!(?canonicalized);
|
||||
self.write_user_type_annotation(hir_id, canonicalized);
|
||||
}
|
||||
|
@ -468,7 +466,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
|
|||
debug!(?ty);
|
||||
|
||||
if Self::can_contain_user_lifetime_bounds(ty.raw) {
|
||||
let c_ty = self.canonicalize_response(UserType::Ty(ty.raw));
|
||||
let c_ty = self.canonicalize_response(ty::UserType::new(ty::UserTypeKind::Ty(ty.raw)));
|
||||
debug!(?c_ty);
|
||||
self.typeck_results.borrow_mut().user_provided_types_mut().insert(hir_ty.hir_id, c_ty);
|
||||
}
|
||||
|
|
|
@ -2,7 +2,7 @@ use rustc_hir as hir;
|
|||
use rustc_hir::intravisit::{self, Visitor};
|
||||
use rustc_hir::{HirId, PatKind};
|
||||
use rustc_infer::traits::ObligationCauseCode;
|
||||
use rustc_middle::ty::{Ty, UserType};
|
||||
use rustc_middle::ty::{self, Ty};
|
||||
use rustc_span::Span;
|
||||
use rustc_span::def_id::LocalDefId;
|
||||
use tracing::debug;
|
||||
|
@ -92,7 +92,9 @@ impl<'a, 'tcx> GatherLocalsVisitor<'a, 'tcx> {
|
|||
Some(ref ty) => {
|
||||
let o_ty = self.fcx.lower_ty(ty);
|
||||
|
||||
let c_ty = self.fcx.infcx.canonicalize_user_type_annotation(UserType::Ty(o_ty.raw));
|
||||
let c_ty = self.fcx.infcx.canonicalize_user_type_annotation(ty::UserType::new(
|
||||
ty::UserTypeKind::Ty(o_ty.raw),
|
||||
));
|
||||
debug!("visit_local: ty.hir_id={:?} o_ty={:?} c_ty={:?}", ty.hir_id, o_ty, c_ty);
|
||||
self.fcx
|
||||
.typeck_results
|
||||
|
|
|
@ -17,7 +17,6 @@ use rustc_middle::ty::adjustment::{
|
|||
use rustc_middle::ty::fold::TypeFoldable;
|
||||
use rustc_middle::ty::{
|
||||
self, GenericArgs, GenericArgsRef, GenericParamDefKind, Ty, TyCtxt, TypeVisitableExt, UserArgs,
|
||||
UserType,
|
||||
};
|
||||
use rustc_middle::{bug, span_bug};
|
||||
use rustc_span::{DUMMY_SP, Span};
|
||||
|
@ -491,9 +490,8 @@ impl<'a, 'tcx> ConfirmContext<'a, 'tcx> {
|
|||
user_self_ty: None, // not relevant here
|
||||
};
|
||||
|
||||
self.fcx.canonicalize_user_type_annotation(UserType::TypeOf(
|
||||
pick.item.def_id,
|
||||
user_args,
|
||||
self.fcx.canonicalize_user_type_annotation(ty::UserType::new(
|
||||
ty::UserTypeKind::TypeOf(pick.item.def_id, user_args),
|
||||
))
|
||||
});
|
||||
|
||||
|
|
|
@ -476,7 +476,7 @@ impl<'cx, 'tcx> WritebackCx<'cx, 'tcx> {
|
|||
for (local_id, c_ty) in sorted_user_provided_types {
|
||||
let hir_id = HirId { owner: common_hir_owner, local_id };
|
||||
|
||||
if let ty::UserType::TypeOf(_, user_args) = c_ty.value {
|
||||
if let ty::UserTypeKind::TypeOf(_, user_args) = c_ty.value.kind {
|
||||
// This is a unit-testing mechanism.
|
||||
let span = self.tcx().hir().span(hir_id);
|
||||
// We need to buffer the errors in order to guarantee a consistent
|
||||
|
|
|
@ -95,7 +95,7 @@ pub use self::sty::{
|
|||
pub use self::trait_def::TraitDef;
|
||||
pub use self::typeck_results::{
|
||||
CanonicalUserType, CanonicalUserTypeAnnotation, CanonicalUserTypeAnnotations, IsIdentity,
|
||||
TypeckResults, UserType, UserTypeAnnotationIndex,
|
||||
TypeckResults, UserType, UserTypeAnnotationIndex, UserTypeKind,
|
||||
};
|
||||
pub use self::visit::{TypeSuperVisitable, TypeVisitable, TypeVisitableExt, TypeVisitor};
|
||||
use crate::error::{OpaqueHiddenTypeMismatch, TypeMismatchReason};
|
||||
|
|
|
@ -700,12 +700,24 @@ pub struct CanonicalUserTypeAnnotation<'tcx> {
|
|||
/// Canonical user type annotation.
|
||||
pub type CanonicalUserType<'tcx> = Canonical<'tcx, UserType<'tcx>>;
|
||||
|
||||
#[derive(Copy, Clone, Debug, PartialEq, TyEncodable, TyDecodable)]
|
||||
#[derive(Eq, Hash, HashStable, TypeFoldable, TypeVisitable)]
|
||||
pub struct UserType<'tcx> {
|
||||
pub kind: UserTypeKind<'tcx>,
|
||||
}
|
||||
|
||||
impl<'tcx> UserType<'tcx> {
|
||||
pub fn new(kind: UserTypeKind<'tcx>) -> UserType<'tcx> {
|
||||
UserType { kind }
|
||||
}
|
||||
}
|
||||
|
||||
/// A user-given type annotation attached to a constant. These arise
|
||||
/// from constants that are named via paths, like `Foo::<A>::new` and
|
||||
/// so forth.
|
||||
#[derive(Copy, Clone, Debug, PartialEq, TyEncodable, TyDecodable)]
|
||||
#[derive(Eq, Hash, HashStable, TypeFoldable, TypeVisitable)]
|
||||
pub enum UserType<'tcx> {
|
||||
pub enum UserTypeKind<'tcx> {
|
||||
Ty(Ty<'tcx>),
|
||||
|
||||
/// The canonical type is the result of `type_of(def_id)` with the
|
||||
|
@ -721,9 +733,11 @@ impl<'tcx> IsIdentity for CanonicalUserType<'tcx> {
|
|||
/// Returns `true` if this represents the generic parameters of the form `[?0, ?1, ?2]`,
|
||||
/// i.e., each thing is mapped to a canonical variable with the same index.
|
||||
fn is_identity(&self) -> bool {
|
||||
match self.value {
|
||||
UserType::Ty(_) => false,
|
||||
UserType::TypeOf(_, user_args) => {
|
||||
// TODO:
|
||||
|
||||
match self.value.kind {
|
||||
UserTypeKind::Ty(_) => false,
|
||||
UserTypeKind::TypeOf(_, user_args) => {
|
||||
if user_args.user_self_ty.is_some() {
|
||||
return false;
|
||||
}
|
||||
|
@ -764,6 +778,14 @@ impl<'tcx> IsIdentity for CanonicalUserType<'tcx> {
|
|||
}
|
||||
|
||||
impl<'tcx> std::fmt::Display for UserType<'tcx> {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
// TODO:
|
||||
|
||||
self.kind.fmt(f)
|
||||
}
|
||||
}
|
||||
|
||||
impl<'tcx> std::fmt::Display for UserTypeKind<'tcx> {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
match self {
|
||||
Self::Ty(arg0) => {
|
||||
|
|
|
@ -176,9 +176,8 @@ impl<'pat, 'tcx> MatchPairTree<'pat, 'tcx> {
|
|||
ty: cx.infcx.next_ty_var(span),
|
||||
})
|
||||
.args;
|
||||
let user_ty = cx.infcx.canonicalize_user_type_annotation(ty::UserType::TypeOf(
|
||||
def_id,
|
||||
ty::UserArgs { args, user_self_ty: None },
|
||||
let user_ty = cx.infcx.canonicalize_user_type_annotation(ty::UserType::new(
|
||||
ty::UserTypeKind::TypeOf(def_id, ty::UserArgs { args, user_self_ty: None }),
|
||||
));
|
||||
let annotation = ty::CanonicalUserTypeAnnotation {
|
||||
inferred_ty: pattern.ty,
|
||||
|
|
|
@ -15,7 +15,6 @@ use rustc_middle::ty::adjustment::{
|
|||
};
|
||||
use rustc_middle::ty::{
|
||||
self, AdtKind, GenericArgs, InlineConstArgs, InlineConstArgsParts, ScalarInt, Ty, UpvarArgs,
|
||||
UserType,
|
||||
};
|
||||
use rustc_middle::{bug, span_bug};
|
||||
use rustc_span::{Span, sym};
|
||||
|
@ -443,7 +442,9 @@ impl<'tcx> Cx<'tcx> {
|
|||
let user_provided_types = self.typeck_results().user_provided_types();
|
||||
let user_ty =
|
||||
user_provided_types.get(fun.hir_id).copied().map(|mut u_ty| {
|
||||
if let UserType::TypeOf(ref mut did, _) = &mut u_ty.value {
|
||||
if let ty::UserTypeKind::TypeOf(ref mut did, _) =
|
||||
&mut u_ty.value.kind
|
||||
{
|
||||
*did = adt_def.did();
|
||||
}
|
||||
Box::new(u_ty)
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
use rustc_hir as hir;
|
||||
use rustc_middle::bug;
|
||||
use rustc_middle::ty::{self, CanonicalUserType, TyCtxt, UserType};
|
||||
use rustc_middle::ty::{self, CanonicalUserType, TyCtxt};
|
||||
use tracing::debug;
|
||||
|
||||
pub(crate) trait UserAnnotatedTyHelpers<'tcx> {
|
||||
|
@ -21,7 +21,7 @@ pub(crate) trait UserAnnotatedTyHelpers<'tcx> {
|
|||
let ty = self.typeck_results().node_type(hir_id);
|
||||
match ty.kind() {
|
||||
ty::Adt(adt_def, ..) => {
|
||||
if let UserType::TypeOf(ref mut did, _) = &mut user_ty.value {
|
||||
if let ty::UserTypeKind::TypeOf(ref mut did, _) = &mut user_ty.value.kind {
|
||||
*did = adt_def.did();
|
||||
}
|
||||
Some(user_ty)
|
||||
|
|
|
@ -3,7 +3,7 @@ use rustc_infer::traits::Obligation;
|
|||
use rustc_middle::traits::query::NoSolution;
|
||||
pub use rustc_middle::traits::query::type_op::AscribeUserType;
|
||||
use rustc_middle::traits::{ObligationCause, ObligationCauseCode};
|
||||
use rustc_middle::ty::{self, ParamEnvAnd, Ty, TyCtxt, UserArgs, UserSelfTy, UserType};
|
||||
use rustc_middle::ty::{self, ParamEnvAnd, Ty, TyCtxt, UserArgs, UserSelfTy, UserTypeKind};
|
||||
use rustc_span::{DUMMY_SP, Span};
|
||||
use tracing::{debug, instrument};
|
||||
|
||||
|
@ -46,9 +46,9 @@ pub fn type_op_ascribe_user_type_with_span<'tcx>(
|
|||
let (param_env, AscribeUserType { mir_ty, user_ty }) = key.into_parts();
|
||||
debug!("type_op_ascribe_user_type: mir_ty={:?} user_ty={:?}", mir_ty, user_ty);
|
||||
let span = span.unwrap_or(DUMMY_SP);
|
||||
match user_ty {
|
||||
UserType::Ty(user_ty) => relate_mir_and_user_ty(ocx, param_env, span, mir_ty, user_ty)?,
|
||||
UserType::TypeOf(def_id, user_args) => {
|
||||
match user_ty.kind {
|
||||
UserTypeKind::Ty(user_ty) => relate_mir_and_user_ty(ocx, param_env, span, mir_ty, user_ty)?,
|
||||
UserTypeKind::TypeOf(def_id, user_args) => {
|
||||
relate_mir_and_user_args(ocx, param_env, span, mir_ty, def_id, user_args)?
|
||||
}
|
||||
};
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue