[Mlir-commits] [mlir] [mlir][OpPrintingFlags] Allow to disable ElementsAttr hex printing (PR #85766)

Andrei Golubev llvmlistbot at llvm.org
Wed Mar 20 04:45:33 PDT 2024


https://github.com/andrey-golubev updated https://github.com/llvm/llvm-project/pull/85766

>From 095619831593e48d3f8afe9c5011836071d6019e Mon Sep 17 00:00:00 2001
From: "Golubev, Andrey" <andrey.golubev at intel.com>
Date: Tue, 19 Mar 2024 09:39:28 +0000
Subject: [PATCH 1/2] [mlir][OpPrintingFlags] Allow to disable ElementsAttr hex
 printing

At present, large ElementsAttr is unconditionally printed with a hex
string. This means that in IR large constant values often look like:
dense<"0x000000000004000000080000000004000000080000000..."> : tensor<10x10xi32>

Hoisting hex printing control to the user level for tooling means that one can
disable the feature and get human-readable values when necessary:
dense<[16, 32, 48, 500...]> : tensor<10x10xi32>

Note: AsmPrinterOptions::printElementsAttrWithHexIfLarger is not always
possible to be used as it requires that one exposes MLIR's command-line
options in user tooling (including an actual compiler).

Co-authored-by: Harald Rotuna <harald.razvan.rotuna at intel.com>
---
 mlir/include/mlir/IR/OperationSupport.h | 10 ++++++++++
 mlir/lib/IR/AsmPrinter.cpp              | 25 ++++++++++++++++++++++---
 2 files changed, 32 insertions(+), 3 deletions(-)

diff --git a/mlir/include/mlir/IR/OperationSupport.h b/mlir/include/mlir/IR/OperationSupport.h
index f2aa6cee840308..7d17efa7ce9b5e 100644
--- a/mlir/include/mlir/IR/OperationSupport.h
+++ b/mlir/include/mlir/IR/OperationSupport.h
@@ -1131,6 +1131,10 @@ class OpPrintingFlags {
   /// elements.
   OpPrintingFlags &elideLargeElementsAttrs(int64_t largeElementLimit = 16);
 
+  /// Enable or disable printing of large element attributes as a hex string. By
+  /// default, printing as hex is allowed (enabled).
+  OpPrintingFlags &allowPrintingElementsAttrWithHex(bool allowHex = true);
+
   /// Enables the elision of large resources strings by omitting them from the
   /// `dialect_resources` section. The `largeResourceLimit` is used to configure
   /// what is considered to be a "large" resource by providing an upper limit to
@@ -1164,6 +1168,9 @@ class OpPrintingFlags {
   /// Return if the given ElementsAttr should be elided.
   bool shouldElideElementsAttr(ElementsAttr attr) const;
 
+  /// Return if ElementsAttr could be printed in hexadecimal form.
+  bool shouldAllowPrintingElementsAttrWithHex() const;
+
   /// Return the size limit for printing large ElementsAttr.
   std::optional<int64_t> getLargeElementsAttrLimit() const;
 
@@ -1217,6 +1224,9 @@ class OpPrintingFlags {
 
   /// Print users of values.
   bool printValueUsersFlag : 1;
+
+  /// Print ElementsAttr in hex form.
+  bool allowPrintingElementsAttrWithHexFlag : 1;
 };
 
 //===----------------------------------------------------------------------===//
diff --git a/mlir/lib/IR/AsmPrinter.cpp b/mlir/lib/IR/AsmPrinter.cpp
index 456cf6a2c27783..693977f35110a1 100644
--- a/mlir/lib/IR/AsmPrinter.cpp
+++ b/mlir/lib/IR/AsmPrinter.cpp
@@ -206,12 +206,17 @@ OpPrintingFlags::OpPrintingFlags()
     : printDebugInfoFlag(false), printDebugInfoPrettyFormFlag(false),
       printGenericOpFormFlag(false), skipRegionsFlag(false),
       assumeVerifiedFlag(false), printLocalScope(false),
-      printValueUsersFlag(false) {
+      printValueUsersFlag(false), allowPrintingElementsAttrWithHexFlag(true) {
   // Initialize based upon command line options, if they are available.
   if (!clOptions.isConstructed())
     return;
   if (clOptions->elideElementsAttrIfLarger.getNumOccurrences())
     elementsAttrElementLimit = clOptions->elideElementsAttrIfLarger;
+  if (clOptions->printElementsAttrWithHexIfLarger.getNumOccurrences()) {
+    // Note: -1 disables the "print with hex string" feature
+    allowPrintingElementsAttrWithHexFlag =
+        (clOptions->printElementsAttrWithHexIfLarger.getValue() != -1);
+  }
   if (clOptions->elideResourceStringsIfLarger.getNumOccurrences())
     resourceStringCharLimit = clOptions->elideResourceStringsIfLarger;
   printDebugInfoFlag = clOptions->printDebugInfoOpt;
@@ -233,6 +238,12 @@ OpPrintingFlags::elideLargeElementsAttrs(int64_t largeElementLimit) {
   return *this;
 }
 
+OpPrintingFlags &
+OpPrintingFlags::allowPrintingElementsAttrWithHex(bool allowHex) {
+  allowPrintingElementsAttrWithHexFlag = allowHex;
+  return *this;
+}
+
 OpPrintingFlags &
 OpPrintingFlags::elideLargeResourceString(int64_t largeResourceLimit) {
   resourceStringCharLimit = largeResourceLimit;
@@ -287,6 +298,10 @@ bool OpPrintingFlags::shouldElideElementsAttr(ElementsAttr attr) const {
          !llvm::isa<SplatElementsAttr>(attr);
 }
 
+bool OpPrintingFlags::shouldAllowPrintingElementsAttrWithHex() const {
+  return allowPrintingElementsAttrWithHexFlag;
+}
+
 /// Return the size limit for printing large ElementsAttr.
 std::optional<int64_t> OpPrintingFlags::getLargeElementsAttrLimit() const {
   return elementsAttrElementLimit;
@@ -2301,7 +2316,9 @@ void AsmPrinter::Impl::printAttributeImpl(Attribute attr,
       printElidedElementsAttr(os);
     } else {
       os << "dense<";
-      printDenseIntOrFPElementsAttr(intOrFpEltAttr, /*allowHex=*/true);
+      printDenseIntOrFPElementsAttr(
+          intOrFpEltAttr,
+          printerFlags.shouldAllowPrintingElementsAttrWithHex());
       os << '>';
     }
 
@@ -2324,7 +2341,9 @@ void AsmPrinter::Impl::printAttributeImpl(Attribute attr,
       if (indices.getNumElements() != 0) {
         printDenseIntOrFPElementsAttr(indices, /*allowHex=*/false);
         os << ", ";
-        printDenseElementsAttr(sparseEltAttr.getValues(), /*allowHex=*/true);
+        printDenseElementsAttr(
+            sparseEltAttr.getValues(),
+            printerFlags.shouldAllowPrintingElementsAttrWithHex());
       }
       os << '>';
     }

>From ffacceb96ed4002f2685c0ea1c75cccbf5cc1211 Mon Sep 17 00:00:00 2001
From: "Golubev, Andrey" <andrey.golubev at intel.com>
Date: Wed, 20 Mar 2024 10:44:24 +0000
Subject: [PATCH 2/2] fixup! [mlir][OpPrintingFlags] Allow to disable
 ElementsAttr hex printing

---
 mlir/include/mlir/IR/OperationSupport.h | 23 +++++++----
 mlir/lib/IR/AsmPrinter.cpp              | 53 +++++++++----------------
 2 files changed, 34 insertions(+), 42 deletions(-)

diff --git a/mlir/include/mlir/IR/OperationSupport.h b/mlir/include/mlir/IR/OperationSupport.h
index 7d17efa7ce9b5e..d79412bc92d1c8 100644
--- a/mlir/include/mlir/IR/OperationSupport.h
+++ b/mlir/include/mlir/IR/OperationSupport.h
@@ -1131,9 +1131,12 @@ class OpPrintingFlags {
   /// elements.
   OpPrintingFlags &elideLargeElementsAttrs(int64_t largeElementLimit = 16);
 
-  /// Enable or disable printing of large element attributes as a hex string. By
-  /// default, printing as hex is allowed (enabled).
-  OpPrintingFlags &allowPrintingElementsAttrWithHex(bool allowHex = true);
+  /// Enables the printing of large element attributes with a hex string. The
+  /// `largeElementLimit` is used to configure what is considered to be a
+  /// "large" ElementsAttr by providing an upper limit to the number of
+  /// elements. Use -1 to disable the hex printing.
+  OpPrintingFlags &
+  printLargeElementsAttrWithHex(int64_t largeElementLimit = 100);
 
   /// Enables the elision of large resources strings by omitting them from the
   /// `dialect_resources` section. The `largeResourceLimit` is used to configure
@@ -1168,12 +1171,15 @@ class OpPrintingFlags {
   /// Return if the given ElementsAttr should be elided.
   bool shouldElideElementsAttr(ElementsAttr attr) const;
 
-  /// Return if ElementsAttr could be printed in hexadecimal form.
-  bool shouldAllowPrintingElementsAttrWithHex() const;
+  /// Return if the given ElementsAttr should be printed as hex string.
+  bool shouldPrintElementsAttrWithHex(ElementsAttr attr) const;
 
   /// Return the size limit for printing large ElementsAttr.
   std::optional<int64_t> getLargeElementsAttrLimit() const;
 
+  /// Return the size limit for printing large ElementsAttr as hex string.
+  int64_t getLargeElementsAttrHexLimit() const;
+
   /// Return the size limit in chars for printing large resources.
   std::optional<uint64_t> getLargeResourceStringLimit() const;
 
@@ -1206,6 +1212,10 @@ class OpPrintingFlags {
   /// Elide printing large resources based on size of string.
   std::optional<uint64_t> resourceStringCharLimit;
 
+  /// Print large element attributes with hex strings if the number of elements
+  /// is larger than the upper limit.
+  int64_t elementsAttrHexElementLimit = 100;
+
   /// Print debug information.
   bool printDebugInfoFlag : 1;
   bool printDebugInfoPrettyFormFlag : 1;
@@ -1224,9 +1234,6 @@ class OpPrintingFlags {
 
   /// Print users of values.
   bool printValueUsersFlag : 1;
-
-  /// Print ElementsAttr in hex form.
-  bool allowPrintingElementsAttrWithHexFlag : 1;
 };
 
 //===----------------------------------------------------------------------===//
diff --git a/mlir/lib/IR/AsmPrinter.cpp b/mlir/lib/IR/AsmPrinter.cpp
index 693977f35110a1..0bbaf30abef5c5 100644
--- a/mlir/lib/IR/AsmPrinter.cpp
+++ b/mlir/lib/IR/AsmPrinter.cpp
@@ -206,16 +206,15 @@ OpPrintingFlags::OpPrintingFlags()
     : printDebugInfoFlag(false), printDebugInfoPrettyFormFlag(false),
       printGenericOpFormFlag(false), skipRegionsFlag(false),
       assumeVerifiedFlag(false), printLocalScope(false),
-      printValueUsersFlag(false), allowPrintingElementsAttrWithHexFlag(true) {
+      printValueUsersFlag(false) {
   // Initialize based upon command line options, if they are available.
   if (!clOptions.isConstructed())
     return;
   if (clOptions->elideElementsAttrIfLarger.getNumOccurrences())
     elementsAttrElementLimit = clOptions->elideElementsAttrIfLarger;
   if (clOptions->printElementsAttrWithHexIfLarger.getNumOccurrences()) {
-    // Note: -1 disables the "print with hex string" feature
-    allowPrintingElementsAttrWithHexFlag =
-        (clOptions->printElementsAttrWithHexIfLarger.getValue() != -1);
+    elementsAttrHexElementLimit =
+        clOptions->printElementsAttrWithHexIfLarger.getValue();
   }
   if (clOptions->elideResourceStringsIfLarger.getNumOccurrences())
     resourceStringCharLimit = clOptions->elideResourceStringsIfLarger;
@@ -239,8 +238,8 @@ OpPrintingFlags::elideLargeElementsAttrs(int64_t largeElementLimit) {
 }
 
 OpPrintingFlags &
-OpPrintingFlags::allowPrintingElementsAttrWithHex(bool allowHex) {
-  allowPrintingElementsAttrWithHexFlag = allowHex;
+OpPrintingFlags::printLargeElementsAttrWithHex(int64_t largeElementLimit) {
+  elementsAttrHexElementLimit = largeElementLimit;
   return *this;
 }
 
@@ -298,8 +297,12 @@ bool OpPrintingFlags::shouldElideElementsAttr(ElementsAttr attr) const {
          !llvm::isa<SplatElementsAttr>(attr);
 }
 
-bool OpPrintingFlags::shouldAllowPrintingElementsAttrWithHex() const {
-  return allowPrintingElementsAttrWithHexFlag;
+/// Return if the given ElementsAttr should be printed as hex string.
+bool OpPrintingFlags::shouldPrintElementsAttrWithHex(ElementsAttr attr) const {
+  // -1 is used to disable hex printing.
+  return (elementsAttrHexElementLimit != -1) &&
+         (elementsAttrHexElementLimit < int64_t(attr.getNumElements())) &&
+         !llvm::isa<SplatElementsAttr>(attr);
 }
 
 /// Return the size limit for printing large ElementsAttr.
@@ -307,6 +310,11 @@ std::optional<int64_t> OpPrintingFlags::getLargeElementsAttrLimit() const {
   return elementsAttrElementLimit;
 }
 
+/// Return the size limit for printing large ElementsAttr as hex string.
+int64_t OpPrintingFlags::getLargeElementsAttrHexLimit() const {
+  return elementsAttrHexElementLimit;
+}
+
 /// Return the size limit for printing large ElementsAttr.
 std::optional<uint64_t> OpPrintingFlags::getLargeResourceStringLimit() const {
   return resourceStringCharLimit;
@@ -343,23 +351,6 @@ bool OpPrintingFlags::shouldPrintValueUsers() const {
   return printValueUsersFlag;
 }
 
-/// Returns true if an ElementsAttr with the given number of elements should be
-/// printed with hex.
-static bool shouldPrintElementsAttrWithHex(int64_t numElements) {
-  // Check to see if a command line option was provided for the limit.
-  if (clOptions.isConstructed()) {
-    if (clOptions->printElementsAttrWithHexIfLarger.getNumOccurrences()) {
-      // -1 is used to disable hex printing.
-      if (clOptions->printElementsAttrWithHexIfLarger == -1)
-        return false;
-      return numElements > clOptions->printElementsAttrWithHexIfLarger;
-    }
-  }
-
-  // Otherwise, default to printing with hex if the number of elements is >100.
-  return numElements > 100;
-}
-
 //===----------------------------------------------------------------------===//
 // NewLineCounter
 //===----------------------------------------------------------------------===//
@@ -2316,9 +2307,7 @@ void AsmPrinter::Impl::printAttributeImpl(Attribute attr,
       printElidedElementsAttr(os);
     } else {
       os << "dense<";
-      printDenseIntOrFPElementsAttr(
-          intOrFpEltAttr,
-          printerFlags.shouldAllowPrintingElementsAttrWithHex());
+      printDenseIntOrFPElementsAttr(intOrFpEltAttr, /*allowHex=*/true);
       os << '>';
     }
 
@@ -2341,9 +2330,7 @@ void AsmPrinter::Impl::printAttributeImpl(Attribute attr,
       if (indices.getNumElements() != 0) {
         printDenseIntOrFPElementsAttr(indices, /*allowHex=*/false);
         os << ", ";
-        printDenseElementsAttr(
-            sparseEltAttr.getValues(),
-            printerFlags.shouldAllowPrintingElementsAttrWithHex());
+        printDenseElementsAttr(sparseEltAttr.getValues(), /*allowHex=*/true);
       }
       os << '>';
     }
@@ -2454,9 +2441,7 @@ void AsmPrinter::Impl::printDenseIntOrFPElementsAttr(
   auto elementType = type.getElementType();
 
   // Check to see if we should format this attribute as a hex string.
-  auto numElements = type.getNumElements();
-  if (!attr.isSplat() && allowHex &&
-      shouldPrintElementsAttrWithHex(numElements)) {
+  if (allowHex && printerFlags.shouldPrintElementsAttrWithHex(attr)) {
     ArrayRef<char> rawData = attr.getRawData();
     if (llvm::endianness::native == llvm::endianness::big) {
       // Convert endianess in big-endian(BE) machines. `rawData` is BE in BE



More information about the Mlir-commits mailing list