aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/compiler.rs2
-rw-r--r--src/error.rs4
-rw-r--r--src/lib.rs3
-rw-r--r--src/main.rs33
-rw-r--r--src/stack.rs3
-rw-r--r--src/vm.rs12
6 files changed, 33 insertions, 24 deletions
diff --git a/src/compiler.rs b/src/compiler.rs
index 866e0a3..559068d 100644
--- a/src/compiler.rs
+++ b/src/compiler.rs
@@ -182,7 +182,7 @@ impl Frame {
}
}
-pub type RustFunction = fn(&[Value]) -> Value;
+pub type RustFunction = fn(&[Value], bool) -> Result<Value, ErrorKind>;
#[derive(Debug, Clone)]
pub struct Blob {
diff --git a/src/error.rs b/src/error.rs
index d8d4664..b489cd1 100644
--- a/src/error.rs
+++ b/src/error.rs
@@ -11,6 +11,7 @@ use crate::vm::{Op, Value};
#[derive(Debug, Clone)]
pub enum ErrorKind {
TypeError(Op, Vec<Type>),
+ ExternTypeMismatch(String, Vec<Type>),
RuntimeTypeError(Op, Vec<Value>),
Assert,
InvalidProgram,
@@ -36,6 +37,9 @@ impl fmt::Display for ErrorKind {
.fold(String::new(), |a, v| { format!("{}{:?}, ", a, v) });
write!(f, "{} Cannot apply {:?} to types {}", "Type Error".bold(), op, types)
}
+ ErrorKind::ExternTypeMismatch(name, types) => {
+ write!(f, "{} Extern function '{}' doesn't accept argument(s) with type(s) {:?}", "Type Error".bold(), name, types)
+ }
ErrorKind::RuntimeTypeError(op, values) => {
let values = values
.iter()
diff --git a/src/lib.rs b/src/lib.rs
index e68adff..17f680c 100644
--- a/src/lib.rs
+++ b/src/lib.rs
@@ -1,11 +1,10 @@
use std::path::Path;
pub mod compiler;
+pub mod error;
pub mod tokenizer;
pub mod vm;
-mod error;
-
use compiler::RustFunction;
use error::Error;
use tokenizer::TokenStream;
diff --git a/src/main.rs b/src/main.rs
index a97cd43..10b88ba 100644
--- a/src/main.rs
+++ b/src/main.rs
@@ -1,7 +1,6 @@
use std::path::{Path, PathBuf};
use tihdy::run_file;
-use tihdy::vm::Value;
struct Args {
file: Option<PathBuf>,
@@ -11,12 +10,14 @@ struct Args {
fn main() {
let args = parse_args();
let file = args.file.unwrap_or_else(|| Path::new("tests/simple.tdy").to_owned());
- if let Err(errs) = run_file(&file, args.print, vec![(String::from("hello"), hello)]) {
- for err in errs.iter() {
- println!("{}", err);
- }
- println!(" {} errors occured.", errs.len());
+ let errs = match run_file(&file, args.print, vec![(String::from("extern_test"), extern_test)]) {
+ Err(it) => it,
+ _ => return,
+ };
+ for err in errs.iter() {
+ println!("{}", err);
}
+ println!(" {} errors occured.", errs.len());
}
fn parse_args() -> Args {
@@ -38,14 +39,12 @@ fn parse_args() -> Args {
args
}
-pub fn hello(parameters: &[Value]) -> Value {
- match parameters {
- [Value::String(s)] => {
- println!("{}", s);
- }
- _ => {
- println!("Bad parameters");
- }
- }
- Value::Nil
-}
+tihdy_derive::extern_function!(
+ extern_test
+ [tihdy::vm::Value::Float(x), tihdy::vm::Value::Float(y)] -> tihdy::vm::Type::Float => {
+ Ok(tihdy::vm::Value::Float(x + y))
+ },
+ [tihdy::vm::Value::Float(x)] -> tihdy::vm::Type::Float => {
+ Ok(tihdy::vm::Value::Float(*x))
+ },
+);
diff --git a/src/stack.rs b/src/stack.rs
new file mode 100644
index 0000000..a75c775
--- /dev/null
+++ b/src/stack.rs
@@ -0,0 +1,3 @@
+struct Stack<T> {
+
+}
diff --git a/src/vm.rs b/src/vm.rs
index da044a5..3559a2d 100644
--- a/src/vm.rs
+++ b/src/vm.rs
@@ -6,8 +6,9 @@ use std::path::{Path, PathBuf};
use std::rc::Rc;
use std::cell::RefCell;
+pub use crate::compiler::Type;
+
use crate::compiler::RustFunction;
-use crate::compiler::Type;
use crate::error::{Error, ErrorKind};
use crate::compiler::{Prog, Blob};
@@ -629,7 +630,7 @@ impl VM {
}
Value::ExternFunction(slot) => {
let extern_func = self.extern_functions[slot];
- let res = extern_func(&self.stack[new_base+1..]);
+ let res = extern_func(&self.stack[new_base+1..], false).unwrap(); //FIXME
self.stack.truncate(new_base);
self.stack.push(res);
}
@@ -869,8 +870,11 @@ impl VM {
self.stack.truncate(new_base + 1);
}
- Value::ExternFunction(_slot) => {
- self.stack.truncate(new_base + 1);
+ Value::ExternFunction(slot) => {
+ let extern_func = self.extern_functions[slot];
+ let res = extern_func(&self.stack[new_base+1..], true).unwrap(); //FIXME
+ self.stack.truncate(new_base);
+ self.stack.push(res);
}
_ => {
error!(self,