From 068db490f5f73abfbc086178db9d9021f439bb09 Mon Sep 17 00:00:00 2001 From: Roberto Raggi Date: Sat, 9 Aug 2025 11:38:02 +0200 Subject: [PATCH] Implement value and sideeffect codegen for the logical expressions Signed-off-by: Roberto Raggi --- src/mlir/cxx/mlir/codegen.cc | 6 ++ src/mlir/cxx/mlir/codegen.h | 3 + src/mlir/cxx/mlir/codegen_expressions.cc | 92 ++++++++++++++++++++++++ 3 files changed, 101 insertions(+) diff --git a/src/mlir/cxx/mlir/codegen.cc b/src/mlir/cxx/mlir/codegen.cc index 71f0a88d..b901edb2 100644 --- a/src/mlir/cxx/mlir/codegen.cc +++ b/src/mlir/cxx/mlir/codegen.cc @@ -81,6 +81,12 @@ auto Codegen::findOrCreateLocal(Symbol* symbol) -> std::optional { return allocaOp; } +auto Codegen::newTemp(const Type* type, SourceLocation loc) + -> mlir::cxx::AllocaOp { + auto ptrType = builder_.getType(convertType(type)); + return builder_.create(getLocation(loc), ptrType); +} + auto Codegen::findOrCreateFunction(FunctionSymbol* functionSymbol) -> mlir::cxx::FuncOp { if (auto it = funcOps_.find(functionSymbol); it != funcOps_.end()) { diff --git a/src/mlir/cxx/mlir/codegen.h b/src/mlir/cxx/mlir/codegen.h index fe79a204..8702fee0 100644 --- a/src/mlir/cxx/mlir/codegen.h +++ b/src/mlir/cxx/mlir/codegen.h @@ -262,6 +262,9 @@ class Codegen { [[nodiscard]] auto findOrCreateFunction(FunctionSymbol* functionSymbol) -> mlir::cxx::FuncOp; + [[nodiscard]] auto newTemp(const Type* type, SourceLocation loc) + -> mlir::cxx::AllocaOp; + [[nodiscard]] auto findOrCreateLocal(Symbol* symbol) -> std::optional; diff --git a/src/mlir/cxx/mlir/codegen_expressions.cc b/src/mlir/cxx/mlir/codegen_expressions.cc index 96275d92..98aae627 100644 --- a/src/mlir/cxx/mlir/codegen_expressions.cc +++ b/src/mlir/cxx/mlir/codegen_expressions.cc @@ -1040,6 +1040,98 @@ auto Codegen::ExpressionVisitor::operator()(BinaryExpressionAST* ast) return gen.expression(ast->rightExpression, format); } + if (ast->op == TokenKind::T_BAR_BAR) { + auto t = gen.newTemp(control()->getBoolType(), ast->opLoc); + + auto trueBlock = gen.newBlock(); + auto continueBlock = gen.newBlock(); + auto falseBlock = gen.newBlock(); + auto endBlock = gen.newBlock(); + + gen.condition(ast->leftExpression, trueBlock, continueBlock); + + gen.builder_.setInsertionPointToEnd(continueBlock); + gen.condition(ast->rightExpression, trueBlock, falseBlock); + + // build the true block + gen.builder_.setInsertionPointToEnd(trueBlock); + + auto i1type = gen.convertType(control()->getBoolType()); + + auto trueValue = gen.builder_.create( + gen.getLocation(ast->opLoc), i1type, true); + + gen.builder_.create(gen.getLocation(ast->opLoc), + trueValue, t); + + auto endLoc = gen.getLocation(ast->lastSourceLocation()); + gen.branch(endLoc, endBlock); + + // build the false block + gen.builder_.setInsertionPointToEnd(falseBlock); + auto falseValue = gen.builder_.create( + gen.getLocation(ast->opLoc), i1type, false); + gen.builder_.create(gen.getLocation(ast->opLoc), + falseValue, t); + gen.branch(gen.getLocation(ast->lastSourceLocation()), endBlock); + + // place the end block + gen.builder_.setInsertionPointToEnd(endBlock); + + if (format == ExpressionFormat::kSideEffect) return {}; + + auto resultType = gen.convertType(ast->type); + auto loadOp = gen.builder_.create( + gen.getLocation(ast->opLoc), resultType, t); + return {loadOp}; + } + + if (ast->op == TokenKind::T_AMP_AMP) { + auto t = gen.newTemp(control()->getBoolType(), ast->opLoc); + + auto trueBlock = gen.newBlock(); + auto continueBlock = gen.newBlock(); + auto falseBlock = gen.newBlock(); + auto endBlock = gen.newBlock(); + + gen.condition(ast->leftExpression, continueBlock, falseBlock); + + gen.builder_.setInsertionPointToEnd(continueBlock); + gen.condition(ast->rightExpression, trueBlock, falseBlock); + + // build the true block + gen.builder_.setInsertionPointToEnd(trueBlock); + + auto i1type = gen.convertType(control()->getBoolType()); + + auto trueValue = gen.builder_.create( + gen.getLocation(ast->opLoc), i1type, true); + + gen.builder_.create(gen.getLocation(ast->opLoc), + trueValue, t); + + auto endLoc = gen.getLocation(ast->lastSourceLocation()); + gen.branch(endLoc, endBlock); + + // build the false block + gen.builder_.setInsertionPointToEnd(falseBlock); + auto falseValue = gen.builder_.create( + gen.getLocation(ast->opLoc), i1type, false); + gen.builder_.create(gen.getLocation(ast->opLoc), + falseValue, t); + gen.branch(gen.getLocation(ast->lastSourceLocation()), endBlock); + + // place the end block + gen.builder_.setInsertionPointToEnd(endBlock); + + if (format == ExpressionFormat::kSideEffect) return {}; + + auto resultType = gen.convertType(ast->type); + auto loadOp = gen.builder_.create( + gen.getLocation(ast->opLoc), resultType, t); + return {loadOp}; + } + auto loc = gen.getLocation(ast->opLoc); auto leftExpressionResult = gen.expression(ast->leftExpression); auto rightExpressionResult = gen.expression(ast->rightExpression);