[llvm-branch-commits] [mlir] 28070f1 - xla_lhlo dialect fixes to work with upstream

2021-11-05 Thread Uday Bondhugula via llvm-branch-commits

Author: Uday Bondhugula
Date: 2021-09-22T14:28:52+05:30
New Revision: 28070f1be700f812dd228e51ecbe1efb3b4a73ea

URL: 
https://github.com/llvm/llvm-project/commit/28070f1be700f812dd228e51ecbe1efb3b4a73ea
DIFF: 
https://github.com/llvm/llvm-project/commit/28070f1be700f812dd228e51ecbe1efb3b4a73ea.diff

LOG: xla_lhlo dialect fixes to work with upstream

Added: 


Modified: 
mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.h
mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
mlir/include/mlir/InitAllDialects.h
mlir/lib/Dialect/LHLO/IR/CMakeLists.txt
mlir/lib/Dialect/LHLO/IR/LHLOOps.cc
mlir/test/Dialect/LHLO/lhlo_ops.mlir

Removed: 




diff  --git a/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.h 
b/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.h
index 45309f5110ad..c17ee6d63bd4 100644
--- a/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.h
+++ b/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.h
@@ -20,28 +20,25 @@ limitations under the License.
 
 #include "llvm/ADT/StringRef.h"
 #include "mlir/IR/Attributes.h"  // from @llvm-project
+#include "mlir/IR/BuiltinTypes.h"  // from @llvm-project
 #include "mlir/IR/Dialect.h"  // from @llvm-project
 #include "mlir/IR/Location.h"  // from @llvm-project
 #include "mlir/IR/MLIRContext.h"  // from @llvm-project
 #include "mlir/IR/OpDefinition.h"  // from @llvm-project
 #include "mlir/IR/Operation.h"  // from @llvm-project
-#include "mlir/IR/StandardTypes.h"  // from @llvm-project
 #include "mlir/IR/Types.h"  // from @llvm-project
 #include "mlir/Interfaces/SideEffectInterfaces.h"  // from @llvm-project
 
 namespace mlir {
 class OpBuilder;
+}  // end namespace mlir
 
 #include "mlir/Dialect/LHLO/IR/LHLOStructs.h.inc"
 
-namespace xla_lhlo {
-
 #include "mlir/Dialect/LHLO/IR/LHLOOpsDialect.h.inc"
 
 #define GET_OP_CLASSES
 #include "mlir/Dialect/LHLO/IR/LHLOOps.h.inc"
 
-}  // namespace xla_lhlo
-}  // end namespace mlir
 
 #endif  // MLIR_DIALECT_LHLO_IR_LHLO_OPS_H_

diff  --git a/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td 
b/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
index 3ae266e82c3c..7f83425f138c 100644
--- a/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
+++ b/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
@@ -24,7 +24,7 @@ include "mlir/Dialect/LHLO/IR/HLOOpsBase.td"
 
 def LHLO_Dialect : Dialect {
   let name = "xla_lhlo";
-  let cppNamespace = "xla_lhlo";
+  let cppNamespace = "::mlir::xla_lhlo";
 }
 
 
//===--===//
@@ -382,7 +382,7 @@ def ConvDimensionNumbers : 
StructAttr<"ConvDimensionNumbers", LHLO_Dialect, [
   StructFieldAttr<"output_feature_dimension", I64Attr>,
   StructFieldAttr<"output_spatial_dimensions", I64ElementsAttr>] > {
 
-  let description = "Structure of dimension information for conv op";
+  let summary = "Structure of dimension information for conv op";
 }
 
 def LHLO_ConvOp : LHLO_Op<"convolution", []>, BASE_HLO_ConvOp {
@@ -427,7 +427,7 @@ def DotDimensionNumbers : StructAttr<"DotDimensionNumbers", 
LHLO_Dialect, [
 StructFieldAttr<"lhs_contracting_dimensions", I64ElementsAttr>,
 StructFieldAttr<"rhs_contracting_dimensions", I64ElementsAttr>
   ]> {
-  let description = "Structure of dimension information for dot product";
+  let summary = "Structure of dimension information for dot product";
 }
 
 def LHLO_DotGeneralOp : LHLO_Op<"dot_general", []>, BASE_HLO_DotGeneralOp {
@@ -452,7 +452,7 @@ def GatherDimensionNumbers: 
StructAttr<"GatherDimensionNumbers", LHLO_Dialect,
   StructFieldAttr<"collapsed_slice_dims", I64ElementsAttr>,
   StructFieldAttr<"start_index_map", I64ElementsAttr>,
   StructFieldAttr<"index_vector_dim", I64Attr>]> {
-  let description = "Structure of dimension information for gather";
+  let summary = "Structure of dimension information for gather";
 }
 
 def LHLO_GatherOp: LHLO_Op<"gather", []>, BASE_HLO_GatherOp {
@@ -489,7 +489,7 @@ def ScatterDimensionNumbers
   StructFieldAttr<"scatter_dims_to_operand_dims", I64ElementsAttr>,
   StructFieldAttr<"index_vector_dim", I64Attr>
 ]> {
-  let description = "Structure of dimension information for scatter";
+  let summary = "Structure of dimension information for scatter";
 }
 
 def LHLO_ScatterOp: LHLO_Op<"scatter", [RecursiveSideEffects]>,
@@ -597,9 +597,7 @@ def LHLO_TupleOp : LHLO_ReadOnlyOp<"tuple", 
[NoSideEffect]>, BASE_HLO_TupleOp {
   let arguments = (ins Arg, "", 
[MemRead]>:$input);
   let results = (outs NestedTupleOf<[LHLO_BufferOrIntOrFP]>);
 
-  let builders = [OpBuilder<
-  "OpBuilder &builder, OperationState &results, "
-  "ValueRange values">];
+  let builders = [OpBuilder<(ins "ValueRange":$values)>];
 }
 
 def LHLO_WhileOp
@@ -642,8 +640,7 @@ def FusionOp : LHLO_Op<"fusion", 
[SingleBlockImplicitTerminator<"TerminatorOp">]
 
   let skipDefaultBuilders = 1;
   let builders = [
- OpBuilder<"OpBuilder &builder, Operatio

[llvm-branch-commits] [mlir] 1e17c40 - [MLIR] Introduce trait EquiMemRefAndEltTypeOperands

2021-11-05 Thread Uday Bondhugula via llvm-branch-commits

Author: Uday Bondhugula
Date: 2021-09-22T14:23:45+05:30
New Revision: 1e17c40c4ce8daf46bf5df28a04d1e9ea5690cb2

URL: 
https://github.com/llvm/llvm-project/commit/1e17c40c4ce8daf46bf5df28a04d1e9ea5690cb2
DIFF: 
https://github.com/llvm/llvm-project/commit/1e17c40c4ce8daf46bf5df28a04d1e9ea5690cb2.diff

LOG: [MLIR] Introduce trait EquiMemRefAndEltTypeOperands

This trait is used by LHLO ops where the operands and result may either
have operands of the same type or equivalent types where a 0-d memref of
an elemental type is considered equivalent to that elemental type.

TODO: add a test dialect test case here.

Added: 


Modified: 
mlir/include/mlir/IR/OpBase.td
mlir/include/mlir/IR/OpDefinition.h
mlir/lib/IR/Operation.cpp

Removed: 




diff  --git a/mlir/include/mlir/IR/OpBase.td b/mlir/include/mlir/IR/OpBase.td
index ac99ac4d0897d..d82b734a329a8 100644
--- a/mlir/include/mlir/IR/OpBase.td
+++ b/mlir/include/mlir/IR/OpBase.td
@@ -1889,6 +1889,9 @@ def IsolatedFromAbove : 
NativeOpTrait<"IsIsolatedFromAbove">;
 def ResultsAreFloatLike : NativeOpTrait<"ResultsAreFloatLike">;
 // Op has the same operand type.
 def SameTypeOperands : NativeOpTrait<"SameTypeOperands">;
+// Op has the same operand type or 0-d memref equivalent type.
+def EquiMemRefAndEltTypeOperands
+: NativeOpTrait<"EquiMemRefAndEltTypeOperands">;
 // Op has same shape for all operands.
 def SameOperandsShape : NativeOpTrait<"SameOperandsShape">;
 // Op has same operand and result shape.

diff  --git a/mlir/include/mlir/IR/OpDefinition.h 
b/mlir/include/mlir/IR/OpDefinition.h
index e7f644f456b22..932ef0542781e 100644
--- a/mlir/include/mlir/IR/OpDefinition.h
+++ b/mlir/include/mlir/IR/OpDefinition.h
@@ -248,6 +248,7 @@ LogicalResult verifyAtLeastNOperands(Operation *op, 
unsigned numOperands);
 LogicalResult verifyOperandsAreFloatLike(Operation *op);
 LogicalResult verifyOperandsAreSignlessIntegerLike(Operation *op);
 LogicalResult verifySameTypeOperands(Operation *op);
+LogicalResult verifyEquiMemRefAndEltTypeOperands(Operation *op);
 LogicalResult verifyZeroRegion(Operation *op);
 LogicalResult verifyOneRegion(Operation *op);
 LogicalResult verifyNRegions(Operation *op, unsigned numRegions);
@@ -1143,6 +1144,18 @@ class SameTypeOperands : public TraitBase {
   }
 };
 
+/// This class verifies that all operands of the specified op have the same
+/// type with the exception that 0-d memref type of an elemental type is 
treated
+/// the same as that elemental type.
+template 
+class EquiMemRefAndEltTypeOperands
+: public TraitBase {
+public:
+  static LogicalResult verifyTrait(Operation *op) {
+return impl::verifyEquiMemRefAndEltTypeOperands(op);
+  }
+};
+
 /// This class provides the API for a sub-set of ops that are known to be
 /// constant-like. These are non-side effecting operations with one result and
 /// zero operands that can always be folded to a specific attribute value.

diff  --git a/mlir/lib/IR/Operation.cpp b/mlir/lib/IR/Operation.cpp
index 457c993b92ad3..657b612ccce16 100644
--- a/mlir/lib/IR/Operation.cpp
+++ b/mlir/lib/IR/Operation.cpp
@@ -792,6 +792,32 @@ LogicalResult 
OpTrait::impl::verifySameTypeOperands(Operation *op) {
   return success();
 }
 
+LogicalResult OpTrait::impl::verifyEquiMemRefAndEltTypeOperands(Operation *op) 
{
+  // Zero or one operand always have the "same" type.
+  unsigned nOperands = op->getNumOperands();
+  if (nOperands < 2)
+return success();
+
+  StringRef msg =
+  "requires all operands to have the same or equivalent type where a 0-d "
+  "memref type is considered equivalent to its elemental type";
+
+  auto prevType = op->getOperand(0).getType();
+  for (auto opType : llvm::drop_begin(op->getOperandTypes(), 1)) {
+if (opType != prevType) {
+  if (auto opMemRefType = opType.dyn_cast())
+if (opMemRefType.getRank() != 0 ||
+opMemRefType.getElementType() != prevType)
+  return op->emitOpError(msg);
+  if (auto prevMemRefType = prevType.dyn_cast())
+if (prevMemRefType.getRank() != 0 &&
+prevMemRefType.getElementType() != opType)
+  return op->emitOpError(msg);
+}
+  }
+  return success();
+}
+
 LogicalResult OpTrait::impl::verifyZeroRegion(Operation *op) {
   if (op->getNumRegions() != 0)
 return op->emitOpError() << "requires zero regions";



___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [mlir] 7a34031 - [MLIR] Add verifier for LHLO get tuple element op

2021-11-05 Thread Uday Bondhugula via llvm-branch-commits

Author: Uday Bondhugula
Date: 2021-09-23T05:52:22+05:30
New Revision: 7a34031a8fdabe5f484a537c96a7cd31999c51d5

URL: 
https://github.com/llvm/llvm-project/commit/7a34031a8fdabe5f484a537c96a7cd31999c51d5
DIFF: 
https://github.com/llvm/llvm-project/commit/7a34031a8fdabe5f484a537c96a7cd31999c51d5.diff

LOG: [MLIR] Add verifier for LHLO get tuple element op

The LHLO GetTupleElementOp was missing its verifier. Add the verifier.

Added: 
mlir/test/Dialect/LHLO/invalid.mlir

Modified: 
mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
mlir/lib/Dialect/LHLO/IR/LHLOOps.cc

Removed: 




diff  --git a/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td 
b/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
index 15c17ee3b85c..104e9c011de6 100644
--- a/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
+++ b/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
@@ -251,6 +251,8 @@ def LHLO_GetTupleElementOp: LHLO_Op<"get_tuple_element", 
[]>, BASE_HLO_GetTupleE
   );
 
   let results = (outs Arg);
+
+  let verifier = [{ return ::verify(*this); }];
 }
 
 def LHLO_CompareOp: LHLO_Op<"compare", []>, BASE_HLO_CompareOp {

diff  --git a/mlir/lib/Dialect/LHLO/IR/LHLOOps.cc 
b/mlir/lib/Dialect/LHLO/IR/LHLOOps.cc
index 26251379be8f..01b0da948dea 100644
--- a/mlir/lib/Dialect/LHLO/IR/LHLOOps.cc
+++ b/mlir/lib/Dialect/LHLO/IR/LHLOOps.cc
@@ -59,11 +59,10 @@ void LHLODialect::initialize() {
   >();
 }
 
-#define GET_OP_CLASSES
-#include "mlir/Dialect/LHLO/IR/LHLOOps.cpp.inc"
-
-namespace mlir {
-namespace xla_lhlo {
+using xla_lhlo::ConstOp;
+using xla_lhlo::FusionOp;
+using xla_lhlo::GetTupleElementOp;
+using xla_lhlo::TupleOp;
 
 
//===--===//
 // ConstOp.
@@ -123,5 +122,30 @@ void TupleOp::build(OpBuilder& builder, OperationState& 
result,
   build(builder, result, builder.getTupleType(types), values);
 }
 
-}  // namespace xla_lhlo
-}  // namespace mlir
+//===--===//
+// GetTupleElementOp
+//===--===//
+
+static LogicalResult verify(GetTupleElementOp op) {
+  unsigned index = op.index();
+  auto operandType = op.getOperand().getType().cast();
+  if (index >= operandType.size()) {
+return op.emitOpError(
+llvm::formatv("index {0} is out of bounds of operand with size {1}",
+  index, operandType.size()));
+  }
+
+  Type expectedType = operandType.getType(index);
+  if (op.getType() != expectedType) {
+return op.emitOpError(llvm::formatv("has return type {0}, but expected 
{1}",
+op.getType(), expectedType));
+  }
+  return success();
+}
+
+//===--===//
+// TableGen'd op method definitions
+//===--===//
+
+#define GET_OP_CLASSES
+#include "mlir/Dialect/LHLO/IR/LHLOOps.cpp.inc"

diff  --git a/mlir/test/Dialect/LHLO/invalid.mlir 
b/mlir/test/Dialect/LHLO/invalid.mlir
new file mode 100644
index ..0e269535d00c
--- /dev/null
+++ b/mlir/test/Dialect/LHLO/invalid.mlir
@@ -0,0 +1,10 @@
+// RUN: mlir-opt %s -split-input-file -verify-diagnostics
+
+func @passthrough(%arg : memref<8xi32>) {
+  %c0_i32 = constant 0 : i32
+  %tuple = "xla_lhlo.tuple"(%c0_i32, %arg) : (i32, memref<8xi32>) -> 
(tuple>)
+  %elt = "xla_lhlo.get_tuple_element"(%tuple) {index = 0 : i32} : (tuple>) -> i32
+  // expected-error@+1{{'xla_lhlo.get_tuple_element' op has return type 
memref<8xi32>, but expected i32}}
+  %mem = "xla_lhlo.get_tuple_element"(%tuple) {index = 0 : i32} : (tuple>) -> memref<8xi32>
+  return
+}



___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [mlir] 071e483 - Add verifier for the LHLO TupleOp

2021-11-05 Thread Uday Bondhugula via llvm-branch-commits

Author: Prateek Gupta
Date: 2021-09-23T05:53:52+05:30
New Revision: 071e483b072ee7ff59ec3386b6bc0155c7a230b3

URL: 
https://github.com/llvm/llvm-project/commit/071e483b072ee7ff59ec3386b6bc0155c7a230b3
DIFF: 
https://github.com/llvm/llvm-project/commit/071e483b072ee7ff59ec3386b6bc0155c7a230b3.diff

LOG: Add verifier for the LHLO TupleOp
Added verification support for LHLO TupleOp, so that inconsistency between 
input and output types for the LHLO TupleOp can be checked.

Added: 


Modified: 
mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
mlir/lib/Dialect/LHLO/IR/LHLOOps.cc
mlir/test/Dialect/LHLO/invalid.mlir

Removed: 




diff  --git a/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td 
b/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
index 104e9c011de6..752992761485 100644
--- a/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
+++ b/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
@@ -600,6 +600,8 @@ def LHLO_TupleOp : LHLO_ReadOnlyOp<"tuple", 
[NoSideEffect]>, BASE_HLO_TupleOp {
   let results = (outs NestedTupleOf<[LHLO_BufferOrIntOrFP]>);
 
   let builders = [OpBuilder<(ins "ValueRange":$values)>];
+
+  let verifier = [{ return::verify(*this);}];
 }
 
 def LHLO_WhileOp

diff  --git a/mlir/lib/Dialect/LHLO/IR/LHLOOps.cc 
b/mlir/lib/Dialect/LHLO/IR/LHLOOps.cc
index 01b0da948dea..27d2596f167e 100644
--- a/mlir/lib/Dialect/LHLO/IR/LHLOOps.cc
+++ b/mlir/lib/Dialect/LHLO/IR/LHLOOps.cc
@@ -122,6 +122,17 @@ void TupleOp::build(OpBuilder& builder, OperationState& 
result,
   build(builder, result, builder.getTupleType(types), values);
 }
 
+static LogicalResult verify(TupleOp op) {
+  SmallVector operandTypes = {op.operand_type_begin(),
+   op.operand_type_end()};
+  auto expectedType = TupleType::get(op.getContext(), operandTypes);
+  if (op.getType() != expectedType) {
+return op.emitOpError(llvm::formatv("has return type {0}, but expected 
{1}",
+op.getType(), expectedType));
+  }
+  return success();
+}
+
 
//===--===//
 // GetTupleElementOp
 
//===--===//

diff  --git a/mlir/test/Dialect/LHLO/invalid.mlir 
b/mlir/test/Dialect/LHLO/invalid.mlir
index 0e269535d00c..98e744c0167c 100644
--- a/mlir/test/Dialect/LHLO/invalid.mlir
+++ b/mlir/test/Dialect/LHLO/invalid.mlir
@@ -8,3 +8,30 @@ func @passthrough(%arg : memref<8xi32>) {
   %mem = "xla_lhlo.get_tuple_element"(%tuple) {index = 0 : i32} : (tuple>) -> memref<8xi32>
   return
 }
+
+// -
+
+func @pass_wrong_number_of_arguments(%arg : memref<8xi32>){
+%c0 = constant 0 : i32
+%c1 = constant 1 : i32
+// expected-error@+1{{'xla_lhlo.tuple' op has return type tuple, but 
expected tuple, i32>}}
+%tuple = "xla_lhlo.tuple"(%c0, %arg, %c1) : (i32, memref<8xi32>, i32) -> 
(tuple)
+}
+
+// -
+
+func @pass_wrong_type(%arg : i32){
+%c = constant 0 : i32
+// expected-error@+1{{'xla_lhlo.tuple' op has return type tuple>, but expected tuple}}
+%tuple = "xla_lhlo.tuple"(%c, %arg) : (i32, i32) -> (tuple>)
+return 
+}
+
+// -
+
+func @pass_wrong_order(%arg : memref<8xi32>){
+%c = constant 0 : i32
+// expected-error@+1{{'xla_lhlo.tuple' op has return type 
tuple, i32>, but expected tuple>}}
+%tuple = "xla_lhlo.tuple"(%c, %arg) : (i32, memref<8xi32>) -> 
(tuple, i32>)
+return 
+}
\ No newline at end of file



___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [mlir] 87b4572 - [MLIR] [NFC] Update xla_lhlo WhileOp documentation

2021-11-05 Thread Uday Bondhugula via llvm-branch-commits

Author: Uday Bondhugula
Date: 2021-09-23T05:33:00+05:30
New Revision: 87b4572a6b574fba930770d0c8c96455d0340809

URL: 
https://github.com/llvm/llvm-project/commit/87b4572a6b574fba930770d0c8c96455d0340809
DIFF: 
https://github.com/llvm/llvm-project/commit/87b4572a6b574fba930770d0c8c96455d0340809.diff

LOG: [MLIR] [NFC] Update xla_lhlo WhileOp documentation

Update xla_lhlo WhileOp documentation. NFC.

Added: 


Modified: 
mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td

Removed: 




diff  --git a/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td 
b/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
index 7f83425f138c..15c17ee3b85c 100644
--- a/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
+++ b/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
@@ -607,7 +607,11 @@ def LHLO_WhileOp
 
   string description = [{
 Returns the result of executing a body function until the cond body returns
-true.
+true. The `body` and `cond` regions are expected to have a single block
+terminated with a `yield`. The operand (`init`), the result, the argument 
to
+the body, the yield value from the body, and the argument to the 
conditional
+are all a single tuple value of the same type. The yield value from the
+conditional is always a boolean of type i1.
 
 See https://www.tensorflow.org/xla/operation_semantics#while.
   }];



___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [mlir] eff9b54 - [MLIR] Introduce IfOp in the xla_lhlo dialect

2021-11-05 Thread Uday Bondhugula via llvm-branch-commits

Author: Uday Bondhugula
Date: 2021-09-23T05:56:13+05:30
New Revision: eff9b542c7e3cbc44faac86046461a982ac9dcdc

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

LOG: [MLIR] Introduce IfOp in the xla_lhlo dialect

Introduce LHLO IfOp to model conditionals on the memref form.  This is
lowered form form of HLO IfOp (the latter operates on tensors).  Its
design is similar to that of the LHLO WhileOp, taking in tuples of
memrefs or elemental types. The true and the false bodies return a tuple
of the same type.

Added: 


Modified: 
mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
mlir/test/Dialect/LHLO/lhlo_ops.mlir

Removed: 




diff  --git a/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td 
b/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
index 752992761485..711549940570 100644
--- a/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
+++ b/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
@@ -467,6 +467,53 @@ def LHLO_GatherOp: LHLO_Op<"gather", []>, 
BASE_HLO_GatherOp {
   );
 }
 
+def LHLO_IfOp : LHLO_Op<"if", [AffineScope, RecursiveSideEffects]> {
+  string summary = "If operator";
+
+  string description = [{
+Returns the result of executing either a true or false function depending 
on
+the result of a condition function. In contrast to the HLO version, the
+tuple operands for the true or false branch are a tuple of memrefs or 
int/fp
+types. Both the true and false branches also return such a tuple type: they
+both return the same type and this match the result type of the op.
+
+Example:
+
+```mlir
+func @lhlo_if(%arg0: memref<1x1x10xf32>, %arg1: memref<1x1x10xf32>, %arg2: 
memref) {
+  %0 = "xla_lhlo.tuple"(%arg0, %arg1) : (memref<1x1x10xf32>, 
memref<1x1x10xf32>) -> tuple, memref<1x1x10xf32>>
+  %1 = "xla_lhlo.if"(%arg2, %0, %0) ( {
+^bb0(%arg3: tuple, memref<1x1x10xf32>>):
+%2 = "xla_lhlo.get_tuple_element"(%arg3) {index = 0 : i32} : 
(tuple, memref<1x1x10xf32>>) -> memref<1x1x10xf32>
+%3 = "xla_lhlo.tuple"(%2) : (memref<1x1x10xf32>) -> 
tuple>
+"xla_lhlo.yield"(%3) : (tuple>) -> ()
+  },  {
+^bb0(%arg3: tuple, memref<1x1x10xf32>>):  // no 
predecessors
+%2 = "xla_lhlo.get_tuple_element"(%arg3) {index = 1 : i32} : 
(tuple, memref<1x1x10xf32>>) -> memref<1x1x10xf32>
+%3 = "xla_lhlo.tuple"(%2) : (memref<1x1x10xf32>) -> 
tuple>
+"xla_lhlo.yield"(%3) : (tuple>) -> ()
+  }) : (memref, tuple, memref<1x1x10xf32>>, 
tuple, memref<1x1x10xf32>>) -> tuple>
+  "xla_lhlo.terminator"() : () -> ()
+}
+```
+
+See https://www.tensorflow.org/xla/operation_semantics#conditional.
+  }];
+
+  let arguments = (ins Arg : $init);
+
+  let arguments = (ins
+LHLO_PredBufferOrI1:$pred,
+LHLO_TupleOfBufferOrIntOrFP:$true_arg,
+LHLO_TupleOfBufferOrIntOrFP:$false_arg
+  );
+
+  let regions = (region AnyRegion:$true_branch,
+AnyRegion:$false_branch);
+
+  let results = (outs Arg);
+}
+
 def LHLO_MapOp : LHLO_Op<"map", [RecursiveSideEffects, SameOperandsShape]>,
  BASE_HLO_MapOp {
   let description = [{

diff  --git a/mlir/test/Dialect/LHLO/lhlo_ops.mlir 
b/mlir/test/Dialect/LHLO/lhlo_ops.mlir
index 30a84c5b4bcb..59ccfc8113be 100644
--- a/mlir/test/Dialect/LHLO/lhlo_ops.mlir
+++ b/mlir/test/Dialect/LHLO/lhlo_ops.mlir
@@ -235,3 +235,40 @@ func @while_op(%arg0: memref<4x?x16xf32>, %arg1: 
memref<4x?x16xf32>) {
 }) : (tuple>) -> tuple>
 "xla_lhlo.terminator"() : () -> ()
 }
+
+// -
+
+func @lhlo_if(%arg0: memref<1x1x10xf32>, %arg1: memref<1x1x10xf32>, %arg2: 
memref) {
+  %0 = "xla_lhlo.tuple"(%arg0, %arg1) : (memref<1x1x10xf32>, 
memref<1x1x10xf32>) -> tuple, memref<1x1x10xf32>>
+  // CHECK: xla_lhlo.if
+  %1 = "xla_lhlo.if"(%arg2, %0, %0) ( {
+^bb0(%arg3: tuple, memref<1x1x10xf32>>):
+%2 = "xla_lhlo.get_tuple_element"(%arg3) {index = 0 : i32} : 
(tuple, memref<1x1x10xf32>>) -> memref<1x1x10xf32>
+%3 = "xla_lhlo.tuple"(%2) : (memref<1x1x10xf32>) -> 
tuple>
+"xla_lhlo.yield"(%3) : (tuple>) -> ()
+  },  {
+^bb0(%arg3: tuple, memref<1x1x10xf32>>):  // no 
predecessors
+%2 = "xla_lhlo.get_tuple_element"(%arg3) {index = 1 : i32} : 
(tuple, memref<1x1x10xf32>>) -> memref<1x1x10xf32>
+%3 = "xla_lhlo.tuple"(%2) : (memref<1x1x10xf32>) -> 
tuple>
+"xla_lhlo.yield"(%3) : (tuple>) -> ()
+  }) : (memref, tuple, memref<1x1x10xf32>>, 
tuple, memref<1x1x10xf32>>) -> tuple>
+  "xla_lhlo.terminator"() : () -> ()
+}
+
+// CHECK-LABEL: func @lhlo_if_empty_arg
+func @lhlo_if_empty_arg(%arg0: memref) {
+  %cst = constant 1.00e+00 : f32
+  %cst_0 = constant 0.00e+00 : f32
+  %0 = "xla_lhlo.tuple"() : () -> tuple<>
+  // CHECK: xla_lhlo.if
+  %1 = "xla_lhlo.if"(%arg0, %0, %0) ( {
+^bb0(%arg1: tuple<>):
+%2 

[llvm-branch-commits] [mlir] 51de919 - Rename xla_lhlo dialect and namespace -> lmhlo

2021-11-05 Thread Uday Bondhugula via llvm-branch-commits

Author: Uday Bondhugula
Date: 2021-09-23T06:12:54+05:30
New Revision: 51de91957abebee3c6fdf870f1388b266ea011b1

URL: 
https://github.com/llvm/llvm-project/commit/51de91957abebee3c6fdf870f1388b266ea011b1
DIFF: 
https://github.com/llvm/llvm-project/commit/51de91957abebee3c6fdf870f1388b266ea011b1.diff

LOG: Rename xla_lhlo dialect and namespace -> lmhlo

This change of name is being done to avoid a clash in the python binding
with the xla_lhlo in Monolith's TensorFlow. While xla_lhlo was moved to
MLIR proper in our branches, Monolith's TensorFlow still has it and its
methods would get called instead of those in MLIR linked in by Monolith.

Added: 


Modified: 
mlir/include/mlir/Dialect/LHLO/IR/CMakeLists.txt
mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.h
mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
mlir/include/mlir/InitAllDialects.h
mlir/lib/Dialect/LHLO/IR/LHLOOps.cc
mlir/test/Dialect/LHLO/invalid.mlir
mlir/test/Dialect/LHLO/lhlo_ops.mlir
mlir/test/mlir-opt/commandline.mlir

Removed: 




diff  --git a/mlir/include/mlir/Dialect/LHLO/IR/CMakeLists.txt 
b/mlir/include/mlir/Dialect/LHLO/IR/CMakeLists.txt
index f5c4548ccf534..b852d42171bd7 100644
--- a/mlir/include/mlir/Dialect/LHLO/IR/CMakeLists.txt
+++ b/mlir/include/mlir/Dialect/LHLO/IR/CMakeLists.txt
@@ -1,4 +1,4 @@
-add_mlir_dialect(LHLOOps xla_lhlo)
+add_mlir_dialect(LHLOOps lmhlo)
 
 set(LLVM_TARGET_DEFINITIONS LHLOOps.td)
 mlir_tablegen(LHLOStructs.h.inc -gen-struct-attr-decls)

diff  --git a/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.h 
b/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.h
index c17ee6d63bd40..94a9de69cfd27 100644
--- a/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.h
+++ b/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.h
@@ -40,5 +40,4 @@ class OpBuilder;
 #define GET_OP_CLASSES
 #include "mlir/Dialect/LHLO/IR/LHLOOps.h.inc"
 
-
 #endif  // MLIR_DIALECT_LHLO_IR_LHLO_OPS_H_

diff  --git a/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td 
b/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
index 711549940570c..0ee24446cad8b 100644
--- a/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
+++ b/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
@@ -23,8 +23,8 @@ include "mlir/Interfaces/SideEffectInterfaces.td"
 include "mlir/Dialect/LHLO/IR/HLOOpsBase.td"
 
 def LHLO_Dialect : Dialect {
-  let name = "xla_lhlo";
-  let cppNamespace = "::mlir::xla_lhlo";
+  let name = "lmhlo";
+  let cppNamespace = "::mlir::lmhlo";
 }
 
 
//===--===//
@@ -481,19 +481,19 @@ def LHLO_IfOp : LHLO_Op<"if", [AffineScope, 
RecursiveSideEffects]> {
 
 ```mlir
 func @lhlo_if(%arg0: memref<1x1x10xf32>, %arg1: memref<1x1x10xf32>, %arg2: 
memref) {
-  %0 = "xla_lhlo.tuple"(%arg0, %arg1) : (memref<1x1x10xf32>, 
memref<1x1x10xf32>) -> tuple, memref<1x1x10xf32>>
-  %1 = "xla_lhlo.if"(%arg2, %0, %0) ( {
+  %0 = "lmhlo.tuple"(%arg0, %arg1) : (memref<1x1x10xf32>, 
memref<1x1x10xf32>) -> tuple, memref<1x1x10xf32>>
+  %1 = "lmhlo.if"(%arg2, %0, %0) ( {
 ^bb0(%arg3: tuple, memref<1x1x10xf32>>):
-%2 = "xla_lhlo.get_tuple_element"(%arg3) {index = 0 : i32} : 
(tuple, memref<1x1x10xf32>>) -> memref<1x1x10xf32>
-%3 = "xla_lhlo.tuple"(%2) : (memref<1x1x10xf32>) -> 
tuple>
-"xla_lhlo.yield"(%3) : (tuple>) -> ()
+%2 = "lmhlo.get_tuple_element"(%arg3) {index = 0 : i32} : 
(tuple, memref<1x1x10xf32>>) -> memref<1x1x10xf32>
+%3 = "lmhlo.tuple"(%2) : (memref<1x1x10xf32>) -> 
tuple>
+"lmhlo.yield"(%3) : (tuple>) -> ()
   },  {
 ^bb0(%arg3: tuple, memref<1x1x10xf32>>):  // no 
predecessors
-%2 = "xla_lhlo.get_tuple_element"(%arg3) {index = 1 : i32} : 
(tuple, memref<1x1x10xf32>>) -> memref<1x1x10xf32>
-%3 = "xla_lhlo.tuple"(%2) : (memref<1x1x10xf32>) -> 
tuple>
-"xla_lhlo.yield"(%3) : (tuple>) -> ()
+%2 = "lmhlo.get_tuple_element"(%arg3) {index = 1 : i32} : 
(tuple, memref<1x1x10xf32>>) -> memref<1x1x10xf32>
+%3 = "lmhlo.tuple"(%2) : (memref<1x1x10xf32>) -> 
tuple>
+"lmhlo.yield"(%3) : (tuple>) -> ()
   }) : (memref, tuple, memref<1x1x10xf32>>, 
tuple, memref<1x1x10xf32>>) -> tuple>
-  "xla_lhlo.terminator"() : () -> ()
+  "lmhlo.terminator"() : () -> ()
 }
 ```
 

diff  --git a/mlir/include/mlir/InitAllDialects.h 
b/mlir/include/mlir/InitAllDialects.h
index e9869365e54eb..43712b70d5362 100644
--- a/mlir/include/mlir/InitAllDialects.h
+++ b/mlir/include/mlir/InitAllDialects.h
@@ -80,7 +80,7 @@ inline void registerAllDialects(DialectRegistry ®istry) {
   tensor::TensorDialect,
   tosa::TosaDialect,
   x86vector::X86VectorDialect,
-  xla_lhlo::LHLODialect>();
+  lmhlo::LHLODialect>();
   // clang-format on
 }
 

diff  --git a/mlir/lib/Dialect/LHLO/IR/LHLOOps.cc 
b/mlir/lib/Dialect/LHLO/IR/LHLOOps.cc
index 27d259

[llvm-branch-commits] [mlir] c6b7f22 - [MLIR] Add xla_lhlo dialect from tensorflow

2021-11-05 Thread Uday Bondhugula via llvm-branch-commits

Author: Uday Bondhugula
Date: 2021-09-22T14:23:46+05:30
New Revision: c6b7f22240229f69af9ebb75d4b7a9b5f1dd0da1

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

LOG: [MLIR] Add xla_lhlo dialect from tensorflow

Add xla_lhlo dialect from tensorflow (the version used by the right
branch of the private repo). This commit brings in just the LHLO ops
part of it. So, LHLO transforms or any conversions out of LHLO are not
included. This is to mainly to allow the use of xla_lhlo dialect ops
along with MLIR.  So, the users would be aware of LHLO ops (make use
of its accessors) as the xla_lhlo dialect would be registered. This is a
temporary arrangement before we can migrate to depending on mlir-hlo.
Depending on tensorflow just for xla_lhlo isn't really feasible.

Added: 
mlir/include/mlir/Dialect/LHLO/CMakeLists.txt
mlir/include/mlir/Dialect/LHLO/IR/CMakeLists.txt
mlir/include/mlir/Dialect/LHLO/IR/HLOOpsBase.td
mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.h
mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
mlir/lib/Dialect/LHLO/CMakeLists.txt
mlir/lib/Dialect/LHLO/IR/CMakeLists.txt
mlir/lib/Dialect/LHLO/IR/LHLOOps.cc
mlir/test/Dialect/LHLO/lhlo_ops.mlir

Modified: 
mlir/include/mlir/Dialect/CMakeLists.txt
mlir/include/mlir/InitAllDialects.h
mlir/lib/Dialect/CMakeLists.txt

Removed: 




diff  --git a/mlir/include/mlir/Dialect/CMakeLists.txt 
b/mlir/include/mlir/Dialect/CMakeLists.txt
index 44a9249cef839..60e31ed7cac55 100644
--- a/mlir/include/mlir/Dialect/CMakeLists.txt
+++ b/mlir/include/mlir/Dialect/CMakeLists.txt
@@ -9,6 +9,7 @@ add_subdirectory(EmitC)
 add_subdirectory(GPU)
 add_subdirectory(Math)
 add_subdirectory(Linalg)
+add_subdirectory(LHLO)
 add_subdirectory(LLVMIR)
 add_subdirectory(MemRef)
 add_subdirectory(OpenACC)

diff  --git a/mlir/include/mlir/Dialect/LHLO/CMakeLists.txt 
b/mlir/include/mlir/Dialect/LHLO/CMakeLists.txt
new file mode 100644
index 0..f33061b2d87cf
--- /dev/null
+++ b/mlir/include/mlir/Dialect/LHLO/CMakeLists.txt
@@ -0,0 +1 @@
+add_subdirectory(IR)

diff  --git a/mlir/include/mlir/Dialect/LHLO/IR/CMakeLists.txt 
b/mlir/include/mlir/Dialect/LHLO/IR/CMakeLists.txt
new file mode 100644
index 0..f5c4548ccf534
--- /dev/null
+++ b/mlir/include/mlir/Dialect/LHLO/IR/CMakeLists.txt
@@ -0,0 +1,8 @@
+add_mlir_dialect(LHLOOps xla_lhlo)
+
+set(LLVM_TARGET_DEFINITIONS LHLOOps.td)
+mlir_tablegen(LHLOStructs.h.inc -gen-struct-attr-decls)
+mlir_tablegen(LHLOStructs.cpp.inc -gen-struct-attr-defs)
+add_public_tablegen_target(MLIRLHLOStructsGen)
+
+add_mlir_doc(LHLOOps -gen-op-doc LHLOOps Dialects/)

diff  --git a/mlir/include/mlir/Dialect/LHLO/IR/HLOOpsBase.td 
b/mlir/include/mlir/Dialect/LHLO/IR/HLOOpsBase.td
new file mode 100644
index 0..9312ed9e96f9f
--- /dev/null
+++ b/mlir/include/mlir/Dialect/LHLO/IR/HLOOpsBase.td
@@ -0,0 +1,1260 @@
+/* Copyright 2019 The TensorFlow Authors. All Rights Reserved.
+
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
+
+http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+==*/
+
+#ifndef HLO_OPS_BASE
+#define HLO_OPS_BASE
+
+include "mlir/IR/OpBase.td"
+
+def HLO_Pred : TypeAlias;
+
+// TODO(hinsu): Use signed integers instead of signless integer which is being
+// used for legacy reasons.
+def HLO_SInt : SignlessIntOfWidths<[8, 16, 32, 64]>;
+def HLO_UInt : UnsignedIntOfWidths<[8, 16, 32, 64]>;
+def HLO_Int : AnyTypeOf<[HLO_SInt, HLO_UInt]>;
+def HLO_I1 : SignlessIntOfWidths<[1]>;
+
+def HLO_Complex : Complex>;
+
+// The broadcasting dimensions correspond to a tuple that describes how a
+// smaller rank shape is broadcast into a larger rank shape. For example,
+// given a 2x3x4 cuboid and a 3x4 matrix, a broadcasting tuple (1,2) means
+// matching the matrix to dimensions 1 and 2 of the cuboid.
+defvar BroadcastDimAttr = I64ElementsAttr;
+
+//===--===//
+// XLA on tensors type definitions.
+//===--===//
+
+// Token type.
+def HLO_Token : Type()">, "token">;
+
+// Any integer tensor types
+def HLO_IntTensor : TensorOf<[HLO_Int]>;
+
+// Any integer tensor type with rank 0 (i.e. representing a single integer).
+def HLO_ScalarIntTensor : Shaped

[llvm-branch-commits] [mlir] db04767 - [MLIR] Add the seed attribute for random_uniform ops in lmhlo dialect. (#35)

2021-11-05 Thread Uday Bondhugula via llvm-branch-commits

Author: Prashant Kumar
Date: 2021-09-23T06:20:43+05:30
New Revision: db04767afbea48b62a7a25017e42248a5d83480c

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

LOG: [MLIR] Add the seed attribute for random_uniform ops in lmhlo dialect. 
(#35)

The `seed` and `seed2` attribute are added to lmhlo dialect in case of
random_uniform ops. The changes are made as a part of hlo-legalize-to-lhlo` 
pass.

Added: 


Modified: 
mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td

Removed: 




diff  --git a/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td 
b/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
index 0ee24446cad8..16fff82d6c7a 100644
--- a/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
+++ b/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
@@ -568,10 +568,17 @@ def LHLO_ReshapeOp: LHLO_Op<"reshape", []>, 
BASE_HLO_ReshapeOp {
 // output memref consistent with HLO op xla_hlo::rng_uniform.
 
//===--===//
 def LHLO_RngUniformOp : LHLO_Op<"rng_uniform", []>, BASE_HLO_RngUniformOp {
+  let summary = [{
+   The generated values follow a uniform distribution in the range [minval, 
maxval]. 
+   Operations that rely on a random seed actually derive it from two seeds:
+   the global and operation-level seeds which are `seed` and `seed2` 
respectively.
+  }];
   let arguments = (ins
 AnyTypeOf<[AnyInteger, AnyFloat]>:$a,
 AnyTypeOf<[AnyInteger, AnyFloat]>:$b,
-Arg:$output
+Arg:$output,
+OptionalAttr:$seed,
+OptionalAttr:$seed2
   );
 }
 



___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [mlir] 10cf6d4 - [MLIR] Add RngNormalOp in LHLO dialect (#60)

2021-11-05 Thread Uday Bondhugula via llvm-branch-commits

Author: Abhishek Varma
Date: 2021-09-23T06:20:44+05:30
New Revision: 10cf6d43c473449402675de0d06650464f01bc9f

URL: 
https://github.com/llvm/llvm-project/commit/10cf6d43c473449402675de0d06650464f01bc9f
DIFF: 
https://github.com/llvm/llvm-project/commit/10cf6d43c473449402675de0d06650464f01bc9f.diff

LOG: [MLIR] Add RngNormalOp in LHLO dialect (#60)

-- This commit introduces RngNormalOp as part of LHLO dialect.

Signed-off-by: Abhishek Varma 

Added: 


Modified: 
mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td

Removed: 




diff  --git a/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td 
b/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
index 16fff82d6c7a..394f6c6679a8 100644
--- a/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
+++ b/mlir/include/mlir/Dialect/LHLO/IR/LHLOOps.td
@@ -582,6 +582,26 @@ def LHLO_RngUniformOp : LHLO_Op<"rng_uniform", []>, 
BASE_HLO_RngUniformOp {
   );
 }
 
+//===--===//
+// RngNormal operator that takes scalar low and high values and populates the
+// output memref consistent with HLO op xla_hlo::rng_normal.
+//===--===//
+def LHLO_RngNormalOp : LHLO_Op<"rng_normal", []>, BASE_HLO_RngNormalOp {
+  let summary = [{
+   The generated values follow a standard normal distribution in the range 
+   [minval, maxval]. Operations that rely on a random seed actually derive it 
+   from two seeds: the global and operation-level seeds which are `seed` and 
+   `seed2` respectively.
+  }];
+  let arguments = (ins
+AnyTypeOf<[AnyInteger, AnyFloat]>:$a,
+AnyTypeOf<[AnyInteger, AnyFloat]>:$b,
+Arg:$output,
+OptionalAttr:$seed,
+OptionalAttr:$seed2
+  );
+}
+
 def LHLO_SelectOp: LHLO_Op<"select", []>, BASE_HLO_SelectOp {
   let arguments = (ins
 Arg:$pred,



___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [mlir] 81fe64d - [MLIR] Add AffineMap::isPureAffine

2021-11-05 Thread Uday Bondhugula via llvm-branch-commits

Author: Uday Bondhugula
Date: 2021-09-23T08:19:19+05:30
New Revision: 81fe64da18fa4d4c9252b2ddd646f6623e1d1704

URL: 
https://github.com/llvm/llvm-project/commit/81fe64da18fa4d4c9252b2ddd646f6623e1d1704
DIFF: 
https://github.com/llvm/llvm-project/commit/81fe64da18fa4d4c9252b2ddd646f6623e1d1704.diff

LOG: [MLIR] Add AffineMap::isPureAffine

Signed-off-by: Uday Bondhugula 

Added: 


Modified: 
mlir/include/mlir/IR/AffineMap.h
mlir/lib/IR/AffineMap.cpp

Removed: 




diff  --git a/mlir/include/mlir/IR/AffineMap.h 
b/mlir/include/mlir/IR/AffineMap.h
index 906c53db4b32..f1f00acd8022 100644
--- a/mlir/include/mlir/IR/AffineMap.h
+++ b/mlir/include/mlir/IR/AffineMap.h
@@ -81,6 +81,11 @@ class AffineMap {
   static AffineMap getPermutationMap(ArrayRef permutation,
  MLIRContext *context);
 
+  /// Returns true if all of this map's result expressions are pure affine,
+  /// i.e., multiplication, floordiv, ceildiv, and mod is only allowed w.r.t
+  /// constants.
+  bool isPureAffine() const;
+
   /// Returns a vector of AffineMaps; each with as many results as
   /// `exprs.size()`, as many dims as the largest dim in `exprs` and as many
   /// symbols as the largest symbol in `exprs`.

diff  --git a/mlir/lib/IR/AffineMap.cpp b/mlir/lib/IR/AffineMap.cpp
index 9c6f25d3c53e..0989d821655d 100644
--- a/mlir/lib/IR/AffineMap.cpp
+++ b/mlir/lib/IR/AffineMap.cpp
@@ -344,6 +344,12 @@ unsigned AffineMap::getPermutedPosition(unsigned input) 
const {
   llvm_unreachable("incorrect permutation request");
 }
 
+bool AffineMap::isPureAffine() const {
+  return llvm::all_of(getResults(), [](AffineExpr expr) {
+return expr.isPureAffine();
+  });
+}
+
 /// Folds the results of the application of an affine map on the provided
 /// operands to a constant if possible. Returns false if the folding happens,
 /// true otherwise.



___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [mlir] eb1aacd - [MLIR-LAIR] Custom printing for multi-dim affine index maps

2021-11-05 Thread Uday Bondhugula via llvm-branch-commits

Author: Uday Bondhugula
Date: 2021-09-23T08:19:53+05:30
New Revision: eb1aacd495d84384e2d2e4e40c893aebfbd19837

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

LOG: [MLIR-LAIR] Custom printing for multi-dim affine index maps

Custom printing for AffineMaps with named SSA values - to aid printing
NGDL accesses.

Added: 


Modified: 
mlir/include/mlir/IR/AffineMap.h
mlir/lib/IR/AsmPrinter.cpp

Removed: 




diff  --git a/mlir/include/mlir/IR/AffineMap.h 
b/mlir/include/mlir/IR/AffineMap.h
index f1f00acd8022..4ab75ad3ea64 100644
--- a/mlir/include/mlir/IR/AffineMap.h
+++ b/mlir/include/mlir/IR/AffineMap.h
@@ -534,6 +534,11 @@ inline raw_ostream &operator<<(raw_ostream &os, AffineMap 
map) {
   map.print(os);
   return os;
 }
+
+/// Prints an affine map index in the form [expr_1][expr_2] with the supplied
+/// names used for the inputs.
+void printAffineMapAccess(AffineMap map, ArrayRef names,
+  raw_ostream &os);
 } // end namespace mlir
 
 namespace llvm {

diff  --git a/mlir/lib/IR/AsmPrinter.cpp b/mlir/lib/IR/AsmPrinter.cpp
index b6d072f9f60a..9c717eef111c 100644
--- a/mlir/lib/IR/AsmPrinter.cpp
+++ b/mlir/lib/IR/AsmPrinter.cpp
@@ -2241,6 +2241,18 @@ void ModulePrinter::printAffineConstraint(AffineExpr 
expr, bool isEq) {
   isEq ? os << " == 0" : os << " >= 0";
 }
 
+void mlir::printAffineMapAccess(AffineMap map, ArrayRef names,
+raw_ostream &os) {
+  assert(map.getNumInputs() == names.size() && "too few/many names");
+  ModulePrinter p(os);
+  auto printValueName = [&](unsigned pos, bool isSymbol) { os << names[pos]; };
+  for (auto expr : map.getResults()) {
+os << '[';
+p.printAffineExpr(expr, printValueName);
+os << ']';
+  }
+}
+
 void ModulePrinter::printAffineMap(AffineMap map) {
   // Dimension identifiers.
   os << '(';



___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [mlir] 5a72ea0 - [MLIR] Add method mlir::isPerfectNestRoot

2021-11-05 Thread Uday Bondhugula via llvm-branch-commits

Author: Uday Bondhugula
Date: 2021-09-23T08:20:06+05:30
New Revision: 5a72ea079cde160b044ec7241928bb9520a5ae75

URL: 
https://github.com/llvm/llvm-project/commit/5a72ea079cde160b044ec7241928bb9520a5ae75
DIFF: 
https://github.com/llvm/llvm-project/commit/5a72ea079cde160b044ec7241928bb9520a5ae75.diff

LOG: [MLIR] Add method mlir::isPerfectNestRoot

Add method to check if an affine.for op is the root of a nest that is
nested perfectly all the way.

Added: 


Modified: 
mlir/include/mlir/Transforms/LoopUtils.h
mlir/lib/Transforms/Utils/LoopUtils.cpp

Removed: 




diff  --git a/mlir/include/mlir/Transforms/LoopUtils.h 
b/mlir/include/mlir/Transforms/LoopUtils.h
index 8c851215e3c08..fe89a86c4d2e8 100644
--- a/mlir/include/mlir/Transforms/LoopUtils.h
+++ b/mlir/include/mlir/Transforms/LoopUtils.h
@@ -57,6 +57,9 @@ LogicalResult loopUnrollUpToFactor(AffineForOp forOp, 
uint64_t unrollFactor);
 /// in it from outermost to innermost.
 bool LLVM_ATTRIBUTE_UNUSED isPerfectlyNested(ArrayRef loops);
 
+/// Returns true if the nest rooted at `loop` is a perfectly nested loop nest.
+bool isPerfectNestRoot(AffineForOp loop);
+
 /// Get perfectly nested sequence of loops starting at root of loop nest
 /// (the first op being another AffineFor, and the second op - a terminator).
 /// A loop is perfectly nested iff: the first op in the loop's body is another

diff  --git a/mlir/lib/Transforms/Utils/LoopUtils.cpp 
b/mlir/lib/Transforms/Utils/LoopUtils.cpp
index 4427001be2204..41a6aa692ee7c 100644
--- a/mlir/lib/Transforms/Utils/LoopUtils.cpp
+++ b/mlir/lib/Transforms/Utils/LoopUtils.cpp
@@ -1543,6 +1543,24 @@ mlir::isPerfectlyNested(ArrayRef loops) {
   return true;
 }
 
+/// Returns true if no other affine for op's are nested within `forOp`.
+static bool isInnermostAffineForOp(AffineForOp forOp) {
+  // Only for the innermost affine.for op's.
+  bool isInnermost = true;
+  forOp.walk([&](AffineForOp thisForOp) {
+isInnermost = (thisForOp == forOp);
+return WalkResult::interrupt();
+  });
+  return isInnermost;
+}
+
+/// Returns true if the nest rooted at `loop` is a perfectly nested loop nest.
+bool mlir::isPerfectNestRoot(AffineForOp loop) {
+  SmallVector nest;
+  getPerfectlyNestedLoops(nest, loop);
+  return isInnermostAffineForOp(nest.back());
+}
+
 // input[i] should move from position i -> permMap[i]. Returns the position in
 // `input` that becomes the new outermost loop.
 unsigned mlir::permuteLoops(MutableArrayRef input,



___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [mlir] 3e07b0b - [MLIR] Fix lowering of affine operations with return values

2020-12-22 Thread Uday Bondhugula via llvm-branch-commits

Author: Prateek Gupta
Date: 2020-12-22T21:44:31+05:30
New Revision: 3e07b0b9d3363fb767cbbaa2593fa91ac393fb7e

URL: 
https://github.com/llvm/llvm-project/commit/3e07b0b9d3363fb767cbbaa2593fa91ac393fb7e
DIFF: 
https://github.com/llvm/llvm-project/commit/3e07b0b9d3363fb767cbbaa2593fa91ac393fb7e.diff

LOG: [MLIR] Fix lowering of affine operations with return values

This commit addresses the issue of lowering affine.for and
affine.parallel having return values. Relevant test cases are also
added.

Signed-off-by: Prateek Gupta 

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

Added: 


Modified: 
mlir/lib/Conversion/AffineToStandard/AffineToStandard.cpp
mlir/test/Conversion/AffineToStandard/lower-affine.mlir

Removed: 




diff  --git a/mlir/lib/Conversion/AffineToStandard/AffineToStandard.cpp 
b/mlir/lib/Conversion/AffineToStandard/AffineToStandard.cpp
index 58f44b6ed207..8721e6b96ed7 100644
--- a/mlir/lib/Conversion/AffineToStandard/AffineToStandard.cpp
+++ b/mlir/lib/Conversion/AffineToStandard/AffineToStandard.cpp
@@ -334,7 +334,13 @@ class AffineYieldOpLowering : public 
OpRewritePattern {
 
   LogicalResult matchAndRewrite(AffineYieldOp op,
 PatternRewriter &rewriter) const override {
-rewriter.replaceOpWithNewOp(op);
+if (isa(op.getParentOp())) {
+  // scf.parallel does not yield any values via its terminator scf.yield 
but
+  // models reductions 
diff erently using additional ops in its region.
+  rewriter.replaceOpWithNewOp(op);
+  return success();
+}
+rewriter.replaceOpWithNewOp(op, op.operands());
 return success();
   }
 };
@@ -349,14 +355,55 @@ class AffineForLowering : public 
OpRewritePattern {
 Value lowerBound = lowerAffineLowerBound(op, rewriter);
 Value upperBound = lowerAffineUpperBound(op, rewriter);
 Value step = rewriter.create(loc, op.getStep());
-auto f = rewriter.create(loc, lowerBound, upperBound, step);
-rewriter.eraseBlock(f.getBody());
-rewriter.inlineRegionBefore(op.region(), f.region(), f.region().end());
-rewriter.eraseOp(op);
+auto scfForOp = rewriter.create(loc, lowerBound, upperBound,
+step, op.getIterOperands());
+rewriter.eraseBlock(scfForOp.getBody());
+rewriter.inlineRegionBefore(op.region(), scfForOp.region(),
+scfForOp.region().end());
+rewriter.replaceOp(op, scfForOp.results());
 return success();
   }
 };
 
+/// Returns the identity value associated with an AtomicRMWKind op.
+static Value getIdentityValue(AtomicRMWKind op, OpBuilder &builder,
+  Location loc) {
+  switch (op) {
+  case AtomicRMWKind::addf:
+return builder.create(loc, builder.getF32FloatAttr(0));
+  case AtomicRMWKind::addi:
+return builder.create(loc, builder.getI32IntegerAttr(0));
+  case AtomicRMWKind::mulf:
+return builder.create(loc, builder.getF32FloatAttr(1));
+  case AtomicRMWKind::muli:
+return builder.create(loc, builder.getI32IntegerAttr(1));
+  // TODO: Add remaining reduction operations.
+  default:
+emitOptionalError(loc, "Reduction operation type not supported");
+  }
+  return nullptr;
+}
+
+/// Return the value obtained by applying the reduction operation kind
+/// associated with a binary AtomicRMWKind op to `lhs` and `rhs`.
+static Value getReductionOp(AtomicRMWKind op, OpBuilder &builder, Location loc,
+Value lhs, Value rhs) {
+  switch (op) {
+  case AtomicRMWKind::addf:
+return builder.create(loc, lhs, rhs);
+  case AtomicRMWKind::addi:
+return builder.create(loc, lhs, rhs);
+  case AtomicRMWKind::mulf:
+return builder.create(loc, lhs, rhs);
+  case AtomicRMWKind::muli:
+return builder.create(loc, lhs, rhs);
+  // TODO: Add remaining reduction operations.
+  default:
+emitOptionalError(loc, "Reduction operation type not supported");
+  }
+  return nullptr;
+}
+
 /// Convert an `affine.parallel` (loop nest) operation into a `scf.parallel`
 /// operation.
 class AffineParallelLowering : public OpRewritePattern {
@@ -369,12 +416,13 @@ class AffineParallelLowering : public 
OpRewritePattern {
 SmallVector steps;
 SmallVector upperBoundTuple;
 SmallVector lowerBoundTuple;
+SmallVector identityVals;
 // Finding lower and upper bound by expanding the map expression.
 // Checking if expandAffineMap is not giving NULL.
-Optional> upperBound = expandAffineMap(
-rewriter, loc, op.upperBoundsMap(), op.getUpperBoundsOperands());
 Optional> lowerBound = expandAffineMap(
 rewriter, loc, op.lowerBoundsMap(), op.getLowerBoundsOperands());
+Optional> upperBound = expandAffineMap(
+rewriter, loc, op.upperBoundsMap(), op.getUpperBoundsOperands());
 if (!lowerBound || !upperBound)
   return failure();
 upperBoundTuple = *upperBound;
@@ -38

[llvm-branch-commits] [mlir] 3bcca6b - [MLIR] Fix affine_map compose with multi-symbols

2021-01-01 Thread Uday Bondhugula via llvm-branch-commits

Author: Chengji Yao
Date: 2021-01-02T06:57:16+05:30
New Revision: 3bcca6b12d4cbe9d4571e799899e9b956e4711bf

URL: 
https://github.com/llvm/llvm-project/commit/3bcca6b12d4cbe9d4571e799899e9b956e4711bf
DIFF: 
https://github.com/llvm/llvm-project/commit/3bcca6b12d4cbe9d4571e799899e9b956e4711bf.diff

LOG: [MLIR] Fix affine_map compose with multi-symbols

Fix bug: https://bugs.llvm.org/show_bug.cgi?id=46845

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

Added: 


Modified: 
mlir/lib/IR/AffineMap.cpp
mlir/test/Dialect/Affine/canonicalize.mlir

Removed: 




diff  --git a/mlir/lib/IR/AffineMap.cpp b/mlir/lib/IR/AffineMap.cpp
index 634917fe0faf..b51636091aad 100644
--- a/mlir/lib/IR/AffineMap.cpp
+++ b/mlir/lib/IR/AffineMap.cpp
@@ -319,7 +319,7 @@ AffineMap AffineMap::compose(AffineMap map) {
   for (unsigned idx = 0; idx < numDims; ++idx) {
 newDims[idx] = getAffineDimExpr(idx, getContext());
   }
-  SmallVector newSymbols(numSymbols);
+  SmallVector newSymbols(numSymbols - numSymbolsThisMap);
   for (unsigned idx = numSymbolsThisMap; idx < numSymbols; ++idx) {
 newSymbols[idx - numSymbolsThisMap] =
 getAffineSymbolExpr(idx, getContext());

diff  --git a/mlir/test/Dialect/Affine/canonicalize.mlir 
b/mlir/test/Dialect/Affine/canonicalize.mlir
index 0e452b0c6338..b185e1c8b707 100644
--- a/mlir/test/Dialect/Affine/canonicalize.mlir
+++ b/mlir/test/Dialect/Affine/canonicalize.mlir
@@ -24,6 +24,9 @@
 // CHECK-DAG: [[$MAP13A:#map[0-9]+]] = affine_map<(d0) -> ((d0 + 6) ceildiv 8)>
 // CHECK-DAG: [[$MAP13B:#map[0-9]+]] = affine_map<(d0) -> ((d0 * 4 - 4) 
floordiv 3)>
 
+// Affine maps for test case: compose_affine_maps_multiple_symbols
+// CHECK-DAG: [[$MAP14:#map[0-9]+]] = affine_map<()[s0, s1] -> (((s1 + s0) * 
4) floordiv s0)>
+
 // Affine maps for test case: partial_fold_map
 // CHECK-DAG: [[$MAP15:#map[0-9]+]] = affine_map<()[s0] -> (s0 - 42)>
 
@@ -218,6 +221,15 @@ func @compose_affine_maps_diamond_dependency(%arg0: f32, 
%arg1: memref<4x4xf32>)
   return
 }
 
+// CHECK-LABEL: func @compose_affine_maps_multiple_symbols
+func @compose_affine_maps_multiple_symbols(%arg0: index, %arg1: index) -> 
index {
+  %a = affine.apply affine_map<(d0)[s0] -> (s0 + d0)> (%arg0)[%arg1]
+  %c = affine.apply affine_map<(d0) -> (d0 * 4)> (%a)
+  %e = affine.apply affine_map<(d0)[s0] -> (d0 floordiv s0)> (%c)[%arg1]
+  // CHECK: [[I0:%[0-9]+]] = affine.apply [[$MAP14]]()[%{{.*}}, %{{.*}}]
+  return %e : index
+}
+
 // CHECK-LABEL: func @arg_used_as_dim_and_symbol
 func @arg_used_as_dim_and_symbol(%arg0: memref<100x100xf32>, %arg1: index, 
%arg2: f32) {
   %c9 = constant 9 : index



___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [mlir] b276bf5 - [MLIR][NFC] Fix mix up between dialect attribute values and names

2020-12-02 Thread Uday Bondhugula via llvm-branch-commits

Author: Uday Bondhugula
Date: 2020-12-03T02:34:15+05:30
New Revision: b276bf5a572b64a02bd4b067125d4f2c9cf6fb6b

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

LOG: [MLIR][NFC] Fix mix up between dialect attribute values and names

Clear up documentation on dialect attribute values. Fix/improve
ModuleOp verifier error message on dialect prefixed attribute names.
Additional discussion is here:
https://llvm.discourse.group/t/moduleop-attributes/2325

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

Added: 


Modified: 
mlir/docs/LangRef.md
mlir/lib/IR/BuiltinDialect.cpp
mlir/test/IR/invalid-module-op.mlir

Removed: 




diff  --git a/mlir/docs/LangRef.md b/mlir/docs/LangRef.md
index 82272d1b729f..fd78d51afd6d 100644
--- a/mlir/docs/LangRef.md
+++ b/mlir/docs/LangRef.md
@@ -1369,39 +1369,39 @@ Example:
 
 Similarly to operations, dialects may define custom attribute values. The
 syntactic structure of these values is identical to custom dialect type values,
-except that dialect attributes values are distinguished with a leading '#',
-while dialect types are distinguished with a leading '!'.
+except that dialect attribute values are distinguished with a leading '#', 
while
+dialect types are distinguished with a leading '!'.
 
 ```
-dialect-attribute ::= '#' opaque-dialect-item
-dialect-attribute ::= '#' pretty-dialect-item
+dialect-attribute-value ::= '#' opaque-dialect-item
+dialect-attribute-value ::= '#' pretty-dialect-item
 ```
 
-Dialect attributes can be specified in a verbose form, e.g. like this:
+Dialect attribute values can be specified in a verbose form, e.g. like this:
 
 ```mlir
-// Complex attribute
+// Complex attribute value.
 #foo<"something">
 
-// Even more complex attribute
+// Even more complex attribute value.
 #foo<"something>>">
 ```
 
-Dialect attributes that are simple enough can use the pretty format, which is a
-lighter weight syntax that is equivalent to the above forms:
+Dialect attribute values that are simple enough can use the pretty format, 
which
+is a lighter weight syntax that is equivalent to the above forms:
 
 ```mlir
 // Complex attribute
 #foo.something
 ```
 
-Sufficiently complex dialect attributes are required to use the verbose form 
for
-generality. For example, the more complex type shown above wouldn't be valid in
-the lighter syntax: `#foo.something>>` because it contains 
characters
-that are not allowed in the lighter syntax, as well as unbalanced `<>`
-characters.
+Sufficiently complex dialect attribute values are required to use the verbose
+form for generality. For example, the more complex type shown above would not 
be
+valid in the lighter syntax: `#foo.something>>` because it contains
+characters that are not allowed in the lighter syntax, as well as unbalanced
+`<>` characters.
 
-See [here](Tutorials/DefiningAttributesAndTypes.md) to learn how to define 
dialect
+See [here](Tutorials/DefiningAttributesAndTypes.md) on how to define dialect
 attribute values.
 
 ### Standard Attribute Values

diff  --git a/mlir/lib/IR/BuiltinDialect.cpp b/mlir/lib/IR/BuiltinDialect.cpp
index 5c0a0380f9af..8f872ac7c9ab 100644
--- a/mlir/lib/IR/BuiltinDialect.cpp
+++ b/mlir/lib/IR/BuiltinDialect.cpp
@@ -228,9 +228,9 @@ static LogicalResult verify(ModuleOp op) {
 ArrayRef{mlir::SymbolTable::getSymbolAttrName(),
 mlir::SymbolTable::getVisibilityAttrName()},
 attr.first.strref()))
-  return op.emitOpError()
- << "can only contain dialect-specific attributes, found: '"
- << attr.first << "'";
+  return op.emitOpError() << "can only contain attributes with "
+ "dialect-prefixed names, found: '"
+  << attr.first << "'";
   }
 
   return success();

diff  --git a/mlir/test/IR/invalid-module-op.mlir 
b/mlir/test/IR/invalid-module-op.mlir
index 73fe188209d1..520821a7b0b4 100644
--- a/mlir/test/IR/invalid-module-op.mlir
+++ b/mlir/test/IR/invalid-module-op.mlir
@@ -44,7 +44,7 @@ func @module_op() {
 
 // -
 
-// expected-error@+1 {{can only contain dialect-specific attributes}}
+// expected-error@+1 {{can only contain attributes with dialect-prefixed 
names}}
 module attributes {attr} {
 }
 



___
llvm-branch-commits mailing list
llvm-branch-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [mlir] b2391d5 - [MLIR] Normalize the results of normalizable operations

2020-12-03 Thread Uday Bondhugula via llvm-branch-commits

Author: Haruki Imai
Date: 2020-12-03T19:34:07+05:30
New Revision: b2391d5f0da2a9122d337de6fa1a6aa9baad3fb4

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

LOG: [MLIR] Normalize the results of normalizable operations

Memrefs with affine_map in the results of normalizable operation were
not normalized by `--normalize-memrefs` option. This patch normalizes
them.

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

Added: 


Modified: 
mlir/lib/Transforms/NormalizeMemRefs.cpp
mlir/test/Transforms/normalize-memrefs-ops.mlir
mlir/test/lib/Dialect/Test/TestOps.td

Removed: 




diff  --git a/mlir/lib/Transforms/NormalizeMemRefs.cpp 
b/mlir/lib/Transforms/NormalizeMemRefs.cpp
index 44b3ccbd2c3f..d7fa212baa73 100644
--- a/mlir/lib/Transforms/NormalizeMemRefs.cpp
+++ b/mlir/lib/Transforms/NormalizeMemRefs.cpp
@@ -36,6 +36,7 @@ struct NormalizeMemRefs : public 
NormalizeMemRefsBase {
   void updateFunctionSignature(FuncOp funcOp, ModuleOp moduleOp);
   void setCalleesAndCallersNonNormalizable(FuncOp funcOp, ModuleOp moduleOp,
DenseSet 
&normalizableFuncs);
+  Operation *createOpResultsNormalized(FuncOp funcOp, Operation *oldOp);
 };
 
 } // end anonymous namespace
@@ -384,6 +385,59 @@ void NormalizeMemRefs::normalizeFuncOpMemRefs(FuncOp 
funcOp,
 funcOp.front().eraseArgument(argIndex + 1);
   }
 
+  // Walk over normalizable operations to normalize memrefs of the operation
+  // results. When `op` has memrefs with affine map in the operation results,
+  // new operation containin normalized memrefs is created. Then, the memrefs
+  // are replaced. `CallOp` is skipped here because it is handled in
+  // `updateFunctionSignature()`.
+  funcOp.walk([&](Operation *op) {
+if (op->hasTrait() &&
+op->getNumResults() > 0 && !isa(op) && !funcOp.isExternal()) {
+  // Create newOp containing normalized memref in the operation result.
+  Operation *newOp = createOpResultsNormalized(funcOp, op);
+  // When all of the operation results have no memrefs or memrefs without
+  // affine map, `newOp` is the same with `op` and following process is
+  // skipped.
+  if (op != newOp) {
+bool replacingMemRefUsesFailed = false;
+for (unsigned resIndex : llvm::seq(0, op->getNumResults())) {
+  // Replace all uses of the old memrefs.
+  Value oldMemRef = op->getResult(resIndex);
+  Value newMemRef = newOp->getResult(resIndex);
+  MemRefType oldMemRefType = 
oldMemRef.getType().dyn_cast();
+  // Check whether the operation result is MemRef type.
+  if (!oldMemRefType)
+continue;
+  MemRefType newMemRefType = newMemRef.getType().cast();
+  if (oldMemRefType == newMemRefType)
+continue;
+  // TODO: Assume single layout map. Multiple maps not supported.
+  AffineMap layoutMap = oldMemRefType.getAffineMaps().front();
+  if (failed(replaceAllMemRefUsesWith(oldMemRef,
+  /*newMemRef=*/newMemRef,
+  /*extraIndices=*/{},
+  /*indexRemap=*/layoutMap,
+  /*extraOperands=*/{},
+  /*symbolOperands=*/{},
+  /*domInstFilter=*/nullptr,
+  /*postDomInstFilter=*/nullptr,
+  /*allowDereferencingOps=*/true,
+  /*replaceInDeallocOp=*/true))) {
+newOp->erase();
+replacingMemRefUsesFailed = true;
+continue;
+  }
+}
+if (!replacingMemRefUsesFailed) {
+  // Replace other ops with new op and delete the old op when the
+  // replacement succeeded.
+  op->replaceAllUsesWith(newOp);
+  op->erase();
+}
+  }
+}
+  });
+
   // In a normal function, memrefs in the return type signature gets normalized
   // as a result of normalization of functions arguments, AllocOps or CallOps'
   // result types. Since an external function doesn't have a body, memrefs in
@@ -417,3 +471,49 @@ void NormalizeMemRefs::normalizeFuncOpMemRefs(FuncOp 
funcOp,
   }
   updateFunctionSignature(funcOp, moduleOp);
 }
+
+/// Create an operation containing normalized memrefs in the operation results.
+/// When the results of `oldOp` have memrefs with affine map, the memrefs are
+/// normalized, and new operation containing them in the operation results is
+/// returned. If all of the results of `oldOp` have no memrefs or memrefs
+/// without affine map, `ol

[llvm-branch-commits] [mlir] dc930e5 - [MLIR][Affine] Add affine.for normalization support

2020-12-07 Thread Uday Bondhugula via llvm-branch-commits

Author: Navdeep Kumar
Date: 2020-12-07T22:04:07+05:30
New Revision: dc930e5f2f91e7eb5ebc9cb61f6a71bc8924559e

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

LOG: [MLIR][Affine] Add affine.for normalization support

Add support to normalize affine.for ops i.e., convert the lower bound to zero
and loop step to one. The Upper bound is set to the trip count of the loop.
The exact value of loopIV is calculated just inside the body of affine.for.
Currently loops with lower bounds having single result are supported. No such
restriction exists on upper bounds.

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

Added: 


Modified: 
mlir/lib/Dialect/Affine/Transforms/AffineLoopNormalize.cpp
mlir/test/Dialect/Affine/affine-loop-normalize.mlir

Removed: 




diff  --git a/mlir/lib/Dialect/Affine/Transforms/AffineLoopNormalize.cpp 
b/mlir/lib/Dialect/Affine/Transforms/AffineLoopNormalize.cpp
index 2ad403e73f72..d863663f86bd 100644
--- a/mlir/lib/Dialect/Affine/Transforms/AffineLoopNormalize.cpp
+++ b/mlir/lib/Dialect/Affine/Transforms/AffineLoopNormalize.cpp
@@ -79,14 +79,104 @@ void mlir::normalizeAffineParallel(AffineParallelOp op) {
   op.setUpperBounds(ranges.getOperands(), newUpperMap);
 }
 
-/// Normalization transformations for affine.for ops. For now, it only removes
-/// single iteration loops. We may want to consider separating redundant loop
-/// elimitation from loop bound normalization, if needed in the future.
+/// Normalizes affine.for ops. If the affine.for op has only a single iteration
+/// only then it is simply promoted, else it is normalized in the traditional
+/// way, by converting the lower bound to zero and loop step to one. The upper
+/// bound is set to the trip count of the loop. For now, original loops must
+/// have lower bound with a single result only. There is no such restriction on
+/// upper bounds.
 static void normalizeAffineFor(AffineForOp op) {
   if (succeeded(promoteIfSingleIteration(op)))
 return;
 
-  // TODO: Normalize loop bounds.
+  // Check if the forop is already normalized.
+  if (op.hasConstantLowerBound() && (op.getConstantLowerBound() == 0) &&
+  (op.getStep() == 1))
+return;
+
+  // Check if the lower bound has a single result only. Loops with a max lower
+  // bound can't be normalized without additional support like
+  // affine.execute_region's. If the lower bound does not have a single result
+  // then skip this op.
+  if (op.getLowerBoundMap().getNumResults() != 1)
+return;
+
+  Location loc = op.getLoc();
+  OpBuilder opBuilder(op);
+  int64_t origLoopStep = op.getStep();
+
+  // Calculate upperBound for normalized loop.
+  SmallVector ubOperands;
+  AffineBound lb = op.getLowerBound();
+  AffineBound ub = op.getUpperBound();
+  ubOperands.reserve(ub.getNumOperands() + lb.getNumOperands());
+  AffineMap origLbMap = lb.getMap();
+  AffineMap origUbMap = ub.getMap();
+
+  // Add dimension operands from upper/lower bound.
+  for (unsigned j = 0, e = origUbMap.getNumDims(); j < e; ++j)
+ubOperands.push_back(ub.getOperand(j));
+  for (unsigned j = 0, e = origLbMap.getNumDims(); j < e; ++j)
+ubOperands.push_back(lb.getOperand(j));
+
+  // Add symbol operands from upper/lower bound.
+  for (unsigned j = 0, e = origUbMap.getNumSymbols(); j < e; ++j)
+ubOperands.push_back(ub.getOperand(origUbMap.getNumDims() + j));
+  for (unsigned j = 0, e = origLbMap.getNumSymbols(); j < e; ++j)
+ubOperands.push_back(lb.getOperand(origLbMap.getNumDims() + j));
+
+  // Add original result expressions from lower/upper bound map.
+  SmallVector origLbExprs(origLbMap.getResults().begin(),
+ origLbMap.getResults().end());
+  SmallVector origUbExprs(origUbMap.getResults().begin(),
+ origUbMap.getResults().end());
+  SmallVector newUbExprs;
+
+  // The original upperBound can have more than one result. For the new
+  // upperBound of this loop, take 
diff erence of all possible combinations of
+  // the ub results and lb result and ceildiv with the loop step. For e.g.,
+  //
+  //  affine.for %i1 = 0 to min affine_map<(d0)[] -> (d0 + 32, 1024)>(%i0)
+  //  will have an upperBound map as,
+  //  affine_map<(d0)[] -> (((d0 + 32) - 0) ceildiv 1, (1024 - 0) ceildiv
+  //  1)>(%i0)
+  //
+  // Insert all combinations of upper/lower bound results.
+  for (unsigned i = 0, e = origUbExprs.size(); i < e; ++i) {
+newUbExprs.push_back(
+(origUbExprs[i] - origLbExprs[0]).ceilDiv(origLoopStep));
+  }
+
+  // Construct newUbMap.
+  AffineMap newUbMap =
+  AffineMap::get(origLbMap.getNumDims() + origUbMap.getNumDims(),
+ origLbMap.getNumSymbols() + origUbMap.getNumSymbols(),
+ newUbExprs, opBuilder.g