From d9e96398a44211f65081f132a6fc2b7eb13a9c05 Mon Sep 17 00:00:00 2001 From: greg Date: Mon, 26 Feb 2018 02:21:21 -0800 Subject: [PATCH] More operator stuff --- src/schala_lang/builtin.rs | 8 +++++++- src/schala_lang/eval.rs | 5 +++++ src/schala_lang/typechecking.rs | 8 ++++++++ 3 files changed, 20 insertions(+), 1 deletion(-) diff --git a/src/schala_lang/builtin.rs b/src/schala_lang/builtin.rs index e462d75..a7a539a 100644 --- a/src/schala_lang/builtin.rs +++ b/src/schala_lang/builtin.rs @@ -44,6 +44,10 @@ impl PrefixOp { pub fn is_prefix(op: &str) -> bool { PREFIX_OPS.get(op).is_some() } + pub fn get_type(&self) -> TypeResult { + let s = self.sigil.as_str(); + PREFIX_OPS.get(s).map(|x| x.0.clone()).ok_or(format!("Prefix op {} not found", s)) + } } lazy_static! { static ref PREFIX_OPS: HashMap<&'static str, (Type, ())> = @@ -51,7 +55,6 @@ lazy_static! { "+" => (Func(bx!(Const(Int)), bx!(Const(Int))), ()), "-" => (Func(bx!(Const(Int)), bx!(Const(Int))), ()), "!" => (Func(bx!(Const(Bool)), bx!(Const(Bool))), ()), - "~" => (Func(bx!(Const(Int)), bx!(Const(Int))), ()), }; } @@ -67,5 +70,8 @@ lazy_static! { "//" => (Func(bx!(Const(Int)), bx!(Func(bx!(Const(Int)), bx!(Const(Int))))), (), 20), "%" => (Func(bx!(Const(Int)), bx!(Func(bx!(Const(Int)), bx!(Const(Int))))), (), 20), "++" => (Func(bx!(Const(StringT)), bx!(Func(bx!(Const(StringT)), bx!(Const(StringT))))), (), 30), + "^" => (Func(bx!(Const(Int)), bx!(Func(bx!(Const(Int)), bx!(Const(Int))))), (), 20), + "&" => (Func(bx!(Const(Int)), bx!(Func(bx!(Const(Int)), bx!(Const(Int))))), (), 20), + "|" => (Func(bx!(Const(Int)), bx!(Func(bx!(Const(Int)), bx!(Const(Int))))), (), 20), }; } diff --git a/src/schala_lang/eval.rs b/src/schala_lang/eval.rs index 4efe4ea..1f12e2f 100644 --- a/src/schala_lang/eval.rs +++ b/src/schala_lang/eval.rs @@ -190,6 +190,9 @@ impl<'a> State<'a> { UnsignedInt(l / r) }, ("%", UnsignedInt(l), UnsignedInt(r)) => UnsignedInt(l % r), + ("^", UnsignedInt(l), UnsignedInt(r)) => UnsignedInt(l ^ r), + ("&", UnsignedInt(l), UnsignedInt(r)) => UnsignedInt(l & r), + ("|", UnsignedInt(l), UnsignedInt(r)) => UnsignedInt(l | r), _ => return Err(format!("Runtime error: not yet implemented")), }) } @@ -204,6 +207,8 @@ impl<'a> State<'a> { ("!", Bool(false)) => Bool(true), ("-", UnsignedInt(n)) => SignedInt(-1*(n as i64)), ("-", SignedInt(n)) => SignedInt(-1*(n as i64)), + ("+", SignedInt(n)) => SignedInt(n), + ("+", UnsignedInt(n)) => UnsignedInt(n), _ => return Err(format!("Runtime error: not yet implemented")), }) } diff --git a/src/schala_lang/typechecking.rs b/src/schala_lang/typechecking.rs index 50e641e..60b227a 100644 --- a/src/schala_lang/typechecking.rs +++ b/src/schala_lang/typechecking.rs @@ -110,6 +110,14 @@ impl TypeContext { other => return Err(format!("{:?} is not a binary function type", other)) } }, + &PrefixExp(ref op, ref expr) => match op.get_type()? { + Func(box t1, box t2) => { + let expr_ty = self.infer(expr)?; + self.unify(t1, expr_ty)?; + Ok(t2) + }, + other => return Err(format!("{:?} is not a prefix op function type", other)) + }, /* PrefixExp(Operation, Box), TupleLiteral(Vec),