Skip to content

Commit

Permalink
Let statements
Browse files Browse the repository at this point in the history
  • Loading branch information
chriseth committed Sep 30, 2024
1 parent a8b1406 commit 1c9fefe
Show file tree
Hide file tree
Showing 2 changed files with 54 additions and 5 deletions.
26 changes: 21 additions & 5 deletions jit-compiler/src/codegen.rs
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,8 @@ use powdr_ast::{
display::quote,
types::{ArrayType, FunctionType, Type, TypeScheme},
ArrayLiteral, BinaryOperation, BinaryOperator, BlockExpression, FunctionCall, IfExpression,
IndexAccess, LambdaExpression, MatchArm, MatchExpression, Number, Pattern,
StatementInsideBlock, UnaryOperation,
IndexAccess, LambdaExpression, LetStatementInsideBlock, MatchArm, MatchExpression, Number,
Pattern, StatementInsideBlock, UnaryOperation,
},
};
use powdr_number::{BigInt, BigUint, FieldElement, LargeInt};
Expand Down Expand Up @@ -309,9 +309,25 @@ impl<'a, T: FieldElement> CodeGenerator<'a, T> {
}

fn format_statement(&mut self, s: &StatementInsideBlock<Expression>) -> Result<String, String> {
Err(format!(
"Compiling statements inside blocks is not yet implemented: {s}"
))
Ok(match s {
StatementInsideBlock::LetStatement(LetStatementInsideBlock { pattern, ty, value }) => {
let Some(value) = value else {
return Err(format!(
"Column creating 'let'-statements not yet supported: {s}"
));
};
let value = self.format_expr(value)?;
let var_name = "scrutinee__";
let ty = ty
.as_ref()
.map(|ty| format!(": {}", map_type(ty)))
.unwrap_or_default();

let (vars, code) = check_pattern(var_name, pattern)?;
format!("let {vars}{ty} = (|{var_name}{ty}| {code})({value}).unwrap().clone();\n",)
}
StatementInsideBlock::Expression(e) => format!("{};\n", self.format_expr(e)?),
})
}

/// Returns a string expression evaluating to the value of the symbol.
Expand Down
33 changes: 33 additions & 0 deletions jit-compiler/tests/execution.rs
Original file line number Diff line number Diff line change
Expand Up @@ -158,3 +158,36 @@ fn match_array() {
assert_eq!(f.call(5), 6);
assert_eq!(f.call(6), 7);
}

#[test]
fn let_simple() {
let f = compile(
r#"let f: int -> int = |x| {
let a = 1;
let b = a + 9;
b - 9 + x
};"#,
"f",
);

assert_eq!(f.call(0), 1);
assert_eq!(f.call(1), 2);
assert_eq!(f.call(2), 3);
assert_eq!(f.call(3), 4);
}

#[test]
fn let_complex() {
let f = compile(
r#"let f: int -> int = |x| {
let (a, b, (c, d)) = (1, 2, ("abc", [4, 5]));
a + b + d[0] + d[1]
};"#,
"f",
);

assert_eq!(f.call(0), 1);
assert_eq!(f.call(1), 2);
assert_eq!(f.call(2), 3);
assert_eq!(f.call(3), 4);
}

0 comments on commit 1c9fefe

Please sign in to comment.