Merge #1015
1015: Change primitive integers to have signedness and bitness r=matklad a=yanchith Fixes #1004 This creates enums: `Signedness`, `IntBitness` and `FloatBitness`, and condenses `UintTy` with `IntTy`, making use of the created enums. `FloatTy` is also changed from an enum into a struct containing `FloatBitness`. `UncertainIntTy` and `UncertainFloatTy` now look much more similar. `Ord` was removed from the types because `{u,i}size` aren't easily orderable with the rest. Fortunately this wasn't depended on anywhere. Co-authored-by: yanchith <yanchi.toth@gmail.com>
This commit is contained in:
commit
6bc09e2ff8
4 changed files with 162 additions and 151 deletions
|
@ -14,7 +14,7 @@ use crate::{
|
|||
name::AsName,
|
||||
type_ref::{Mutability, TypeRef},
|
||||
};
|
||||
use crate::{ path::GenericArgs, ty::primitive::{UintTy, UncertainIntTy, UncertainFloatTy}};
|
||||
use crate::{ path::GenericArgs, ty::primitive::{IntTy, UncertainIntTy, FloatTy, UncertainFloatTy}};
|
||||
|
||||
pub use self::scope::{ExprScopes, ScopesWithSourceMap, ScopeEntryWithSyntax};
|
||||
|
||||
|
@ -723,7 +723,8 @@ impl ExprCollector {
|
|||
|
||||
let lit = match child.flavor() {
|
||||
LiteralFlavor::IntNumber { suffix } => {
|
||||
let known_name = suffix.and_then(|it| UncertainIntTy::from_suffix(&it));
|
||||
let known_name = suffix
|
||||
.and_then(|it| IntTy::from_suffix(&it).map(UncertainIntTy::Known));
|
||||
|
||||
Literal::Int(
|
||||
Default::default(),
|
||||
|
@ -731,7 +732,8 @@ impl ExprCollector {
|
|||
)
|
||||
}
|
||||
LiteralFlavor::FloatNumber { suffix } => {
|
||||
let known_name = suffix.and_then(|it| UncertainFloatTy::from_suffix(&it));
|
||||
let known_name = suffix
|
||||
.and_then(|it| FloatTy::from_suffix(&it).map(UncertainFloatTy::Known));
|
||||
|
||||
Literal::Float(
|
||||
Default::default(),
|
||||
|
@ -741,7 +743,7 @@ impl ExprCollector {
|
|||
LiteralFlavor::ByteString => Literal::ByteString(Default::default()),
|
||||
LiteralFlavor::String => Literal::String(Default::default()),
|
||||
LiteralFlavor::Byte => {
|
||||
Literal::Int(Default::default(), UncertainIntTy::Unsigned(UintTy::U8))
|
||||
Literal::Int(Default::default(), UncertainIntTy::Known(IntTy::u8()))
|
||||
}
|
||||
LiteralFlavor::Bool => Literal::Bool(Default::default()),
|
||||
LiteralFlavor::Char => Literal::Char(Default::default()),
|
||||
|
|
|
@ -990,7 +990,12 @@ impl<'a, D: HirDatabase> InferenceContext<'a, D> {
|
|||
match &inner_ty {
|
||||
Ty::Apply(a_ty) => match a_ty.ctor {
|
||||
TypeCtor::Int(primitive::UncertainIntTy::Unknown)
|
||||
| TypeCtor::Int(primitive::UncertainIntTy::Signed(..))
|
||||
| TypeCtor::Int(primitive::UncertainIntTy::Known(
|
||||
primitive::IntTy {
|
||||
signedness: primitive::Signedness::Signed,
|
||||
..
|
||||
},
|
||||
))
|
||||
| TypeCtor::Float(..) => inner_ty,
|
||||
_ => Ty::Unknown,
|
||||
},
|
||||
|
@ -1064,8 +1069,8 @@ impl<'a, D: HirDatabase> InferenceContext<'a, D> {
|
|||
Ty::apply_one(TypeCtor::Ref(Mutability::Shared), Ty::simple(TypeCtor::Str))
|
||||
}
|
||||
Literal::ByteString(..) => {
|
||||
let byte_type = Ty::simple(TypeCtor::Int(primitive::UncertainIntTy::Unsigned(
|
||||
primitive::UintTy::U8,
|
||||
let byte_type = Ty::simple(TypeCtor::Int(primitive::UncertainIntTy::Known(
|
||||
primitive::IntTy::u8(),
|
||||
)));
|
||||
let slice_type = Ty::apply_one(TypeCtor::Slice, byte_type);
|
||||
Ty::apply_one(TypeCtor::Ref(Mutability::Shared), slice_type)
|
||||
|
@ -1208,10 +1213,10 @@ impl InferTy {
|
|||
match self {
|
||||
InferTy::TypeVar(..) => Ty::Unknown,
|
||||
InferTy::IntVar(..) => {
|
||||
Ty::simple(TypeCtor::Int(primitive::UncertainIntTy::Signed(primitive::IntTy::I32)))
|
||||
Ty::simple(TypeCtor::Int(primitive::UncertainIntTy::Known(primitive::IntTy::i32())))
|
||||
}
|
||||
InferTy::FloatVar(..) => Ty::simple(TypeCtor::Float(
|
||||
primitive::UncertainFloatTy::Known(primitive::FloatTy::F64),
|
||||
primitive::UncertainFloatTy::Known(primitive::FloatTy::f64()),
|
||||
)),
|
||||
}
|
||||
}
|
||||
|
|
|
@ -61,10 +61,10 @@ impl Ty {
|
|||
pub(crate) fn from_hir_path(db: &impl HirDatabase, resolver: &Resolver, path: &Path) -> Self {
|
||||
if let Some(name) = path.as_ident() {
|
||||
// TODO handle primitive type names in resolver as well?
|
||||
if let Some(int_ty) = primitive::UncertainIntTy::from_type_name(name) {
|
||||
return Ty::simple(TypeCtor::Int(int_ty));
|
||||
} else if let Some(float_ty) = primitive::UncertainFloatTy::from_type_name(name) {
|
||||
return Ty::simple(TypeCtor::Float(float_ty));
|
||||
if let Some(int_ty) = primitive::IntTy::from_type_name(name) {
|
||||
return Ty::simple(TypeCtor::Int(primitive::UncertainIntTy::Known(int_ty)));
|
||||
} else if let Some(float_ty) = primitive::FloatTy::from_type_name(name) {
|
||||
return Ty::simple(TypeCtor::Float(primitive::UncertainFloatTy::Known(float_ty)));
|
||||
} else if let Some(known) = name.as_known_name() {
|
||||
match known {
|
||||
KnownName::Bool => return Ty::simple(TypeCtor::Bool),
|
||||
|
|
|
@ -2,61 +2,49 @@ use std::fmt;
|
|||
|
||||
use crate::{Name, KnownName};
|
||||
|
||||
#[derive(Debug, Clone, Eq, PartialEq, Hash, Copy)]
|
||||
pub enum UncertainIntTy {
|
||||
Unknown,
|
||||
Unsigned(UintTy),
|
||||
Signed(IntTy),
|
||||
#[derive(Debug, Copy, Clone, Eq, PartialEq, Hash)]
|
||||
pub enum Signedness {
|
||||
Signed,
|
||||
Unsigned,
|
||||
}
|
||||
|
||||
impl UncertainIntTy {
|
||||
pub(crate) fn from_type_name(name: &Name) -> Option<UncertainIntTy> {
|
||||
if let Some(ty) = IntTy::from_type_name(name) {
|
||||
Some(UncertainIntTy::Signed(ty))
|
||||
} else if let Some(ty) = UintTy::from_type_name(name) {
|
||||
Some(UncertainIntTy::Unsigned(ty))
|
||||
} else {
|
||||
None
|
||||
}
|
||||
}
|
||||
#[derive(Debug, Copy, Clone, Eq, PartialEq, Hash)]
|
||||
pub enum IntBitness {
|
||||
Xsize,
|
||||
X8,
|
||||
X16,
|
||||
X32,
|
||||
X64,
|
||||
X128,
|
||||
}
|
||||
|
||||
pub(crate) fn from_suffix(suffix: &str) -> Option<UncertainIntTy> {
|
||||
if let Some(ty) = IntTy::from_suffix(suffix) {
|
||||
Some(UncertainIntTy::Signed(ty))
|
||||
} else if let Some(ty) = UintTy::from_suffix(suffix) {
|
||||
Some(UncertainIntTy::Unsigned(ty))
|
||||
} else {
|
||||
None
|
||||
}
|
||||
}
|
||||
#[derive(Debug, Copy, Clone, Eq, PartialEq, Hash)]
|
||||
pub enum FloatBitness {
|
||||
X32,
|
||||
X64,
|
||||
}
|
||||
|
||||
#[derive(Debug, Copy, Clone, Eq, PartialEq, Hash)]
|
||||
pub enum UncertainIntTy {
|
||||
Unknown,
|
||||
Known(IntTy),
|
||||
}
|
||||
|
||||
impl fmt::Display for UncertainIntTy {
|
||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||
match *self {
|
||||
UncertainIntTy::Unknown => write!(f, "{{integer}}"),
|
||||
UncertainIntTy::Signed(ty) => write!(f, "{}", ty),
|
||||
UncertainIntTy::Unsigned(ty) => write!(f, "{}", ty),
|
||||
UncertainIntTy::Known(ty) => write!(f, "{}", ty),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug, Clone, Eq, PartialEq, Hash, Copy)]
|
||||
#[derive(Debug, Copy, Clone, Eq, PartialEq, Hash)]
|
||||
pub enum UncertainFloatTy {
|
||||
Unknown,
|
||||
Known(FloatTy),
|
||||
}
|
||||
|
||||
impl UncertainFloatTy {
|
||||
pub(crate) fn from_type_name(name: &Name) -> Option<UncertainFloatTy> {
|
||||
FloatTy::from_type_name(name).map(UncertainFloatTy::Known)
|
||||
}
|
||||
|
||||
pub(crate) fn from_suffix(suffix: &str) -> Option<UncertainFloatTy> {
|
||||
FloatTy::from_suffix(suffix).map(UncertainFloatTy::Known)
|
||||
}
|
||||
}
|
||||
|
||||
impl fmt::Display for UncertainFloatTy {
|
||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||
match *self {
|
||||
|
@ -66,14 +54,10 @@ impl fmt::Display for UncertainFloatTy {
|
|||
}
|
||||
}
|
||||
|
||||
#[derive(Clone, PartialEq, Eq, PartialOrd, Ord, Hash, Copy)]
|
||||
pub enum IntTy {
|
||||
Isize,
|
||||
I8,
|
||||
I16,
|
||||
I32,
|
||||
I64,
|
||||
I128,
|
||||
#[derive(Copy, Clone, Eq, PartialEq, Hash)]
|
||||
pub struct IntTy {
|
||||
pub signedness: Signedness,
|
||||
pub bitness: IntBitness,
|
||||
}
|
||||
|
||||
impl fmt::Debug for IntTy {
|
||||
|
@ -84,104 +68,116 @@ impl fmt::Debug for IntTy {
|
|||
|
||||
impl fmt::Display for IntTy {
|
||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||
let s = match *self {
|
||||
IntTy::Isize => "isize",
|
||||
IntTy::I8 => "i8",
|
||||
IntTy::I16 => "i16",
|
||||
IntTy::I32 => "i32",
|
||||
IntTy::I64 => "i64",
|
||||
IntTy::I128 => "i128",
|
||||
};
|
||||
write!(f, "{}", s)
|
||||
write!(f, "{}", self.ty_to_string())
|
||||
}
|
||||
}
|
||||
|
||||
impl IntTy {
|
||||
fn from_type_name(name: &Name) -> Option<IntTy> {
|
||||
pub fn isize() -> IntTy {
|
||||
IntTy { signedness: Signedness::Signed, bitness: IntBitness::Xsize }
|
||||
}
|
||||
|
||||
pub fn i8() -> IntTy {
|
||||
IntTy { signedness: Signedness::Signed, bitness: IntBitness::X8 }
|
||||
}
|
||||
|
||||
pub fn i16() -> IntTy {
|
||||
IntTy { signedness: Signedness::Signed, bitness: IntBitness::X16 }
|
||||
}
|
||||
|
||||
pub fn i32() -> IntTy {
|
||||
IntTy { signedness: Signedness::Signed, bitness: IntBitness::X32 }
|
||||
}
|
||||
|
||||
pub fn i64() -> IntTy {
|
||||
IntTy { signedness: Signedness::Signed, bitness: IntBitness::X64 }
|
||||
}
|
||||
|
||||
pub fn i128() -> IntTy {
|
||||
IntTy { signedness: Signedness::Signed, bitness: IntBitness::X128 }
|
||||
}
|
||||
|
||||
pub fn usize() -> IntTy {
|
||||
IntTy { signedness: Signedness::Unsigned, bitness: IntBitness::Xsize }
|
||||
}
|
||||
|
||||
pub fn u8() -> IntTy {
|
||||
IntTy { signedness: Signedness::Unsigned, bitness: IntBitness::X8 }
|
||||
}
|
||||
|
||||
pub fn u16() -> IntTy {
|
||||
IntTy { signedness: Signedness::Unsigned, bitness: IntBitness::X16 }
|
||||
}
|
||||
|
||||
pub fn u32() -> IntTy {
|
||||
IntTy { signedness: Signedness::Unsigned, bitness: IntBitness::X32 }
|
||||
}
|
||||
|
||||
pub fn u64() -> IntTy {
|
||||
IntTy { signedness: Signedness::Unsigned, bitness: IntBitness::X64 }
|
||||
}
|
||||
|
||||
pub fn u128() -> IntTy {
|
||||
IntTy { signedness: Signedness::Unsigned, bitness: IntBitness::X128 }
|
||||
}
|
||||
|
||||
pub(crate) fn ty_to_string(&self) -> &'static str {
|
||||
match (self.signedness, self.bitness) {
|
||||
(Signedness::Signed, IntBitness::Xsize) => "isize",
|
||||
(Signedness::Signed, IntBitness::X8) => "i8",
|
||||
(Signedness::Signed, IntBitness::X16) => "i16",
|
||||
(Signedness::Signed, IntBitness::X32) => "i32",
|
||||
(Signedness::Signed, IntBitness::X64) => "i64",
|
||||
(Signedness::Signed, IntBitness::X128) => "i128",
|
||||
(Signedness::Unsigned, IntBitness::Xsize) => "usize",
|
||||
(Signedness::Unsigned, IntBitness::X8) => "u8",
|
||||
(Signedness::Unsigned, IntBitness::X16) => "u16",
|
||||
(Signedness::Unsigned, IntBitness::X32) => "u32",
|
||||
(Signedness::Unsigned, IntBitness::X64) => "u64",
|
||||
(Signedness::Unsigned, IntBitness::X128) => "u128",
|
||||
}
|
||||
}
|
||||
|
||||
pub(crate) fn from_type_name(name: &Name) -> Option<IntTy> {
|
||||
match name.as_known_name()? {
|
||||
KnownName::Isize => Some(IntTy::Isize),
|
||||
KnownName::I8 => Some(IntTy::I8),
|
||||
KnownName::I16 => Some(IntTy::I16),
|
||||
KnownName::I32 => Some(IntTy::I32),
|
||||
KnownName::I64 => Some(IntTy::I64),
|
||||
KnownName::I128 => Some(IntTy::I128),
|
||||
KnownName::Isize => Some(IntTy::isize()),
|
||||
KnownName::I8 => Some(IntTy::i8()),
|
||||
KnownName::I16 => Some(IntTy::i16()),
|
||||
KnownName::I32 => Some(IntTy::i32()),
|
||||
KnownName::I64 => Some(IntTy::i64()),
|
||||
KnownName::I128 => Some(IntTy::i128()),
|
||||
KnownName::Usize => Some(IntTy::usize()),
|
||||
KnownName::U8 => Some(IntTy::u8()),
|
||||
KnownName::U16 => Some(IntTy::u16()),
|
||||
KnownName::U32 => Some(IntTy::u32()),
|
||||
KnownName::U64 => Some(IntTy::u64()),
|
||||
KnownName::U128 => Some(IntTy::u128()),
|
||||
_ => None,
|
||||
}
|
||||
}
|
||||
|
||||
fn from_suffix(suffix: &str) -> Option<IntTy> {
|
||||
pub(crate) fn from_suffix(suffix: &str) -> Option<IntTy> {
|
||||
match suffix {
|
||||
"isize" => Some(IntTy::Isize),
|
||||
"i8" => Some(IntTy::I8),
|
||||
"i16" => Some(IntTy::I16),
|
||||
"i32" => Some(IntTy::I32),
|
||||
"i64" => Some(IntTy::I64),
|
||||
"i128" => Some(IntTy::I128),
|
||||
"isize" => Some(IntTy::isize()),
|
||||
"i8" => Some(IntTy::i8()),
|
||||
"i16" => Some(IntTy::i16()),
|
||||
"i32" => Some(IntTy::i32()),
|
||||
"i64" => Some(IntTy::i64()),
|
||||
"i128" => Some(IntTy::i128()),
|
||||
"usize" => Some(IntTy::usize()),
|
||||
"u8" => Some(IntTy::u8()),
|
||||
"u16" => Some(IntTy::u16()),
|
||||
"u32" => Some(IntTy::u32()),
|
||||
"u64" => Some(IntTy::u64()),
|
||||
"u128" => Some(IntTy::u128()),
|
||||
_ => None,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Clone, PartialEq, Eq, PartialOrd, Ord, Hash, Copy)]
|
||||
pub enum UintTy {
|
||||
Usize,
|
||||
U8,
|
||||
U16,
|
||||
U32,
|
||||
U64,
|
||||
U128,
|
||||
}
|
||||
|
||||
impl fmt::Display for UintTy {
|
||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||
let s = match *self {
|
||||
UintTy::Usize => "usize",
|
||||
UintTy::U8 => "u8",
|
||||
UintTy::U16 => "u16",
|
||||
UintTy::U32 => "u32",
|
||||
UintTy::U64 => "u64",
|
||||
UintTy::U128 => "u128",
|
||||
};
|
||||
write!(f, "{}", s)
|
||||
}
|
||||
}
|
||||
|
||||
impl UintTy {
|
||||
fn from_type_name(name: &Name) -> Option<UintTy> {
|
||||
match name.as_known_name()? {
|
||||
KnownName::Usize => Some(UintTy::Usize),
|
||||
KnownName::U8 => Some(UintTy::U8),
|
||||
KnownName::U16 => Some(UintTy::U16),
|
||||
KnownName::U32 => Some(UintTy::U32),
|
||||
KnownName::U64 => Some(UintTy::U64),
|
||||
KnownName::U128 => Some(UintTy::U128),
|
||||
_ => None,
|
||||
}
|
||||
}
|
||||
|
||||
fn from_suffix(suffix: &str) -> Option<UintTy> {
|
||||
match suffix {
|
||||
"usize" => Some(UintTy::Usize),
|
||||
"u8" => Some(UintTy::U8),
|
||||
"u16" => Some(UintTy::U16),
|
||||
"u32" => Some(UintTy::U32),
|
||||
"u64" => Some(UintTy::U64),
|
||||
"u128" => Some(UintTy::U128),
|
||||
_ => None,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl fmt::Debug for UintTy {
|
||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||
fmt::Display::fmt(self, f)
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Clone, PartialEq, Eq, Hash, Copy, PartialOrd, Ord)]
|
||||
pub enum FloatTy {
|
||||
F32,
|
||||
F64,
|
||||
#[derive(Copy, Clone, PartialEq, Eq, Hash)]
|
||||
pub struct FloatTy {
|
||||
pub bitness: FloatBitness,
|
||||
}
|
||||
|
||||
impl fmt::Debug for FloatTy {
|
||||
|
@ -197,25 +193,33 @@ impl fmt::Display for FloatTy {
|
|||
}
|
||||
|
||||
impl FloatTy {
|
||||
pub fn ty_to_string(self) -> &'static str {
|
||||
match self {
|
||||
FloatTy::F32 => "f32",
|
||||
FloatTy::F64 => "f64",
|
||||
pub fn f32() -> FloatTy {
|
||||
FloatTy { bitness: FloatBitness::X32 }
|
||||
}
|
||||
|
||||
pub fn f64() -> FloatTy {
|
||||
FloatTy { bitness: FloatBitness::X64 }
|
||||
}
|
||||
|
||||
pub(crate) fn ty_to_string(self) -> &'static str {
|
||||
match self.bitness {
|
||||
FloatBitness::X32 => "f32",
|
||||
FloatBitness::X64 => "f64",
|
||||
}
|
||||
}
|
||||
|
||||
fn from_type_name(name: &Name) -> Option<FloatTy> {
|
||||
pub(crate) fn from_type_name(name: &Name) -> Option<FloatTy> {
|
||||
match name.as_known_name()? {
|
||||
KnownName::F32 => Some(FloatTy::F32),
|
||||
KnownName::F64 => Some(FloatTy::F64),
|
||||
KnownName::F32 => Some(FloatTy::f32()),
|
||||
KnownName::F64 => Some(FloatTy::f64()),
|
||||
_ => None,
|
||||
}
|
||||
}
|
||||
|
||||
fn from_suffix(suffix: &str) -> Option<FloatTy> {
|
||||
pub(crate) fn from_suffix(suffix: &str) -> Option<FloatTy> {
|
||||
match suffix {
|
||||
"f32" => Some(FloatTy::F32),
|
||||
"f64" => Some(FloatTy::F64),
|
||||
"f32" => Some(FloatTy::f32()),
|
||||
"f64" => Some(FloatTy::f64()),
|
||||
_ => None,
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Add table
Reference in a new issue