Add if-statements, fix some bugs
This commit is contained in:
parent
1f14f2b9f9
commit
eaf5e9a30a
@ -112,10 +112,20 @@ impl Statement {
|
||||
|
||||
match self {
|
||||
Statement::Assignment(access_modifier, names, expr_list) => {
|
||||
instructions.push(Instruction::LoadNil(
|
||||
scope.register_counter.0 + 1,
|
||||
scope.register_counter.0 + names.len() as u16,
|
||||
));
|
||||
let new_registers = if *access_modifier == Some(AccessModifier::Local) {
|
||||
let min_reg = scope.register_counter.0 + 1;
|
||||
let max_reg = scope.register_counter.0 + names.len() as u16;
|
||||
instructions.push(Instruction::LoadNil(min_reg, max_reg));
|
||||
scope.register_counter.0 += names.len() as u16;
|
||||
|
||||
let mut new_registers = Vec::new();
|
||||
for i in min_reg..=max_reg {
|
||||
new_registers.push(i);
|
||||
}
|
||||
new_registers
|
||||
} else {
|
||||
Vec::new()
|
||||
};
|
||||
|
||||
let mut expr_regs = Vec::new();
|
||||
for expr in &expr_list.0 {
|
||||
@ -131,57 +141,45 @@ impl Statement {
|
||||
instructions.extend(instr);
|
||||
expr_regs.extend(regs);
|
||||
}
|
||||
|
||||
match access_modifier {
|
||||
Some(AccessModifier::Local) => {
|
||||
for (i, name) in names.iter().enumerate() {
|
||||
scope.locals.insert(
|
||||
name.kind.clone(),
|
||||
expr_regs
|
||||
.get(i)
|
||||
.cloned()
|
||||
.unwrap_or(scope.register_counter.0 + i as u16),
|
||||
);
|
||||
instructions.push(Instruction::Move(
|
||||
*new_registers.get(i).unwrap(),
|
||||
expr_regs.get(i).cloned().unwrap(),
|
||||
));
|
||||
scope
|
||||
.locals
|
||||
.insert(name.kind.clone(), *new_registers.get(i).unwrap());
|
||||
}
|
||||
dbg!(&scope.locals);
|
||||
}
|
||||
Some(AccessModifier::Global) => {
|
||||
for (i, name) in names.iter().enumerate() {
|
||||
let global = state.get_constant(&Constant::String(name.kind.clone()));
|
||||
instructions.push(Instruction::SetGlobal(
|
||||
expr_regs
|
||||
.get(i)
|
||||
.cloned()
|
||||
.unwrap_or(scope.register_counter.0 + i as u16),
|
||||
expr_regs.get(i).cloned().unwrap(),
|
||||
global,
|
||||
));
|
||||
}
|
||||
}
|
||||
None => {
|
||||
for (i, name) in names.iter().enumerate() {
|
||||
if scope.locals.contains_key(&name.kind) {
|
||||
scope.locals.insert(
|
||||
name.kind.clone(),
|
||||
expr_regs
|
||||
.get(i)
|
||||
.cloned()
|
||||
.unwrap_or(scope.register_counter.0 + i as u16),
|
||||
);
|
||||
if let Some(reg) = scope.locals.get(&name.kind) {
|
||||
instructions.push(Instruction::Move(
|
||||
*reg,
|
||||
expr_regs.get(i).cloned().unwrap(),
|
||||
));
|
||||
} else if let Some(upval_reg) = scope.upvalues.get(&name.kind) {
|
||||
instructions.push(Instruction::SetUpVal(
|
||||
*upval_reg,
|
||||
expr_regs
|
||||
.get(i)
|
||||
.cloned()
|
||||
.unwrap_or(scope.register_counter.0 + i as u16),
|
||||
expr_regs.get(i).cloned().unwrap(),
|
||||
));
|
||||
} else {
|
||||
let global =
|
||||
state.get_constant(&Constant::String(name.kind.clone()));
|
||||
instructions.push(Instruction::SetGlobal(
|
||||
expr_regs
|
||||
.get(i)
|
||||
.cloned()
|
||||
.unwrap_or(scope.register_counter.0 + i as u16),
|
||||
expr_regs.get(i).cloned().unwrap(),
|
||||
global,
|
||||
));
|
||||
}
|
||||
@ -218,13 +216,22 @@ impl Statement {
|
||||
*ret_register = new_reg;
|
||||
}
|
||||
|
||||
dbg!(&ret_registers);
|
||||
instructions.push(Instruction::Return(
|
||||
*ret_registers.first().unwrap_or(&scope.register_counter.0),
|
||||
*ret_registers.last().unwrap_or(&0),
|
||||
));
|
||||
}
|
||||
Statement::If(node, block) => todo!(),
|
||||
Statement::If(expr, block) => {
|
||||
let (instr, regs) = expr.kind.compile(state, scope, Some(1));
|
||||
instructions.extend(instr);
|
||||
|
||||
let local = scope.register_counter.next();
|
||||
instructions.push(Instruction::Test(local, *regs.first().unwrap(), 0));
|
||||
|
||||
let block_instructions = block.compile(state, scope);
|
||||
instructions.push(Instruction::Jmp(block_instructions.len() as i32));
|
||||
instructions.extend(block_instructions);
|
||||
}
|
||||
Statement::Expression(expr) => {
|
||||
let (instr, _) = expr.kind.compile(state, scope, None);
|
||||
instructions.extend(instr);
|
||||
@ -333,15 +340,17 @@ impl Expression {
|
||||
.insert(param.kind.clone(), inner_scope.register_counter.next());
|
||||
}
|
||||
|
||||
inner_scope.highest_upvalue =
|
||||
scope.highest_upvalue + inner_scope.register_counter.0;
|
||||
inner_scope.highest_upvalue = scope.highest_upvalue + scope.register_counter.0;
|
||||
inner_scope.upvalues = scope.upvalues.clone();
|
||||
|
||||
for (name, reg) in &scope.locals {
|
||||
let new_reg = *reg + inner_scope.highest_upvalue + 1;
|
||||
let new_reg = *reg + inner_scope.highest_upvalue;
|
||||
inner_scope.upvalues.insert(name.clone(), new_reg);
|
||||
}
|
||||
|
||||
dbg!(&inner_scope.highest_upvalue);
|
||||
dbg!(&inner_scope.upvalues);
|
||||
|
||||
let instructions = block.compile(state, &mut inner_scope);
|
||||
state.prototypes.push(instructions);
|
||||
|
||||
|
||||
@ -274,7 +274,7 @@ impl ClosureRunner {
|
||||
}
|
||||
Instruction::Test(a, b, c) => {
|
||||
let is_true = match self.stack.get(b).unwrap_or(&Value::Nil) {
|
||||
Value::Number(val) => (*val as u16) == *c,
|
||||
Value::Number(val) => (LuaNumber::from_bits(*val) as u16) == *c,
|
||||
_ => false,
|
||||
};
|
||||
if is_true {
|
||||
@ -355,6 +355,7 @@ impl ClosureRunner {
|
||||
.max()
|
||||
.unwrap_or(0);
|
||||
|
||||
dbg!(&self.stack);
|
||||
let mut upvalues = self.closure.upvalues.clone();
|
||||
for (reg, value) in &self.stack {
|
||||
upvalues.insert(
|
||||
@ -363,6 +364,7 @@ impl ClosureRunner {
|
||||
);
|
||||
}
|
||||
|
||||
dbg!(&upvalues);
|
||||
self.stack.insert(
|
||||
*reg,
|
||||
Value::Function(Closure {
|
||||
@ -388,7 +390,6 @@ impl ClosureRunner {
|
||||
for i in reg_start..=reg_end {
|
||||
ret_values.push(self.stack.get(&i).cloned().unwrap_or(Value::Nil));
|
||||
}
|
||||
// dbg!(&self.closure.upvalues);
|
||||
return Some(ret_values);
|
||||
}
|
||||
Instruction::Add(res, lhs, rhs) => {
|
||||
|
||||
Loading…
Reference in New Issue
Block a user