diff --git a/Cargo.lock b/Cargo.lock index 13cd4ba..d716884 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -119,6 +119,13 @@ dependencies = [ "dvm-lib", ] +[[package]] +name = "dm-core-impl" +version = "0.1.0" +dependencies = [ + "dvm-lib", +] + [[package]] name = "dm-std-lib" version = "0.1.0" diff --git a/Cargo.toml b/Cargo.toml index 6cc2db1..9a161bc 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -1,3 +1,3 @@ [workspace] resolver = "3" -members = ["dm", "dm-std-lib", "dmc-lib", "dvm-lib", "e2e-tests"] +members = ["dm", "dm-core-impl", "dm-std-lib", "dmc-lib", "dvm-lib", "e2e-tests"] diff --git a/dm-core-impl/Cargo.toml b/dm-core-impl/Cargo.toml new file mode 100644 index 0000000..8e0f97d --- /dev/null +++ b/dm-core-impl/Cargo.toml @@ -0,0 +1,7 @@ +[package] +name = "dm-core-impl" +version = "0.1.0" +edition = "2024" + +[dependencies] +dvm-lib = { path = "../dvm-lib" } \ No newline at end of file diff --git a/dm-core-impl/src/error.rs b/dm-core-impl/src/error.rs new file mode 100644 index 0000000..8d96804 --- /dev/null +++ b/dm-core-impl/src/error.rs @@ -0,0 +1,31 @@ +use std::error::Error; +use std::fmt::{Display, Formatter}; + +#[derive(Debug)] +pub struct IllegalArgumentError { + message: String, +} + +// Eventually we'll want support for source position, so we can highlight which argument(s) +// are wrong +impl IllegalArgumentError { + pub fn wrong_type(expected: &str, found: &str) -> Self { + Self { + message: format!("Expected {} but found {}", expected, found), + } + } + + pub fn wrong_number(expected: usize, found: usize) -> Self { + Self { + message: format!("Expected {} argument(s) but found {}", expected, found), + } + } +} + +impl Display for IllegalArgumentError { + fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result { + write!(f, "IllegalArgumentError: {}", self.message) + } +} + +impl Error for IllegalArgumentError {} diff --git a/dm-core-impl/src/lib.rs b/dm-core-impl/src/lib.rs new file mode 100644 index 0000000..4d7815f --- /dev/null +++ b/dm-core-impl/src/lib.rs @@ -0,0 +1,7 @@ +mod error; +pub mod print; +pub mod string; +mod util; + +pub use print::*; +pub use string::*; diff --git a/dm-core-impl/src/print.rs b/dm-core-impl/src/print.rs new file mode 100644 index 0000000..885c499 --- /dev/null +++ b/dm-core-impl/src/print.rs @@ -0,0 +1,56 @@ +use crate::error::IllegalArgumentError; +use dvm_lib::vm::value::Value; +use std::error::Error; +use std::ops::Deref; + +pub fn core_print(args: &[Value]) -> Result> { + match args.get(0) { + None => Err(Box::new(IllegalArgumentError::wrong_number(1, 0))), + Some(msg) => { + match msg { + Value::Object(object) => { + todo!("printing objects") + } + Value::Int(i) => { + print!("{}", i); + } + Value::Double(d) => { + print!("{}", d); + } + Value::String(s) => { + print!("{}", s.deref()); + } + Value::Null => { + print!("Null"); + } + } + Ok(Value::Null) + } + } +} + +pub fn core_println(args: &[Value]) -> Result> { + match args.get(0) { + None => Err(Box::new(IllegalArgumentError::wrong_number(1, 0))), + Some(msg) => { + match msg { + Value::Object(object) => { + todo!("printing objects") + } + Value::Int(i) => { + println!("{}", i); + } + Value::Double(d) => { + println!("{}", d); + } + Value::String(s) => { + println!("{}", s.deref()); + } + Value::Null => { + print!("Null"); + } + } + Ok(Value::Null) + } + } +} diff --git a/dm-core-impl/src/string.rs b/dm-core-impl/src/string.rs new file mode 100644 index 0000000..42dc9f2 --- /dev/null +++ b/dm-core-impl/src/string.rs @@ -0,0 +1,21 @@ +use crate::error::IllegalArgumentError; +use crate::util::value_to_variant_name; +use dvm_lib::vm::value::Value; +use std::error::Error; + +pub fn core_string_len(args: &[Value]) -> Result> { + let this = args.get(0); + match this { + None => Err(Box::new(IllegalArgumentError::wrong_number(1, 0))), + Some(this) => match this { + Value::String(s) => { + let len: i64 = s.len().try_into()?; + todo!("Long Values") + } + _ => Err(Box::new(IllegalArgumentError::wrong_type( + "String", + value_to_variant_name(this), + ))), + }, + } +} diff --git a/dm-core-impl/src/util.rs b/dm-core-impl/src/util.rs new file mode 100644 index 0000000..5eddffe --- /dev/null +++ b/dm-core-impl/src/util.rs @@ -0,0 +1,11 @@ +use dvm_lib::vm::value::Value; + +pub fn value_to_variant_name(value: &Value) -> &'static str { + match value { + Value::Object(_) => "Object", // todo: lookup class + Value::Int(_) => "Int", + Value::Double(_) => "Double", + Value::String(_) => "String", + Value::Null => "Null", + } +} diff --git a/dm-core/src/lib.dm b/dm-core/src/lib.dm new file mode 100644 index 0000000..eff4bc1 --- /dev/null +++ b/dm-core/src/lib.dm @@ -0,0 +1,6 @@ +mod ops +mod print +mod string + +pub use print::* +pub use string::* diff --git a/dm-core/src/ops.dm b/dm-core/src/ops.dm new file mode 100644 index 0000000..85d8927 --- /dev/null +++ b/dm-core/src/ops.dm @@ -0,0 +1,6 @@ +pub trait Add + type Right = Self + type Result = Self + + fn add(right: Self::Right) -> Self::Result +end diff --git a/dm-core/src/print.dm b/dm-core/src/print.dm new file mode 100644 index 0000000..c141ccb --- /dev/null +++ b/dm-core/src/print.dm @@ -0,0 +1,3 @@ +pub extern fn print(msg: Any) -> Void + +pub extern fn println(msg: Any) -> Void diff --git a/dm-core/src/string.dm b/dm-core/src/string.dm new file mode 100644 index 0000000..f11eb90 --- /dev/null +++ b/dm-core/src/string.dm @@ -0,0 +1,5 @@ +pub extern class String + pub extern fn len() -> Long +end + +intrinsic impl Add for String end