Skip to content

Commit

Permalink
Support and/or/not operators in compile-time checks
Browse files Browse the repository at this point in the history
  • Loading branch information
Akuli committed Feb 19, 2024
1 parent 5bbbe2d commit 46c538c
Show file tree
Hide file tree
Showing 3 changed files with 34 additions and 0 deletions.
8 changes: 8 additions & 0 deletions self_hosted/evaluate.jou
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,14 @@ def evaluate_condition(expr: AstExpression*) -> bool:
return True
if v == 0:
return False

if expr->kind == AstExpressionKind::And:
return evaluate_condition(&expr->operands[0]) and evaluate_condition(&expr->operands[1])
if expr->kind == AstExpressionKind::Or:
return evaluate_condition(&expr->operands[0]) or evaluate_condition(&expr->operands[1])
if expr->kind == AstExpressionKind::Not:
return not evaluate_condition(&expr->operands[0])

fail(expr->location, "cannot evaluate condition at compile time")


Expand Down
7 changes: 7 additions & 0 deletions src/evaluate.c
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,13 @@ static bool evaluate_condition(const AstExpression *expr)
return (bool)v;
}

if (expr->kind == AST_EXPR_AND)
return evaluate_condition(&expr->data.operands[0]) && evaluate_condition(&expr->data.operands[1]);
if (expr->kind == AST_EXPR_OR)
return evaluate_condition(&expr->data.operands[0]) || evaluate_condition(&expr->data.operands[1]);
if (expr->kind == AST_EXPR_NOT)
return !evaluate_condition(&expr->data.operands[0]);

fail(expr->location, "cannot evaluate condition at compile time");
}

Expand Down
19 changes: 19 additions & 0 deletions tests/should_succeed/compile_time_if.jou
Original file line number Diff line number Diff line change
Expand Up @@ -12,11 +12,30 @@ else:
# python uses 777 as default perms, see help(os.mkdir)
mkdir("tmp/tests/foo", 0o777)


# Test and,or,not operators
if WINDOWS or MACOS:
def bar1() -> None:
printf("One")
def bar2() -> None:
printf("Two\n")

if not WINDOWS and not MACOS:
def bar1() -> None:
printf("OneTwo\n")
def bar2() -> None:
pass


def main() -> int:
make_foo()
f = fopen("tmp/tests/foo/bar", "w")
if f != NULL:
puts("ok") # Output: ok
fclose(f)

# Output: OneTwo
bar1()
bar2()

return 0

0 comments on commit 46c538c

Please sign in to comment.