feat: add support for if/else statements
This commit is contained in:
@@ -154,12 +154,53 @@ struct FunctionTranslator<'a> {
|
||||
|
||||
impl<'a> FunctionTranslator<'a> {
|
||||
/// Translates a statement, recursively compiling its inner components.
|
||||
fn translate_stmt(&mut self, stmt: &TypedStmt) {
|
||||
/// Returns `true` if the statement resulted in a basic block terminator.
|
||||
fn translate_stmt(&mut self, stmt: &TypedStmt) -> bool {
|
||||
match stmt {
|
||||
TypedStmt::Compound { inner } => {
|
||||
for s in inner {
|
||||
self.translate_stmt(s);
|
||||
if self.translate_stmt(s) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
false
|
||||
}
|
||||
TypedStmt::If {
|
||||
condition,
|
||||
then,
|
||||
elze,
|
||||
} => {
|
||||
let cond_val = self.translate_expr(condition);
|
||||
|
||||
let then_block = self.builder.create_block();
|
||||
let else_block = self.builder.create_block();
|
||||
let merge_block = self.builder.create_block();
|
||||
|
||||
self.builder
|
||||
.ins()
|
||||
.brif(cond_val, then_block, &[], else_block, &[]);
|
||||
|
||||
self.builder.switch_to_block(then_block);
|
||||
self.builder.seal_block(then_block);
|
||||
let then_terminated = self.translate_stmt(then);
|
||||
if !then_terminated {
|
||||
self.builder.ins().jump(merge_block, &[]);
|
||||
}
|
||||
|
||||
self.builder.switch_to_block(else_block);
|
||||
self.builder.seal_block(else_block);
|
||||
let else_terminated = elze
|
||||
.as_ref()
|
||||
.map(|stmt| self.translate_stmt(stmt))
|
||||
.unwrap_or(false);
|
||||
if !else_terminated {
|
||||
self.builder.ins().jump(merge_block, &[]);
|
||||
}
|
||||
|
||||
self.builder.switch_to_block(merge_block);
|
||||
self.builder.seal_block(merge_block);
|
||||
|
||||
then_terminated && else_terminated
|
||||
}
|
||||
TypedStmt::Return { value } => {
|
||||
if let Some(expr) = value {
|
||||
@@ -168,6 +209,7 @@ impl<'a> FunctionTranslator<'a> {
|
||||
} else {
|
||||
self.builder.ins().return_(&[]);
|
||||
}
|
||||
true
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user