[Mlir-commits] [mlir] [mlir][tblgen] Migrate tests to properties for attributes, fix remove*Attr() (PR #123505)

Krzysztof Drewniak llvmlistbot at llvm.org
Sun Jan 19 00:37:12 PST 2025


https://github.com/krzysz00 created https://github.com/llvm/llvm-project/pull/123505

The only in-tree user of `bit usePropertiesForAttributes = 0;` was a series of tests for the output of -gen-op-{decls,defs}. This commit updates those tests to match the rest of the repository.

In the short term, this is intended to enable testing upcoming updates to collective builders. In the long term, this is a step in the removal of usePropertiesForAttributes = 0.

One side effect of these tests updates was the realization that the autogenerated implementations of removeFooAttr() were not returning the value of the removed attribute. This issue has been addressed and the tests have been updated to reflect the change. This is the only functionality change in this PR.

>From 14a07e9e8ae507b879ec0d7a2f01f8f8b029e942 Mon Sep 17 00:00:00 2001
From: Krzysztof Drewniak <krzysdrewniak at gmail.com>
Date: Sun, 19 Jan 2025 00:31:07 -0800
Subject: [PATCH] [mlir][tblgen] Migrate tests to properties for attributes,
 fix remove*Attr()

The only in-tree user of `bit usePropertiesForAttributes = 0;` was a series
of tests for the output of -gen-op-{decls,defs}. This commit updates those
tests to match the rest of the repository.

In the short term, this is intended to enable testing upcoming updates to
collective builders. In the long term, this is a step in the removal of
usePropertiesForAttributes = 0.

One side effect of these tests updates was the realization that the
autogenerated implementations of removeFooAttr() were not returning
the value of the removed attribute. This issue has been addressed and
the tests have been updated to reflect the change. This is the only
functionality change in this PR.
---
 mlir/test/mlir-tblgen/constraint-unique.td  |   9 +-
 mlir/test/mlir-tblgen/op-attribute.td       | 122 +++++++++-----------
 mlir/test/mlir-tblgen/op-decl-and-defs.td   |  21 ++--
 mlir/test/mlir-tblgen/op-format.td          |   3 +-
 mlir/test/mlir-tblgen/op-result.td          |   3 +-
 mlir/tools/mlir-tblgen/OpDefinitionsGen.cpp |   4 +-
 6 files changed, 75 insertions(+), 87 deletions(-)

diff --git a/mlir/test/mlir-tblgen/constraint-unique.td b/mlir/test/mlir-tblgen/constraint-unique.td
index 214cd6cc8e550c..d51e1a5f43ee75 100644
--- a/mlir/test/mlir-tblgen/constraint-unique.td
+++ b/mlir/test/mlir-tblgen/constraint-unique.td
@@ -4,7 +4,6 @@ include "mlir/IR/OpBase.td"
 
 def Test_Dialect : Dialect {
   let name = "test";
-  let usePropertiesForAttributes = 0;
 }
 
 class NS_Op<string mnemonic, list<Trait> traits = []> :
@@ -117,8 +116,8 @@ def OpC : NS_Op<"op_c"> {
 // CHECK-NEXT:       << "failed to verify constraint: another region";
 
 /// Test that the uniqued constraints are being used.
-// CHECK-LABEL: OpA::verify
-// CHECK:         ::mlir::Attribute [[$B_ATTR:.*b]];
+// CHECK-LABEL: OpA::verifyInvariantsImpl
+// CHECK:         auto [[$B_ATTR:.*b]] = getProperties().b;
 // CHECK:         if (::mlir::failed([[$A_ATTR_CONSTRAINT]](*this, [[$B_ATTR]], "b")))
 // CHECK-NEXT:      return ::mlir::failure();
 // CHECK:         auto [[$A_VALUE_GROUP:.*]] = getODSOperands(0);
@@ -138,8 +137,8 @@ def OpC : NS_Op<"op_c"> {
 
 /// Test that the op with the same predicates but different with descriptions
 /// uses the different constraints.
-// CHECK-LABEL: OpC::verify
-// CHECK:         ::mlir::Attribute [[$B_ATTR:.*b]];
+// CHECK-LABEL: OpC::verifyInvariantsImpl
+// CHECK:         auto [[$B_ATTR:.*b]] = getProperties().b;
 // CHECK:         if (::mlir::failed([[$O_ATTR_CONSTRAINT]](*this, [[$B_ATTR]], "b")))
 // CHECK-NEXT:      return ::mlir::failure();
 // CHECK:         auto [[$A_VALUE_GROUP:.*]] = getODSOperands(0);
diff --git a/mlir/test/mlir-tblgen/op-attribute.td b/mlir/test/mlir-tblgen/op-attribute.td
index a82cd2eadcaed9..55382a5bd3f8c8 100644
--- a/mlir/test/mlir-tblgen/op-attribute.td
+++ b/mlir/test/mlir-tblgen/op-attribute.td
@@ -9,7 +9,6 @@ include "mlir/IR/OpBase.td"
 def Test_Dialect : Dialect {
   let name = "test";
   let cppNamespace = "foobar";
-  let usePropertiesForAttributes = 0;
 }
 class NS_Op<string mnemonic, list<Trait> traits> :
     Op<Test_Dialect, mnemonic, traits>;
@@ -69,23 +68,12 @@ def AOp : NS_Op<"a_op", []> {
 // ---
 
 // DEF:      ::llvm::LogicalResult AOpAdaptor::verify
-// DEF:      ::mlir::Attribute tblgen_aAttr;
-// DEF: while (true) {
-// DEF-NEXT:   if (namedAttrIt == namedAttrRange.end())
-// DEF-NEXT:     return emitError(loc, "'test.a_op' op ""requires attribute 'aAttr'");
-// DEF-NEXT:   if (namedAttrIt->getName() == AOp::getAAttrAttrName(*odsOpName)) {
-// DEF-NEXT:     tblgen_aAttr = namedAttrIt->getValue();
-// DEF-NEXT:     break;
-// DEF:      ::mlir::Attribute tblgen_bAttr;
-// DEF-NEXT: ::mlir::Attribute tblgen_cAttr;
-// DEF-NEXT: ::mlir::Attribute tblgen_dAttr;
-// DEF-NEXT: while (true) {
-// DEF-NEXT:   if (namedAttrIt == namedAttrRange.end())
-// DEF-NEXT:     break;
-// DEF:        if (namedAttrIt->getName() == AOp::getBAttrAttrName(*odsOpName))
-// DEF-NEXT:     tblgen_bAttr = namedAttrIt->getValue();
-// DEF:        if (namedAttrIt->getName() == AOp::getCAttrAttrName(*odsOpName))
-// DEF-NEXT:     tblgen_cAttr = namedAttrIt->getValue();
+// DEF-NEXT: auto tblgen_aAttr = getProperties().aAttr; (void)tblgen_aAttr;
+// DEF-NEXT: if (!tblgen_aAttr) return emitError(loc, "'test.a_op' op ""requires attribute 'aAttr'");
+// DEF-NEXT: auto tblgen_bAttr = getProperties().bAttr; (void)tblgen_bAttr;
+// DEF-NEXT: auto tblgen_cAttr = getProperties().cAttr; (void)tblgen_cAttr;
+// DEF-NEXT: auto tblgen_dAttr = getProperties().dAttr; (void)tblgen_dAttr;
+
 // DEF:      if (tblgen_aAttr && !((some-condition)))
 // DEF-NEXT:   return emitError(loc, "'test.a_op' op ""attribute 'aAttr' failed to satisfy constraint: some attribute kind");
 // DEF:      if (tblgen_bAttr && !((some-condition)))
@@ -99,25 +87,25 @@ def AOp : NS_Op<"a_op", []> {
 // ---
 
 // DECL:      some-attr-kind getAAttrAttr()
-// DECL-NEXT:   ::llvm::cast<some-attr-kind>(::mlir::impl::getAttrFromSortedRange((*this)->getAttrs().begin() + 0, (*this)->getAttrs().end() - 0, getAAttrAttrName()))
+// DECL-NEXT:   ::llvm::cast<some-attr-kind>(getProperties().aAttr)
 // DEF:      some-return-type AOp::getAAttr() {
 // DEF-NEXT:   auto attr = getAAttrAttr()
 // DEF-NEXT:   return attr.some-convert-from-storage();
 
 // DECL:      some-attr-kind getBAttrAttr()
-// DECL-NEXT:   ::llvm::dyn_cast_or_null<some-attr-kind>(::mlir::impl::getAttrFromSortedRange((*this)->getAttrs().begin() + 1, (*this)->getAttrs().end() - 0, getBAttrAttrName()))
+// DECL-NEXT:   ::llvm::dyn_cast_or_null<some-attr-kind>(getProperties().bAttr)
 // DEF:      some-return-type AOp::getBAttr() {
 // DEF-NEXT:   auto attr = getBAttrAttr();
 // DEF-NEXT:   return attr.some-convert-from-storage();
 
 // DECL:      some-attr-kind getCAttrAttr()
-// DECL-NEXT:   ::llvm::dyn_cast_or_null<some-attr-kind>(::mlir::impl::getAttrFromSortedRange((*this)->getAttrs().begin() + 1, (*this)->getAttrs().end() - 0, getCAttrAttrName()))
+// DECL-NEXT:   ::llvm::dyn_cast_or_null<some-attr-kind>(getProperties().cAttr)
 // DEF:      ::std::optional<some-return-type> AOp::getCAttr() {
 // DEF-NEXT:   auto attr = getCAttrAttr()
 // DEF-NEXT:   return attr ? ::std::optional<some-return-type>(attr.some-convert-from-storage()) : (::std::nullopt);
 
 // DECL:      some-attr-kind getDAttrAttr()
-// DECL-NEXT:   ::llvm::dyn_cast_or_null<some-attr-kind>(::mlir::impl::getAttrFromSortedRange((*this)->getAttrs().begin() + 1, (*this)->getAttrs().end() - 0, getDAttrAttrName()))
+// DECL-NEXT:   ::llvm::dyn_cast_or_null<some-attr-kind>(getProperties().dAttr)
 // DEF:      some-return-type AOp::getDAttr() {
 // DEF-NEXT:   auto attr = getDAttrAttr();
 // DEF-NEXT:   if (!attr)
@@ -128,59 +116,62 @@ def AOp : NS_Op<"a_op", []> {
 // ---
 
 // DECL:      void setAAttrAttr(some-attr-kind attr) {
-// DECL-NEXT:   (*this)->setAttr(getAAttrAttrName(), attr);
+// DECL-NEXT:   getProperties().aAttr = attr;
 // DEF:      void AOp::setAAttr(some-return-type attrValue) {
-// DEF-NEXT:   (*this)->setAttr(getAAttrAttrName(), some-const-builder-call(::mlir::Builder((*this)->getContext()), attrValue));
+// DEF-NEXT:   getProperties().aAttr = some-const-builder-call(::mlir::Builder((*this)->getContext()), attrValue);
 // DECL:      void setBAttrAttr(some-attr-kind attr) {
-// DECL-NEXT:   (*this)->setAttr(getBAttrAttrName(), attr);
+// DECL-NEXT:   getProperties().bAttr = attr;
 // DEF:      void AOp::setBAttr(some-return-type attrValue) {
-// DEF-NEXT:   (*this)->setAttr(getBAttrAttrName(), some-const-builder-call(::mlir::Builder((*this)->getContext()), attrValue));
+// DEF-NEXT:   getProperties().bAttr = some-const-builder-call(::mlir::Builder((*this)->getContext()), attrValue);
 // DECL:      void setCAttrAttr(some-attr-kind attr) {
-// DECL-NEXT:   (*this)->setAttr(getCAttrAttrName(), attr);
+// DECL-NEXT:   getProperties().cAttr = attr;
 // DEF:      void AOp::setCAttr(::std::optional<some-return-type> attrValue) {
+// DEF-NEXT:   auto &odsProp = getProperties().cAttr;
 // DEF-NEXT:   if (attrValue)
-// DEF-NEXT:     return (*this)->setAttr(getCAttrAttrName(), some-const-builder-call(::mlir::Builder((*this)->getContext()), *attrValue));
-// DEF-NEXT:   (*this)->removeAttr(getCAttrAttrName());
+// DEF-NEXT:     odsProp = some-const-builder-call(::mlir::Builder((*this)->getContext()), *attrValue);
+// DEF-NEXT:   else
+// DEF-NEXT:     odsProp = nullptr;
 
 // Test remove methods
 // ---
 
 // DECL: ::mlir::Attribute removeCAttrAttr() {
-// DECL-NEXT: return (*this)->removeAttr(getCAttrAttrName());
+// DECL-NEXT: auto attr = getProperties().cAttr;
+// DECL-NEXT: getProperties().cAttr = {};
+// DECL-NEXT: return attr;
 
 // Test build methods
 // ---
 
 // DEF:      void AOp::build(
-// DEF:        odsState.addAttribute(getAAttrAttrName(odsState.name), aAttr);
-// DEF:        odsState.addAttribute(getBAttrAttrName(odsState.name), bAttr);
+// DEF:        odsState.getOrAddProperties<Properties>().aAttr = aAttr;
+// DEF:        odsState.getOrAddProperties<Properties>().bAttr = bAttr;
 // DEF:        if (cAttr) {
-// DEF-NEXT:     odsState.addAttribute(getCAttrAttrName(odsState.name), cAttr);
+// DEF-NEXT:     odsState.getOrAddProperties<Properties>().cAttr = cAttr;
 
-// DEF:        odsState.addAttribute(getAAttrAttrName(odsState.name), some-const-builder-call(odsBuilder, aAttr));
-// DEF-NEXT:   odsState.addAttribute(getBAttrAttrName(odsState.name), some-const-builder-call(odsBuilder, bAttr));
+// DEF:        odsState.getOrAddProperties<Properties>().aAttr = some-const-builder-call(odsBuilder, aAttr);
+// DEF-NEXT:   odsState.getOrAddProperties<Properties>().bAttr = some-const-builder-call(odsBuilder, bAttr);
 // DEF-NEXT:   if (cAttr) {
-// DEF-NEXT:   odsState.addAttribute(getCAttrAttrName(odsState.name), cAttr);
+// DEF-NEXT:   odsState.getOrAddProperties<Properties>().cAttr = cAttr;
 // DEF-NEXT:   }
 // DEF-NOT:    if (dAttr)
-// DEF:        odsState.addAttribute(getDAttrAttrName(odsState.name), some-const-builder-call(odsBuilder, dAttr));
+// DEF:        odsState.getOrAddProperties<Properties>().dAttr = some-const-builder-call(odsBuilder, dAttr);
 
 // DEF:      void AOp::build(
 // DEF:        some-return-type aAttr, some-return-type bAttr, /*optional*/some-attr-kind cAttr
-// DEF:        odsState.addAttribute(getAAttrAttrName(odsState.name), some-const-builder-call(odsBuilder, aAttr));
+// DEF:        odsState.getOrAddProperties<Properties>().aAttr = some-const-builder-call(odsBuilder, aAttr);
 
 // DEF:      void AOp::build(
 // DEF:        ::llvm::ArrayRef<::mlir::NamedAttribute> attributes
 // DEF:      odsState.addAttributes(attributes);
 
-// DEF:      void AOp::populateDefaultAttrs
+// DEF:      void AOp::populateDefaultProperties
 
 // Test the above but with prefix.
 
 def Test2_Dialect : Dialect {
   let name = "test2";
   let cppNamespace = "foobar2";
-  let usePropertiesForAttributes = 0;
 }
 def AgetOp : Op<Test2_Dialect, "a_get_op", []> {
   let arguments = (ins
@@ -221,13 +212,10 @@ def AgetOp : Op<Test2_Dialect, "a_get_op", []> {
 // ---
 
 // DEF:      ::llvm::LogicalResult AgetOpAdaptor::verify
-// DEF:      ::mlir::Attribute tblgen_aAttr;
-// DEF: while (true)
-// DEF:      ::mlir::Attribute tblgen_bAttr;
-// DEF-NEXT: ::mlir::Attribute tblgen_cAttr;
-// DEF: while (true)
-// DEF:      if (tblgen_aAttr && !((some-condition)))
-// DEF-NEXT:   return emitError(loc, "'test2.a_get_op' op ""attribute 'aAttr' failed to satisfy constraint: some attribute kind");
+// DEF: auto tblgen_aAttr = getProperties().aAttr; (void)tblgen_aAttr;
+// DEF: if (!tblgen_aAttr) return emitError(loc, "'test2.a_get_op' op ""requires attribute 'aAttr'");
+// DEF: auto tblgen_bAttr = getProperties().bAttr; (void)tblgen_bAttr;
+// DEF: auto tblgen_cAttr = getProperties().cAttr; (void)tblgen_cAttr;
 // DEF:      if (tblgen_bAttr && !((some-condition)))
 // DEF-NEXT:   return emitError(loc, "'test2.a_get_op' op ""attribute 'bAttr' failed to satisfy constraint: some attribute kind");
 // DEF:      if (tblgen_cAttr && !((some-condition)))
@@ -237,13 +225,13 @@ def AgetOp : Op<Test2_Dialect, "a_get_op", []> {
 // ---
 
 // DECL:      some-attr-kind getAAttrAttr()
-// DECL-NEXT:   ::llvm::cast<some-attr-kind>(::mlir::impl::getAttrFromSortedRange({{.*}}))
+// DECL-NEXT:   ::llvm::cast<some-attr-kind>(getProperties().aAttr)
 // DEF:      some-return-type AgetOp::getAAttr() {
 // DEF-NEXT:   auto attr = getAAttrAttr()
 // DEF-NEXT:   return attr.some-convert-from-storage();
 
 // DECL:      some-attr-kind getBAttrAttr()
-// DECL-NEXT:   return ::llvm::dyn_cast_or_null<some-attr-kind>(::mlir::impl::getAttrFromSortedRange({{.*}}))
+// DECL-NEXT:   return ::llvm::dyn_cast_or_null<some-attr-kind>(getProperties().bAttr)
 // DEF:      some-return-type AgetOp::getBAttr() {
 // DEF-NEXT:   auto attr = getBAttrAttr();
 // DEF-NEXT:   if (!attr)
@@ -251,7 +239,7 @@ def AgetOp : Op<Test2_Dialect, "a_get_op", []> {
 // DEF-NEXT:   return attr.some-convert-from-storage();
 
 // DECL:      some-attr-kind getCAttrAttr()
-// DECL-NEXT:   return ::llvm::dyn_cast_or_null<some-attr-kind>(::mlir::impl::getAttrFromSortedRange({{.*}}))
+// DECL-NEXT:   return ::llvm::dyn_cast_or_null<some-attr-kind>(getProperties().cAttr)
 // DEF:      ::std::optional<some-return-type> AgetOp::getCAttr() {
 // DEF-NEXT:   auto attr = getCAttrAttr()
 // DEF-NEXT:   return attr ? ::std::optional<some-return-type>(attr.some-convert-from-storage()) : (::std::nullopt);
@@ -260,30 +248,32 @@ def AgetOp : Op<Test2_Dialect, "a_get_op", []> {
 // ---
 
 // DECL:      void setAAttrAttr(some-attr-kind attr) {
-// DECL-NEXT:   (*this)->setAttr(getAAttrAttrName(), attr);
+// DECL-NEXT:   getProperties().aAttr = attr;
 // DECL:      void setBAttrAttr(some-attr-kind attr) {
-// DECL-NEXT:   (*this)->setAttr(getBAttrAttrName(), attr);
+// DECL-NEXT:   getProperties().bAttr = attr;
 // DECL:      void setCAttrAttr(some-attr-kind attr) {
-// DECL-NEXT:   (*this)->setAttr(getCAttrAttrName(), attr);
+// DECL-NEXT:   getProperties().cAttr = attr;
 
 // Test remove methods
 // ---
 
 // DECL: ::mlir::Attribute removeCAttrAttr() {
-// DECL-NEXT: return (*this)->removeAttr(getCAttrAttrName());
+// DECL-NEXT: auto attr = getProperties().cAttr;
+// DECL-NEXT: getProperties().cAttr = {};
+// DECL-NEXT: return attr;
 
 // Test build methods
 // ---
 
 // DEF:      void AgetOp::build(
-// DEF:        odsState.addAttribute(getAAttrAttrName(odsState.name), aAttr);
-// DEF:        odsState.addAttribute(getBAttrAttrName(odsState.name), bAttr);
+// DEF:        odsState.getOrAddProperties<Properties>().aAttr = aAttr;
+// DEF:        odsState.getOrAddProperties<Properties>().bAttr = bAttr;
 // DEF:        if (cAttr) {
-// DEF-NEXT:     odsState.addAttribute(getCAttrAttrName(odsState.name), cAttr);
+// DEF-NEXT:     odsState.getOrAddProperties<Properties>().cAttr = cAttr;
 
 // DEF:      void AgetOp::build(
 // DEF:        some-return-type aAttr, /*optional*/some-return-type bAttr, /*optional*/some-attr-kind cAttr
-// DEF:        odsState.addAttribute(getAAttrAttrName(odsState.name), some-const-builder-call(odsBuilder, aAttr));
+// DEF:        odsState.getOrAddProperties<Properties>().aAttr = some-const-builder-call(odsBuilder, aAttr);
 
 // DEF:      void AgetOp::build(
 // DEF:        ::llvm::ArrayRef<::mlir::NamedAttribute> attributes
@@ -405,8 +395,8 @@ def DOp : NS_Op<"d_op", []> {
 // DECL: static void build({{.*}}, uint32_t i32_attr, ::llvm::APFloat f64_attr, ::llvm::StringRef str_attr, bool bool_attr, ::SomeI32Enum enum_attr, uint32_t dv_i32_attr, ::llvm::APFloat dv_f64_attr, ::llvm::StringRef dv_str_attr = "abc", bool dv_bool_attr = true, ::SomeI32Enum dv_enum_attr = ::SomeI32Enum::case5)
 
 // DEF-LABEL: DOp definitions
-// DEF: odsState.addAttribute(getStrAttrAttrName(odsState.name), odsBuilder.getStringAttr(str_attr));
-// DEF: odsState.addAttribute(getDvStrAttrAttrName(odsState.name), odsBuilder.getStringAttr(dv_str_attr));
+// DEF: odsState.getOrAddProperties<Properties>().str_attr = odsBuilder.getStringAttr(str_attr);
+// DEF: odsState.getOrAddProperties<Properties>().dv_str_attr = odsBuilder.getStringAttr(dv_str_attr);
 
 
 // Test default dictionary attribute.
@@ -420,10 +410,10 @@ def DefaultDictAttrOp : NS_Op<"default_dict_attr_op", []> {
 }
 
 // DEF-LABEL: DefaultDictAttrOp definitions
-// DEF: if (!attributes.get(attrNames[0]))
-// DEF:   attributes.append(attrNames[0], odsBuilder.getDictionaryAttr({}));
-// DEF: if (!attributes.get(attrNames[1]))
-// DEF:   attributes.append(attrNames[1], odsBuilder.getDictionaryAttr(getDefaultDictAttrs(odsBuilder)));
+// DEF: if (!properties.empty)
+// DEF:   properties.empty = odsBuilder.getDictionaryAttr({});
+// DEF: if (!properties.non_empty)
+// DEF:   properties.non_empty = odsBuilder.getDictionaryAttr(getDefaultDictAttrs(odsBuilder));
 
 // DECL-LABEL: DefaultDictAttrOp declarations
 // DECL: build(::mlir::OpBuilder &odsBuilder, ::mlir::OperationState &odsState, ::mlir::DictionaryAttr empty = nullptr, ::mlir::DictionaryAttr non_empty = nullptr)
@@ -538,7 +528,9 @@ def UnitAttrOp : NS_Op<"unit_attr_op", []> {
 
 // DECL-LABEL: UnitAttrOp declarations
 // DECL: ::mlir::Attribute removeAttrAttr() {
-// DECL-NEXT:   (*this)->removeAttr(getAttrAttrName());
+// DECL-NEXT:   auto attr = getProperties().attr;
+// DECL-NEXT:   getProperties().attr = {};
+// DECL-NEXT:   return attr;
 // DECL: build(::mlir::OpBuilder &odsBuilder, ::mlir::OperationState &odsState, /*optional*/bool attr = false)
 
 
diff --git a/mlir/test/mlir-tblgen/op-decl-and-defs.td b/mlir/test/mlir-tblgen/op-decl-and-defs.td
index a03d0b40d4655c..ee800a2952bac1 100644
--- a/mlir/test/mlir-tblgen/op-decl-and-defs.td
+++ b/mlir/test/mlir-tblgen/op-decl-and-defs.td
@@ -12,7 +12,6 @@ include "mlir/Interfaces/SideEffectInterfaces.td"
 def Test_Dialect : Dialect {
   let name = "test";
   let cppNamespace = "NS";
-  let usePropertiesForAttributes = 0;
 }
 class NS_Op<string mnemonic, list<Trait> traits> :
     Op<Test_Dialect, mnemonic, traits>;
@@ -58,11 +57,11 @@ def NS_AOp : NS_Op<"a_op", [IsolatedFromAbove, IsolatedFromAbove]> {
 // CHECK: namespace detail {
 // CHECK: class AOpGenericAdaptorBase {
 // CHECK: public:
-// CHECK:   AOpGenericAdaptorBase(::mlir::DictionaryAttr attrs = {}, const ::mlir::EmptyProperties &properties = {}, ::mlir::RegionRange regions = {}) : odsAttrs(attrs), odsRegions(regions)
-// CHECK:   AOpGenericAdaptorBase(::mlir::Operation *op) : odsAttrs(op->getRawDictionaryAttrs()), odsOpName(op->getName()), odsRegions(op->getRegions()) {}
-// CHECK:   ::mlir::IntegerAttr getAttr1Attr();
+// CHECK:   AOpGenericAdaptorBase(::mlir::DictionaryAttr attrs, const Properties &properties, ::mlir::RegionRange regions = {}) : odsAttrs(attrs), properties(properties), odsRegions(regions)
+// CHECK:   AOpGenericAdaptorBase(AOp op);
+// CHECK:   ::mlir::IntegerAttr getAttr1Attr() {
 // CHECK:   uint32_t getAttr1();
-// CHECK:   ::mlir::FloatAttr getSomeAttr2Attr();
+// CHECK:   ::mlir::FloatAttr getSomeAttr2Attr() {
 // CHECK:   ::std::optional< ::llvm::APFloat > getSomeAttr2();
 // CHECK:   ::mlir::Region &getSomeRegion() {
 // CHECK:   ::mlir::RegionRange getSomeRegions() {
@@ -72,8 +71,9 @@ def NS_AOp : NS_Op<"a_op", [IsolatedFromAbove, IsolatedFromAbove]> {
 // CHECK: template <typename RangeT>
 // CHECK: class AOpGenericAdaptor : public detail::AOpGenericAdaptorBase {
 // CHECK: public:
-// CHECK:   AOpGenericAdaptor(RangeT values, ::mlir::DictionaryAttr attrs = {}, const ::mlir::EmptyProperties &properties = {}, ::mlir::RegionRange regions = {}) : Base(attrs, properties, regions), odsOperands(values) {}
-// CHECK:   AOpGenericAdaptor(RangeT values, ::mlir::DictionaryAttr attrs, ::mlir::OpaqueProperties properties, ::mlir::RegionRange regions = {}) : AOpGenericAdaptor(values, attrs, (properties ? *properties.as<::mlir::EmptyProperties *>() : ::mlir::EmptyProperties{}), regions) {}
+// CHECK:   AOpGenericAdaptor(RangeT values, ::mlir::DictionaryAttr attrs, const Properties &properties, ::mlir::RegionRange regions = {}) : Base(attrs, properties, regions), odsOperands(values) {}
+// CHECK:   AOpGenericAdaptor(RangeT values, ::mlir::DictionaryAttr attrs, ::mlir::OpaqueProperties properties, ::mlir::RegionRange regions = {}) : AOpGenericAdaptor(values, attrs, (properties ? *properties.as<Properties *>() : Properties{}), regions) {}
+// CHECK:   AOpGenericAdaptor(RangeT values, ::mlir::DictionaryAttr attrs = nullptr) : AOpGenericAdaptor(values, attrs, Properties{}, {}) {}
 // CHECK:   AOpGenericAdaptor(RangeT values, const AOpGenericAdaptorBase &base) : Base(base), odsOperands(values) {}
 // CHECK:   RangeT getODSOperands(unsigned index) {
 // CHECK:   ValueT getA() {
@@ -88,7 +88,7 @@ def NS_AOp : NS_Op<"a_op", [IsolatedFromAbove, IsolatedFromAbove]> {
 // CHECK:   ::llvm::LogicalResult verify(
 // CHECK: };
 
-// CHECK: class AOp : public ::mlir::Op<AOp, ::mlir::OpTrait::AtLeastNRegions<1>::Impl, ::mlir::OpTrait::AtLeastNResults<1>::Impl, ::mlir::OpTrait::ZeroSuccessors, ::mlir::OpTrait::AtLeastNOperands<1>::Impl, ::mlir::OpTrait::OpInvariants, ::mlir::OpTrait::IsIsolatedFromAbove
+// CHECK: class AOp : public ::mlir::Op<AOp, ::mlir::OpTrait::AtLeastNRegions<1>::Impl, ::mlir::OpTrait::AtLeastNResults<1>::Impl, ::mlir::OpTrait::ZeroSuccessors, ::mlir::OpTrait::AtLeastNOperands<1>::Impl, ::mlir::OpTrait::OpInvariants, ::mlir::BytecodeOpInterface::Trait, ::mlir::OpTrait::IsIsolatedFromAbove
 // CHECK-NOT: ::mlir::OpTrait::IsIsolatedFromAbove
 // CHECK: public:
 // CHECK:   using Op::Op;
@@ -145,13 +145,12 @@ def NS_AttrSizedOperandOp : NS_Op<"attr_sized_operands",
     Variadic<I32>:$a,
     Variadic<I32>:$b,
     I32:$c,
-    Variadic<I32>:$d,
-    I32ElementsAttr:$operandSegmentSizes
+    Variadic<I32>:$d
   );
 }
 
 // CHECK-LABEL: class AttrSizedOperandOpGenericAdaptorBase {
-// CHECK:  ::mlir::DenseIntElementsAttr getOperandSegmentSizes();
+// CHECK: ::llvm::ArrayRef<int32_t> getOperandSegmentSizes() const
 
 // CHECK-LABEL: AttrSizedOperandOpGenericAdaptor(
 // CHECK-SAME:    RangeT values
diff --git a/mlir/test/mlir-tblgen/op-format.td b/mlir/test/mlir-tblgen/op-format.td
index 8af4341952f040..73f9315f6bcfef 100644
--- a/mlir/test/mlir-tblgen/op-format.td
+++ b/mlir/test/mlir-tblgen/op-format.td
@@ -4,7 +4,6 @@ include "mlir/IR/OpBase.td"
 
 def TestDialect : Dialect {
   let name = "test";
-  let usePropertiesForAttributes = 0;
 }
 class TestFormat_Op<string fmt, list<Trait> traits = []>
     : Op<TestDialect, "format_op", traits> {
@@ -70,7 +69,7 @@ def OptionalGroupA : TestFormat_Op<[{
 // CHECK-LABEL: OptionalGroupB::parse
 // CHECK: if (::mlir::succeeded(parser.parseOptionalKeyword("foo")))
 // CHECK-NEXT: else
-// CHECK-NEXT: result.addAttribute("a", parser.getBuilder().getUnitAttr())
+// CHECK-NEXT: result.getOrAddProperties<OptionalGroupB::Properties>().a = parser.getBuilder().getUnitAttr()
 // CHECK: parser.parseKeyword("bar")
 // CHECK-LABEL: OptionalGroupB::print
 // CHECK: if (!(getAAttr() && getAAttr() != ((false) ? ::mlir::OpBuilder((*this)->getContext()).getUnitAttr() : nullptr)))
diff --git a/mlir/test/mlir-tblgen/op-result.td b/mlir/test/mlir-tblgen/op-result.td
index f668d9a5a6644a..212d3189cf571e 100644
--- a/mlir/test/mlir-tblgen/op-result.td
+++ b/mlir/test/mlir-tblgen/op-result.td
@@ -6,7 +6,6 @@ include "mlir/Interfaces/InferTypeOpInterface.td"
 
 def Test_Dialect : Dialect {
   let name = "test";
-  let usePropertiesForAttributes = 0;
 }
 class NS_Op<string mnemonic, list<Trait> traits> :
     Op<Test_Dialect, mnemonic, traits>;
@@ -206,4 +205,4 @@ def OpM : NS_Op<"mix_diff_size_variadic_and_normal_results_op", [AttrSizedResult
 }
 
 // CHECK-LABEL: OpM::build(::mlir::OpBuilder &odsBuilder, ::mlir::OperationState &odsState, ::mlir::TypeRange output1, ::mlir::Type output2, /*optional*/::mlir::Type output3)
-// CHECK: odsState.addAttribute(getResultSegmentSizesAttrName(odsState.name), odsBuilder.getDenseI32ArrayAttr({static_cast<int32_t>(output1.size()), 1, (output3 ? 1 : 0)}));
+// CHECK: ::llvm::copy(::llvm::ArrayRef<int32_t>({static_cast<int32_t>(output1.size()), 1, (output3 ? 1 : 0)}),  odsState.getOrAddProperties<Properties>().resultSegmentSizes.begin());
diff --git a/mlir/tools/mlir-tblgen/OpDefinitionsGen.cpp b/mlir/tools/mlir-tblgen/OpDefinitionsGen.cpp
index a970cbc5cacebe..e3c41c5123ee66 100644
--- a/mlir/tools/mlir-tblgen/OpDefinitionsGen.cpp
+++ b/mlir/tools/mlir-tblgen/OpDefinitionsGen.cpp
@@ -2076,8 +2076,8 @@ void OpEmitter::genOptionalAttrRemovers() {
       return;
     if (useProperties) {
       method->body() << formatv(R"(
-    auto &attr = getProperties().{0};
-    attr = {{};
+    auto attr = getProperties().{0};
+    getProperties().{0} = {{};
     return attr;
 )",
                                 name);



More information about the Mlir-commits mailing list