[Mlir-commits] [mlir] [mlir][emitc] Add op modelling C expressions (PR #71631)

Simon Camphausen llvmlistbot at llvm.org
Thu Nov 9 06:21:44 PST 2023


================
@@ -839,15 +975,70 @@ LogicalResult CppEmitter::emitAttribute(Location loc, Attribute attr) {
   return emitError(loc, "cannot emit attribute: ") << attr;
 }
 
+LogicalResult CppEmitter::emitExpression(ExpressionOp expressionOp) {
+  assert(emittedExpressionPrecedence.empty() &&
+         "Expected precedence stack to be empty");
+  Operation *rootOp = expressionOp.getRootOp();
+
+  emittedExpression = expressionOp;
+  pushExpressionPrecedence(getOperatorPrecedence(rootOp));
+
+  if (failed(emitOperation(*rootOp, /*trailingSemicolon=*/false)))
+    return failure();
+
+  popExpressionPrecedence();
+  assert(emittedExpressionPrecedence.empty() &&
+         "Expected precedence stack to be empty");
+  emittedExpression = nullptr;
+
+  return success();
+}
+
+LogicalResult CppEmitter::emitOperand(Value value) {
+  if (isPartOfCurrentExpression(value)) {
+    Operation *def = value.getDefiningOp();
+    assert(def && "Expected operand to be defined by an operation");
+    int precedence = getOperatorPrecedence(def);
+    bool encloseInParenthesis = precedence < getExpressionPrecedence();
+    if (encloseInParenthesis) {
+      os << "(";
+      pushExpressionPrecedence(lowestPrecedence());
+    } else
+      pushExpressionPrecedence(precedence);
+
+    if (failed(emitOperation(*def, /*trailingSemicolon=*/false)))
+      return failure();
+
+    if (encloseInParenthesis)
+      os << ")";
+
+    popExpressionPrecedence();
+    return success();
+  }
+
+  auto expressionOp = dyn_cast_if_present<ExpressionOp>(value.getDefiningOp());
+  if (expressionOp && shouldBeInlined(expressionOp))
+    return emitExpression(expressionOp);
+
+  auto literalOp = dyn_cast_if_present<LiteralOp>(value.getDefiningOp());
+  if (!literalOp && !hasValueInScope(value))
+    return failure();
+  os << getOrCreateName(value);
+  return success();
+}
+
 LogicalResult CppEmitter::emitOperands(Operation &op) {
-  auto emitOperandName = [&](Value result) -> LogicalResult {
-    auto literalDef = dyn_cast_if_present<LiteralOp>(result.getDefiningOp());
-    if (!literalDef && !hasValueInScope(result))
-      return op.emitOpError() << "operand value not in scope";
-    os << getOrCreateName(result);
+  return interleaveCommaWithError(op.getOperands(), os, [&](Value operand) {
+    // If an expression is being omitted, push lowest precedence as these
----------------
simon-camp wrote:

emitted

https://github.com/llvm/llvm-project/pull/71631


More information about the Mlir-commits mailing list