Skip to content

Commit

Permalink
refactor: Remove type wrappers
Browse files Browse the repository at this point in the history
  • Loading branch information
sbwtw committed Nov 8, 2024
1 parent ec959f1 commit 36d03df
Show file tree
Hide file tree
Showing 6 changed files with 72 additions and 67 deletions.
8 changes: 4 additions & 4 deletions lib/src/analysis/type_analyze.rs
Original file line number Diff line number Diff line change
Expand Up @@ -169,18 +169,18 @@ fn analyze_op_expr_type(op1: &Option<Type>, op2: &Option<Type>) -> Option<Type>
let tc2 = op2.as_ref()?.type_class();

// Usertype is not handled
if matches!(tc1, TypeClass::UserType(..)) {
if matches!(tc1, TypeClass::UserType) {
return None;
}
if matches!(tc2, TypeClass::UserType(..)) {
if matches!(tc2, TypeClass::UserType) {
return None;
}

// Array is not handled
if matches!(tc1, TypeClass::Array(..)) {
if matches!(tc1, TypeClass::Array) {
return None;
}
if matches!(tc2, TypeClass::Array(..)) {
if matches!(tc2, TypeClass::Array) {
return None;
}

Expand Down
100 changes: 45 additions & 55 deletions lib/src/ast/mod.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
use crate::parser::{LiteralValue, Operator, StString};
use bitflags::bitflags;
use smallvec::SmallVec;
use std::any::Any;
use std::fmt::{self, Debug, Display, Formatter};
use std::hash::{Hash, Hasher};
use std::sync::{Arc, RwLock};
Expand Down Expand Up @@ -127,36 +128,61 @@ impl_into_expression!(LiteralValue, |x| Expression::literal(Box::new(
LiteralExpression::new(x)
)));

#[derive(Clone, Debug)]
pub trait TypeTrait: Send + Sync {
fn class(&self) -> TypeClass;
fn as_any(&self) -> &dyn Any;
}

#[derive(Clone)]
pub struct Type {
inner: Arc<TypeInner>,
inner: Arc<TypeEnum>,
}

pub enum TypeEnum {
Basic(TypeClass),
Complex(Box<dyn TypeTrait>),
}

impl Debug for Type {
fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
f.write_fmt(format_args!("{}", self.type_class()))
}
}

impl Type {
pub fn from_class(class: TypeClass) -> Self {
Self {
inner: Arc::new(TypeInner { class }),
inner: Arc::new(TypeEnum::Basic(class)),
}
}

pub fn from_object(o: impl TypeTrait + 'static) -> Self {
Self {
inner: Arc::new(TypeEnum::Complex(Box::new(o))),
}
}

pub fn type_class(&self) -> &TypeClass {
&self.inner.class
pub fn type_class(&self) -> TypeClass {
match self.inner.as_ref() {
TypeEnum::Basic(basic) => *basic,
TypeEnum::Complex(complex) => complex.class(),
}
}

pub fn cast<T>(self) -> T {
todo!()
pub fn complex(&self) -> bool {
matches!(*self.inner, TypeEnum::Complex(..))
}
}

impl Display for Type {
fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
write!(f, "{}", *self.inner)
write!(f, "{}", self.type_class())
}
}

impl PartialEq for Type {
fn eq(&self, other: &Self) -> bool {
self.inner.as_ref() == other.inner.as_ref()
self.type_class() == other.type_class()
}
}

Expand Down Expand Up @@ -286,7 +312,7 @@ pub enum UserTypeClass {
Union,
}

#[derive(Debug, Clone)]
#[derive(Debug, Copy, Clone, Eq, PartialEq)]
pub enum TypeClass {
/// 'BIT', one bit type
Bit,
Expand Down Expand Up @@ -315,36 +341,11 @@ pub enum TypeClass {
/// 'STRING' string type
String,
/// UserType
UserType(Arc<RwLock<UserType>>),
UserType,
/// ArrayType
Array(Arc<RwLock<ArrayType>>),
Array,
}

impl PartialEq for TypeClass {
fn eq(&self, other: &Self) -> bool {
match (self, other) {
(Self::Int, Self::Int) => true,
(Self::Bit, Self::Bit) => true,
(Self::Bool, Self::Bool) => true,
(Self::SInt, Self::SInt) => true,
(Self::Byte, Self::Byte) => true,
(Self::UInt, Self::UInt) => true,
(Self::UDInt, Self::UDInt) => true,
(Self::ULInt, Self::ULInt) => true,
(Self::Real, Self::Real) => true,
(Self::LReal, Self::LReal) => true,
(Self::String, Self::String) => true,
(Self::UserType(a), Self::UserType(b)) => {
a.read().unwrap().name() == b.read().unwrap().name()
}
(Self::Array(a), Self::Array(b)) => false,
_ => false,
}
}
}

impl Eq for TypeClass {}

impl Hash for TypeClass {
fn hash<H: Hasher>(&self, state: &mut H) {
let tag = match self {
Expand All @@ -353,25 +354,13 @@ impl Hash for TypeClass {
TypeClass::Byte => 3,
TypeClass::UInt => 4,
TypeClass::Int => 5,
_ => unimplemented!("{:?}", self),
TypeClass::UserType => 6,
TypeClass::Array => 7,
// Some type shouldn't hash directly like ArrayType or UserType
_ => unreachable!("TypeClass shouldn't hash: {:?}", self),
};

tag.hash(state);

// TODO: incomplete implements
match self {
TypeClass::UserType(user_type) => {
// user_type.borrow().name().hash(state);
user_type.read().unwrap().name().hash(state);
}
TypeClass::Array(array_type) => {
// let array_type = array_type.borrow();
let array_type = array_type.read().unwrap();
let base_type = array_type.base_type().read().unwrap();
base_type.type_class().hash(state);
}
_ => {}
}
}
}

Expand All @@ -391,8 +380,9 @@ impl Display for TypeClass {
TypeClass::Real => write!(f, "REAL"),
TypeClass::LReal => write!(f, "LREAL"),
TypeClass::String => write!(f, "STRING"),
TypeClass::UserType(u) => write!(f, "{}", u.read().unwrap()),
TypeClass::Array(arr) => write!(f, "{}", arr.read().unwrap()),
TypeClass::UserType | TypeClass::Array => {
unreachable!("UserType or ArrayType can't display without Type object")
}
}
}
}
24 changes: 20 additions & 4 deletions lib/src/ast/types.rs
Original file line number Diff line number Diff line change
Expand Up @@ -59,9 +59,17 @@ impl UserType {

impl From<UserType> for Type {
fn from(value: UserType) -> Self {
let class = TypeClass::UserType(Arc::new(RwLock::new(value)));
Type::from_object(value)
}
}

impl TypeTrait for UserType {
fn class(&self) -> TypeClass {
TypeClass::UserType
}

Type::from_class(class)
fn as_any(&self) -> &dyn Any {
self
}
}

Expand Down Expand Up @@ -219,8 +227,16 @@ impl Clone for ArrayType {

impl From<ArrayType> for Type {
fn from(value: ArrayType) -> Self {
let class = TypeClass::Array(Arc::new(RwLock::new(value)));
Type::from_object(value)
}
}

impl TypeTrait for ArrayType {
fn class(&self) -> TypeClass {
TypeClass::Array
}

Type::from_class(class)
fn as_any(&self) -> &dyn Any {
self
}
}
1 change: 0 additions & 1 deletion lib/src/parser/default_impl/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,6 @@ use crate::parser::token::Token;
use crate::parser::*;

use smallvec::smallvec;
use std::rc::Rc;
use std::sync::Arc;

///
Expand Down
2 changes: 1 addition & 1 deletion lib/src/test/test_type_analyze.rs
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,7 @@ fn test_type_analyze() {
// test left side type
assert!(assign_expr.left().ty().is_some());
assert_eq!(
*assign_expr.left().ty().unwrap().type_class(),
assign_expr.left().ty().unwrap().type_class(),
TypeClass::Real
);

Expand Down
4 changes: 2 additions & 2 deletions lsp/src/lsp.rs
Original file line number Diff line number Diff line change
Expand Up @@ -33,15 +33,15 @@ fn semantic_token_type_id(tok: &TokenKind) -> (u32, u32) {
pub struct StcLsp {
client: Client,
src_mgr: DashMap<Url, Rope>,
units_mgr: UnitsManager,
_units_mgr: UnitsManager,
}

impl StcLsp {
pub fn new(c: Client) -> Self {
Self {
client: c,
src_mgr: DashMap::new(),
units_mgr: UnitsManager::new(),
_units_mgr: UnitsManager::new(),
}
}
}
Expand Down

0 comments on commit 36d03df

Please sign in to comment.