cas_compiler/expr/
if_expr.rs

1use cas_compute::numerical::value::Value;
2use cas_error::Error;
3use cas_parser::parser::ast::if_expr::If;
4use crate::{Compile, Compiler, InstructionKind};
5
6impl Compile for If {
7    fn compile(&self, compiler: &mut Compiler) -> Result<(), Error> {
8        self.condition.compile(compiler)?;
9
10        let else_start = compiler.new_unassociated_label();
11        compiler.add_instr_with_spans(
12            InstructionKind::JumpIfFalse(else_start),
13            // for error if condition doesn't evaluate to boolean
14            vec![self.condition.span(), self.then_expr.span()],
15        );
16
17        self.then_expr.compile(compiler)?;
18
19        let if_end = compiler.new_unassociated_label();
20        compiler.add_instr(InstructionKind::Jump(if_end));
21
22        compiler.set_end_label(else_start);
23        if let Some(else_expr) = &self.else_expr {
24            else_expr.compile(compiler)?;
25        } else {
26            compiler.add_instr(InstructionKind::LoadConst(Value::Unit));
27        }
28
29        compiler.set_end_label(if_end);
30
31        Ok(())
32    }
33}