[Mlir-commits] [mlir] 239777c - [mlir][emitc] Add literal constant.

Jacques Pienaar llvmlistbot at llvm.org
Sat Jul 29 12:27:30 PDT 2023


Author: Jacques Pienaar
Date: 2023-07-29T12:27:23-07:00
New Revision: 239777c8616a614531bed68fff2eaa0c97721cb3

URL: https://github.com/llvm/llvm-project/commit/239777c8616a614531bed68fff2eaa0c97721cb3
DIFF: https://github.com/llvm/llvm-project/commit/239777c8616a614531bed68fff2eaa0c97721cb3.diff

LOG: [mlir][emitc] Add literal constant.

A literal constant is not emitted as a variable but rather printed inline. The
form used is same as the Attribute emission form.

Differential Revision: https://reviews.llvm.org/D150356

Added: 
    

Modified: 
    mlir/include/mlir/Dialect/EmitC/IR/EmitC.td
    mlir/lib/Dialect/EmitC/IR/EmitC.cpp
    mlir/lib/Target/Cpp/TranslateToCpp.cpp
    mlir/test/Target/Cpp/for.mlir

Removed: 
    


################################################################################
diff  --git a/mlir/include/mlir/Dialect/EmitC/IR/EmitC.td b/mlir/include/mlir/Dialect/EmitC/IR/EmitC.td
index ddf6c41468be71..a10b64da436140 100644
--- a/mlir/include/mlir/Dialect/EmitC/IR/EmitC.td
+++ b/mlir/include/mlir/Dialect/EmitC/IR/EmitC.td
@@ -234,6 +234,20 @@ def EmitC_IncludeOp
   let hasCustomAssemblyFormat = 1;
 }
 
+def EmitC_LiteralOp : EmitC_Op<"literal", [Pure]> {
+  let summary = "Literal operation";
+  let description = [{
+    The `literal` operation produces an SSA value equal to some constant
+    specified by an attribute.
+  }];
+
+  let arguments = (ins StrAttr:$value);
+  let results = (outs AnyType:$result);
+
+  let hasVerifier = 1;
+  let assemblyFormat = "$value attr-dict `:` type($result)";
+}
+
 def EmitC_MulOp : EmitC_BinaryArithOp<"mul", []> {
   let summary = "Multiplication operation";
   let description = [{

diff  --git a/mlir/lib/Dialect/EmitC/IR/EmitC.cpp b/mlir/lib/Dialect/EmitC/IR/EmitC.cpp
index a99a7d2b72f54e..ceb1e94ce8177d 100644
--- a/mlir/lib/Dialect/EmitC/IR/EmitC.cpp
+++ b/mlir/lib/Dialect/EmitC/IR/EmitC.cpp
@@ -199,6 +199,16 @@ ParseResult IncludeOp::parse(OpAsmParser &parser, OperationState &result) {
   return success();
 }
 
+//===----------------------------------------------------------------------===//
+// LiteralOp
+//===----------------------------------------------------------------------===//
+
+/// The literal op requires a non-empty value.
+LogicalResult emitc::LiteralOp::verify() {
+  if (getValue().empty())
+    return emitOpError() << "value must not be empty";
+  return success();
+}
 //===----------------------------------------------------------------------===//
 // SubOp
 //===----------------------------------------------------------------------===//
@@ -220,7 +230,6 @@ LogicalResult SubOp::verify() {
       !resultType.isa<IntegerType, emitc::OpaqueType>())
     return emitOpError("requires that the result is an integer or of opaque "
                        "type if lhs and rhs are pointers");
-
   return success();
 }
 

diff  --git a/mlir/lib/Target/Cpp/TranslateToCpp.cpp b/mlir/lib/Target/Cpp/TranslateToCpp.cpp
index 2ac6915a1c182e..396895d3b559da 100644
--- a/mlir/lib/Target/Cpp/TranslateToCpp.cpp
+++ b/mlir/lib/Target/Cpp/TranslateToCpp.cpp
@@ -714,7 +714,7 @@ static LogicalResult printOperation(CppEmitter &emitter,
       // When generating code for an scf.for op, printing a trailing semicolon
       // is handled within the printOperation function.
       bool trailingSemicolon =
-          !isa<scf::IfOp, scf::ForOp, cf::CondBranchOp>(op);
+          !isa<cf::CondBranchOp, emitc::LiteralOp, scf::IfOp, scf::ForOp>(op);
 
       if (failed(emitter.emitOperation(
               op, /*trailingSemicolon=*/trailingSemicolon)))
@@ -733,6 +733,8 @@ CppEmitter::CppEmitter(raw_ostream &os, bool declareVariablesAtTop)
 
 /// Return the existing or a new name for a Value.
 StringRef CppEmitter::getOrCreateName(Value val) {
+  if (auto literal = dyn_cast_if_present<emitc::LiteralOp>(val.getDefiningOp()))
+    return literal.getValue();
   if (!valueMapper.count(val))
     valueMapper.insert(val, formatv("v{0}", ++valueInScopeCount.top()));
   return *valueMapper.begin(val);
@@ -987,12 +989,17 @@ LogicalResult CppEmitter::emitOperation(Operation &op, bool trailingSemicolon) {
           // Arithmetic ops.
           .Case<arith::ConstantOp>(
               [&](auto op) { return printOperation(*this, op); })
+          .Case<emitc::LiteralOp>([&](auto op) { return success(); })
           .Default([&](Operation *) {
             return op.emitOpError("unable to find printer for op");
           });
 
   if (failed(status))
     return failure();
+
+  if (isa<emitc::LiteralOp>(op))
+    return success();
+
   os << (trailingSemicolon ? ";\n" : "\n");
   return success();
 }

diff  --git a/mlir/test/Target/Cpp/for.mlir b/mlir/test/Target/Cpp/for.mlir
index 08ff3f77c0c92e..e904c99820ad84 100644
--- a/mlir/test/Target/Cpp/for.mlir
+++ b/mlir/test/Target/Cpp/for.mlir
@@ -82,3 +82,23 @@ func.func @test_for_yield() {
 // CPP-DECLTOP-NEXT: [[SE]] = [[SI]];
 // CPP-DECLTOP-NEXT: [[PE]] = [[PI]];
 // CPP-DECLTOP-NEXT: return;
+
+func.func @test_for_yield_2() {
+  %start = emitc.literal "0" : index
+  %stop = emitc.literal "10" : index
+  %step = emitc.literal "1" : index
+
+  %s0 = emitc.literal "0" : i32
+  %p0 = emitc.literal "M_PI" : f32
+
+  %result:2 = scf.for %iter = %start to %stop step %step iter_args(%si = %s0, %pi = %p0) -> (i32, f32) {
+    %sn = emitc.call "add"(%si, %iter) : (i32, index) -> i32
+    %pn = emitc.call "mul"(%pi, %iter) : (f32, index) -> f32
+    scf.yield %sn, %pn : i32, f32
+  }
+
+  return
+}
+// CPP-DEFAULT: void test_for_yield_2() {
+// CPP-DEFAULT: float{{.*}}= M_PI
+// CPP-DEFAULT: for (size_t [[IN:.*]] = 0; [[IN]] < 10; [[IN]] += 1) {


        


More information about the Mlir-commits mailing list