1use rustc_macros::{StableHash, TyDecodable, TyEncodable};
5use rustc_span::bug;
6
7use crate::mir;
8use crate::ty::{self, Ty};
9
10#[derive(#[automatically_derived]
impl ::core::marker::Copy for IntTy { }Copy, #[automatically_derived]
#[doc(hidden)]
unsafe impl ::core::clone::TrivialClone for IntTy { }
#[automatically_derived]
impl ::core::clone::Clone for IntTy {
#[inline]
fn clone(&self) -> Self {
let _: ::core::clone::AssertParamIsClone<ty::UintTy>;
*self
}
}Clone, #[automatically_derived]
impl ::core::fmt::Debug for IntTy {
#[inline]
fn fmt(&self, f: &mut ::core::fmt::Formatter) -> ::core::fmt::Result {
match self {
IntTy::U(__self_0) =>
::core::fmt::Formatter::debug_tuple_field1_finish(f, "U",
&__self_0),
IntTy::I => ::core::fmt::Formatter::write_str(f, "I"),
IntTy::CEnum => ::core::fmt::Formatter::write_str(f, "CEnum"),
IntTy::Bool => ::core::fmt::Formatter::write_str(f, "Bool"),
IntTy::Char => ::core::fmt::Formatter::write_str(f, "Char"),
}
}
}Debug, #[automatically_derived]
impl ::core::marker::StructuralPartialEq for IntTy { }
#[automatically_derived]
impl ::core::cmp::PartialEq for IntTy {
#[inline]
fn eq(&self, other: &Self) -> bool {
let __self_discr = ::core::intrinsics::discriminant_value(self);
let __arg1_discr = ::core::intrinsics::discriminant_value(other);
__self_discr == __arg1_discr &&
match (self, other) {
(IntTy::U(__self_0), IntTy::U(__arg1_0)) =>
__self_0 == __arg1_0,
_ => true,
}
}
}PartialEq, #[automatically_derived]
impl ::core::cmp::Eq for IntTy {
#[inline]
#[doc(hidden)]
#[coverage(off)]
fn assert_fields_are_eq(&self) {
let _: ::core::cmp::AssertParamIsEq<ty::UintTy>;
}
}Eq)]
12pub enum IntTy {
13 U(ty::UintTy),
14 I,
15 CEnum,
16 Bool,
17 Char,
18}
19
20impl IntTy {
21 pub fn is_signed(self) -> bool {
22 #[allow(non_exhaustive_omitted_patterns)] match self {
Self::I => true,
_ => false,
}matches!(self, Self::I)
23 }
24}
25
26#[derive(#[automatically_derived]
impl<'tcx> ::core::marker::Copy for CastTy<'tcx> { }Copy, #[automatically_derived]
#[doc(hidden)]
unsafe impl<'tcx> ::core::clone::TrivialClone for CastTy<'tcx> { }
#[automatically_derived]
impl<'tcx> ::core::clone::Clone for CastTy<'tcx> {
#[inline]
fn clone(&self) -> Self {
let _: ::core::clone::AssertParamIsClone<IntTy>;
let _: ::core::clone::AssertParamIsClone<ty::TypeAndMut<'tcx>>;
*self
}
}Clone, #[automatically_derived]
impl<'tcx> ::core::fmt::Debug for CastTy<'tcx> {
#[inline]
fn fmt(&self, f: &mut ::core::fmt::Formatter) -> ::core::fmt::Result {
match self {
CastTy::Int(__self_0) =>
::core::fmt::Formatter::debug_tuple_field1_finish(f, "Int",
&__self_0),
CastTy::Float => ::core::fmt::Formatter::write_str(f, "Float"),
CastTy::FnPtr => ::core::fmt::Formatter::write_str(f, "FnPtr"),
CastTy::Ptr(__self_0) =>
::core::fmt::Formatter::debug_tuple_field1_finish(f, "Ptr",
&__self_0),
}
}
}Debug, #[automatically_derived]
impl<'tcx> ::core::marker::StructuralPartialEq for CastTy<'tcx> { }
#[automatically_derived]
impl<'tcx> ::core::cmp::PartialEq for CastTy<'tcx> {
#[inline]
fn eq(&self, other: &Self) -> bool {
let __self_discr = ::core::intrinsics::discriminant_value(self);
let __arg1_discr = ::core::intrinsics::discriminant_value(other);
__self_discr == __arg1_discr &&
match (self, other) {
(CastTy::Int(__self_0), CastTy::Int(__arg1_0)) =>
__self_0 == __arg1_0,
(CastTy::Ptr(__self_0), CastTy::Ptr(__arg1_0)) =>
__self_0 == __arg1_0,
_ => true,
}
}
}PartialEq, #[automatically_derived]
impl<'tcx> ::core::cmp::Eq for CastTy<'tcx> {
#[inline]
#[doc(hidden)]
#[coverage(off)]
fn assert_fields_are_eq(&self) {
let _: ::core::cmp::AssertParamIsEq<IntTy>;
let _: ::core::cmp::AssertParamIsEq<ty::TypeAndMut<'tcx>>;
}
}Eq)]
28pub enum CastTy<'tcx> {
29 Int(IntTy),
32 Float,
34 FnPtr,
36 Ptr(ty::TypeAndMut<'tcx>),
38}
39
40#[derive(#[automatically_derived]
impl ::core::marker::Copy for CastKind { }Copy, #[automatically_derived]
#[doc(hidden)]
unsafe impl ::core::clone::TrivialClone for CastKind { }
#[automatically_derived]
impl ::core::clone::Clone for CastKind {
#[inline]
fn clone(&self) -> Self { *self }
}Clone, #[automatically_derived]
impl ::core::fmt::Debug for CastKind {
#[inline]
fn fmt(&self, f: &mut ::core::fmt::Formatter) -> ::core::fmt::Result {
::core::fmt::Formatter::write_str(f,
match self {
CastKind::PtrPtrCast => "PtrPtrCast",
CastKind::PtrAddrCast => "PtrAddrCast",
CastKind::AddrPtrCast => "AddrPtrCast",
CastKind::NumericCast => "NumericCast",
CastKind::EnumCast => "EnumCast",
CastKind::PrimIntCast => "PrimIntCast",
CastKind::U8CharCast => "U8CharCast",
CastKind::ArrayPtrCast => "ArrayPtrCast",
CastKind::FnPtrPtrCast => "FnPtrPtrCast",
CastKind::FnPtrAddrCast => "FnPtrAddrCast",
})
}
}Debug, const _: () =
{
impl<'tcx, __E: ::rustc_middle::ty::codec::TyEncoder<'tcx>>
::rustc_serialize::Encodable<__E> for CastKind {
fn encode(&self, __encoder: &mut __E) {
let disc =
match *self {
CastKind::PtrPtrCast => { 0usize }
CastKind::PtrAddrCast => { 1usize }
CastKind::AddrPtrCast => { 2usize }
CastKind::NumericCast => { 3usize }
CastKind::EnumCast => { 4usize }
CastKind::PrimIntCast => { 5usize }
CastKind::U8CharCast => { 6usize }
CastKind::ArrayPtrCast => { 7usize }
CastKind::FnPtrPtrCast => { 8usize }
CastKind::FnPtrAddrCast => { 9usize }
};
::rustc_serialize::Encoder::emit_u8(__encoder, disc as u8);
}
}
};TyEncodable, const _: () =
{
impl<'tcx, __D: ::rustc_middle::ty::codec::TyDecoder<'tcx>>
::rustc_serialize::Decodable<__D> for CastKind {
fn decode(__decoder: &mut __D) -> Self {
match ::rustc_serialize::Decoder::read_u8(__decoder) as usize
{
0usize => { CastKind::PtrPtrCast }
1usize => { CastKind::PtrAddrCast }
2usize => { CastKind::AddrPtrCast }
3usize => { CastKind::NumericCast }
4usize => { CastKind::EnumCast }
5usize => { CastKind::PrimIntCast }
6usize => { CastKind::U8CharCast }
7usize => { CastKind::ArrayPtrCast }
8usize => { CastKind::FnPtrPtrCast }
9usize => { CastKind::FnPtrAddrCast }
n => {
::core::panicking::panic_fmt(format_args!("invalid enum variant tag while decoding `CastKind`, expected 0..10, actual {0}",
n));
}
}
}
}
};TyDecodable, const _: () =
{
impl ::rustc_data_structures::stable_hash::StableHash for CastKind {
#[inline]
fn stable_hash<__Hcx: ::rustc_data_structures::stable_hash::StableHashCtxt>(&self,
__hcx: &mut __Hcx,
__hasher:
&mut ::rustc_data_structures::stable_hash::StableHasher) {
::std::mem::discriminant(self).stable_hash(__hcx, __hasher);
match *self {
CastKind::PtrPtrCast => {}
CastKind::PtrAddrCast => {}
CastKind::AddrPtrCast => {}
CastKind::NumericCast => {}
CastKind::EnumCast => {}
CastKind::PrimIntCast => {}
CastKind::U8CharCast => {}
CastKind::ArrayPtrCast => {}
CastKind::FnPtrPtrCast => {}
CastKind::FnPtrAddrCast => {}
}
}
}
};StableHash)]
43pub enum CastKind {
44 PtrPtrCast,
45 PtrAddrCast,
46 AddrPtrCast,
47 NumericCast,
48 EnumCast,
49 PrimIntCast,
50 U8CharCast,
51 ArrayPtrCast,
52 FnPtrPtrCast,
53 FnPtrAddrCast,
54}
55
56impl<'tcx> CastTy<'tcx> {
57 pub fn from_ty(t: Ty<'tcx>) -> Option<CastTy<'tcx>> {
60 match *t.kind() {
61 ty::Bool => Some(CastTy::Int(IntTy::Bool)),
62 ty::Char => Some(CastTy::Int(IntTy::Char)),
63 ty::Int(_) => Some(CastTy::Int(IntTy::I)),
64 ty::Infer(ty::InferTy::IntVar(_)) => Some(CastTy::Int(IntTy::I)),
65 ty::Infer(ty::InferTy::FloatVar(_)) => Some(CastTy::Float),
66 ty::Uint(u) => Some(CastTy::Int(IntTy::U(u))),
67 ty::Float(_) => Some(CastTy::Float),
68 ty::Adt(d, _) if d.is_enum() && d.is_payloadfree() => Some(CastTy::Int(IntTy::CEnum)),
69 ty::RawPtr(ty, mutbl) => Some(CastTy::Ptr(ty::TypeAndMut { ty, mutbl })),
70 ty::FnPtr(..) => Some(CastTy::FnPtr),
71 _ => None,
72 }
73 }
74}
75
76pub fn mir_cast_kind<'tcx>(from_ty: Ty<'tcx>, cast_ty: Ty<'tcx>) -> mir::CastKind {
78 let from = CastTy::from_ty(from_ty);
79 let cast = CastTy::from_ty(cast_ty);
80 let cast_kind = match (from, cast) {
81 (Some(CastTy::Ptr(_) | CastTy::FnPtr), Some(CastTy::Int(_))) => {
82 mir::CastKind::PointerExposeProvenance
83 }
84 (Some(CastTy::Int(_)), Some(CastTy::Ptr(_))) => mir::CastKind::PointerWithExposedProvenance,
85 (Some(CastTy::Int(_)), Some(CastTy::Int(_))) => mir::CastKind::IntToInt,
86 (Some(CastTy::FnPtr), Some(CastTy::Ptr(_))) => mir::CastKind::FnPtrToPtr,
87
88 (Some(CastTy::Float), Some(CastTy::Int(_))) => mir::CastKind::FloatToInt,
89 (Some(CastTy::Int(_)), Some(CastTy::Float)) => mir::CastKind::IntToFloat,
90 (Some(CastTy::Float), Some(CastTy::Float)) => mir::CastKind::FloatToFloat,
91 (Some(CastTy::Ptr(_)), Some(CastTy::Ptr(_))) => mir::CastKind::PtrToPtr,
92
93 (_, _) => {
94 ::rustc_span::macros::bug_impl(None,
format_args!("Attempting to cast non-castable types {0:?} and {1:?}",
from_ty, cast_ty), Location::caller())bug!("Attempting to cast non-castable types {:?} and {:?}", from_ty, cast_ty)
95 }
96 };
97 cast_kind
98}