Compare commits
No commits in common. "3360f1491340d4035898c9a2923fc0fc7b4a09ae" and "1811b91922f8e76b7f563622b14d2a8933c15ab2" have entirely different histories.
3360f14913
...
1811b91922
@ -109,4 +109,3 @@ SETMETATABLE(table, {
|
|||||||
|
|
||||||
print(table + 5)
|
print(table + 5)
|
||||||
print(table("hello", "there"))
|
print(table("hello", "there"))
|
||||||
print("hello ", table)
|
|
||||||
@ -25,14 +25,7 @@ impl value::RustFunction for Max {
|
|||||||
pub struct Print;
|
pub struct Print;
|
||||||
impl value::RustFunction for Print {
|
impl value::RustFunction for Print {
|
||||||
fn execute(&self, parameters: Vec<value::Value>) -> Result<Vec<value::Value>, RuntimeError> {
|
fn execute(&self, parameters: Vec<value::Value>) -> Result<Vec<value::Value>, RuntimeError> {
|
||||||
println!(
|
println!("{:?}", parameters);
|
||||||
"{}",
|
|
||||||
parameters
|
|
||||||
.iter()
|
|
||||||
.map(|v| format!("{}", v))
|
|
||||||
.collect::<Vec<_>>()
|
|
||||||
.join("\t")
|
|
||||||
);
|
|
||||||
Ok(Vec::new())
|
Ok(Vec::new())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
111
src/vm/mod.rs
111
src/vm/mod.rs
@ -657,7 +657,7 @@ impl ClosureRunner {
|
|||||||
vec![value.unwrap().clone(), index_value.clone()],
|
vec![value.unwrap().clone(), index_value.clone()],
|
||||||
) {
|
) {
|
||||||
Ok(value) => {
|
Ok(value) => {
|
||||||
StackValue::Value(value?.first().unwrap().clone())
|
StackValue::Value(value.first().unwrap().clone())
|
||||||
}
|
}
|
||||||
Err(_) => StackValue::Value(Value::Nil),
|
Err(_) => StackValue::Value(Value::Nil),
|
||||||
}
|
}
|
||||||
@ -816,7 +816,7 @@ impl ClosureRunner {
|
|||||||
let mut metamethod_params = vec![value.clone()];
|
let mut metamethod_params = vec![value.clone()];
|
||||||
metamethod_params.extend(params);
|
metamethod_params.extend(params);
|
||||||
let ret_values =
|
let ret_values =
|
||||||
self.call_metamethod(&metatable, "__call", metamethod_params)??;
|
self.call_metamethod(&metatable, "__call", metamethod_params)?;
|
||||||
|
|
||||||
if *ret_len != 0 {
|
if *ret_len != 0 {
|
||||||
for i in 0..=(*ret_len - 2) {
|
for i in 0..=(*ret_len - 2) {
|
||||||
@ -890,7 +890,7 @@ impl ClosureRunner {
|
|||||||
"__concat",
|
"__concat",
|
||||||
lhs,
|
lhs,
|
||||||
rhs,
|
rhs,
|
||||||
)??),
|
)?),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -903,7 +903,7 @@ impl ClosureRunner {
|
|||||||
"__add",
|
"__add",
|
||||||
lhs,
|
lhs,
|
||||||
rhs,
|
rhs,
|
||||||
)??),
|
)?),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
Instruction::Sub(res, lhs, rhs) => {
|
Instruction::Sub(res, lhs, rhs) => {
|
||||||
@ -915,7 +915,7 @@ impl ClosureRunner {
|
|||||||
"__sub",
|
"__sub",
|
||||||
lhs,
|
lhs,
|
||||||
rhs,
|
rhs,
|
||||||
)??),
|
)?),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
Instruction::Mult(res, lhs, rhs) => {
|
Instruction::Mult(res, lhs, rhs) => {
|
||||||
@ -927,7 +927,7 @@ impl ClosureRunner {
|
|||||||
"__mult",
|
"__mult",
|
||||||
lhs,
|
lhs,
|
||||||
rhs,
|
rhs,
|
||||||
)??),
|
)?),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
Instruction::Div(res, lhs, rhs) => {
|
Instruction::Div(res, lhs, rhs) => {
|
||||||
@ -939,7 +939,7 @@ impl ClosureRunner {
|
|||||||
"__div",
|
"__div",
|
||||||
lhs,
|
lhs,
|
||||||
rhs,
|
rhs,
|
||||||
)??),
|
)?),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
Instruction::IDiv(res, lhs, rhs) => {
|
Instruction::IDiv(res, lhs, rhs) => {
|
||||||
@ -951,7 +951,7 @@ impl ClosureRunner {
|
|||||||
"__idiv",
|
"__idiv",
|
||||||
lhs,
|
lhs,
|
||||||
rhs,
|
rhs,
|
||||||
)??),
|
)?),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
Instruction::Mod(res, lhs, rhs) => {
|
Instruction::Mod(res, lhs, rhs) => {
|
||||||
@ -963,7 +963,7 @@ impl ClosureRunner {
|
|||||||
"__mod",
|
"__mod",
|
||||||
lhs,
|
lhs,
|
||||||
rhs,
|
rhs,
|
||||||
)??),
|
)?),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
Instruction::Exp(res, lhs, rhs) => {
|
Instruction::Exp(res, lhs, rhs) => {
|
||||||
@ -975,7 +975,7 @@ impl ClosureRunner {
|
|||||||
"__exp",
|
"__exp",
|
||||||
lhs,
|
lhs,
|
||||||
rhs,
|
rhs,
|
||||||
)??),
|
)?),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -988,7 +988,7 @@ impl ClosureRunner {
|
|||||||
"__band",
|
"__band",
|
||||||
lhs,
|
lhs,
|
||||||
rhs,
|
rhs,
|
||||||
)??),
|
)?),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
Instruction::BitOr(res, lhs, rhs) => {
|
Instruction::BitOr(res, lhs, rhs) => {
|
||||||
@ -1000,7 +1000,7 @@ impl ClosureRunner {
|
|||||||
"__bor",
|
"__bor",
|
||||||
lhs,
|
lhs,
|
||||||
rhs,
|
rhs,
|
||||||
)??),
|
)?),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
Instruction::BitXOr(res, lhs, rhs) => {
|
Instruction::BitXOr(res, lhs, rhs) => {
|
||||||
@ -1012,7 +1012,7 @@ impl ClosureRunner {
|
|||||||
"__bxor",
|
"__bxor",
|
||||||
lhs,
|
lhs,
|
||||||
rhs,
|
rhs,
|
||||||
)??),
|
)?),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
Instruction::BitSRight(res, lhs, rhs) => {
|
Instruction::BitSRight(res, lhs, rhs) => {
|
||||||
@ -1024,7 +1024,7 @@ impl ClosureRunner {
|
|||||||
"__shr",
|
"__shr",
|
||||||
lhs,
|
lhs,
|
||||||
rhs,
|
rhs,
|
||||||
)??),
|
)?),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
Instruction::BitSLeft(res, lhs, rhs) => {
|
Instruction::BitSLeft(res, lhs, rhs) => {
|
||||||
@ -1036,7 +1036,7 @@ impl ClosureRunner {
|
|||||||
"__shl",
|
"__shl",
|
||||||
lhs,
|
lhs,
|
||||||
rhs,
|
rhs,
|
||||||
)??),
|
)?),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1051,7 +1051,7 @@ impl ClosureRunner {
|
|||||||
metatable,
|
metatable,
|
||||||
"__eq",
|
"__eq",
|
||||||
vec![lhs.clone(), rhs.clone()],
|
vec![lhs.clone(), rhs.clone()],
|
||||||
)??
|
)?
|
||||||
.first()
|
.first()
|
||||||
.unwrap()
|
.unwrap()
|
||||||
.is_truthy(),
|
.is_truthy(),
|
||||||
@ -1073,7 +1073,7 @@ impl ClosureRunner {
|
|||||||
"__lt",
|
"__lt",
|
||||||
lhs.clone(),
|
lhs.clone(),
|
||||||
rhs.clone(),
|
rhs.clone(),
|
||||||
)??
|
)?
|
||||||
.is_truthy(),
|
.is_truthy(),
|
||||||
))),
|
))),
|
||||||
);
|
);
|
||||||
@ -1088,7 +1088,7 @@ impl ClosureRunner {
|
|||||||
"__le",
|
"__le",
|
||||||
lhs.clone(),
|
lhs.clone(),
|
||||||
rhs.clone(),
|
rhs.clone(),
|
||||||
)??
|
)?
|
||||||
.is_truthy(),
|
.is_truthy(),
|
||||||
))),
|
))),
|
||||||
);
|
);
|
||||||
@ -1115,7 +1115,7 @@ impl ClosureRunner {
|
|||||||
value.unm(),
|
value.unm(),
|
||||||
"__unm",
|
"__unm",
|
||||||
value.clone(),
|
value.clone(),
|
||||||
)??),
|
)?),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
Instruction::Len(res, reg) => {
|
Instruction::Len(res, reg) => {
|
||||||
@ -1130,7 +1130,7 @@ impl ClosureRunner {
|
|||||||
Ok(result) => {
|
Ok(result) => {
|
||||||
self.set_stack(
|
self.set_stack(
|
||||||
*res,
|
*res,
|
||||||
StackValue::Value(result?.first().unwrap().clone()),
|
StackValue::Value(result.first().unwrap().clone()),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
Err(_) => {
|
Err(_) => {
|
||||||
@ -1216,20 +1216,20 @@ impl ClosureRunner {
|
|||||||
value: Result<Value, RuntimeError>,
|
value: Result<Value, RuntimeError>,
|
||||||
metamethod: &str,
|
metamethod: &str,
|
||||||
param: Value,
|
param: Value,
|
||||||
) -> Result<Result<Value, RuntimeError>, RuntimeError> {
|
) -> Result<Value, RuntimeError> {
|
||||||
match value {
|
match value {
|
||||||
Ok(value) => Ok(Ok(value)),
|
Ok(value) => Ok(value),
|
||||||
Err(_) => match ¶m {
|
Err(_) => match ¶m {
|
||||||
Value::Table { metatable, .. } => {
|
Value::Table { metatable, .. } => {
|
||||||
if metatable
|
if metatable
|
||||||
.borrow()
|
.borrow()
|
||||||
.contains_key(&IndexableValue::String(metamethod.to_owned()))
|
.contains_key(&IndexableValue::String(metamethod.to_owned()))
|
||||||
{
|
{
|
||||||
Ok(extract_ret_value(self.call_metamethod(
|
Ok(self
|
||||||
metatable,
|
.call_metamethod(metatable, metamethod, vec![param.clone()])?
|
||||||
metamethod,
|
.into_iter()
|
||||||
vec![param.clone()],
|
.next()
|
||||||
)?))
|
.unwrap())
|
||||||
} else {
|
} else {
|
||||||
Err(RuntimeError::InvalidUnop(
|
Err(RuntimeError::InvalidUnop(
|
||||||
metamethod.to_owned(),
|
metamethod.to_owned(),
|
||||||
@ -1251,31 +1251,35 @@ impl ClosureRunner {
|
|||||||
metamethod: &str,
|
metamethod: &str,
|
||||||
lhs: Value,
|
lhs: Value,
|
||||||
rhs: Value,
|
rhs: Value,
|
||||||
) -> Result<Result<Value, RuntimeError>, RuntimeError> {
|
) -> Result<Value, RuntimeError> {
|
||||||
match value {
|
match value {
|
||||||
Ok(value) => Ok(Ok(value)),
|
Ok(value) => Ok(value),
|
||||||
Err(_) => {
|
Err(_) => {
|
||||||
if let Value::Table { metatable, .. } = &lhs {
|
if let Value::Table { metatable, .. } = &lhs {
|
||||||
if metatable
|
if metatable
|
||||||
.borrow()
|
.borrow()
|
||||||
.contains_key(&IndexableValue::String(metamethod.to_owned()))
|
.contains_key(&IndexableValue::String(metamethod.to_owned()))
|
||||||
{
|
{
|
||||||
Ok(extract_ret_value(self.call_metamethod(
|
Ok(self
|
||||||
&metatable,
|
.call_metamethod(&metatable, metamethod, vec![lhs.clone(), rhs])?
|
||||||
metamethod,
|
.into_iter()
|
||||||
vec![lhs.clone(), rhs],
|
.next()
|
||||||
)?))
|
.unwrap())
|
||||||
} else {
|
} else {
|
||||||
if let Value::Table { metatable, .. } = &rhs {
|
if let Value::Table { metatable, .. } = &rhs {
|
||||||
if metatable
|
if metatable
|
||||||
.borrow()
|
.borrow()
|
||||||
.contains_key(&IndexableValue::String(metamethod.to_owned()))
|
.contains_key(&IndexableValue::String(metamethod.to_owned()))
|
||||||
{
|
{
|
||||||
Ok(extract_ret_value(self.call_metamethod(
|
Ok(self
|
||||||
&metatable,
|
.call_metamethod(
|
||||||
metamethod,
|
&metatable,
|
||||||
vec![lhs, rhs.clone()],
|
metamethod,
|
||||||
)?))
|
vec![lhs, rhs.clone()],
|
||||||
|
)?
|
||||||
|
.into_iter()
|
||||||
|
.next()
|
||||||
|
.unwrap())
|
||||||
} else {
|
} else {
|
||||||
Err(RuntimeError::InvalidBinop(
|
Err(RuntimeError::InvalidBinop(
|
||||||
metamethod.to_owned(),
|
metamethod.to_owned(),
|
||||||
@ -1296,11 +1300,11 @@ impl ClosureRunner {
|
|||||||
.borrow()
|
.borrow()
|
||||||
.contains_key(&IndexableValue::String(metamethod.to_owned()))
|
.contains_key(&IndexableValue::String(metamethod.to_owned()))
|
||||||
{
|
{
|
||||||
Ok(extract_ret_value(self.call_metamethod(
|
Ok(self
|
||||||
&metatable,
|
.call_metamethod(&metatable, metamethod, vec![lhs, rhs.clone()])?
|
||||||
metamethod,
|
.into_iter()
|
||||||
vec![lhs, rhs.clone()],
|
.next()
|
||||||
)?))
|
.unwrap())
|
||||||
} else {
|
} else {
|
||||||
Err(RuntimeError::InvalidBinop(
|
Err(RuntimeError::InvalidBinop(
|
||||||
metamethod.to_owned(),
|
metamethod.to_owned(),
|
||||||
@ -1324,28 +1328,25 @@ impl ClosureRunner {
|
|||||||
metatable: &Table,
|
metatable: &Table,
|
||||||
metamethod: &str,
|
metamethod: &str,
|
||||||
params: Vec<Value>,
|
params: Vec<Value>,
|
||||||
) -> Result<Result<Vec<Value>, RuntimeError>, RuntimeError> {
|
) -> Result<Vec<Value>, RuntimeError> {
|
||||||
if let Some(value) = metatable
|
if let Some(value) = metatable
|
||||||
.borrow()
|
.borrow()
|
||||||
.get(&IndexableValue::String(metamethod.to_owned()))
|
.get(&IndexableValue::String(metamethod.to_owned()))
|
||||||
{
|
{
|
||||||
match value {
|
match value {
|
||||||
Value::RustFunction(function) => {
|
Value::RustFunction(function) => {
|
||||||
let result = function.borrow_mut().execute(params);
|
let result = function.borrow_mut().execute(params)?;
|
||||||
Ok(result)
|
Ok(result)
|
||||||
}
|
}
|
||||||
Value::Function(closure) => {
|
Value::Function(closure) => {
|
||||||
let mut runnable = closure.run(params);
|
let mut runnable = closure.run(params);
|
||||||
#[allow(unused_assignments)]
|
#[allow(unused_assignments)]
|
||||||
let mut return_value = Ok(None);
|
let mut return_value = None;
|
||||||
while {
|
while {
|
||||||
return_value = runnable.next();
|
return_value = runnable.next()?;
|
||||||
match return_value {
|
return_value.is_none()
|
||||||
Ok(None) => true,
|
|
||||||
_ => false,
|
|
||||||
}
|
|
||||||
} {}
|
} {}
|
||||||
Ok(return_value.map(|v| v.unwrap()))
|
Ok(return_value.unwrap())
|
||||||
}
|
}
|
||||||
_ => Err(RuntimeError::MetafunctionNotCallable(value.clone())),
|
_ => Err(RuntimeError::MetafunctionNotCallable(value.clone())),
|
||||||
}
|
}
|
||||||
@ -1370,7 +1371,3 @@ impl ClosureRunner {
|
|||||||
)
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn extract_ret_value(values: Result<Vec<Value>, RuntimeError>) -> Result<Value, RuntimeError> {
|
|
||||||
values.map(|v| v.into_iter().next().unwrap())
|
|
||||||
}
|
|
||||||
|
|||||||
@ -125,8 +125,7 @@ impl Debug for Constant {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub type Table = Rc<RefCell<TableMap>>;
|
pub type Table = Rc<RefCell<HashMap<IndexableValue, Value>>>;
|
||||||
pub type TableMap = HashMap<IndexableValue, Value>;
|
|
||||||
|
|
||||||
#[derive(Clone)]
|
#[derive(Clone)]
|
||||||
pub enum Value {
|
pub enum Value {
|
||||||
@ -152,7 +151,7 @@ impl Value {
|
|||||||
}
|
}
|
||||||
Value::Function(closure) => Ok(IndexableValue::Function(closure.prototype)),
|
Value::Function(closure) => Ok(IndexableValue::Function(closure.prototype)),
|
||||||
Value::Nil => Err(RuntimeError::InvalidTableIndex(self)),
|
Value::Nil => Err(RuntimeError::InvalidTableIndex(self)),
|
||||||
Value::Table { contents, .. } => Ok(IndexableValue::Table(contents.as_ptr())),
|
Value::Table { .. } => Err(RuntimeError::InvalidTableIndex(self)),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -202,7 +201,7 @@ impl Display for Value {
|
|||||||
}
|
}
|
||||||
Value::Function(closure) => write!(f, "<function({})>", closure.prototype),
|
Value::Function(closure) => write!(f, "<function({})>", closure.prototype),
|
||||||
Value::Nil => write!(f, "nil"),
|
Value::Nil => write!(f, "nil"),
|
||||||
Value::Table { contents, .. } => write!(f, "<table#{}>", contents.as_ptr() as u64),
|
Value::Table { .. } => write!(f, "<table>"),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -622,7 +621,6 @@ pub enum IndexableValue {
|
|||||||
Bool(LuaBool),
|
Bool(LuaBool),
|
||||||
RustFunction(String),
|
RustFunction(String),
|
||||||
Function(u32),
|
Function(u32),
|
||||||
Table(*mut TableMap),
|
|
||||||
}
|
}
|
||||||
|
|
||||||
impl From<&str> for IndexableValue {
|
impl From<&str> for IndexableValue {
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user