Added mir::UserTypeProjection
, a stub for a structure that projects *into* a given UserTypeAnnotation.
(That is, it will pull out some component type held or referenced by the type annotation.) Note: this still needs to actually do projection itself. That comes in a later commit
This commit is contained in:
parent
36d8432a6d
commit
28ce99df86
10 changed files with 71 additions and 33 deletions
|
@ -606,3 +606,5 @@ impl<'a, 'gcx> HashStable<StableHashingContext<'a>> for mir::UserTypeAnnotation<
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl_stable_hash_for!(struct mir::UserTypeProjection<'tcx> { base });
|
||||||
|
|
|
@ -710,7 +710,7 @@ pub struct LocalDecl<'tcx> {
|
||||||
/// e.g. via `let x: T`, then we carry that type here. The MIR
|
/// e.g. via `let x: T`, then we carry that type here. The MIR
|
||||||
/// borrow checker needs this information since it can affect
|
/// borrow checker needs this information since it can affect
|
||||||
/// region inference.
|
/// region inference.
|
||||||
pub user_ty: Option<(UserTypeAnnotation<'tcx>, Span)>,
|
pub user_ty: Option<(UserTypeProjection<'tcx>, Span)>,
|
||||||
|
|
||||||
/// Name of the local, used in debuginfo and pretty-printing.
|
/// Name of the local, used in debuginfo and pretty-printing.
|
||||||
///
|
///
|
||||||
|
@ -1741,7 +1741,7 @@ pub enum StatementKind<'tcx> {
|
||||||
/// - `Contravariant` -- requires that `T_y :> T`
|
/// - `Contravariant` -- requires that `T_y :> T`
|
||||||
/// - `Invariant` -- requires that `T_y == T`
|
/// - `Invariant` -- requires that `T_y == T`
|
||||||
/// - `Bivariant` -- no effect
|
/// - `Bivariant` -- no effect
|
||||||
AscribeUserType(Place<'tcx>, ty::Variance, Box<UserTypeAnnotation<'tcx>>),
|
AscribeUserType(Place<'tcx>, ty::Variance, Box<UserTypeProjection<'tcx>>),
|
||||||
|
|
||||||
/// No-op. Useful for deleting instructions without affecting statement indices.
|
/// No-op. Useful for deleting instructions without affecting statement indices.
|
||||||
Nop,
|
Nop,
|
||||||
|
@ -2449,6 +2449,17 @@ EnumLiftImpl! {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash, RustcEncodable, RustcDecodable)]
|
||||||
|
pub struct UserTypeProjection<'tcx> {
|
||||||
|
pub base: UserTypeAnnotation<'tcx>,
|
||||||
|
}
|
||||||
|
|
||||||
|
BraceStructTypeFoldableImpl! {
|
||||||
|
impl<'tcx> TypeFoldable<'tcx> for UserTypeProjection<'tcx> {
|
||||||
|
base
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
newtype_index! {
|
newtype_index! {
|
||||||
pub struct Promoted {
|
pub struct Promoted {
|
||||||
DEBUG_FORMAT = "promoted[{}]"
|
DEBUG_FORMAT = "promoted[{}]"
|
||||||
|
|
|
@ -147,7 +147,7 @@ macro_rules! make_mir_visitor {
|
||||||
fn visit_ascribe_user_ty(&mut self,
|
fn visit_ascribe_user_ty(&mut self,
|
||||||
place: & $($mutability)* Place<'tcx>,
|
place: & $($mutability)* Place<'tcx>,
|
||||||
variance: & $($mutability)* ty::Variance,
|
variance: & $($mutability)* ty::Variance,
|
||||||
user_ty: & $($mutability)* UserTypeAnnotation<'tcx>,
|
user_ty: & $($mutability)* UserTypeProjection<'tcx>,
|
||||||
location: Location) {
|
location: Location) {
|
||||||
self.super_ascribe_user_ty(place, variance, user_ty, location);
|
self.super_ascribe_user_ty(place, variance, user_ty, location);
|
||||||
}
|
}
|
||||||
|
@ -213,6 +213,13 @@ macro_rules! make_mir_visitor {
|
||||||
self.super_ty(ty);
|
self.super_ty(ty);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn visit_user_type_projection(
|
||||||
|
&mut self,
|
||||||
|
ty: & $($mutability)* UserTypeProjection<'tcx>,
|
||||||
|
) {
|
||||||
|
self.super_user_type_projection(ty);
|
||||||
|
}
|
||||||
|
|
||||||
fn visit_user_type_annotation(
|
fn visit_user_type_annotation(
|
||||||
&mut self,
|
&mut self,
|
||||||
ty: & $($mutability)* UserTypeAnnotation<'tcx>,
|
ty: & $($mutability)* UserTypeAnnotation<'tcx>,
|
||||||
|
@ -639,10 +646,10 @@ macro_rules! make_mir_visitor {
|
||||||
fn super_ascribe_user_ty(&mut self,
|
fn super_ascribe_user_ty(&mut self,
|
||||||
place: & $($mutability)* Place<'tcx>,
|
place: & $($mutability)* Place<'tcx>,
|
||||||
_variance: & $($mutability)* ty::Variance,
|
_variance: & $($mutability)* ty::Variance,
|
||||||
user_ty: & $($mutability)* UserTypeAnnotation<'tcx>,
|
user_ty: & $($mutability)* UserTypeProjection<'tcx>,
|
||||||
location: Location) {
|
location: Location) {
|
||||||
self.visit_place(place, PlaceContext::Validate, location);
|
self.visit_place(place, PlaceContext::Validate, location);
|
||||||
self.visit_user_type_annotation(user_ty);
|
self.visit_user_type_projection(user_ty);
|
||||||
}
|
}
|
||||||
|
|
||||||
fn super_place(&mut self,
|
fn super_place(&mut self,
|
||||||
|
@ -737,7 +744,7 @@ macro_rules! make_mir_visitor {
|
||||||
source_info: *source_info,
|
source_info: *source_info,
|
||||||
});
|
});
|
||||||
if let Some((user_ty, _)) = user_ty {
|
if let Some((user_ty, _)) = user_ty {
|
||||||
self.visit_user_type_annotation(user_ty);
|
self.visit_user_type_projection(user_ty);
|
||||||
}
|
}
|
||||||
self.visit_source_info(source_info);
|
self.visit_source_info(source_info);
|
||||||
self.visit_source_scope(visibility_scope);
|
self.visit_source_scope(visibility_scope);
|
||||||
|
@ -784,6 +791,16 @@ macro_rules! make_mir_visitor {
|
||||||
self.visit_source_scope(scope);
|
self.visit_source_scope(scope);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn super_user_type_projection(
|
||||||
|
&mut self,
|
||||||
|
ty: & $($mutability)* UserTypeProjection<'tcx>,
|
||||||
|
) {
|
||||||
|
let UserTypeProjection {
|
||||||
|
ref $($mutability)* base,
|
||||||
|
} = *ty;
|
||||||
|
self.visit_user_type_annotation(base)
|
||||||
|
}
|
||||||
|
|
||||||
fn super_user_type_annotation(
|
fn super_user_type_annotation(
|
||||||
&mut self,
|
&mut self,
|
||||||
_ty: & $($mutability)* UserTypeAnnotation<'tcx>,
|
_ty: & $($mutability)* UserTypeAnnotation<'tcx>,
|
||||||
|
|
|
@ -18,7 +18,7 @@ use rustc::mir::visit::TyContext;
|
||||||
use rustc::mir::visit::Visitor;
|
use rustc::mir::visit::Visitor;
|
||||||
use rustc::mir::{BasicBlock, BasicBlockData, Location, Mir, Place, Rvalue};
|
use rustc::mir::{BasicBlock, BasicBlockData, Location, Mir, Place, Rvalue};
|
||||||
use rustc::mir::{Statement, Terminator};
|
use rustc::mir::{Statement, Terminator};
|
||||||
use rustc::mir::UserTypeAnnotation;
|
use rustc::mir::UserTypeProjection;
|
||||||
use rustc::ty::fold::TypeFoldable;
|
use rustc::ty::fold::TypeFoldable;
|
||||||
use rustc::ty::subst::Substs;
|
use rustc::ty::subst::Substs;
|
||||||
use rustc::ty::{self, ClosureSubsts, GeneratorSubsts, RegionVid};
|
use rustc::ty::{self, ClosureSubsts, GeneratorSubsts, RegionVid};
|
||||||
|
@ -183,7 +183,7 @@ impl<'cg, 'cx, 'gcx, 'tcx> Visitor<'tcx> for ConstraintGeneration<'cg, 'cx, 'gcx
|
||||||
&mut self,
|
&mut self,
|
||||||
_place: &Place<'tcx>,
|
_place: &Place<'tcx>,
|
||||||
_variance: &ty::Variance,
|
_variance: &ty::Variance,
|
||||||
_user_ty: &UserTypeAnnotation<'tcx>,
|
_user_ty: &UserTypeProjection<'tcx>,
|
||||||
_location: Location,
|
_location: Location,
|
||||||
) {
|
) {
|
||||||
}
|
}
|
||||||
|
|
|
@ -284,7 +284,7 @@ impl<'a, 'b, 'gcx, 'tcx> Visitor<'tcx> for TypeVerifier<'a, 'b, 'gcx, 'tcx> {
|
||||||
if let Err(terr) = self.cx.relate_type_and_user_type(
|
if let Err(terr) = self.cx.relate_type_and_user_type(
|
||||||
constant.ty,
|
constant.ty,
|
||||||
ty::Variance::Invariant,
|
ty::Variance::Invariant,
|
||||||
user_ty,
|
UserTypeProjection { base: user_ty },
|
||||||
location.to_locations(),
|
location.to_locations(),
|
||||||
ConstraintCategory::Boring,
|
ConstraintCategory::Boring,
|
||||||
) {
|
) {
|
||||||
|
@ -971,7 +971,7 @@ impl<'a, 'gcx, 'tcx> TypeChecker<'a, 'gcx, 'tcx> {
|
||||||
&mut self,
|
&mut self,
|
||||||
a: Ty<'tcx>,
|
a: Ty<'tcx>,
|
||||||
v: ty::Variance,
|
v: ty::Variance,
|
||||||
user_ty: UserTypeAnnotation<'tcx>,
|
user_ty: UserTypeProjection<'tcx>,
|
||||||
locations: Locations,
|
locations: Locations,
|
||||||
category: ConstraintCategory,
|
category: ConstraintCategory,
|
||||||
) -> Fallible<()> {
|
) -> Fallible<()> {
|
||||||
|
@ -980,7 +980,8 @@ impl<'a, 'gcx, 'tcx> TypeChecker<'a, 'gcx, 'tcx> {
|
||||||
a, v, user_ty, locations,
|
a, v, user_ty, locations,
|
||||||
);
|
);
|
||||||
|
|
||||||
match user_ty {
|
// FIXME
|
||||||
|
match user_ty.base {
|
||||||
UserTypeAnnotation::Ty(canonical_ty) => {
|
UserTypeAnnotation::Ty(canonical_ty) => {
|
||||||
let (ty, _) = self.infcx
|
let (ty, _) = self.infcx
|
||||||
.instantiate_canonical_with_fresh_inference_vars(DUMMY_SP, &canonical_ty);
|
.instantiate_canonical_with_fresh_inference_vars(DUMMY_SP, &canonical_ty);
|
||||||
|
@ -1172,7 +1173,7 @@ impl<'a, 'gcx, 'tcx> TypeChecker<'a, 'gcx, 'tcx> {
|
||||||
if let Err(terr) = self.relate_type_and_user_type(
|
if let Err(terr) = self.relate_type_and_user_type(
|
||||||
rv_ty,
|
rv_ty,
|
||||||
ty::Variance::Invariant,
|
ty::Variance::Invariant,
|
||||||
user_ty,
|
UserTypeProjection { base: user_ty },
|
||||||
location.to_locations(),
|
location.to_locations(),
|
||||||
ConstraintCategory::Boring,
|
ConstraintCategory::Boring,
|
||||||
) {
|
) {
|
||||||
|
|
|
@ -147,7 +147,7 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> {
|
||||||
kind: StatementKind::AscribeUserType(
|
kind: StatementKind::AscribeUserType(
|
||||||
place.clone(),
|
place.clone(),
|
||||||
Variance::Invariant,
|
Variance::Invariant,
|
||||||
box user_ty,
|
box UserTypeProjection { base: user_ty },
|
||||||
),
|
),
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
|
@ -167,7 +167,7 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> {
|
||||||
kind: StatementKind::AscribeUserType(
|
kind: StatementKind::AscribeUserType(
|
||||||
Place::Local(temp.clone()),
|
Place::Local(temp.clone()),
|
||||||
Variance::Invariant,
|
Variance::Invariant,
|
||||||
box user_ty,
|
box UserTypeProjection { base: user_ty },
|
||||||
),
|
),
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
|
|
|
@ -491,7 +491,7 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> {
|
||||||
pub(super) fn visit_bindings(
|
pub(super) fn visit_bindings(
|
||||||
&mut self,
|
&mut self,
|
||||||
pattern: &Pattern<'tcx>,
|
pattern: &Pattern<'tcx>,
|
||||||
mut pattern_user_ty: Option<(PatternTypeAnnotation<'tcx>, Span)>,
|
mut pattern_user_ty: Option<(PatternTypeProjection<'tcx>, Span)>,
|
||||||
f: &mut impl FnMut(
|
f: &mut impl FnMut(
|
||||||
&mut Self,
|
&mut Self,
|
||||||
Mutability,
|
Mutability,
|
||||||
|
@ -500,7 +500,7 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> {
|
||||||
NodeId,
|
NodeId,
|
||||||
Span,
|
Span,
|
||||||
Ty<'tcx>,
|
Ty<'tcx>,
|
||||||
Option<(PatternTypeAnnotation<'tcx>, Span)>,
|
Option<(PatternTypeProjection<'tcx>, Span)>,
|
||||||
),
|
),
|
||||||
) {
|
) {
|
||||||
match *pattern.kind {
|
match *pattern.kind {
|
||||||
|
@ -626,7 +626,7 @@ struct Binding<'tcx> {
|
||||||
struct Ascription<'tcx> {
|
struct Ascription<'tcx> {
|
||||||
span: Span,
|
span: Span,
|
||||||
source: Place<'tcx>,
|
source: Place<'tcx>,
|
||||||
user_ty: PatternTypeAnnotation<'tcx>,
|
user_ty: PatternTypeProjection<'tcx>,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
@ -1470,7 +1470,7 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> {
|
||||||
num_patterns: usize,
|
num_patterns: usize,
|
||||||
var_id: NodeId,
|
var_id: NodeId,
|
||||||
var_ty: Ty<'tcx>,
|
var_ty: Ty<'tcx>,
|
||||||
user_var_ty: Option<(PatternTypeAnnotation<'tcx>, Span)>,
|
user_var_ty: Option<(PatternTypeProjection<'tcx>, Span)>,
|
||||||
has_guard: ArmHasGuard,
|
has_guard: ArmHasGuard,
|
||||||
opt_match_place: Option<(Option<Place<'tcx>>, Span)>,
|
opt_match_place: Option<(Option<Place<'tcx>>, Span)>,
|
||||||
pat_span: Span,
|
pat_span: Span,
|
||||||
|
@ -1489,7 +1489,7 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> {
|
||||||
let local = LocalDecl::<'tcx> {
|
let local = LocalDecl::<'tcx> {
|
||||||
mutability,
|
mutability,
|
||||||
ty: var_ty,
|
ty: var_ty,
|
||||||
user_ty: user_var_ty.map(|(pat_ty, span)|(pat_ty.user_ty(), span)),
|
user_ty: user_var_ty.map(|(ut, sp)| (ut.user_ty(), sp)),
|
||||||
name: Some(name),
|
name: Some(name),
|
||||||
source_info,
|
source_info,
|
||||||
visibility_scope,
|
visibility_scope,
|
||||||
|
|
|
@ -91,7 +91,7 @@ fn mirror_stmts<'a, 'gcx, 'tcx>(cx: &mut Cx<'a, 'gcx, 'tcx>,
|
||||||
ty: pattern.ty,
|
ty: pattern.ty,
|
||||||
span: pattern.span,
|
span: pattern.span,
|
||||||
kind: Box::new(PatternKind::AscribeUserType {
|
kind: Box::new(PatternKind::AscribeUserType {
|
||||||
user_ty: PatternTypeAnnotation::from_c_ty(user_ty),
|
user_ty: PatternTypeProjection::from_canonical_ty(user_ty),
|
||||||
user_ty_span: ty.span,
|
user_ty_span: ty.span,
|
||||||
subpattern: pattern
|
subpattern: pattern
|
||||||
})
|
})
|
||||||
|
|
|
@ -27,7 +27,7 @@ use self::cx::Cx;
|
||||||
pub mod cx;
|
pub mod cx;
|
||||||
|
|
||||||
pub mod pattern;
|
pub mod pattern;
|
||||||
pub use self::pattern::{BindingMode, Pattern, PatternKind, PatternTypeAnnotation, FieldPattern};
|
pub use self::pattern::{BindingMode, Pattern, PatternKind, PatternTypeProjection, FieldPattern};
|
||||||
|
|
||||||
mod util;
|
mod util;
|
||||||
|
|
||||||
|
|
|
@ -20,7 +20,8 @@ use const_eval::{const_field, const_variant_index};
|
||||||
|
|
||||||
use hair::util::UserAnnotatedTyHelpers;
|
use hair::util::UserAnnotatedTyHelpers;
|
||||||
|
|
||||||
use rustc::mir::{fmt_const_val, Field, BorrowKind, Mutability, UserTypeAnnotation};
|
use rustc::mir::{fmt_const_val, Field, BorrowKind, Mutability};
|
||||||
|
use rustc::mir::{UserTypeAnnotation, UserTypeProjection};
|
||||||
use rustc::mir::interpret::{Scalar, GlobalId, ConstValue, sign_extend};
|
use rustc::mir::interpret::{Scalar, GlobalId, ConstValue, sign_extend};
|
||||||
use rustc::ty::{self, Region, TyCtxt, AdtDef, Ty};
|
use rustc::ty::{self, Region, TyCtxt, AdtDef, Ty};
|
||||||
use rustc::ty::subst::{Substs, Kind};
|
use rustc::ty::subst::{Substs, Kind};
|
||||||
|
@ -65,17 +66,22 @@ pub struct Pattern<'tcx> {
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Copy, Clone, Debug)]
|
#[derive(Copy, Clone, Debug)]
|
||||||
pub struct PatternTypeAnnotation<'tcx>(UserTypeAnnotation<'tcx>);
|
pub struct PatternTypeProjection<'tcx>(UserTypeProjection<'tcx>);
|
||||||
|
|
||||||
impl<'tcx> PatternTypeAnnotation<'tcx> {
|
impl<'tcx> PatternTypeProjection<'tcx> {
|
||||||
pub(crate) fn from_c_ty(c_ty: ty::CanonicalTy<'tcx>) -> Self {
|
pub(crate) fn from_canonical_ty(c_ty: ty::CanonicalTy<'tcx>) -> Self {
|
||||||
Self::from_u_ty(UserTypeAnnotation::Ty(c_ty))
|
Self::from_user_type(UserTypeAnnotation::Ty(c_ty))
|
||||||
}
|
|
||||||
pub(crate) fn from_u_ty(u_ty: UserTypeAnnotation<'tcx>) -> Self {
|
|
||||||
PatternTypeAnnotation(u_ty)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
pub(crate) fn user_ty(self) -> UserTypeAnnotation<'tcx> { self.0 }
|
pub(crate) fn from_user_type(u_ty: UserTypeAnnotation<'tcx>) -> Self {
|
||||||
|
Self::from_user_type_proj(UserTypeProjection { base: u_ty })
|
||||||
|
}
|
||||||
|
|
||||||
|
pub(crate) fn from_user_type_proj(u_ty: UserTypeProjection<'tcx>) -> Self {
|
||||||
|
PatternTypeProjection(u_ty)
|
||||||
|
}
|
||||||
|
|
||||||
|
pub(crate) fn user_ty(self) -> UserTypeProjection<'tcx> { self.0 }
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
@ -83,7 +89,7 @@ pub enum PatternKind<'tcx> {
|
||||||
Wild,
|
Wild,
|
||||||
|
|
||||||
AscribeUserType {
|
AscribeUserType {
|
||||||
user_ty: PatternTypeAnnotation<'tcx>,
|
user_ty: PatternTypeProjection<'tcx>,
|
||||||
subpattern: Pattern<'tcx>,
|
subpattern: Pattern<'tcx>,
|
||||||
user_ty_span: Span,
|
user_ty_span: Span,
|
||||||
},
|
},
|
||||||
|
@ -704,7 +710,7 @@ impl<'a, 'tcx> PatternContext<'a, 'tcx> {
|
||||||
|
|
||||||
debug!("pattern user_ty = {:?} for pattern at {:?}", user_ty, span);
|
debug!("pattern user_ty = {:?} for pattern at {:?}", user_ty, span);
|
||||||
|
|
||||||
let pat_ty = PatternTypeAnnotation::from_u_ty(user_ty);
|
let pat_ty = PatternTypeProjection::from_user_type(user_ty);
|
||||||
kind = PatternKind::AscribeUserType {
|
kind = PatternKind::AscribeUserType {
|
||||||
subpattern,
|
subpattern,
|
||||||
user_ty: pat_ty,
|
user_ty: pat_ty,
|
||||||
|
@ -995,7 +1001,8 @@ macro_rules! CloneImpls {
|
||||||
CloneImpls!{ <'tcx>
|
CloneImpls!{ <'tcx>
|
||||||
Span, Field, Mutability, ast::Name, ast::NodeId, usize, &'tcx ty::Const<'tcx>,
|
Span, Field, Mutability, ast::Name, ast::NodeId, usize, &'tcx ty::Const<'tcx>,
|
||||||
Region<'tcx>, Ty<'tcx>, BindingMode<'tcx>, &'tcx AdtDef,
|
Region<'tcx>, Ty<'tcx>, BindingMode<'tcx>, &'tcx AdtDef,
|
||||||
&'tcx Substs<'tcx>, &'tcx Kind<'tcx>, UserTypeAnnotation<'tcx>, PatternTypeAnnotation<'tcx>
|
&'tcx Substs<'tcx>, &'tcx Kind<'tcx>, UserTypeAnnotation<'tcx>,
|
||||||
|
UserTypeProjection<'tcx>, PatternTypeProjection<'tcx>
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'tcx> PatternFoldable<'tcx> for FieldPattern<'tcx> {
|
impl<'tcx> PatternFoldable<'tcx> for FieldPattern<'tcx> {
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue