[Mlir-commits] [mlir] [mlir] Migrate users to explicitly discardable/inherent attribute APIs (PR #217233)
Mehdi Amini
llvmlistbot at llvm.org
Wed Aug 19 01:02:45 PDT 2026
https://github.com/joker-eph created https://github.com/llvm/llvm-project/pull/217233
Start to require explicit handling of discardable attributes. Use operation-specific accessors for attributes stored as properties.
This is both more efficient (no need to materialize the combine dictionnary) and a step in the direction of deprecating these combined APIs.
Assisted-by: Codex
>From c5196f0c3b74db0aed0622ecc7a4521a9293e3d2 Mon Sep 17 00:00:00 2001
From: Mehdi Amini <joker.eph at gmail.com>
Date: Wed, 19 Aug 2026 00:55:40 -0700
Subject: [PATCH] [mlir] Migrate users to explicitly discardable/inherent
attribute APIs
Start to require explicit handling of discardable attributes.
Use operation-specific accessors for attributes stored as properties.
This is both more efficient (no need to materialize the combine dictionnary)
and a step in the direction of deprecating these combined APIs.
Assisted-by: Codex
---
mlir/examples/toy/Ch2/mlir/Dialect.cpp | 6 +-
mlir/examples/toy/Ch3/mlir/Dialect.cpp | 6 +-
mlir/examples/toy/Ch4/mlir/Dialect.cpp | 10 +-
mlir/examples/toy/Ch5/mlir/Dialect.cpp | 10 +-
mlir/examples/toy/Ch6/mlir/Dialect.cpp | 10 +-
mlir/examples/toy/Ch7/mlir/Dialect.cpp | 10 +-
.../ArithCommon/AttrToLLVMConverter.h | 17 ++-
.../mlir/Conversion/LLVMCommon/Pattern.h | 5 +-
.../Conversion/LLVMCommon/VectorPattern.h | 7 +-
.../mlir/Dialect/ArmSME/IR/ArmSMEOps.td | 4 +-
.../include/mlir/Dialect/Async/IR/AsyncOps.td | 4 +-
mlir/include/mlir/Dialect/EmitC/IR/EmitC.td | 4 +-
mlir/include/mlir/Dialect/Func/IR/FuncOps.td | 4 +-
mlir/include/mlir/Dialect/GPU/IR/GPUOps.td | 6 +-
.../LLVMIR/BasicPtxBuilderInterface.td | 17 ++-
.../mlir/Dialect/LLVMIR/LLVMInterfaces.td | 11 ++
mlir/include/mlir/Dialect/LLVMIR/NVVMOps.td | 3 +-
mlir/include/mlir/Dialect/OpenACC/OpenACC.h | 5 +-
.../Interfaces/AtomicInterfaces.td | 9 +-
.../Dialect/OpenMP/OpenMPOpsInterfaces.td | 45 ++++----
.../mlir/Dialect/Shard/Transforms/Simplify.h | 5 +-
.../mlir/Dialect/Tosa/Utils/ConversionUtils.h | 8 +-
mlir/include/mlir/IR/Matchers.h | 13 ++-
mlir/include/mlir/IR/Operation.h | 100 +++++++++++++++---
mlir/include/mlir/IR/SymbolInterfaces.td | 7 +-
mlir/include/mlir/Target/SMTLIB/Namespace.h | 5 +-
mlir/lib/Analysis/CallGraph.cpp | 13 ++-
.../DataFlow/ConstantPropagationAnalysis.cpp | 8 +-
mlir/lib/Bytecode/Writer/BytecodeWriter.cpp | 11 +-
mlir/lib/Bytecode/Writer/IRNumbering.cpp | 12 ++-
mlir/lib/CAPI/Dialect/Linalg.cpp | 5 +-
mlir/lib/CAPI/IR/IR.cpp | 8 +-
.../AMDGPUToROCDL/AMDGPUToROCDL.cpp | 6 +-
.../Conversion/ArithToLLVM/ArithToLLVM.cpp | 8 +-
.../Conversion/ArithToSPIRV/ArithToSPIRV.cpp | 12 ++-
.../ComplexToLLVM/ComplexToLLVM.cpp | 4 +-
.../ControlFlowToLLVM/ControlFlowToLLVM.cpp | 4 +-
.../Conversion/FuncToEmitC/FuncToEmitC.cpp | 21 +++-
mlir/lib/Conversion/FuncToLLVM/FuncToLLVM.cpp | 44 ++++----
.../Conversion/FuncToSPIRV/FuncToSPIRV.cpp | 12 ++-
.../Conversion/GPUCommon/GPUOpsLowering.cpp | 14 +--
.../GPUCommon/IndexIntrinsicsOpLowering.h | 2 +-
.../GPUToNVVM/LowerGpuOpsToNVVMOps.cpp | 4 +-
.../GPUToROCDL/LowerGpuOpsToROCDLOps.cpp | 11 +-
mlir/lib/Conversion/GPUToSPIRV/GPUToSPIRV.cpp | 41 +++++--
.../Conversion/GPUToSPIRV/GPUToSPIRVPass.cpp | 4 +-
.../LowerFunctionDiscardablesToLLVM.cpp | 3 +-
mlir/lib/Conversion/LLVMCommon/Pattern.cpp | 2 +-
.../LinalgToStandard/LinalgToStandard.cpp | 4 +-
.../Conversion/MathToFuncs/MathToFuncs.cpp | 6 +-
mlir/lib/Conversion/MathToLibm/MathToLibm.cpp | 4 +-
mlir/lib/Conversion/MathToXeVM/MathToXeVM.cpp | 3 +-
.../MapMemRefStorageClassPass.cpp | 6 +-
.../Conversion/NVGPUToNVVM/NVGPUToNVVM.cpp | 4 +-
.../Conversion/OpenMPToLLVM/OpenMPToLLVM.cpp | 11 +-
.../Conversion/RaiseWasm/RaiseWasmMLIR.cpp | 8 +-
.../SCFToControlFlow/SCFToControlFlow.cpp | 4 +-
mlir/lib/Conversion/SCFToGPU/SCFToGPU.cpp | 19 ++--
mlir/lib/Conversion/SCFToSPIRV/SCFToSPIRV.cpp | 11 +-
.../ConvertLaunchFuncToLLVMCalls.cpp | 29 ++---
.../Conversion/SPIRVToLLVM/SPIRVToLLVM.cpp | 37 ++++---
.../Conversion/TosaToLinalg/TosaToLinalg.cpp | 13 +--
.../TosaToLinalg/TosaToLinalgNamed.cpp | 6 +-
.../TosaToSPIRVTosa/TosaToSPIRVTosa.cpp | 4 +-
.../TosaToSPIRVTosaConstants.cpp | 5 +-
.../TosaToSPIRVTosa/TosaToSPIRVTosaPass.cpp | 4 +-
.../VectorToArmSME/VectorToArmSME.cpp | 6 +-
.../Conversion/VectorToSCF/VectorToSCF.cpp | 10 +-
.../Conversion/XeGPUToXeVM/XeGPUToXeVM.cpp | 4 +-
mlir/lib/Conversion/XeVMToLLVM/XeVMToLLVM.cpp | 29 +++--
.../AMDGPU/Transforms/EmulateAtomics.cpp | 3 +-
.../AMDGPU/Transforms/MaskedloadToLoad.cpp | 4 +-
mlir/lib/Dialect/Affine/Analysis/Utils.cpp | 3 +-
mlir/lib/Dialect/Affine/IR/AffineOps.cpp | 100 ++++++++----------
.../Transforms/PipelineDataTransfer.cpp | 2 +-
.../Transforms/SimplifyAffineStructures.cpp | 9 +-
.../Affine/Transforms/SuperVectorize.cpp | 8 +-
mlir/lib/Dialect/Affine/Utils/Utils.cpp | 19 ++--
mlir/lib/Dialect/Arith/IR/ArithOps.cpp | 13 ++-
.../Transforms/EmulateUnsupportedFloats.cpp | 8 +-
.../Transforms/IntRangeOptimizations.cpp | 5 +-
.../Transforms/UnsignedWhenEquivalent.cpp | 5 +-
.../ArmSME/Transforms/EnableArmStreaming.cpp | 6 +-
.../Transforms/LegalizeVectorStorage.cpp | 4 +-
mlir/lib/Dialect/Async/IR/Async.cpp | 7 +-
.../Async/Transforms/AsyncToAsyncRuntime.cpp | 11 +-
.../Bufferization/IR/BufferizationOps.cpp | 7 +-
.../FuncBufferizableOpInterfaceImpl.cpp | 6 +-
.../Transforms/OneShotAnalysis.cpp | 26 +++--
.../Transforms/OneShotModuleBufferize.cpp | 6 +-
.../OwnershipBasedBufferDeallocation.cpp | 12 +--
mlir/lib/Dialect/DLTI/DLTI.cpp | 2 +-
mlir/lib/Dialect/DLTI/Traits.cpp | 4 +-
mlir/lib/Dialect/EmitC/IR/EmitC.cpp | 9 +-
.../EmitC/Transforms/MLGOAddReflectionMap.cpp | 3 +-
mlir/lib/Dialect/Func/IR/FuncOps.cpp | 8 +-
.../DuplicateFunctionElimination.cpp | 3 +-
mlir/lib/Dialect/GPU/IR/GPUDialect.cpp | 44 ++++----
.../GPU/IR/InferIntRangeInterfaceImpls.cpp | 4 +-
.../GPU/Transforms/EliminateBarriers.cpp | 2 +-
.../GPU/Transforms/KernelOutlining.cpp | 8 +-
.../GPU/Transforms/ParallelLoopMapper.cpp | 7 +-
mlir/lib/Dialect/IRDL/IRDLLoading.cpp | 4 +-
mlir/lib/Dialect/LLVMIR/IR/LLVMAttrs.cpp | 4 +-
mlir/lib/Dialect/LLVMIR/IR/LLVMDialect.cpp | 35 +++---
mlir/lib/Dialect/LLVMIR/IR/NVVMDialect.cpp | 31 ++++--
.../Transforms/InlinerInterfaceImpl.cpp | 2 +-
.../LLVMIR/Transforms/RequestCWrappers.cpp | 5 +-
.../Dialect/Linalg/IR/LinalgInterfaces.cpp | 8 +-
mlir/lib/Dialect/Linalg/IR/LinalgOps.cpp | 65 +++++++-----
.../TransformOps/LinalgTransformOps.cpp | 15 ++-
.../BufferizableOpInterfaceImpl.cpp | 17 ++-
.../Linalg/Transforms/DropUnitDims.cpp | 4 +-
.../Linalg/Transforms/ElementwiseToLinalg.cpp | 9 +-
.../EraseUnusedOperandsAndResults.cpp | 4 +-
.../Linalg/Transforms/FoldIntoElementwise.cpp | 3 +-
.../Transforms/SimplifyDepthwiseConv.cpp | 2 +-
.../Linalg/Transforms/TilingInterfaceImpl.cpp | 26 +++--
.../Linalg/Transforms/Vectorization.cpp | 18 ++--
.../Transforms/PolynomialApproximation.cpp | 4 +-
mlir/lib/Dialect/MemRef/IR/MemRefOps.cpp | 14 +--
.../Transforms/AllocationOpInterfaceImpl.cpp | 11 +-
.../Dialect/MemRef/Transforms/MultiBuffer.cpp | 5 +-
.../MemRef/Transforms/NormalizeMemRefs.cpp | 3 +-
mlir/lib/Dialect/NVGPU/IR/NVGPUDialect.cpp | 5 +-
.../NVGPU/Transforms/MmaSyncTF32Transform.cpp | 2 +-
mlir/lib/Dialect/OpenACC/IR/OpenACC.cpp | 2 +-
mlir/lib/Dialect/OpenACC/IR/OpenACCCG.cpp | 18 ++--
.../OpenACC/Transforms/ACCBindRoutine.cpp | 8 +-
.../Dialect/OpenACC/Transforms/ACCCGToGPU.cpp | 10 +-
.../OpenACC/Transforms/ACCComputeLowering.cpp | 2 +-
.../ACCDeclareGPUModuleInsertion.cpp | 21 ++--
.../OpenACC/Transforms/ACCEmitRemarksData.cpp | 2 +-
.../OpenACC/Transforms/ACCEmitRemarksLoop.cpp | 2 +-
.../OpenACC/Transforms/ACCImplicitData.cpp | 4 +-
.../OpenACC/Transforms/ACCImplicitDeclare.cpp | 9 +-
.../OpenACC/Transforms/ACCImplicitRoutine.cpp | 4 +-
.../Transforms/ACCRecipeMaterialization.cpp | 16 +--
.../OpenACC/Transforms/ACCRoutineLowering.cpp | 16 +--
.../Transforms/ACCRoutineToGPUFunc.cpp | 16 +--
.../Dialect/OpenACC/Utils/OpenACCUtils.cpp | 16 +--
.../Dialect/OpenACC/Utils/OpenACCUtilsCG.cpp | 25 +++--
.../Dialect/OpenACC/Utils/OpenACCUtilsGPU.cpp | 4 +-
.../OpenACC/Utils/OpenACCUtilsLoop.cpp | 8 +-
mlir/lib/Dialect/OpenMP/IR/OpenMPDialect.cpp | 24 +++--
mlir/lib/Dialect/OpenMP/Utils/Utils.cpp | 8 +-
mlir/lib/Dialect/PDLInterp/IR/PDLInterp.cpp | 2 +-
.../Quant/Transforms/NormalizeQuantTypes.cpp | 3 +-
mlir/lib/Dialect/SCF/IR/SCF.cpp | 49 +++++----
.../BufferizableOpInterfaceImpl.cpp | 3 +-
.../lib/Dialect/SCF/Transforms/ForToWhile.cpp | 5 +-
.../SCF/Transforms/ForallToParallel.cpp | 2 +-
.../SCF/Transforms/LoopSpecialization.cpp | 16 +--
.../Transforms/StructuralTypeConversions.cpp | 4 +-
mlir/lib/Dialect/SMT/IR/SMTOps.cpp | 12 ++-
mlir/lib/Dialect/SPIRV/IR/AtomicOps.cpp | 6 +-
mlir/lib/Dialect/SPIRV/IR/ControlFlowOps.cpp | 4 +-
mlir/lib/Dialect/SPIRV/IR/DotProductOps.cpp | 14 +--
mlir/lib/Dialect/SPIRV/IR/GroupOps.cpp | 6 +-
mlir/lib/Dialect/SPIRV/IR/MemoryOps.cpp | 33 +++---
.../SPIRV/IR/SPIRVCanonicalization.cpp | 9 +-
mlir/lib/Dialect/SPIRV/IR/SPIRVOps.cpp | 30 +++---
mlir/lib/Dialect/SPIRV/IR/TargetAndABI.cpp | 4 +-
.../Linking/ModuleCombiner/ModuleCombiner.cpp | 9 +-
.../DecorateCompositeTypeLayoutPass.cpp | 11 +-
.../Transforms/LowerABIAttributesPass.cpp | 12 ++-
.../SPIRV/Transforms/SPIRVConversion.cpp | 26 +++--
.../Transforms/UnifyAliasedResourcePass.cpp | 10 +-
.../SPIRV/Transforms/UpdateVCEPass.cpp | 2 +-
mlir/lib/Dialect/Shape/IR/Shape.cpp | 20 ++--
.../SparseTensor/IR/SparseTensorDialect.cpp | 2 +-
.../Transforms/SparseAssembler.cpp | 9 +-
.../Transforms/SparseGPUCodegen.cpp | 7 +-
.../Transforms/SparseReinterpretMap.cpp | 4 +-
.../Transforms/SparseVectorization.cpp | 9 +-
.../Transforms/Sparsification.cpp | 4 +-
.../Transforms/Utils/CodegenUtils.cpp | 4 +-
.../Transforms/Utils/LoopEmitter.h | 3 +-
.../Transforms/ScalarizeFunctionResult.cpp | 3 +-
mlir/lib/Dialect/Tosa/IR/TargetEnv.cpp | 3 +-
mlir/lib/Dialect/Tosa/IR/TosaOps.cpp | 21 ++--
.../Tosa/Transforms/TosaAttachTarget.cpp | 2 +-
.../TosaConvertIntegerTypeToSignless.cpp | 3 +-
.../Tosa/Transforms/TosaNarrowTypes.cpp | 6 +-
.../Tosa/Transforms/TosaReduceTransposes.cpp | 14 +--
.../Tosa/Transforms/TosaValidation.cpp | 6 +-
.../Dialect/Tosa/Utils/ConversionUtils.cpp | 3 +-
.../Dialect/Transform/IR/TransformDialect.cpp | 4 +-
.../lib/Dialect/Transform/IR/TransformOps.cpp | 11 +-
.../Interfaces/TransformInterfaces.cpp | 4 +-
.../Transform/Transforms/InterpreterPass.cpp | 2 +-
.../Transforms/TransformInterpreterUtils.cpp | 4 +-
mlir/lib/Dialect/Utils/StructuredOpsUtils.cpp | 8 +-
mlir/lib/Dialect/Vector/IR/VectorOps.cpp | 30 +++---
.../Vector/Transforms/VectorDistribute.cpp | 3 +-
.../Transforms/VectorDropLeadUnitDim.cpp | 20 ++--
.../Vector/Transforms/VectorLinearize.cpp | 8 +-
.../VectorTransferSplitRewritePatterns.cpp | 8 +-
.../Vector/Transforms/VectorTransforms.cpp | 20 ++--
.../Vector/Transforms/VectorUnroll.cpp | 6 +-
.../XeGPU/Transforms/XeGPUBlocking.cpp | 20 ++--
.../XeGPU/Transforms/XeGPULayoutImpl.cpp | 10 +-
.../XeGPU/Transforms/XeGPUPropagateLayout.cpp | 10 +-
.../Transforms/XeGPUSgToLaneDistribute.cpp | 13 ++-
.../Dialect/XeGPU/Transforms/XeGPUUnroll.cpp | 30 +++---
.../Transforms/XeGPUWgToSgDistribute.cpp | 5 +-
mlir/lib/Dialect/XeGPU/Utils/XeGPUUtils.cpp | 27 ++---
mlir/lib/IR/AsmPrinter.cpp | 13 ++-
mlir/lib/IR/AttrTypeSubElements.cpp | 13 ++-
mlir/lib/IR/BuiltinAttributes.cpp | 7 +-
mlir/lib/IR/BuiltinDialect.cpp | 11 +-
mlir/lib/IR/Operation.cpp | 7 +-
mlir/lib/IR/OperationSupport.cpp | 8 +-
mlir/lib/IR/PatternMatch.cpp | 4 +-
mlir/lib/IR/SymbolTable.cpp | 84 ++++++++++-----
.../lib/Interfaces/FunctionImplementation.cpp | 18 ++--
mlir/lib/Interfaces/Utils/MemorySlotUtils.cpp | 3 +-
mlir/lib/Pass/IRPrinting.cpp | 11 +-
mlir/lib/Rewrite/ByteCode.cpp | 10 +-
mlir/lib/Target/Cpp/TranslateToCpp.cpp | 6 +-
mlir/lib/Target/LLVM/XeVM/Target.cpp | 3 +-
.../LLVMIR/LLVMIRToLLVMTranslation.cpp | 2 +-
.../LLVMIR/LLVMToLLVMIRTranslation.cpp | 2 +-
.../OpenMP/OpenMPToLLVMIRTranslation.cpp | 5 +-
.../ROCDL/ROCDLToLLVMIRTranslation.cpp | 8 +-
mlir/lib/Target/LLVMIR/ModuleImport.cpp | 27 ++---
mlir/lib/Target/LLVMIR/ModuleTranslation.cpp | 12 ++-
.../LLVMIR/Transforms/TargetToDataLayout.cpp | 9 +-
.../Transforms/TargetToTargetFeatures.cpp | 5 +-
.../SPIRV/Deserialization/Deserializer.cpp | 33 +++---
.../SPIRV/Serialization/SerializeOps.cpp | 44 ++++----
.../Target/SPIRV/Serialization/Serializer.cpp | 15 +--
mlir/lib/Target/Wasm/TranslateFromWasm.cpp | 6 +-
.../Transforms/Utils/DialectConversion.cpp | 17 +--
mlir/lib/Transforms/ViewOpGraph.cpp | 10 +-
mlir/python/mlir/dialects/gpu/__init__.py | 10 +-
.../DataFlow/TestDeadCodeAnalysis.cpp | 2 +-
.../TestDenseBackwardDataFlowAnalysis.cpp | 13 +--
.../DataFlow/TestDenseDataFlowAnalysis.h | 2 +-
.../TestDenseForwardDataFlowAnalysis.cpp | 5 +-
.../TestIntegerDivisibilityAnalysis.cpp | 5 +-
.../DataFlow/TestLivenessAnalysis.cpp | 2 +-
.../TestSparseBackwardDataFlowAnalysis.cpp | 6 +-
mlir/test/lib/Analysis/TestAliasAnalysis.cpp | 5 +-
.../lib/Analysis/TestDataFlowFramework.cpp | 15 +--
mlir/test/lib/Analysis/TestSlice.cpp | 4 +-
.../test/lib/Analysis/TestTopologicalSort.cpp | 8 +-
.../TestTensorLikeAndBufferLike.cpp | 2 +-
.../lib/Dialect/DLTI/TestDataLayoutQuery.cpp | 2 +-
mlir/test/lib/Dialect/LLVM/TestPatterns.cpp | 5 +-
.../Dialect/OpenACC/TestOpenACCSupport.cpp | 7 +-
.../OpenACC/TestPointerLikeTypeInterface.cpp | 18 ++--
.../Dialect/OpenACC/TestRecipePopulate.cpp | 2 +-
.../lib/Dialect/SCF/TestLoopUnrolling.cpp | 2 +-
.../Dialect/SCF/TestParallelLoopUnrolling.cpp | 2 +-
mlir/test/lib/Dialect/SCF/TestSCFUtils.cpp | 25 +++--
.../lib/Dialect/SPIRV/TestAvailability.cpp | 5 +-
.../lib/Dialect/SPIRV/TestEntryPointAbi.cpp | 14 +--
.../lib/Dialect/Shape/TestShapeFunctions.cpp | 2 +-
.../Dialect/Tensor/TestTensorTransforms.cpp | 6 +-
mlir/test/lib/Dialect/Test/TestDialect.cpp | 6 +-
.../Dialect/Test/TestDialectInterfaces.cpp | 5 +-
mlir/test/lib/Dialect/Test/TestOpDefs.cpp | 29 +++--
mlir/test/lib/Dialect/Test/TestOps.td | 23 ++--
mlir/test/lib/Dialect/Test/TestOpsSyntax.cpp | 3 +-
mlir/test/lib/Dialect/Test/TestPatterns.cpp | 83 ++++++++-------
.../TestTransformDialectExtension.cpp | 13 +--
.../lib/Dialect/XeGPU/TestXeGPUTransforms.cpp | 5 +-
mlir/test/lib/IR/TestAffineWalk.cpp | 2 +-
.../lib/IR/TestBuiltinAttributeInterfaces.cpp | 5 +-
.../lib/IR/TestBuiltinDistinctAttributes.cpp | 8 +-
mlir/test/lib/IR/TestDiagnostics.cpp | 3 +-
mlir/test/lib/IR/TestDiagnosticsMetadata.cpp | 3 +-
mlir/test/lib/IR/TestDominance.cpp | 5 +-
mlir/test/lib/IR/TestFunc.cpp | 13 ++-
mlir/test/lib/IR/TestOperationEquals.cpp | 6 +-
mlir/test/lib/IR/TestPrintNesting.cpp | 7 +-
mlir/test/lib/IR/TestSymbolUses.cpp | 3 +-
mlir/test/lib/IR/TestVisitors.cpp | 8 +-
mlir/test/lib/IR/TestVisitorsGeneric.cpp | 20 ++--
.../lib/Transforms/TestControlFlowSink.cpp | 4 +-
.../test-linalg-ods-yaml-gen.yaml | 2 +-
.../mlir-linalg-ods-yaml-gen.cpp | 8 +-
mlir/tools/mlir-tblgen/DialectGen.cpp | 10 +-
mlir/tools/mlir-tblgen/OpDefinitionsGen.cpp | 11 +-
mlir/tools/mlir-tblgen/OpFormatGen.cpp | 24 +++--
mlir/tools/mlir-tblgen/SPIRVUtilsGen.cpp | 13 ++-
mlir/unittests/Bytecode/BytecodeTest.cpp | 4 +-
.../Dialect/OpenACC/OpenACCUtilsCGTest.cpp | 2 +-
.../Dialect/OpenACC/OpenACCUtilsGPUTest.cpp | 4 +-
.../Dialect/OpenACC/OpenACCUtilsLoopTest.cpp | 4 +-
.../Dialect/OpenACC/OpenACCUtilsTest.cpp | 15 +--
.../Dialect/SPIRV/SerializationTest.cpp | 2 +-
mlir/unittests/IR/BlobManagerTest.cpp | 3 +-
mlir/unittests/IR/OpPropertiesTest.cpp | 10 +-
mlir/unittests/IR/OperationSupportTest.cpp | 2 +-
.../Interfaces/DataLayoutInterfacesTest.cpp | 12 ++-
mlir/unittests/Pass/PassManagerTest.cpp | 12 +--
mlir/unittests/TableGen/OpBuildGen.cpp | 23 ++--
.../Target/LLVM/SerializeToLLVMBitcode.cpp | 5 +-
300 files changed, 1955 insertions(+), 1341 deletions(-)
diff --git a/mlir/examples/toy/Ch2/mlir/Dialect.cpp b/mlir/examples/toy/Ch2/mlir/Dialect.cpp
index 489f348c8be52..41c451e94d322 100644
--- a/mlir/examples/toy/Ch2/mlir/Dialect.cpp
+++ b/mlir/examples/toy/Ch2/mlir/Dialect.cpp
@@ -84,7 +84,7 @@ static mlir::ParseResult parseBinaryOp(mlir::OpAsmParser &parser,
/// forms depending on if all of the types match.
static void printBinaryOp(mlir::OpAsmPrinter &printer, mlir::Operation *op) {
printer << " " << op->getOperands();
- printer.printOptionalAttrDict(op->getAttrs());
+ printer.printOptionalAttrDict(op->getDiscardableAttrDictionary().getValue());
printer << " : ";
// If all of the types are the same, print the type directly.
@@ -135,7 +135,9 @@ mlir::ParseResult ConstantOp::parse(mlir::OpAsmParser &parser,
/// strings, attributes, operands, types, etc.
void ConstantOp::print(mlir::OpAsmPrinter &printer) {
printer << " ";
- printer.printOptionalAttrDict((*this)->getAttrs(), /*elidedAttrs=*/{"value"});
+ printer.printOptionalAttrDict(
+ (*this)->getDiscardableAttrDictionary().getValue(),
+ /*elidedAttrs=*/{"value"});
printer << getValue();
}
diff --git a/mlir/examples/toy/Ch3/mlir/Dialect.cpp b/mlir/examples/toy/Ch3/mlir/Dialect.cpp
index 708855f18cf45..bfd4480db5702 100644
--- a/mlir/examples/toy/Ch3/mlir/Dialect.cpp
+++ b/mlir/examples/toy/Ch3/mlir/Dialect.cpp
@@ -84,7 +84,7 @@ static mlir::ParseResult parseBinaryOp(mlir::OpAsmParser &parser,
/// forms depending on if all of the types match.
static void printBinaryOp(mlir::OpAsmPrinter &printer, mlir::Operation *op) {
printer << " " << op->getOperands();
- printer.printOptionalAttrDict(op->getAttrs());
+ printer.printOptionalAttrDict(op->getDiscardableAttrDictionary().getValue());
printer << " : ";
// If all of the types are the same, print the type directly.
@@ -135,7 +135,9 @@ mlir::ParseResult ConstantOp::parse(mlir::OpAsmParser &parser,
/// strings, attributes, operands, types, etc.
void ConstantOp::print(mlir::OpAsmPrinter &printer) {
printer << " ";
- printer.printOptionalAttrDict((*this)->getAttrs(), /*elidedAttrs=*/{"value"});
+ printer.printOptionalAttrDict(
+ (*this)->getDiscardableAttrDictionary().getValue(),
+ /*elidedAttrs=*/{"value"});
printer << getValue();
}
diff --git a/mlir/examples/toy/Ch4/mlir/Dialect.cpp b/mlir/examples/toy/Ch4/mlir/Dialect.cpp
index 1e5e67296a753..298491ad3476e 100644
--- a/mlir/examples/toy/Ch4/mlir/Dialect.cpp
+++ b/mlir/examples/toy/Ch4/mlir/Dialect.cpp
@@ -146,7 +146,7 @@ static mlir::ParseResult parseBinaryOp(mlir::OpAsmParser &parser,
/// forms depending on if all of the types match.
static void printBinaryOp(mlir::OpAsmPrinter &printer, mlir::Operation *op) {
printer << " " << op->getOperands();
- printer.printOptionalAttrDict(op->getAttrs());
+ printer.printOptionalAttrDict(op->getDiscardableAttrDictionary().getValue());
printer << " : ";
// If all of the types are the same, print the type directly.
@@ -197,7 +197,9 @@ mlir::ParseResult ConstantOp::parse(mlir::OpAsmParser &parser,
/// strings, attributes, operands, types, etc.
void ConstantOp::print(mlir::OpAsmPrinter &printer) {
printer << " ";
- printer.printOptionalAttrDict((*this)->getAttrs(), /*elidedAttrs=*/{"value"});
+ printer.printOptionalAttrDict(
+ (*this)->getDiscardableAttrDictionary().getValue(),
+ /*elidedAttrs=*/{"value"});
printer << getValue();
}
@@ -328,13 +330,13 @@ void GenericCallOp::build(mlir::OpBuilder &builder, mlir::OperationState &state,
/// Return the callee of the generic call operation, this is required by the
/// call interface.
CallInterfaceCallable GenericCallOp::getCallableForCallee() {
- return (*this)->getAttrOfType<SymbolRefAttr>("callee");
+ return getCalleeAttr();
}
/// Set the callee for the generic call operation, this is required by the call
/// interface.
void GenericCallOp::setCalleeFromCallable(CallInterfaceCallable callee) {
- (*this)->setAttr("callee", cast<SymbolRefAttr>(callee));
+ setCalleeAttr(cast<FlatSymbolRefAttr>(cast<SymbolRefAttr>(callee)));
}
/// Get the argument operands to the called function, this is required by the
diff --git a/mlir/examples/toy/Ch5/mlir/Dialect.cpp b/mlir/examples/toy/Ch5/mlir/Dialect.cpp
index 69fb69fd6e7ba..0f9c24eba0cc7 100644
--- a/mlir/examples/toy/Ch5/mlir/Dialect.cpp
+++ b/mlir/examples/toy/Ch5/mlir/Dialect.cpp
@@ -146,7 +146,7 @@ static mlir::ParseResult parseBinaryOp(mlir::OpAsmParser &parser,
/// forms depending on if all of the types match.
static void printBinaryOp(mlir::OpAsmPrinter &printer, mlir::Operation *op) {
printer << " " << op->getOperands();
- printer.printOptionalAttrDict(op->getAttrs());
+ printer.printOptionalAttrDict(op->getDiscardableAttrDictionary().getValue());
printer << " : ";
// If all of the types are the same, print the type directly.
@@ -197,7 +197,9 @@ mlir::ParseResult ConstantOp::parse(mlir::OpAsmParser &parser,
/// strings, attributes, operands, types, etc.
void ConstantOp::print(mlir::OpAsmPrinter &printer) {
printer << " ";
- printer.printOptionalAttrDict((*this)->getAttrs(), /*elidedAttrs=*/{"value"});
+ printer.printOptionalAttrDict(
+ (*this)->getDiscardableAttrDictionary().getValue(),
+ /*elidedAttrs=*/{"value"});
printer << getValue();
}
@@ -328,13 +330,13 @@ void GenericCallOp::build(mlir::OpBuilder &builder, mlir::OperationState &state,
/// Return the callee of the generic call operation, this is required by the
/// call interface.
CallInterfaceCallable GenericCallOp::getCallableForCallee() {
- return (*this)->getAttrOfType<SymbolRefAttr>("callee");
+ return getCalleeAttr();
}
/// Set the callee for the generic call operation, this is required by the call
/// interface.
void GenericCallOp::setCalleeFromCallable(CallInterfaceCallable callee) {
- (*this)->setAttr("callee", cast<SymbolRefAttr>(callee));
+ setCalleeAttr(cast<FlatSymbolRefAttr>(cast<SymbolRefAttr>(callee)));
}
/// Get the argument operands to the called function, this is required by the
diff --git a/mlir/examples/toy/Ch6/mlir/Dialect.cpp b/mlir/examples/toy/Ch6/mlir/Dialect.cpp
index 69fb69fd6e7ba..0f9c24eba0cc7 100644
--- a/mlir/examples/toy/Ch6/mlir/Dialect.cpp
+++ b/mlir/examples/toy/Ch6/mlir/Dialect.cpp
@@ -146,7 +146,7 @@ static mlir::ParseResult parseBinaryOp(mlir::OpAsmParser &parser,
/// forms depending on if all of the types match.
static void printBinaryOp(mlir::OpAsmPrinter &printer, mlir::Operation *op) {
printer << " " << op->getOperands();
- printer.printOptionalAttrDict(op->getAttrs());
+ printer.printOptionalAttrDict(op->getDiscardableAttrDictionary().getValue());
printer << " : ";
// If all of the types are the same, print the type directly.
@@ -197,7 +197,9 @@ mlir::ParseResult ConstantOp::parse(mlir::OpAsmParser &parser,
/// strings, attributes, operands, types, etc.
void ConstantOp::print(mlir::OpAsmPrinter &printer) {
printer << " ";
- printer.printOptionalAttrDict((*this)->getAttrs(), /*elidedAttrs=*/{"value"});
+ printer.printOptionalAttrDict(
+ (*this)->getDiscardableAttrDictionary().getValue(),
+ /*elidedAttrs=*/{"value"});
printer << getValue();
}
@@ -328,13 +330,13 @@ void GenericCallOp::build(mlir::OpBuilder &builder, mlir::OperationState &state,
/// Return the callee of the generic call operation, this is required by the
/// call interface.
CallInterfaceCallable GenericCallOp::getCallableForCallee() {
- return (*this)->getAttrOfType<SymbolRefAttr>("callee");
+ return getCalleeAttr();
}
/// Set the callee for the generic call operation, this is required by the call
/// interface.
void GenericCallOp::setCalleeFromCallable(CallInterfaceCallable callee) {
- (*this)->setAttr("callee", cast<SymbolRefAttr>(callee));
+ setCalleeAttr(cast<FlatSymbolRefAttr>(cast<SymbolRefAttr>(callee)));
}
/// Get the argument operands to the called function, this is required by the
diff --git a/mlir/examples/toy/Ch7/mlir/Dialect.cpp b/mlir/examples/toy/Ch7/mlir/Dialect.cpp
index 4d2f063afd0fb..db0364307af94 100644
--- a/mlir/examples/toy/Ch7/mlir/Dialect.cpp
+++ b/mlir/examples/toy/Ch7/mlir/Dialect.cpp
@@ -138,7 +138,7 @@ static mlir::ParseResult parseBinaryOp(mlir::OpAsmParser &parser,
/// forms depending on if all of the types match.
static void printBinaryOp(mlir::OpAsmPrinter &printer, mlir::Operation *op) {
printer << " " << op->getOperands();
- printer.printOptionalAttrDict(op->getAttrs());
+ printer.printOptionalAttrDict(op->getDiscardableAttrDictionary().getValue());
printer << " : ";
// If all of the types are the same, print the type directly.
@@ -189,7 +189,9 @@ mlir::ParseResult ConstantOp::parse(mlir::OpAsmParser &parser,
/// strings, attributes, operands, types, etc.
void ConstantOp::print(mlir::OpAsmPrinter &printer) {
printer << " ";
- printer.printOptionalAttrDict((*this)->getAttrs(), /*elidedAttrs=*/{"value"});
+ printer.printOptionalAttrDict(
+ (*this)->getDiscardableAttrDictionary().getValue(),
+ /*elidedAttrs=*/{"value"});
printer << getValue();
}
@@ -361,13 +363,13 @@ void GenericCallOp::build(mlir::OpBuilder &builder, mlir::OperationState &state,
/// Return the callee of the generic call operation, this is required by the
/// call interface.
CallInterfaceCallable GenericCallOp::getCallableForCallee() {
- return (*this)->getAttrOfType<SymbolRefAttr>("callee");
+ return getCalleeAttr();
}
/// Set the callee for the generic call operation, this is required by the call
/// interface.
void GenericCallOp::setCalleeFromCallable(CallInterfaceCallable callee) {
- (*this)->setAttr("callee", cast<SymbolRefAttr>(callee));
+ setCalleeAttr(cast<FlatSymbolRefAttr>(cast<SymbolRefAttr>(callee)));
}
/// Get the argument operands to the called function, this is required by the
diff --git a/mlir/include/mlir/Conversion/ArithCommon/AttrToLLVMConverter.h b/mlir/include/mlir/Conversion/ArithCommon/AttrToLLVMConverter.h
index feb74c86e349f..497ab3b7152da 100644
--- a/mlir/include/mlir/Conversion/ArithCommon/AttrToLLVMConverter.h
+++ b/mlir/include/mlir/Conversion/ArithCommon/AttrToLLVMConverter.h
@@ -18,6 +18,15 @@
namespace mlir {
namespace arith {
+
+template <typename SourceOp>
+static NamedAttrList getAttrsWithProperties(SourceOp srcOp) {
+ NamedAttrList attrs(srcOp->getDiscardableAttrDictionary());
+ if (auto properties =
+ dyn_cast_or_null<DictionaryAttr>(srcOp->getPropertiesAsAttribute()))
+ attrs.append(properties.getValue());
+ return attrs;
+}
/// Maps arithmetic fastmath enum values to LLVM enum values.
LLVM::FastmathFlags
convertArithFastMathFlagsToLLVM(arith::FastMathFlags arithFMF);
@@ -53,7 +62,7 @@ class AttrConvertFastMathToLLVM {
public:
AttrConvertFastMathToLLVM(SourceOp srcOp) {
// Copy the source attributes.
- convertedAttr = NamedAttrList{srcOp->getAttrs()};
+ convertedAttr = getAttrsWithProperties(srcOp);
// Get the name of the arith fastmath attribute.
StringRef arithFMFAttrName = SourceOp::getFastMathAttrName();
// Remove the source fastmath attribute.
@@ -82,7 +91,7 @@ class AttrConvertOverflowToLLVM {
using IntegerOverflowFlagsAttr = LLVM::IntegerOverflowFlagsAttr;
// Copy the source attributes.
- convertedAttr = NamedAttrList{srcOp->getAttrs()};
+ convertedAttr = getAttrsWithProperties(srcOp);
// Get the name of the arith overflow attribute.
StringRef arithAttrName = SourceOp::getIntegerOverflowAttrName();
// Remove the source overflow attribute from the set that will be present
@@ -118,7 +127,7 @@ template <typename SourceOp, typename TargetOp>
class AttrConvertNonNegToLLVM {
public:
AttrConvertNonNegToLLVM(SourceOp srcOp) {
- convertedAttr = NamedAttrList{srcOp->getAttrs()};
+ convertedAttr = getAttrsWithProperties(srcOp);
if (!convertedAttr.erase("nonNeg"))
return;
MLIRContext *ctx = srcOp.getOperation()->getContext();
@@ -144,7 +153,7 @@ class AttrConverterConstrainedFPToLLVM {
public:
AttrConverterConstrainedFPToLLVM(SourceOp srcOp) {
// Copy the source attributes.
- convertedAttr = NamedAttrList{srcOp->getAttrs()};
+ convertedAttr = getAttrsWithProperties(srcOp);
if constexpr (TargetOp::template hasTrait<
LLVM::RoundingModeOpInterface::Trait>()) {
diff --git a/mlir/include/mlir/Conversion/LLVMCommon/Pattern.h b/mlir/include/mlir/Conversion/LLVMCommon/Pattern.h
index 2f468458addd3..b50aeb1e274b3 100644
--- a/mlir/include/mlir/Conversion/LLVMCommon/Pattern.h
+++ b/mlir/include/mlir/Conversion/LLVMCommon/Pattern.h
@@ -338,8 +338,9 @@ class OneToOneConvertToLLVMPattern : public ConvertOpToLLVMPattern<SourceOp> {
matchAndRewrite(SourceOp op, typename SourceOp::Adaptor adaptor,
ConversionPatternRewriter &rewriter) const override {
return LLVM::detail::oneToOneRewrite(
- op, TargetOp::getOperationName(), adaptor.getOperands(), op->getAttrs(),
- /*propertiesAttr=*/Attribute{}, *this->getTypeConverter(), rewriter);
+ op, TargetOp::getOperationName(), adaptor.getOperands(),
+ op->getDiscardableAttrDictionary().getValue(),
+ op->getPropertiesAsAttribute(), *this->getTypeConverter(), rewriter);
}
};
diff --git a/mlir/include/mlir/Conversion/LLVMCommon/VectorPattern.h b/mlir/include/mlir/Conversion/LLVMCommon/VectorPattern.h
index 65988a2466318..fdc787d84383e 100644
--- a/mlir/include/mlir/Conversion/LLVMCommon/VectorPattern.h
+++ b/mlir/include/mlir/Conversion/LLVMCommon/VectorPattern.h
@@ -70,13 +70,16 @@ LogicalResult vectorOneToOneRewrite(Operation *op, StringRef targetOp,
template <typename SourceOp, typename TargetOp>
class AttrConvertPassThrough {
public:
- AttrConvertPassThrough(SourceOp srcOp) : srcAttrs(srcOp->getAttrs()) {}
+ AttrConvertPassThrough(SourceOp srcOp)
+ : srcAttrs(srcOp->getDiscardableAttrDictionary().getValue()),
+ propertiesAttr(srcOp->getPropertiesAsAttribute()) {}
ArrayRef<NamedAttribute> getAttrs() const { return srcAttrs; }
- Attribute getPropAttr() const { return {}; }
+ Attribute getPropAttr() const { return propertiesAttr; }
private:
ArrayRef<NamedAttribute> srcAttrs;
+ Attribute propertiesAttr;
};
/// Basic lowering implementation to rewrite Ops with just one result to the
diff --git a/mlir/include/mlir/Dialect/ArmSME/IR/ArmSMEOps.td b/mlir/include/mlir/Dialect/ArmSME/IR/ArmSMEOps.td
index 264c3969a1152..22ed496a9f48f 100644
--- a/mlir/include/mlir/Dialect/ArmSME/IR/ArmSMEOps.td
+++ b/mlir/include/mlir/Dialect/ArmSME/IR/ArmSMEOps.td
@@ -63,7 +63,7 @@ def ArmSMETileOpInterface : OpInterface<"ArmSMETileOpInterface"> {
if (!tileId)
return;
::mlir::Operation* op = this->getOperation();
- op->setAttr("tile_id", tileId);
+ op->setDiscardableAttr("tile_id", tileId);
}]
>,
InterfaceMethod<
@@ -77,7 +77,7 @@ def ArmSMETileOpInterface : OpInterface<"ArmSMETileOpInterface"> {
/*methodBody=*/[{}],
/*defaultImpl=*/ [{
::mlir::Operation* op = this->getOperation();
- return op->getAttrOfType<mlir::IntegerAttr>("tile_id");
+ return op->getDiscardableAttrOfType<mlir::IntegerAttr>("tile_id");
}]
>,
InterfaceMethod<
diff --git a/mlir/include/mlir/Dialect/Async/IR/AsyncOps.td b/mlir/include/mlir/Dialect/Async/IR/AsyncOps.td
index 722370b8f3e29..0368bb55ca271 100644
--- a/mlir/include/mlir/Dialect/Async/IR/AsyncOps.td
+++ b/mlir/include/mlir/Dialect/Async/IR/AsyncOps.td
@@ -261,12 +261,12 @@ def Async_CallOp : Async_Op<"call",
/// Return the callee of this operation.
CallInterfaceCallable getCallableForCallee() {
- return (*this)->getAttrOfType<SymbolRefAttr>("callee");
+ return getCalleeAttr();
}
/// Set the callee for this operation.
void setCalleeFromCallable(CallInterfaceCallable callee) {
- (*this)->setAttr("callee", cast<SymbolRefAttr>(callee));
+ setCalleeAttr(cast<FlatSymbolRefAttr>(cast<SymbolRefAttr>(callee)));
}
}];
diff --git a/mlir/include/mlir/Dialect/EmitC/IR/EmitC.td b/mlir/include/mlir/Dialect/EmitC/IR/EmitC.td
index 49412d1dfb01c..0e7ea45d6d091 100644
--- a/mlir/include/mlir/Dialect/EmitC/IR/EmitC.td
+++ b/mlir/include/mlir/Dialect/EmitC/IR/EmitC.td
@@ -794,12 +794,12 @@ def EmitC_CallOp : EmitC_Op<"call",
/// Return the callee of this operation.
CallInterfaceCallable getCallableForCallee() {
- return (*this)->getAttrOfType<SymbolRefAttr>("callee");
+ return getCalleeAttr();
}
/// Set the callee for this operation.
void setCalleeFromCallable(CallInterfaceCallable callee) {
- (*this)->setAttr("callee", cast<SymbolRefAttr>(callee));
+ setCalleeAttr(cast<FlatSymbolRefAttr>(cast<SymbolRefAttr>(callee)));
}
bool hasSideEffects() {
diff --git a/mlir/include/mlir/Dialect/Func/IR/FuncOps.td b/mlir/include/mlir/Dialect/Func/IR/FuncOps.td
index a31b860276099..f86dac3a772f1 100644
--- a/mlir/include/mlir/Dialect/Func/IR/FuncOps.td
+++ b/mlir/include/mlir/Dialect/Func/IR/FuncOps.td
@@ -110,12 +110,12 @@ def CallOp : Func_Op<"call",
/// Return the callee of this operation.
CallInterfaceCallable getCallableForCallee() {
- return (*this)->getAttrOfType<SymbolRefAttr>("callee");
+ return getCalleeAttr();
}
/// Set the callee for this operation.
void setCalleeFromCallable(CallInterfaceCallable callee) {
- (*this)->setAttr("callee", cast<SymbolRefAttr>(callee));
+ setCalleeAttr(cast<FlatSymbolRefAttr>(cast<SymbolRefAttr>(callee)));
}
}];
diff --git a/mlir/include/mlir/Dialect/GPU/IR/GPUOps.td b/mlir/include/mlir/Dialect/GPU/IR/GPUOps.td
index de145960692ad..7dbce7bed893a 100644
--- a/mlir/include/mlir/Dialect/GPU/IR/GPUOps.td
+++ b/mlir/include/mlir/Dialect/GPU/IR/GPUOps.td
@@ -419,7 +419,9 @@ def GPU_GPUFuncOp : GPU_Op<"func", [
attribution.
}];
- let arguments = (ins TypeAttrOf<FunctionType>:$function_type,
+ let arguments = (ins SymbolNameAttr:$sym_name,
+ OptionalAttr<StrAttr>:$sym_visibility,
+ TypeAttrOf<FunctionType>:$function_type,
OptionalAttr<DictArrayAttr>:$arg_attrs,
OptionalAttr<DictArrayAttr>:$res_attrs,
OptionalAttr<DictArrayAttr>:$workgroup_attrib_attrs,
@@ -447,7 +449,7 @@ def GPU_GPUFuncOp : GPU_Op<"func", [
bool isKernel() {
if (getKernel())
return true;
- return (*this)->getAttrOfType<UnitAttr>(
+ return (*this)->getDiscardableAttrOfType<UnitAttr>(
GPUDialect::getKernelFuncAttrName()) != nullptr;
}
diff --git a/mlir/include/mlir/Dialect/LLVMIR/BasicPtxBuilderInterface.td b/mlir/include/mlir/Dialect/LLVMIR/BasicPtxBuilderInterface.td
index 2834ae160595d..b631ec169f943 100644
--- a/mlir/include/mlir/Dialect/LLVMIR/BasicPtxBuilderInterface.td
+++ b/mlir/include/mlir/Dialect/LLVMIR/BasicPtxBuilderInterface.td
@@ -157,11 +157,18 @@ def BasicPtxBuilderOpInterface : OpInterface<"BasicPtxBuilderInterface"> {
for (auto val : op->getOperands())
asmValues.push_back({val, mlir::NVVM::PTXRegisterMod::Read});
- // Step 3. Add attributes
- for (auto attr : op->getAttrs()) {
- if (auto intAttr = dyn_cast<mlir::IntegerAttr>(attr.getValue())) {
- ::mlir::Value val = makeConstantI32(rewriter, intAttr.getInt());
- asmValues.push_back({val, mlir::NVVM::PTXRegisterMod::Read});
+ // Step 3. Add inherent attributes.
+ auto properties = llvm::dyn_cast_or_null<mlir::DictionaryAttr>(
+ op->getPropertiesAsAttribute());
+ if (properties) {
+ for (auto attr : properties) {
+ if (auto intAttr =
+ dyn_cast<mlir::IntegerAttr>(attr.getValue())) {
+ ::mlir::Value val =
+ makeConstantI32(rewriter, intAttr.getInt());
+ asmValues.push_back(
+ {val, mlir::NVVM::PTXRegisterMod::Read});
+ }
}
}
return false; // No manual mapping needed
diff --git a/mlir/include/mlir/Dialect/LLVMIR/LLVMInterfaces.td b/mlir/include/mlir/Dialect/LLVMIR/LLVMInterfaces.td
index c59b38c416956..66a1fe0ce251a 100644
--- a/mlir/include/mlir/Dialect/LLVMIR/LLVMInterfaces.td
+++ b/mlir/include/mlir/Dialect/LLVMIR/LLVMInterfaces.td
@@ -35,6 +35,17 @@ def FastmathFlagsInterface : OpInterface<"FastmathFlagsInterface"> {
return op.getFastmathFlagsAttr();
}]
>,
+ InterfaceMethod<
+ /*desc=*/ "Sets the FastmathFlagsAttr attribute for the operation",
+ /*returnType=*/ "void",
+ /*methodName=*/ "setFastmathAttr",
+ /*args=*/ (ins "::mlir::LLVM::FastmathFlagsAttr":$attr),
+ /*methodBody=*/ [{}],
+ /*defaultImpl=*/ [{
+ auto op = cast<ConcreteOp>(this->getOperation());
+ op.setFastmathFlagsAttr(attr);
+ }]
+ >,
StaticInterfaceMethod<
/*desc=*/ [{Returns the name of the FastmathFlagsAttr attribute
for the operation}],
diff --git a/mlir/include/mlir/Dialect/LLVMIR/NVVMOps.td b/mlir/include/mlir/Dialect/LLVMIR/NVVMOps.td
index 6241606122f43..e1d3a1940a223 100644
--- a/mlir/include/mlir/Dialect/LLVMIR/NVVMOps.td
+++ b/mlir/include/mlir/Dialect/LLVMIR/NVVMOps.td
@@ -277,7 +277,8 @@ class NVVM_PureSpecialRangeableRegisterOp<string mnemonic, list<Trait> traits =
void $cppClass::inferResultRanges(
ArrayRef<::mlir::ConstantIntRanges> argRanges,
SetIntRangeFn setResultRanges) {
- nvvmInferResultRanges(getOperation(), getResult(), argRanges, setResultRanges);
+ nvvmInferResultRanges(getRange(), getResult(), argRanges,
+ setResultRanges);
}
// Verify the range attribute satisfies LLVM ConstantRange constructor requirements.
diff --git a/mlir/include/mlir/Dialect/OpenACC/OpenACC.h b/mlir/include/mlir/Dialect/OpenACC/OpenACC.h
index 4abc3971f12c0..ff455fa2b7b20 100644
--- a/mlir/include/mlir/Dialect/OpenACC/OpenACC.h
+++ b/mlir/include/mlir/Dialect/OpenACC/OpenACC.h
@@ -193,13 +193,14 @@ static constexpr StringLiteral getSpecializedRoutineAttrName() {
/// Used to check whether the current operation is marked with
/// `acc routine`. The operation passed in should be a function.
inline bool isAccRoutine(mlir::Operation *op) {
- return op && op->hasAttr(mlir::acc::getRoutineInfoAttrName());
+ return op && op->hasDiscardableAttr(mlir::acc::getRoutineInfoAttrName());
}
/// Used to check whether this is a specialized accelerator version of
/// `acc routine` function.
inline bool isSpecializedAccRoutine(mlir::Operation *op) {
- return op && op->hasAttr(mlir::acc::getSpecializedRoutineAttrName());
+ return op &&
+ op->hasDiscardableAttr(mlir::acc::getSpecializedRoutineAttrName());
}
static constexpr StringLiteral getFromDefaultClauseAttrName() {
diff --git a/mlir/include/mlir/Dialect/OpenACCMPCommon/Interfaces/AtomicInterfaces.td b/mlir/include/mlir/Dialect/OpenACCMPCommon/Interfaces/AtomicInterfaces.td
index a61c43e2fd9cd..90c6a5fba8429 100644
--- a/mlir/include/mlir/Dialect/OpenACCMPCommon/Interfaces/AtomicInterfaces.td
+++ b/mlir/include/mlir/Dialect/OpenACCMPCommon/Interfaces/AtomicInterfaces.td
@@ -445,7 +445,8 @@ def AtomicCompareOpInterface : OpInterface<"AtomicCompareOpInterface"> {
llvm::StringRef opName = op.getName().getStringRef();
if (opName == "arith.cmpi" || opName == "llvm.icmp") {
foundComparison = true;
- auto predAttr = op.getAttrOfType<mlir::IntegerAttr>("predicate");
+ auto predAttr = llvm::dyn_cast_or_null<mlir::IntegerAttr>(
+ op.getInherentAttr("predicate").value_or(mlir::Attribute{}));
if (predAttr) {
auto predName = mlir::arith::stringifyCmpIPredicate(
static_cast<mlir::arith::CmpIPredicate>(predAttr.getInt()));
@@ -460,7 +461,8 @@ def AtomicCompareOpInterface : OpInterface<"AtomicCompareOpInterface"> {
break;
} else if (opName == "arith.cmpf" || opName == "llvm.fcmp") {
foundComparison = true;
- auto predAttr = op.getAttrOfType<mlir::IntegerAttr>("predicate");
+ auto predAttr = llvm::dyn_cast_or_null<mlir::IntegerAttr>(
+ op.getInherentAttr("predicate").value_or(mlir::Attribute{}));
if (predAttr) {
auto predName = mlir::arith::stringifyCmpFPredicate(
static_cast<mlir::arith::CmpFPredicate>(predAttr.getInt()));
@@ -475,7 +477,8 @@ def AtomicCompareOpInterface : OpInterface<"AtomicCompareOpInterface"> {
break;
} else if (opName == "fir.cmpc") {
foundComparison = true;
- auto predAttr = op.getAttrOfType<mlir::IntegerAttr>("predicate");
+ auto predAttr = llvm::dyn_cast_or_null<mlir::IntegerAttr>(
+ op.getInherentAttr("predicate").value_or(mlir::Attribute{}));
if (predAttr) {
auto predName = mlir::arith::stringifyCmpFPredicate(
static_cast<mlir::arith::CmpFPredicate>(predAttr.getInt()));
diff --git a/mlir/include/mlir/Dialect/OpenMP/OpenMPOpsInterfaces.td b/mlir/include/mlir/Dialect/OpenMP/OpenMPOpsInterfaces.td
index 51f925b17f47e..6b66ba6a7022d 100644
--- a/mlir/include/mlir/Dialect/OpenMP/OpenMPOpsInterfaces.td
+++ b/mlir/include/mlir/Dialect/OpenMP/OpenMPOpsInterfaces.td
@@ -157,6 +157,13 @@ def BlockArgOpenMPOpInterface : OpInterface<"BlockArgOpenMPOpInterface"> {
"iface." # clause.blockArgsMethod.name # "()))" # [{
pairs.emplace_back(var, arg);
} }]), "\n")
+ >,
+ InterfaceMethod<
+ "Get the symbols referenced by the private clause.",
+ "::mlir::ArrayAttr", "getPrivateSymsAttribute", (ins), [{}], [{
+ auto attr = $_op->getInherentAttr("private_syms");
+ return ::llvm::cast<::mlir::ArrayAttr>(attr.value());
+ }]
>
]
);
@@ -297,7 +304,7 @@ def ComposableOpInterface : OpInterface<"ComposableOpInterface"> {
/*retTy=*/"bool",
/*methodName=*/"isComposite",
(ins ), [{}], [{
- return $_op->hasAttr("omp.composite");
+ return $_op->hasDiscardableAttr("omp.composite");
}]
>,
InterfaceMethod<
@@ -322,7 +329,7 @@ def ComposableOpInterface : OpInterface<"ComposableOpInterface"> {
/*retTy=*/"bool",
/*methodName=*/"isCombined",
(ins ), [{}], [{
- return $_op->hasAttr("omp.combined");
+ return $_op->hasDiscardableAttr("omp.combined");
}]
>,
InterfaceMethod<
@@ -377,7 +384,7 @@ def DeclareTargetInterface : OpInterface<"DeclareTargetInterface"> {
(ins "mlir::omp::DeclareTargetDeviceType":$deviceType,
"mlir::omp::DeclareTargetCaptureClause":$captureClause,
"bool":$automap), [{}], [{
- $_op->setAttr("omp.declare_target",
+ $_op->setDiscardableAttr("omp.declare_target",
mlir::omp::DeclareTargetAttr::get(
$_op->getContext(),
mlir::omp::DeclareTargetDeviceTypeAttr::get(
@@ -395,7 +402,7 @@ def DeclareTargetInterface : OpInterface<"DeclareTargetInterface"> {
/*retTy=*/"bool",
/*methodName=*/"isDeclareTarget",
(ins), [{}], [{
- return $_op->hasAttr("omp.declare_target");
+ return $_op->hasDiscardableAttr("omp.declare_target");
}]>,
InterfaceMethod<
/*description=*/[{
@@ -405,7 +412,7 @@ def DeclareTargetInterface : OpInterface<"DeclareTargetInterface"> {
/*retTy=*/"mlir::omp::DeclareTargetDeviceType",
/*methodName=*/"getDeclareTargetDeviceType",
(ins), [{}], [{
- if (mlir::Attribute dTar = $_op->getAttr("omp.declare_target"))
+ if (mlir::Attribute dTar = $_op->getDiscardableAttr("omp.declare_target"))
if (auto dAttr = llvm::dyn_cast_or_null<mlir::omp::DeclareTargetAttr>(dTar))
return dAttr.getDeviceType().getValue();
return {};
@@ -418,7 +425,7 @@ def DeclareTargetInterface : OpInterface<"DeclareTargetInterface"> {
/*retTy=*/"mlir::omp::DeclareTargetCaptureClause",
/*methodName=*/"getDeclareTargetCaptureClause",
(ins), [{}], [{
- if (mlir::Attribute dTar = $_op->getAttr("omp.declare_target"))
+ if (mlir::Attribute dTar = $_op->getDiscardableAttr("omp.declare_target"))
if (auto dAttr = llvm::dyn_cast_or_null<mlir::omp::DeclareTargetAttr>(dTar))
return dAttr.getCaptureClause().getValue();
return {};
@@ -430,7 +437,7 @@ def DeclareTargetInterface : OpInterface<"DeclareTargetInterface"> {
/*retTy=*/"bool",
/*methodName=*/"getDeclareTargetAutomap",
(ins), [{}], [{
- if (mlir::Attribute dTar = $_op->getAttr("omp.declare_target"))
+ if (mlir::Attribute dTar = $_op->getDiscardableAttr("omp.declare_target"))
if (auto dAttr = llvm::dyn_cast_or_null<mlir::omp::DeclareTargetAttr>(dTar))
if (auto autoVal = dAttr.getAutomap())
return autoVal.getValue();
@@ -456,7 +463,7 @@ def OffloadModuleInterface : OpInterface<"OffloadModuleInterface"> {
/*retTy=*/"void",
/*methodName=*/"setIsTargetDevice",
(ins "bool":$isTargetDevice), [{}], [{
- $_op->setAttr(
+ $_op->setDiscardableAttr(
mlir::StringAttr::get($_op->getContext(), llvm::Twine{"omp.is_target_device"}),
mlir::BoolAttr::get($_op->getContext(), isTargetDevice));
}]>,
@@ -468,7 +475,7 @@ def OffloadModuleInterface : OpInterface<"OffloadModuleInterface"> {
/*retTy=*/"bool",
/*methodName=*/"getIsTargetDevice",
(ins), [{}], [{
- if (Attribute isTargetDevice = $_op->getAttr("omp.is_target_device"))
+ if (Attribute isTargetDevice = $_op->getDiscardableAttr("omp.is_target_device"))
if (::llvm::isa<mlir::BoolAttr>(isTargetDevice))
return ::llvm::dyn_cast<BoolAttr>(isTargetDevice).getValue();
return false;
@@ -481,7 +488,7 @@ def OffloadModuleInterface : OpInterface<"OffloadModuleInterface"> {
/*retTy=*/"void",
/*methodName=*/"setIsGPU",
(ins "bool":$isGPU), [{}], [{
- $_op->setAttr(
+ $_op->setDiscardableAttr(
mlir::StringAttr::get($_op->getContext(), "omp.is_gpu"),
mlir::BoolAttr::get($_op->getContext(), isGPU));
}]>,
@@ -493,7 +500,7 @@ def OffloadModuleInterface : OpInterface<"OffloadModuleInterface"> {
/*retTy=*/"bool",
/*methodName=*/"getIsGPU",
(ins), [{}], [{
- if (Attribute isTargetCGAttr = $_op->getAttr("omp.is_gpu"))
+ if (Attribute isTargetCGAttr = $_op->getDiscardableAttr("omp.is_gpu"))
if (auto isTargetCGVal = ::llvm::dyn_cast<BoolAttr>(isTargetCGAttr))
return isTargetCGVal.getValue();
return false;
@@ -506,7 +513,7 @@ def OffloadModuleInterface : OpInterface<"OffloadModuleInterface"> {
/*retTy=*/"mlir::omp::FlagsAttr",
/*methodName=*/"getFlags",
(ins), [{}], [{
- if (Attribute flags = $_op->getAttr("omp.flags"))
+ if (Attribute flags = $_op->getDiscardableAttr("omp.flags"))
return ::llvm::dyn_cast_or_null<mlir::omp::FlagsAttr>(flags);
return nullptr;
}]>,
@@ -524,7 +531,7 @@ def OffloadModuleInterface : OpInterface<"OffloadModuleInterface"> {
"bool":$assumeNoNestedParallelism,
"uint32_t":$openmpDeviceVersion,
"bool":$noGPULib), [{}], [{
- $_op->setAttr(("omp." + mlir::omp::FlagsAttr::getMnemonic()).str(),
+ $_op->setDiscardableAttr(("omp." + mlir::omp::FlagsAttr::getMnemonic()).str(),
mlir::omp::FlagsAttr::get($_op->getContext(), debugKind,
assumeTeamsOversubscription, assumeThreadsOversubscription,
assumeNoThreadState, assumeNoNestedParallelism, noGPULib, openmpDeviceVersion));
@@ -538,7 +545,7 @@ def OffloadModuleInterface : OpInterface<"OffloadModuleInterface"> {
/*retTy=*/"void",
/*methodName=*/"setHostIRFilePath",
(ins "std::string":$hostIRFilePath), [{}], [{
- $_op->setAttr(
+ $_op->setDiscardableAttr(
mlir::StringAttr::get($_op->getContext(), llvm::Twine{"omp.host_ir_filepath"}),
mlir::StringAttr::get($_op->getContext(), hostIRFilePath));
}]>,
@@ -552,7 +559,7 @@ def OffloadModuleInterface : OpInterface<"OffloadModuleInterface"> {
/*retTy=*/"llvm::StringRef",
/*methodName=*/"getHostIRFilePath",
(ins), [{}], [{
- if (Attribute filepath = $_op->getAttr("omp.host_ir_filepath"))
+ if (Attribute filepath = $_op->getDiscardableAttr("omp.host_ir_filepath"))
if (::llvm::isa<mlir::StringAttr>(filepath))
return ::llvm::dyn_cast<mlir::StringAttr>(filepath).getValue();
return {};
@@ -566,7 +573,7 @@ def OffloadModuleInterface : OpInterface<"OffloadModuleInterface"> {
/*retTy=*/"::mlir::omp::ClauseRequires",
/*methodName=*/"getRequires",
(ins), [{}], [{
- if (Attribute requiresAttr = $_op->getAttr("omp.requires"))
+ if (Attribute requiresAttr = $_op->getDiscardableAttr("omp.requires"))
if (auto requiresVal = ::llvm::dyn_cast<mlir::omp::ClauseRequiresAttr>(requiresAttr))
return requiresVal.getValue();
return mlir::omp::ClauseRequires::none;
@@ -578,7 +585,7 @@ def OffloadModuleInterface : OpInterface<"OffloadModuleInterface"> {
/*retTy=*/"void",
/*methodName=*/"setRequires",
(ins "::mlir::omp::ClauseRequires":$clauses), [{}], [{
- $_op->setAttr(mlir::StringAttr::get($_op->getContext(), "omp.requires"),
+ $_op->setDiscardableAttr(mlir::StringAttr::get($_op->getContext(), "omp.requires"),
mlir::omp::ClauseRequiresAttr::get($_op->getContext(), clauses));
}]>,
InterfaceMethod<
@@ -589,7 +596,7 @@ def OffloadModuleInterface : OpInterface<"OffloadModuleInterface"> {
/*retTy=*/"::llvm::ArrayRef<::mlir::Attribute>",
/*methodName=*/"getTargetTriples",
(ins), [{}], [{
- if (Attribute triplesAttr = $_op->getAttr("omp.target_triples"))
+ if (Attribute triplesAttr = $_op->getDiscardableAttr("omp.target_triples"))
if (auto triples = ::llvm::dyn_cast<::mlir::ArrayAttr>(triplesAttr))
return triples.getValue();
return {};
@@ -605,7 +612,7 @@ def OffloadModuleInterface : OpInterface<"OffloadModuleInterface"> {
targetTriples, [&](::std::string str) -> ::mlir::Attribute {
return mlir::StringAttr::get($_op->getContext(), str);
}));
- $_op->setAttr(
+ $_op->setDiscardableAttr(
::mlir::StringAttr::get($_op->getContext(), "omp.target_triples"),
::mlir::ArrayAttr::get($_op->getContext(), names));
}]>
diff --git a/mlir/include/mlir/Dialect/Shard/Transforms/Simplify.h b/mlir/include/mlir/Dialect/Shard/Transforms/Simplify.h
index f3f4feffd8a71..5f961743015f9 100644
--- a/mlir/include/mlir/Dialect/Shard/Transforms/Simplify.h
+++ b/mlir/include/mlir/Dialect/Shard/Transforms/Simplify.h
@@ -84,7 +84,10 @@ void populateAllReduceEndomorphismSimplifyPatterns(RewritePatternSet &patterns,
auto refAllReduceOp = llvm::dyn_cast<AllReduceOp>(referenceOp.value());
auto refType = cast<ShapedType>(refAllReduceOp.getResult().getType());
- return refAllReduceOp->getAttrs() == allReduceOp->getAttrs() &&
+ return refAllReduceOp.getGridAttr() == allReduceOp.getGridAttr() &&
+ refAllReduceOp.getGridAxesAttr() == allReduceOp.getGridAxesAttr() &&
+ refAllReduceOp->getDiscardableAttrDictionary() ==
+ allReduceOp->getDiscardableAttrDictionary() &&
inType.getElementType() == refType.getElementType();
};
auto isAlgebraicOp = [](Operation *op) { return isa<AlgebraicOp>(op); };
diff --git a/mlir/include/mlir/Dialect/Tosa/Utils/ConversionUtils.h b/mlir/include/mlir/Dialect/Tosa/Utils/ConversionUtils.h
index df4dabc2afda8..15b91bb529390 100644
--- a/mlir/include/mlir/Dialect/Tosa/Utils/ConversionUtils.h
+++ b/mlir/include/mlir/Dialect/Tosa/Utils/ConversionUtils.h
@@ -101,10 +101,10 @@ TosaOp createOpAndInferShape(ImplicitLocOpBuilder &builder, Type resultTy,
SmallVector<ShapedTypeComponents> returnedShapes;
if (shapeInterface
- .inferReturnTypeComponents(op.getContext(), builder.getLoc(),
- op->getOperands(), op->getAttrDictionary(),
- op->getPropertiesStorage(),
- op->getRegions(), returnedShapes)
+ .inferReturnTypeComponents(
+ op.getContext(), builder.getLoc(), op->getOperands(),
+ op->getDiscardableAttrDictionary(), op->getPropertiesStorage(),
+ op->getRegions(), returnedShapes)
.failed())
return op;
diff --git a/mlir/include/mlir/IR/Matchers.h b/mlir/include/mlir/IR/Matchers.h
index e577909621cb8..c2169c3d19238 100644
--- a/mlir/include/mlir/IR/Matchers.h
+++ b/mlir/include/mlir/IR/Matchers.h
@@ -65,7 +65,13 @@ struct NameOpMatcher {
/// The matcher that matches operations that have the specified attribute name.
struct AttrOpMatcher {
AttrOpMatcher(StringRef attrName) : attrName(attrName) {}
- bool match(Operation *op) { return op->hasAttr(attrName); }
+ bool match(Operation *op) {
+ std::optional<Attribute> inherent;
+ if (op->getPropertiesStorageSize())
+ inherent = op->getInherentAttr(attrName);
+ return inherent.has_value() ? static_cast<bool>(*inherent)
+ : op->hasDiscardableAttr(attrName);
+ }
StringRef attrName;
};
@@ -146,7 +152,10 @@ struct AttrOpBinder {
AttrOpBinder(StringRef attrName) : attrName(attrName), bindValue(nullptr) {}
bool match(Operation *op) {
- if (auto attr = op->getAttrOfType<AttrT>(attrName)) {
+ Attribute rawAttr = op->getDiscardableAttr(attrName);
+ if (op->getPropertiesStorageSize())
+ rawAttr = op->getInherentAttr(attrName).value_or(rawAttr);
+ if (auto attr = dyn_cast_or_null<AttrT>(rawAttr)) {
if (bindValue)
*bindValue = attr;
return true;
diff --git a/mlir/include/mlir/IR/Operation.h b/mlir/include/mlir/IR/Operation.h
index 793c046fbf2e5..03f0afdf64b25 100644
--- a/mlir/include/mlir/IR/Operation.h
+++ b/mlir/include/mlir/IR/Operation.h
@@ -481,6 +481,26 @@ class alignas(8) Operation final
/// discardable attribute does not exist.
Attribute getDiscardableAttr(StringAttr name) { return attrs.get(name); }
+ /// Access a discardable attribute by name and cast it to `AttrClass`.
+ template <typename AttrClass>
+ AttrClass getDiscardableAttrOfType(StringRef name) {
+ return llvm::dyn_cast_or_null<AttrClass>(getDiscardableAttr(name));
+ }
+ template <typename AttrClass>
+ AttrClass getDiscardableAttrOfType(StringAttr name) {
+ return llvm::dyn_cast_or_null<AttrClass>(getDiscardableAttr(name));
+ }
+
+ /// Return true if this operation has a discardable attribute with the
+ /// provided name.
+ bool hasDiscardableAttr(StringRef name) { return bool(attrs.get(name)); }
+ bool hasDiscardableAttr(StringAttr name) { return bool(attrs.get(name)); }
+ template <typename AttrClass, typename NameT>
+ bool hasDiscardableAttrOfType(NameT &&name) {
+ return static_cast<bool>(
+ getDiscardableAttrOfType<AttrClass>(std::forward<NameT>(name)));
+ }
+
/// Set a discardable attribute by name.
void setDiscardableAttr(StringAttr name, Attribute value) {
NamedAttrList attributes(attrs);
@@ -534,15 +554,25 @@ class alignas(8) Operation final
DictionaryAttr getRawDictionaryAttrs() { return attrs; }
/// Return all of the attributes on this operation.
- ArrayRef<NamedAttribute> getAttrs() { return getAttrDictionary().getValue(); }
+ [[deprecated("use getDiscardableAttrs() and operation-specific accessors "
+ "instead")]]
+ ArrayRef<NamedAttribute> getAttrs() {
+ return getAttrDictionary().getValue();
+ }
/// Return all of the attributes on this operation as a DictionaryAttr.
+ [[deprecated("use getDiscardableAttrDictionary() and operation-specific "
+ "accessors instead")]]
DictionaryAttr getAttrDictionary();
/// Set the attributes from a dictionary on this operation.
/// These methods are expensive: if the dictionary only contains discardable
/// attributes, `setDiscardableAttrs` is more efficient.
+ [[deprecated("use setDiscardableAttrs() and operation-specific mutators "
+ "instead")]]
void setAttrs(DictionaryAttr newAttrs);
+ [[deprecated("use setDiscardableAttrs() and operation-specific mutators "
+ "instead")]]
void setAttrs(ArrayRef<NamedAttribute> newAttrs);
/// Set the discardable attribute dictionary on this operation.
void setDiscardableAttrs(DictionaryAttr newAttrs) {
@@ -556,6 +586,8 @@ class alignas(8) Operation final
/// Return the specified attribute if present, null otherwise.
/// These methods are expensive: if the dictionary only contains discardable
/// attributes, `getDiscardableAttr` is more efficient.
+ [[deprecated("use getDiscardableAttr() or an operation-specific accessor "
+ "instead")]]
Attribute getAttr(StringAttr name) {
if (getPropertiesStorageSize()) {
if (std::optional<Attribute> inherentAttr = getInherentAttr(name))
@@ -563,6 +595,8 @@ class alignas(8) Operation final
}
return attrs.get(name);
}
+ [[deprecated("use getDiscardableAttr() or an operation-specific accessor "
+ "instead")]]
Attribute getAttr(StringRef name) {
if (getPropertiesStorageSize()) {
if (std::optional<Attribute> inherentAttr = getInherentAttr(name))
@@ -572,16 +606,22 @@ class alignas(8) Operation final
}
template <typename AttrClass>
+ [[deprecated("use getDiscardableAttrOfType() or an operation-specific "
+ "accessor instead")]]
AttrClass getAttrOfType(StringAttr name) {
return llvm::dyn_cast_or_null<AttrClass>(getAttr(name));
}
template <typename AttrClass>
+ [[deprecated("use getDiscardableAttrOfType() or an operation-specific "
+ "accessor instead")]]
AttrClass getAttrOfType(StringRef name) {
return llvm::dyn_cast_or_null<AttrClass>(getAttr(name));
}
/// Return true if the operation has an attribute with the provided name,
/// false otherwise.
+ [[deprecated("use hasDiscardableAttr() or an operation-specific accessor "
+ "instead")]]
bool hasAttr(StringAttr name) {
if (getPropertiesStorageSize()) {
if (std::optional<Attribute> inherentAttr = getInherentAttr(name))
@@ -589,6 +629,8 @@ class alignas(8) Operation final
}
return attrs.contains(name);
}
+ [[deprecated("use hasDiscardableAttr() or an operation-specific accessor "
+ "instead")]]
bool hasAttr(StringRef name) {
if (getPropertiesStorageSize()) {
if (std::optional<Attribute> inherentAttr = getInherentAttr(name))
@@ -597,6 +639,8 @@ class alignas(8) Operation final
return attrs.contains(name);
}
template <typename AttrClass, typename NameT>
+ [[deprecated("use hasDiscardableAttrOfType() or an operation-specific "
+ "accessor instead")]]
bool hasAttrOfType(NameT &&name) {
return static_cast<bool>(
getAttrOfType<AttrClass>(std::forward<NameT>(name)));
@@ -604,6 +648,8 @@ class alignas(8) Operation final
/// If the an attribute exists with the specified name, change it to the new
/// value. Otherwise, add a new attribute with the specified name/value.
+ [[deprecated("use setDiscardableAttr() or an operation-specific mutator "
+ "instead")]]
void setAttr(StringAttr name, Attribute value) {
if (getPropertiesStorageSize()) {
if (getInherentAttr(name)) {
@@ -615,6 +661,8 @@ class alignas(8) Operation final
if (attributes.set(name, value) != value)
attrs = attributes.getDictionary(getContext());
}
+ [[deprecated("use setDiscardableAttr() or an operation-specific mutator "
+ "instead")]]
void setAttr(StringRef name, Attribute value) {
setAttr(StringAttr::get(getContext(), name), value);
}
@@ -622,6 +670,8 @@ class alignas(8) Operation final
/// Remove the attribute with the specified name if it exists. Return the
/// attribute that was erased, or nullptr if there was no attribute with such
/// name.
+ [[deprecated("use removeDiscardableAttr() or an operation-specific mutator "
+ "instead")]]
Attribute removeAttr(StringAttr name) {
if (getPropertiesStorageSize()) {
if (std::optional<Attribute> inherentAttr = getInherentAttr(name)) {
@@ -635,6 +685,8 @@ class alignas(8) Operation final
attrs = attributes.getDictionary(getContext());
return removedAttr;
}
+ [[deprecated("use removeDiscardableAttr() or an operation-specific mutator "
+ "instead")]]
Attribute removeAttr(StringRef name) {
return removeAttr(StringAttr::get(getContext(), name));
}
@@ -660,35 +712,51 @@ class alignas(8) Operation final
/// Return a range corresponding to the dialect attributes for this operation.
dialect_attr_range getDialectAttrs() {
- auto attrs = getAttrs();
- return {dialect_attr_iterator(attrs.begin(), attrs.end()),
- dialect_attr_iterator(attrs.end(), attrs.end())};
+ ArrayRef<NamedAttribute> rawAttrs = attrs.getValue();
+ return {dialect_attr_iterator(rawAttrs.begin(), rawAttrs.end()),
+ dialect_attr_iterator(rawAttrs.end(), rawAttrs.end())};
}
dialect_attr_iterator dialect_attr_begin() {
- auto attrs = getAttrs();
- return dialect_attr_iterator(attrs.begin(), attrs.end());
+ ArrayRef<NamedAttribute> rawAttrs = attrs.getValue();
+ return dialect_attr_iterator(rawAttrs.begin(), rawAttrs.end());
}
dialect_attr_iterator dialect_attr_end() {
- auto attrs = getAttrs();
- return dialect_attr_iterator(attrs.end(), attrs.end());
+ ArrayRef<NamedAttribute> rawAttrs = attrs.getValue();
+ return dialect_attr_iterator(rawAttrs.end(), rawAttrs.end());
}
/// Set the dialect attributes for this operation, and preserve all inherent.
template <typename DialectAttrT>
void setDialectAttrs(DialectAttrT &&dialectAttrs) {
- NamedAttrList attrs;
- attrs.append(std::begin(dialectAttrs), std::end(dialectAttrs));
- for (auto attr : getAttrs())
+ NamedAttrList newAttrs;
+ newAttrs.append(std::begin(dialectAttrs), std::end(dialectAttrs));
+ for (auto attr : attrs)
if (!attr.getName().strref().contains('.'))
- attrs.push_back(attr);
- setAttrs(attrs.getDictionary(getContext()));
+ newAttrs.push_back(attr);
+ setDiscardableAttrs(newAttrs.getDictionary(getContext()));
}
/// Sets default attributes on unset attributes.
void populateDefaultAttrs() {
- NamedAttrList attrs(getAttrDictionary());
- name.populateDefaultAttrs(attrs);
- setAttrs(attrs.getDictionary(getContext()));
+ NamedAttrList allAttrs;
+ if (getPropertiesStorageSize())
+ name.populateInherentAttrs(this, allAttrs);
+ allAttrs.append(getDiscardableAttrDictionary().getValue());
+ name.populateDefaultAttrs(allAttrs);
+
+ if (!getPropertiesStorageSize()) {
+ setDiscardableAttrs(allAttrs.getDictionary(getContext()));
+ return;
+ }
+
+ NamedAttrList discardableAttrs;
+ for (NamedAttribute attr : allAttrs) {
+ if (getInherentAttr(attr.getName()).has_value())
+ setInherentAttr(attr.getName(), attr.getValue());
+ else
+ discardableAttrs.append(attr);
+ }
+ setDiscardableAttrs(discardableAttrs.getDictionary(getContext()));
}
//===--------------------------------------------------------------------===//
diff --git a/mlir/include/mlir/IR/SymbolInterfaces.td b/mlir/include/mlir/IR/SymbolInterfaces.td
index 292c355cbe157..473aa0a1b85ed 100644
--- a/mlir/include/mlir/IR/SymbolInterfaces.td
+++ b/mlir/include/mlir/IR/SymbolInterfaces.td
@@ -42,8 +42,7 @@ def Symbol : OpInterface<"SymbolOpInterface"> {
InterfaceMethod<"Sets the name of this symbol.",
"void", "setName", (ins "::mlir::StringAttr":$name), [{}],
/*defaultImplementation=*/[{
- this->getOperation()->setAttr(
- mlir::SymbolTable::getSymbolAttrName(), name);
+ mlir::SymbolTable::setSymbolName(this->getOperation(), name);
}]
>,
InterfaceMethod<"Gets the visibility of this symbol.",
@@ -197,7 +196,9 @@ def Symbol : OpInterface<"SymbolOpInterface"> {
// Add additional classof checks to properly handle "optional" symbols.
let extraClassOf = [{
- return $_op->hasAttr(::mlir::SymbolTable::getSymbolAttrName());
+ return static_cast<bool>(
+ $_op->getInherentAttr(::mlir::SymbolTable::getSymbolAttrName())
+ .value_or(::mlir::Attribute{}));
}];
}
diff --git a/mlir/include/mlir/Target/SMTLIB/Namespace.h b/mlir/include/mlir/Target/SMTLIB/Namespace.h
index 09bd5cd2d407b..8032292cddd38 100644
--- a/mlir/include/mlir/Target/SMTLIB/Namespace.h
+++ b/mlir/include/mlir/Target/SMTLIB/Namespace.h
@@ -47,8 +47,9 @@ class Namespace {
void add(mlir::ModuleOp module) {
assert(module->getNumRegions() == 1);
for (auto &op : module.getBody(0)->getOperations())
- if (auto symbol = op.getAttrOfType<mlir::StringAttr>(
- mlir::SymbolTable::getSymbolAttrName()))
+ if (auto symbol = llvm::dyn_cast_or_null<mlir::StringAttr>(
+ op.getInherentAttr(mlir::SymbolTable::getSymbolAttrName())
+ .value_or(mlir::Attribute{})))
nextIndex.insert({symbol.getValue(), 0});
}
diff --git a/mlir/lib/Analysis/CallGraph.cpp b/mlir/lib/Analysis/CallGraph.cpp
index d6fe62d8e58d6..a09c913029e57 100644
--- a/mlir/lib/Analysis/CallGraph.cpp
+++ b/mlir/lib/Analysis/CallGraph.cpp
@@ -195,9 +195,16 @@ void CallGraph::print(raw_ostream &os) const {
auto *parentOp = callableRegion->getParentOp();
os << "'" << callableRegion->getParentOp()->getName() << "' - Region #"
<< callableRegion->getRegionNumber();
- auto attrs = parentOp->getAttrDictionary();
- if (!attrs.empty())
- os << " : " << attrs;
+ NamedAttrList attrs(parentOp->getDiscardableAttrDictionary());
+ parentOp->getName().populateInherentAttrs(parentOp, attrs);
+ if (!attrs.empty()) {
+ os << " : { ";
+ llvm::interleaveComma(attrs, os, [&](NamedAttribute attr) {
+ os << attr.getName().getValue() << " = ";
+ attr.getValue().print(os);
+ });
+ os << " }";
+ }
};
for (auto &nodeIt : nodes) {
diff --git a/mlir/lib/Analysis/DataFlow/ConstantPropagationAnalysis.cpp b/mlir/lib/Analysis/DataFlow/ConstantPropagationAnalysis.cpp
index e6e7491b041ee..d067365a65c6c 100644
--- a/mlir/lib/Analysis/DataFlow/ConstantPropagationAnalysis.cpp
+++ b/mlir/lib/Analysis/DataFlow/ConstantPropagationAnalysis.cpp
@@ -70,7 +70,8 @@ LogicalResult SparseConstantPropagation::visitOperation(
// folds in-place. The constant passed in may not correspond to the real
// runtime value, so in-place updates are not allowed.
SmallVector<Value, 8> originalOperands(op->getOperands());
- DictionaryAttr originalAttrs = op->getAttrDictionary();
+ DictionaryAttr originalAttrs = op->getDiscardableAttrDictionary();
+ Attribute originalProperties = op->getPropertiesAsAttribute();
// Simulate the result of folding this operation to a constant.
SmallVector<OpFoldResult, 8> foldResults;
@@ -83,7 +84,10 @@ LogicalResult SparseConstantPropagation::visitOperation(
// relinks use-lists even for identical values.
if (!llvm::equal(op->getOperands(), originalOperands))
op->setOperands(originalOperands);
- op->setAttrs(originalAttrs);
+ op->setDiscardableAttrs(originalAttrs);
+ if (originalProperties)
+ (void)op->setPropertiesFromAttribute(originalProperties,
+ /*emitError=*/nullptr);
// If folding failed or was in-place, mark the results as overdefined. We
// don't allow in-place folds here: the goal is simulated execution, not
diff --git a/mlir/lib/Bytecode/Writer/BytecodeWriter.cpp b/mlir/lib/Bytecode/Writer/BytecodeWriter.cpp
index 90a1de6691d99..15d41acea84d2 100644
--- a/mlir/lib/Bytecode/Writer/BytecodeWriter.cpp
+++ b/mlir/lib/Bytecode/Writer/BytecodeWriter.cpp
@@ -1015,14 +1015,17 @@ LogicalResult BytecodeWriter::writeOp(EncodingEmitter &emitter, Operation *op) {
emitter.emitVarInt(numberingState.getNumber(op->getLoc()), "op location");
// Emit the attributes of this operation.
- DictionaryAttr attrs = op->getDiscardableAttrDictionary();
+ DictionaryAttr attrs = op->getRawDictionaryAttrs();
// Allow deployment to version <kNativePropertiesEncoding by merging inherent
// attribute with the discardable ones. We should fail if there are any
// conflicts. When properties are not used by the op, also store everything as
// attributes.
- if (config.bytecodeVersion < bytecode::kNativePropertiesEncoding ||
- !op->getPropertiesStorage()) {
- attrs = op->getAttrDictionary();
+ if (config.bytecodeVersion < bytecode::kNativePropertiesEncoding &&
+ op->getPropertiesStorage()) {
+ NamedAttrList allAttrs;
+ op->getName().populateInherentAttrs(op, allAttrs);
+ allAttrs.append(op->getDiscardableAttrDictionary().getValue());
+ attrs = allAttrs.getDictionary(op->getContext());
}
if (!attrs.empty()) {
opEncodingMask |= bytecode::OpEncodingMask::kHasAttrs;
diff --git a/mlir/lib/Bytecode/Writer/IRNumbering.cpp b/mlir/lib/Bytecode/Writer/IRNumbering.cpp
index 04625628fa5a6..fa6580a76d0e1 100644
--- a/mlir/lib/Bytecode/Writer/IRNumbering.cpp
+++ b/mlir/lib/Bytecode/Writer/IRNumbering.cpp
@@ -446,10 +446,16 @@ void IRNumberingState::number(Operation &op) {
// not used, we need to number also the merged dictionary containing both the
// inherent and discardable attribute.
DictionaryAttr dictAttr;
- if (config.getDesiredBytecodeVersion() >= bytecode::kNativePropertiesEncoding)
+ if (config.getDesiredBytecodeVersion() >=
+ bytecode::kNativePropertiesEncoding ||
+ !op.getPropertiesStorage())
dictAttr = op.getRawDictionaryAttrs();
- else
- dictAttr = op.getAttrDictionary();
+ else {
+ NamedAttrList attrs;
+ op.getName().populateInherentAttrs(&op, attrs);
+ attrs.append(op.getDiscardableAttrDictionary().getValue());
+ dictAttr = attrs.getDictionary(op.getContext());
+ }
// Only number the operation's dictionary if it isn't empty.
if (!dictAttr.empty())
number(dictAttr);
diff --git a/mlir/lib/CAPI/Dialect/Linalg.cpp b/mlir/lib/CAPI/Dialect/Linalg.cpp
index 92ead3eed9a95..3ddb76d865246 100644
--- a/mlir/lib/CAPI/Dialect/Linalg.cpp
+++ b/mlir/lib/CAPI/Dialect/Linalg.cpp
@@ -39,7 +39,10 @@ void mlirLinalgFillBuiltinNamedOpRegion(MlirOperation mlirOp) {
Region ®ion = op->getRegion(0);
Block *body = b.createBlock(®ion, /*insertPt=*/{}, argTypes, argLocs);
b.setInsertionPointToStart(body);
- fun(b, *body, op->getAttrs(), /*emitError=*/{});
+ NamedAttrList attrs;
+ op->getName().populateInherentAttrs(op, attrs);
+ attrs.append(op->getDiscardableAttrDictionary().getValue());
+ fun(b, *body, attrs, /*emitError=*/{});
}
MLIR_CAPI_EXPORTED bool mlirLinalgIsAContractionOp(MlirOperation op) {
diff --git a/mlir/lib/CAPI/IR/IR.cpp b/mlir/lib/CAPI/IR/IR.cpp
index ef730b26cdd5d..0cc65e4fa7989 100644
--- a/mlir/lib/CAPI/IR/IR.cpp
+++ b/mlir/lib/CAPI/IR/IR.cpp
@@ -806,13 +806,13 @@ void mlirOperationSetInherentAttributeByName(MlirOperation op,
intptr_t mlirOperationGetNumDiscardableAttributes(MlirOperation op) {
return static_cast<intptr_t>(
- llvm::range_size(unwrap(op)->getDiscardableAttrs()));
+ llvm::range_size(unwrap(op)->getDiscardableAttrDictionary().getValue()));
}
MlirNamedAttribute mlirOperationGetDiscardableAttribute(MlirOperation op,
intptr_t pos) {
- NamedAttribute attr =
- *std::next(unwrap(op)->getDiscardableAttrs().begin(), pos);
+ NamedAttribute attr = *std::next(
+ unwrap(op)->getDiscardableAttrDictionary().getValue().begin(), pos);
return MlirNamedAttribute{wrap(attr.getName()), wrap(attr.getValue())};
}
@@ -837,6 +837,7 @@ void mlirOperationSetSuccessor(MlirOperation op, intptr_t pos,
unwrap(op)->setSuccessor(unwrap(block), static_cast<unsigned>(pos));
}
+LLVM_SUPPRESS_DEPRECATED_DECLARATIONS_PUSH
intptr_t mlirOperationGetNumAttributes(MlirOperation op) {
return static_cast<intptr_t>(unwrap(op)->getAttrs().size());
}
@@ -859,6 +860,7 @@ void mlirOperationSetAttributeByName(MlirOperation op, MlirStringRef name,
bool mlirOperationRemoveAttributeByName(MlirOperation op, MlirStringRef name) {
return !!unwrap(op)->removeAttr(unwrap(name));
}
+LLVM_SUPPRESS_DEPRECATED_DECLARATIONS_POP
void mlirOperationPrint(MlirOperation op, MlirStringCallback callback,
void *userData) {
diff --git a/mlir/lib/Conversion/AMDGPUToROCDL/AMDGPUToROCDL.cpp b/mlir/lib/Conversion/AMDGPUToROCDL/AMDGPUToROCDL.cpp
index e8f77d6c9f435..fe160132f40f1 100644
--- a/mlir/lib/Conversion/AMDGPUToROCDL/AMDGPUToROCDL.cpp
+++ b/mlir/lib/Conversion/AMDGPUToROCDL/AMDGPUToROCDL.cpp
@@ -3219,9 +3219,9 @@ struct AMDGPUDPPLowering : public ConvertOpToLLVMPattern<DPPOp> {
// Check for row_mask, bank_mask, bound_ctrl if they exist and create
// constants
- auto rowMask = DppOp->getAttrOfType<IntegerAttr>("row_mask").getInt();
- auto bankMask = DppOp->getAttrOfType<IntegerAttr>("bank_mask").getInt();
- bool boundCtrl = DppOp->getAttrOfType<BoolAttr>("bound_ctrl").getValue();
+ auto rowMask = DppOp.getRowMask();
+ auto bankMask = DppOp.getBankMask();
+ bool boundCtrl = DppOp.getBoundCtrl();
// create a ROCDL_DPPMovOp instruction with the appropriate attributes
auto dppMovOp =
diff --git a/mlir/lib/Conversion/ArithToLLVM/ArithToLLVM.cpp b/mlir/lib/Conversion/ArithToLLVM/ArithToLLVM.cpp
index 4e8ef252a10c9..d766c47a817f5 100644
--- a/mlir/lib/Conversion/ArithToLLVM/ArithToLLVM.cpp
+++ b/mlir/lib/Conversion/ArithToLLVM/ArithToLLVM.cpp
@@ -374,10 +374,10 @@ struct SelectOpOneToNLowering : public ConvertOpToLLVMPattern<arith::SelectOp> {
LogicalResult
ConstantOpLowering::matchAndRewrite(arith::ConstantOp op, OpAdaptor adaptor,
ConversionPatternRewriter &rewriter) const {
- return LLVM::detail::oneToOneRewrite(op, LLVM::ConstantOp::getOperationName(),
- adaptor.getOperands(), op->getAttrs(),
- /*propAttr=*/Attribute{},
- *getTypeConverter(), rewriter);
+ return LLVM::detail::oneToOneRewrite(
+ op, LLVM::ConstantOp::getOperationName(), adaptor.getOperands(),
+ op->getDiscardableAttrDictionary().getValue(),
+ op->getPropertiesAsAttribute(), *getTypeConverter(), rewriter);
}
//===----------------------------------------------------------------------===//
diff --git a/mlir/lib/Conversion/ArithToSPIRV/ArithToSPIRV.cpp b/mlir/lib/Conversion/ArithToSPIRV/ArithToSPIRV.cpp
index 614ac2b43b5f2..6478c188d7d2a 100644
--- a/mlir/lib/Conversion/ArithToSPIRV/ArithToSPIRV.cpp
+++ b/mlir/lib/Conversion/ArithToSPIRV/ArithToSPIRV.cpp
@@ -214,12 +214,14 @@ struct ElementwiseArithOpPattern final : OpConversionPattern<Op> {
op, dstType, adaptor.getOperands());
if (bitEnumContainsAny(overflowFlags, arith::IntegerOverflowFlags::nsw))
- newOp->setAttr(getDecorationString(spirv::Decoration::NoSignedWrap),
- rewriter.getUnitAttr());
+ newOp->setDiscardableAttr(
+ getDecorationString(spirv::Decoration::NoSignedWrap),
+ rewriter.getUnitAttr());
if (bitEnumContainsAny(overflowFlags, arith::IntegerOverflowFlags::nuw))
- newOp->setAttr(getDecorationString(spirv::Decoration::NoUnsignedWrap),
- rewriter.getUnitAttr());
+ newOp->setDiscardableAttr(
+ getDecorationString(spirv::Decoration::NoUnsignedWrap),
+ rewriter.getUnitAttr());
return success();
}
@@ -1059,7 +1061,7 @@ struct TypeCastingOpPattern final : public OpConversionPattern<Op> {
auto newOp = rewriter.template replaceOpWithNewOp<SPIRVOp>(
op, dstType, adaptor.getOperands());
if (rm) {
- newOp->setAttr(
+ newOp->setDiscardableAttr(
getDecorationString(spirv::Decoration::FPRoundingMode),
spirv::FPRoundingModeAttr::get(rewriter.getContext(), *rm));
}
diff --git a/mlir/lib/Conversion/ComplexToLLVM/ComplexToLLVM.cpp b/mlir/lib/Conversion/ComplexToLLVM/ComplexToLLVM.cpp
index ceda3888360ce..74acbe325c656 100644
--- a/mlir/lib/Conversion/ComplexToLLVM/ComplexToLLVM.cpp
+++ b/mlir/lib/Conversion/ComplexToLLVM/ComplexToLLVM.cpp
@@ -96,8 +96,8 @@ struct ConstantOpLowering : public ConvertOpToLLVMPattern<complex::ConstantOp> {
ConversionPatternRewriter &rewriter) const override {
return LLVM::detail::oneToOneRewrite(
op, LLVM::ConstantOp::getOperationName(), adaptor.getOperands(),
- op->getAttrs(), /*propAttr=*/Attribute{}, *getTypeConverter(),
- rewriter);
+ op->getDiscardableAttrDictionary().getValue(),
+ op->getPropertiesAsAttribute(), *getTypeConverter(), rewriter);
}
};
diff --git a/mlir/lib/Conversion/ControlFlowToLLVM/ControlFlowToLLVM.cpp b/mlir/lib/Conversion/ControlFlowToLLVM/ControlFlowToLLVM.cpp
index fef78a46d69fc..bf82d30d527ad 100644
--- a/mlir/lib/Conversion/ControlFlowToLLVM/ControlFlowToLLVM.cpp
+++ b/mlir/lib/Conversion/ControlFlowToLLVM/ControlFlowToLLVM.cpp
@@ -148,12 +148,12 @@ struct BranchOpLowering : public ConvertOpToLLVMPattern<cf::BranchOp> {
TypeRange(ValueRange(flattenedAdaptor)));
if (failed(convertedBlock))
return failure();
- DictionaryAttr attrs = op->getAttrDictionary();
+ DictionaryAttr attrs = op->getDiscardableAttrDictionary();
Operation *newOp = rewriter.replaceOpWithNewOp<LLVM::BrOp>(
op, flattenedAdaptor, *convertedBlock);
// TODO: We should not just forward all attributes like that. But there are
// existing Flang tests that depend on this behavior.
- newOp->setAttrs(attrs);
+ newOp->setDiscardableAttrs(attrs);
return success();
}
};
diff --git a/mlir/lib/Conversion/FuncToEmitC/FuncToEmitC.cpp b/mlir/lib/Conversion/FuncToEmitC/FuncToEmitC.cpp
index 81d15be7d548e..cec82782fc802 100644
--- a/mlir/lib/Conversion/FuncToEmitC/FuncToEmitC.cpp
+++ b/mlir/lib/Conversion/FuncToEmitC/FuncToEmitC.cpp
@@ -188,9 +188,12 @@ class CallOpConversion final : public OpConversionPattern<func::CallOp> {
}
if (callOp.getNumResults() <= 1) {
- rewriter.replaceOpWithNewOp<emitc::CallOp>(callOp, convertedResultTypes,
- adaptor.getOperands(),
- callOp->getAttrs());
+ auto newCall = rewriter.replaceOpWithNewOp<emitc::CallOp>(
+ callOp, callOp.getCalleeAttr(), convertedResultTypes,
+ adaptor.getOperands());
+ newCall.setArgAttrsAttr(callOp.getArgAttrsAttr());
+ newCall.setResAttrsAttr(callOp.getResAttrsAttr());
+ newCall->setDiscardableAttrs(callOp->getDiscardableAttrDictionary());
return success();
}
@@ -292,11 +295,19 @@ class FuncOpConversion final : public OpConversionPattern<func::FuncOp> {
signatureConverter.getConvertedTypes(),
resultType ? TypeRange(resultType) : TypeRange()));
+ newFuncOp.setArgAttrsAttr(funcOp.getArgAttrsAttr());
+ newFuncOp.setResAttrsAttr(funcOp.getResAttrsAttr());
+ if (StringAttr visibility = funcOp.getSymVisibilityAttr())
+ newFuncOp->setDiscardableAttr(SymbolTable::getVisibilityAttrName(),
+ visibility);
+
// Copy over all attributes other than the function name and type.
- for (const auto &namedAttr : funcOp->getAttrs()) {
+ for (const auto &namedAttr :
+ funcOp->getDiscardableAttrDictionary().getValue()) {
if (namedAttr.getName() != funcOp.getFunctionTypeAttrName() &&
namedAttr.getName() != SymbolTable::getSymbolAttrName())
- newFuncOp->setAttr(namedAttr.getName(), namedAttr.getValue());
+ newFuncOp->setDiscardableAttr(namedAttr.getName(),
+ namedAttr.getValue());
}
// Add `extern` to specifiers if `func.func` is declaration only.
diff --git a/mlir/lib/Conversion/FuncToLLVM/FuncToLLVM.cpp b/mlir/lib/Conversion/FuncToLLVM/FuncToLLVM.cpp
index 2686158f67e76..d531d6d7c18f1 100644
--- a/mlir/lib/Conversion/FuncToLLVM/FuncToLLVM.cpp
+++ b/mlir/lib/Conversion/FuncToLLVM/FuncToLLVM.cpp
@@ -58,7 +58,7 @@ static constexpr StringRef barePtrAttrName = "llvm.bareptr";
/// Return `true` if the `op` should use bare pointer calling convention.
static bool shouldUseBarePtrCallConv(Operation *op,
const LLVMTypeConverter *typeConverter) {
- return (op && op->hasAttr(barePtrAttrName)) ||
+ return (op && op->hasDiscardableAttr(barePtrAttrName)) ||
typeConverter->getOptions().useBarePtrCallConv;
}
@@ -71,7 +71,8 @@ static bool isDiscardableAttr(StringRef name) {
/// `LLVMFuncOp::build`.
static void filterFuncAttributes(FunctionOpInterface func,
SmallVectorImpl<NamedAttribute> &result) {
- for (const NamedAttribute &attr : func->getDiscardableAttrs()) {
+ for (const NamedAttribute &attr :
+ func->getDiscardableAttrDictionary().getValue()) {
if (isDiscardableAttr(attr.getName().strref()))
continue;
result.push_back(attr);
@@ -298,7 +299,8 @@ static FailureOr<LLVM::LLVMFunctionType> convertFuncSignature(
FunctionOpInterface funcOp, const LLVMTypeConverter &converter,
bool useBarePtrCallConv, TypeConverter::SignatureConversion &result,
SmallVectorImpl<std::optional<NamedAttribute>> &byValRefNonPtrAttrs) {
- auto varargsAttr = funcOp->getAttrOfType<BoolAttr>(varargsAttrName);
+ auto varargsAttr =
+ funcOp->getDiscardableAttrOfType<BoolAttr>(varargsAttrName);
auto llvmType = dyn_cast_or_null<LLVM::LLVMFunctionType>(
converter.convertFunctionSignature(
funcOp, varargsAttr && varargsAttr.getValue(), useBarePtrCallConv,
@@ -334,7 +336,7 @@ static LLVM::LLVMFuncOp createLLVMFuncOp(FunctionOpInterface funcOp,
.setVisibility(funcOp.getVisibility());
// Set readnone memory effects
- if (funcOp->hasAttr(LLVM::LLVMDialect::getReadnoneAttrName())) {
+ if (funcOp->hasDiscardableAttr(LLVM::LLVMDialect::getReadnoneAttrName())) {
auto memoryAttr = LLVM::MemoryEffectsAttr::get(
rewriter.getContext(), {/*other=*/LLVM::ModRefInfo::NoModRef,
/*argMem=*/LLVM::ModRefInfo::NoModRef,
@@ -466,7 +468,7 @@ FailureOr<LLVM::LLVMFuncOp> mlir::convertFuncOpToLLVMFuncOp(
return rewriter.notifyMatchFailure(funcOp, "signature conversion failed");
// Validate C wrapper varargs constraint
- bool emitCWrapper = funcOp->hasAttrOfType<UnitAttr>(
+ bool emitCWrapper = funcOp->hasDiscardableAttrOfType<UnitAttr>(
LLVM::LLVMDialect::getEmitCWrapperAttrName());
if (!useBarePtrCallConv && emitCWrapper && llvmType->isVarArg())
return funcOp.emitError("C interface for variadic functions is not "
@@ -549,10 +551,11 @@ struct ConstantOpLowering : public ConvertOpToLLVMPattern<func::ConstantOp> {
auto newOp =
LLVM::AddressOfOp::create(rewriter, op.getLoc(), type, op.getValue());
- for (const NamedAttribute &attr : op->getAttrs()) {
+ for (const NamedAttribute &attr :
+ op->getDiscardableAttrDictionary().getValue()) {
if (attr.getName().strref() == "value")
continue;
- newOp->setAttr(attr.getName(), attr.getValue());
+ newOp->setDiscardableAttr(attr.getName(), attr.getValue());
}
rewriter.replaceOp(op, newOp->getResults());
return success();
@@ -597,10 +600,12 @@ struct CallOpInterfaceLowering : public ConvertOpToLLVMPattern<CallOpType> {
auto promoted = this->getTypeConverter()->promoteOperands(
callOp.getLoc(), /*opOperands=*/callOp->getOperands(),
adaptor.getOperands(), rewriter, useBarePtrCallConv);
- auto newOp = LLVM::CallOp::create(rewriter, callOp.getLoc(),
- packedResult ? TypeRange(packedResult)
- : TypeRange(),
- promoted, callOp->getAttrs());
+ auto newOp = LLVM::CallOp::create(
+ rewriter, callOp.getLoc(),
+ packedResult ? TypeRange(packedResult) : TypeRange(), promoted,
+ callOp->getDiscardableAttrDictionary().getValue());
+ if constexpr (std::is_same_v<CallOpType, func::CallOp>)
+ newOp.setCalleeAttr(callOp.getCalleeAttr());
newOp.getProperties().operandSegmentSizes = {
static_cast<int32_t>(promoted.size()), 0};
@@ -687,13 +692,13 @@ class CallOpLowering : public CallOpInterfaceLowering<func::CallOp> {
Operation *callee =
symbolTables->lookupNearestSymbolFrom(callOp, callOp.getCalleeAttr());
useBarePtrCallConv =
- callee != nullptr && callee->hasAttr(barePtrAttrName);
+ callee != nullptr && callee->hasDiscardableAttr(barePtrAttrName);
} else {
// Warning: This is a linear lookup.
Operation *callee =
SymbolTable::lookupNearestSymbolFrom(callOp, callOp.getCalleeAttr());
useBarePtrCallConv =
- callee != nullptr && callee->hasAttr(barePtrAttrName);
+ callee != nullptr && callee->hasDiscardableAttr(barePtrAttrName);
}
return matchAndRewriteImpl(callOp, adaptor, rewriter, useBarePtrCallConv);
}
@@ -795,7 +800,8 @@ struct ReturnOpLowering : public ConvertOpToLLVMPattern<func::ReturnOp> {
// If ReturnOp has 0 or 1 operand, create it and return immediately.
if (updatedOperands.size() <= 1) {
rewriter.replaceOpWithNewOp<LLVM::ReturnOp>(
- op, TypeRange(), updatedOperands, op->getAttrs());
+ op, TypeRange(), updatedOperands,
+ op->getDiscardableAttrDictionary().getValue());
return success();
}
@@ -811,8 +817,8 @@ struct ReturnOpLowering : public ConvertOpToLLVMPattern<func::ReturnOp> {
for (auto [idx, operand] : llvm::enumerate(updatedOperands)) {
packed = LLVM::InsertValueOp::create(rewriter, loc, packed, operand, idx);
}
- rewriter.replaceOpWithNewOp<LLVM::ReturnOp>(op, TypeRange(), packed,
- op->getAttrs());
+ rewriter.replaceOpWithNewOp<LLVM::ReturnOp>(
+ op, TypeRange(), packed, op->getDiscardableAttrDictionary().getValue());
return success();
}
};
@@ -845,7 +851,7 @@ struct ConvertFuncToLLVMPass
ModuleOp m = getOperation();
StringRef dataLayout;
auto dataLayoutAttr = dyn_cast_or_null<StringAttr>(
- m->getAttr(LLVM::LLVMDialect::getDataLayoutAttrName()));
+ m->getDiscardableAttr(LLVM::LLVMDialect::getDataLayoutAttrName()));
if (dataLayoutAttr)
dataLayout = dataLayoutAttr.getValue();
@@ -896,8 +902,8 @@ struct SetLLVMModuleDataLayoutPass
return;
}
ModuleOp m = getOperation();
- m->setAttr(LLVM::LLVMDialect::getDataLayoutAttrName(),
- StringAttr::get(m.getContext(), this->dataLayout));
+ m->setDiscardableAttr(LLVM::LLVMDialect::getDataLayoutAttrName(),
+ StringAttr::get(m.getContext(), this->dataLayout));
}
};
} // namespace
diff --git a/mlir/lib/Conversion/FuncToSPIRV/FuncToSPIRV.cpp b/mlir/lib/Conversion/FuncToSPIRV/FuncToSPIRV.cpp
index 7ceab394a67ff..7956e07b012fb 100644
--- a/mlir/lib/Conversion/FuncToSPIRV/FuncToSPIRV.cpp
+++ b/mlir/lib/Conversion/FuncToSPIRV/FuncToSPIRV.cpp
@@ -68,11 +68,15 @@ class CallOpPattern final : public OpConversionPattern<func::CallOp> {
getTypeConverter()->convertType(callOp.getResult(0).getType());
if (!resultType)
return failure();
- rewriter.replaceOpWithNewOp<spirv::FunctionCallOp>(
- callOp, resultType, adaptor.getOperands(), callOp->getAttrs());
+ auto newCall = rewriter.replaceOpWithNewOp<spirv::FunctionCallOp>(
+ callOp, resultType, callOp.getCalleeAttr(), adaptor.getOperands(),
+ callOp.getArgAttrsAttr(), callOp.getResAttrsAttr());
+ newCall->setDiscardableAttrs(callOp->getDiscardableAttrDictionary());
} else {
- rewriter.replaceOpWithNewOp<spirv::FunctionCallOp>(
- callOp, TypeRange(), adaptor.getOperands(), callOp->getAttrs());
+ auto newCall = rewriter.replaceOpWithNewOp<spirv::FunctionCallOp>(
+ callOp, TypeRange(), callOp.getCalleeAttr(), adaptor.getOperands(),
+ callOp.getArgAttrsAttr(), callOp.getResAttrsAttr());
+ newCall->setDiscardableAttrs(callOp->getDiscardableAttrDictionary());
}
return success();
}
diff --git a/mlir/lib/Conversion/GPUCommon/GPUOpsLowering.cpp b/mlir/lib/Conversion/GPUCommon/GPUOpsLowering.cpp
index eeb90a7ff8150..3ce209213f2a0 100644
--- a/mlir/lib/Conversion/GPUCommon/GPUOpsLowering.cpp
+++ b/mlir/lib/Conversion/GPUCommon/GPUOpsLowering.cpp
@@ -630,7 +630,6 @@ static Value scalarizeVectorOpHelper(Operation *op, ValueRange operands,
Location loc = op->getLoc();
Value result = LLVM::PoisonOp::create(rewriter, loc, vectorType);
Type indexType = converter.convertType(rewriter.getIndexType());
- StringAttr name = op->getName().getIdentifier();
Type elementType = vectorType.getElementType();
for (int64_t i = 0; i < vectorType.getNumElements(); ++i) {
@@ -641,8 +640,10 @@ static Value scalarizeVectorOpHelper(Operation *op, ValueRange operands,
return LLVM::ExtractElementOp::create(rewriter, loc, operand, index);
};
auto scalarOperands = llvm::map_to_vector(operands, extractElement);
- Operation *scalarOp =
- rewriter.create(loc, name, scalarOperands, elementType, op->getAttrs());
+ OperationState state(loc, op->getName(), scalarOperands, elementType,
+ op->getDiscardableAttrDictionary().getValue());
+ state.propertiesAttr = op->getPropertiesAsAttribute();
+ Operation *scalarOp = rewriter.create(state);
result = LLVM::InsertElementOp::create(rewriter, loc, result,
scalarOp->getResult(0), index);
}
@@ -808,7 +809,8 @@ LogicalResult GPUReturnOpLowering::matchAndRewrite(
// If ReturnOp has 0 or 1 operand, create it and return immediately.
if (numArguments <= 1) {
rewriter.replaceOpWithNewOp<LLVM::ReturnOp>(
- op, TypeRange(), updatedOperands, op->getAttrs());
+ op, TypeRange(), updatedOperands,
+ op->getDiscardableAttrDictionary().getValue());
return success();
}
@@ -824,8 +826,8 @@ LogicalResult GPUReturnOpLowering::matchAndRewrite(
for (auto [idx, operand] : llvm::enumerate(updatedOperands)) {
packed = LLVM::InsertValueOp::create(rewriter, loc, packed, operand, idx);
}
- rewriter.replaceOpWithNewOp<LLVM::ReturnOp>(op, TypeRange(), packed,
- op->getAttrs());
+ rewriter.replaceOpWithNewOp<LLVM::ReturnOp>(
+ op, TypeRange(), packed, op->getDiscardableAttrDictionary().getValue());
return success();
}
diff --git a/mlir/lib/Conversion/GPUCommon/IndexIntrinsicsOpLowering.h b/mlir/lib/Conversion/GPUCommon/IndexIntrinsicsOpLowering.h
index 777f3b92b941c..2a6036ab97bb6 100644
--- a/mlir/lib/Conversion/GPUCommon/IndexIntrinsicsOpLowering.h
+++ b/mlir/lib/Conversion/GPUCommon/IndexIntrinsicsOpLowering.h
@@ -87,7 +87,7 @@ struct OpLowering : public ConvertOpToLLVMPattern<Op> {
opBound = static_cast<uint32_t>(bound->getZExtValue());
if (auto range = getIndexOpRange(op, op.getDimension(), opBound, indexKind,
intrType, /*bitWidth=*/32))
- newOp->setAttr("range", range);
+ newOp->setInherentAttr(rewriter.getStringAttr("range"), range);
if (indexBitwidth > 32) {
newOp = LLVM::SExtOp::create(rewriter, loc,
diff --git a/mlir/lib/Conversion/GPUToNVVM/LowerGpuOpsToNVVMOps.cpp b/mlir/lib/Conversion/GPUToNVVM/LowerGpuOpsToNVVMOps.cpp
index 80420c26537c3..2b57e90efe7a5 100644
--- a/mlir/lib/Conversion/GPUToNVVM/LowerGpuOpsToNVVMOps.cpp
+++ b/mlir/lib/Conversion/GPUToNVVM/LowerGpuOpsToNVVMOps.cpp
@@ -513,8 +513,8 @@ struct LowerGpuOpsToNVVMOpsPass final
// Request C wrapper emission.
for (auto func : m.getOps<func::FuncOp>()) {
- func->setAttr(LLVM::LLVMDialect::getEmitCWrapperAttrName(),
- UnitAttr::get(&getContext()));
+ func->setDiscardableAttr(LLVM::LLVMDialect::getEmitCWrapperAttrName(),
+ UnitAttr::get(&getContext()));
}
// Customize the bitwidth used for the device side index computations.
diff --git a/mlir/lib/Conversion/GPUToROCDL/LowerGpuOpsToROCDLOps.cpp b/mlir/lib/Conversion/GPUToROCDL/LowerGpuOpsToROCDLOps.cpp
index a3819df4f8a84..ab7666bc5d530 100644
--- a/mlir/lib/Conversion/GPUToROCDL/LowerGpuOpsToROCDLOps.cpp
+++ b/mlir/lib/Conversion/GPUToROCDL/LowerGpuOpsToROCDLOps.cpp
@@ -302,7 +302,7 @@ struct GPUSubgroupIdOpToROCDL : ConvertOpToLLVMPattern<gpu::SubgroupIdOp> {
op, dim, std::nullopt,
gpu::index_lowering::IndexKind::Block,
gpu::index_lowering::IntrType::Id, 32))
- tidOp->setAttr("range", range);
+ tidOp->setInherentAttr(rewriter.getStringAttr("range"), range);
};
setBoundFromContext(tidX, gpu::Dimension::x);
setBoundFromContext(tidY, gpu::Dimension::y);
@@ -737,16 +737,17 @@ struct LowerGpuOpsToROCDLOpsPass final
gpu::GPUModuleOp m = getOperation();
MLIRContext *ctx = m.getContext();
- auto llvmDataLayout = m->getAttrOfType<StringAttr>(
+ auto llvmDataLayout = m->getDiscardableAttrOfType<StringAttr>(
LLVM::LLVMDialect::getDataLayoutAttrName());
if (!llvmDataLayout) {
llvmDataLayout = StringAttr::get(ctx, amdgcnDataLayout);
- m->setAttr(LLVM::LLVMDialect::getDataLayoutAttrName(), llvmDataLayout);
+ m->setDiscardableAttr(LLVM::LLVMDialect::getDataLayoutAttrName(),
+ llvmDataLayout);
}
// Request C wrapper emission.
for (auto func : m.getOps<func::FuncOp>()) {
- func->setAttr(LLVM::LLVMDialect::getEmitCWrapperAttrName(),
- UnitAttr::get(ctx));
+ func->setDiscardableAttr(LLVM::LLVMDialect::getEmitCWrapperAttrName(),
+ UnitAttr::get(ctx));
}
FailureOr<amdgpu::Chipset> maybeChipset = amdgpu::Chipset::parse(chipset);
diff --git a/mlir/lib/Conversion/GPUToSPIRV/GPUToSPIRV.cpp b/mlir/lib/Conversion/GPUToSPIRV/GPUToSPIRV.cpp
index 609dbe57a9a46..1ebf2daf557d3 100644
--- a/mlir/lib/Conversion/GPUToSPIRV/GPUToSPIRV.cpp
+++ b/mlir/lib/Conversion/GPUToSPIRV/GPUToSPIRV.cpp
@@ -294,11 +294,34 @@ lowerAsEntryFunction(gpu::GPUFuncOp funcOp, const TypeConverter &typeConverter,
auto newFuncOp = spirv::FuncOp::create(
rewriter, funcOp.getLoc(), funcOp.getName(),
rewriter.getFunctionType(signatureConverter.getConvertedTypes(), {}));
- for (const auto &namedAttr : funcOp->getAttrs()) {
+ newFuncOp.setArgAttrsAttr(funcOp.getArgAttrsAttr());
+ newFuncOp.setResAttrsAttr(funcOp.getResAttrsAttr());
+ cast<SymbolOpInterface>(newFuncOp.getOperation())
+ .setVisibility(
+ cast<SymbolOpInterface>(funcOp.getOperation()).getVisibility());
+
+ auto copyGPUProperty = [&](StringAttr name, Attribute value) {
+ if (value)
+ newFuncOp->setDiscardableAttr(name, value);
+ };
+ copyGPUProperty(funcOp.getWorkgroupAttribAttrsAttrName(),
+ funcOp.getWorkgroupAttribAttrsAttr());
+ copyGPUProperty(funcOp.getPrivateAttribAttrsAttrName(),
+ funcOp.getPrivateAttribAttrsAttr());
+ copyGPUProperty(funcOp.getKnownBlockSizeAttrName(),
+ funcOp.getKnownBlockSizeAttr());
+ copyGPUProperty(funcOp.getKnownGridSizeAttrName(),
+ funcOp.getKnownGridSizeAttr());
+ copyGPUProperty(funcOp.getKnownClusterSizeAttrName(),
+ funcOp.getKnownClusterSizeAttr());
+ copyGPUProperty(funcOp.getWorkgroupAttributionsAttrName(),
+ funcOp.getWorkgroupAttributionsAttr());
+ for (const auto &namedAttr :
+ funcOp->getDiscardableAttrDictionary().getValue()) {
if (namedAttr.getName() == funcOp.getFunctionTypeAttrName() ||
namedAttr.getName() == SymbolTable::getSymbolAttrName())
continue;
- newFuncOp->setAttr(namedAttr.getName(), namedAttr.getValue());
+ newFuncOp->setDiscardableAttr(namedAttr.getName(), namedAttr.getValue());
}
rewriter.inlineRegionBefore(funcOp.getBody(), newFuncOp.getBody(),
@@ -313,7 +336,8 @@ lowerAsEntryFunction(gpu::GPUFuncOp funcOp, const TypeConverter &typeConverter,
for (auto argIndex : llvm::seq<unsigned>(0, argABIInfo.size())) {
newFuncOp.setArgAttr(argIndex, argABIAttrName, argABIInfo[argIndex]);
}
- newFuncOp->setAttr(spirv::getEntryPointABIAttrName(), entryPointInfo);
+ newFuncOp->setDiscardableAttr(spirv::getEntryPointABIAttrName(),
+ entryPointInfo);
return newFuncOp;
}
@@ -378,7 +402,7 @@ LogicalResult GPUFuncOpConversion::matchAndRewrite(
funcOp, *getTypeConverter(), rewriter, entryPointAttr, argABI);
if (!newFuncOp)
return failure();
- newFuncOp->removeAttr(
+ newFuncOp->removeDiscardableAttr(
rewriter.getStringAttr(gpu::GPUDialect::getKernelFuncAttrName()));
return success();
}
@@ -416,14 +440,15 @@ LogicalResult GPUModuleConversion::matchAndRewrite(
// will fail if called after GPUModuleConversion and we don't preserve
// `TargetEnv` attribute.
// Copy TargetEnvAttr only if it is attached directly to the GPUModuleOp.
- if (auto attr = moduleOp->getAttrOfType<spirv::TargetEnvAttr>(
+ if (auto attr = moduleOp->getDiscardableAttrOfType<spirv::TargetEnvAttr>(
spirv::getTargetEnvAttrName()))
- spvModule->setAttr(spirv::getTargetEnvAttrName(), attr);
+ spvModule->setDiscardableAttr(spirv::getTargetEnvAttrName(), attr);
if (ArrayAttr targets = moduleOp.getTargetsAttr()) {
for (Attribute targetAttr : targets)
if (auto spirvTargetEnvAttr =
dyn_cast<spirv::TargetEnvAttr>(targetAttr)) {
- spvModule->setAttr(spirv::getTargetEnvAttrName(), spirvTargetEnvAttr);
+ spvModule->setDiscardableAttr(spirv::getTargetEnvAttrName(),
+ spirvTargetEnvAttr);
break;
}
}
@@ -986,7 +1011,7 @@ LogicalResult GPUPrintfConversion::matchAndRewrite(
rewriter, loc, ptrType, globalVarName,
FlatSymbolRefAttr::get(specCstComposite));
- globalVar->setAttr("Constant", rewriter.getUnitAttr());
+ globalVar->setDiscardableAttr("Constant", rewriter.getUnitAttr());
}
// Get SSA value of Global variable and create pointer to i8 to point to
// the format string.
diff --git a/mlir/lib/Conversion/GPUToSPIRV/GPUToSPIRVPass.cpp b/mlir/lib/Conversion/GPUToSPIRV/GPUToSPIRVPass.cpp
index 1b49e9d6305f1..b687283da0477 100644
--- a/mlir/lib/Conversion/GPUToSPIRV/GPUToSPIRVPass.cpp
+++ b/mlir/lib/Conversion/GPUToSPIRV/GPUToSPIRVPass.cpp
@@ -177,8 +177,8 @@ void GPUToSPIRVPass::runOnOperation() {
auto entryBlock = newFuncOp.addEntryBlock();
builder.setInsertionPointToEnd(entryBlock);
func::ReturnOp::create(builder, funcOp.getLoc());
- newFuncOp->setAttr(gpu::GPUDialect::getKernelFuncAttrName(),
- builder.getUnitAttr());
+ newFuncOp->setDiscardableAttr(gpu::GPUDialect::getKernelFuncAttrName(),
+ builder.getUnitAttr());
funcOp.erase();
});
}
diff --git a/mlir/lib/Conversion/LLVMCommon/LowerFunctionDiscardablesToLLVM.cpp b/mlir/lib/Conversion/LLVMCommon/LowerFunctionDiscardablesToLLVM.cpp
index 5427877fdfd8d..859d96d7e2377 100644
--- a/mlir/lib/Conversion/LLVMCommon/LowerFunctionDiscardablesToLLVM.cpp
+++ b/mlir/lib/Conversion/LLVMCommon/LowerFunctionDiscardablesToLLVM.cpp
@@ -29,7 +29,8 @@ mlir::lowerDiscardableAttrsForLLVMFunc(FunctionOpInterface funcOp,
NamedAttrList inherentAttrs;
- for (const NamedAttribute &attr : funcOp->getDiscardableAttrs()) {
+ for (const NamedAttribute &attr :
+ funcOp->getDiscardableAttrDictionary().getValue()) {
StringRef attrName = attr.getName().strref();
if (odsAttrNames.contains(attrName)) {
diff --git a/mlir/lib/Conversion/LLVMCommon/Pattern.cpp b/mlir/lib/Conversion/LLVMCommon/Pattern.cpp
index 2e0d92c3ba847..91ef201ea4065 100644
--- a/mlir/lib/Conversion/LLVMCommon/Pattern.cpp
+++ b/mlir/lib/Conversion/LLVMCommon/Pattern.cpp
@@ -367,7 +367,7 @@ LogicalResult LLVM::detail::intrinsicRewrite(
auto callIntrOp = LLVM::CallIntrinsicOp::create(
rewriter, loc, resType, rewriter.getStringAttr(intrinsic), operands);
// Propagate attributes.
- callIntrOp->setAttrs(op->getAttrDictionary());
+ callIntrOp->setDiscardableAttrs(op->getDiscardableAttrDictionary());
if (numResults <= 1) {
// Directly replace the original op.
diff --git a/mlir/lib/Conversion/LinalgToStandard/LinalgToStandard.cpp b/mlir/lib/Conversion/LinalgToStandard/LinalgToStandard.cpp
index 54c554eb6bd93..b5b2b0ba2c277 100644
--- a/mlir/lib/Conversion/LinalgToStandard/LinalgToStandard.cpp
+++ b/mlir/lib/Conversion/LinalgToStandard/LinalgToStandard.cpp
@@ -83,8 +83,8 @@ getLibraryCallSymbolRef(Operation *op, PatternRewriter &rewriter) {
// Insert a function attribute that will trigger the emission of the
// corresponding `_mlir_ciface_xxx` interface so that external libraries see
// a normalized ABI. This interface is added during std to llvm conversion.
- funcOp->setAttr(LLVM::LLVMDialect::getEmitCWrapperAttrName(),
- UnitAttr::get(op->getContext()));
+ funcOp->setDiscardableAttr(LLVM::LLVMDialect::getEmitCWrapperAttrName(),
+ UnitAttr::get(op->getContext()));
funcOp.setPrivate();
return fnNameAttr;
}
diff --git a/mlir/lib/Conversion/MathToFuncs/MathToFuncs.cpp b/mlir/lib/Conversion/MathToFuncs/MathToFuncs.cpp
index 2774adb071c91..9ff2e3e4fdf7f 100644
--- a/mlir/lib/Conversion/MathToFuncs/MathToFuncs.cpp
+++ b/mlir/lib/Conversion/MathToFuncs/MathToFuncs.cpp
@@ -197,7 +197,7 @@ static func::FuncOp createElementIPowIFunc(ModuleOp *module, Type elementType) {
LLVM::linkage::Linkage inlineLinkage = LLVM::linkage::Linkage::LinkonceODR;
Attribute linkage =
LLVM::LinkageAttr::get(builder.getContext(), inlineLinkage);
- funcOp->setAttr("llvm.linkage", linkage);
+ funcOp->setDiscardableAttr("llvm.linkage", linkage);
funcOp.setPrivate();
Block *entryBlock = funcOp.addEntryBlock();
@@ -424,7 +424,7 @@ static func::FuncOp createElementFPowIFunc(ModuleOp *module,
LLVM::linkage::Linkage inlineLinkage = LLVM::linkage::Linkage::LinkonceODR;
Attribute linkage =
LLVM::LinkageAttr::get(builder.getContext(), inlineLinkage);
- funcOp->setAttr("llvm.linkage", linkage);
+ funcOp->setDiscardableAttr("llvm.linkage", linkage);
funcOp.setPrivate();
Block *entryBlock = funcOp.addEntryBlock();
@@ -674,7 +674,7 @@ static func::FuncOp createCtlzFunc(ModuleOp *module, Type elementType) {
LLVM::linkage::Linkage inlineLinkage = LLVM::linkage::Linkage::LinkonceODR;
Attribute linkage =
LLVM::LinkageAttr::get(builder.getContext(), inlineLinkage);
- funcOp->setAttr("llvm.linkage", linkage);
+ funcOp->setDiscardableAttr("llvm.linkage", linkage);
funcOp.setPrivate();
// set the insertion point to the start of the function
diff --git a/mlir/lib/Conversion/MathToLibm/MathToLibm.cpp b/mlir/lib/Conversion/MathToLibm/MathToLibm.cpp
index d43b70467cd04..1f8020152807a 100644
--- a/mlir/lib/Conversion/MathToLibm/MathToLibm.cpp
+++ b/mlir/lib/Conversion/MathToLibm/MathToLibm.cpp
@@ -150,8 +150,8 @@ ScalarOpToLibmCall<Op>::matchAndRewrite(Op op,
// optimization opportunities (e.g. LICM) for backends targeting LLVM IR.
// This will have to be changed, when strict FP behavior is supported
// by Math dialect.
- opFunc->setAttr(LLVM::LLVMDialect::getReadnoneAttrName(),
- UnitAttr::get(rewriter.getContext()));
+ opFunc->setDiscardableAttr(LLVM::LLVMDialect::getReadnoneAttrName(),
+ UnitAttr::get(rewriter.getContext()));
}
assert(isa<FunctionOpInterface>(SymbolTable::lookupSymbolIn(module, name)));
diff --git a/mlir/lib/Conversion/MathToXeVM/MathToXeVM.cpp b/mlir/lib/Conversion/MathToXeVM/MathToXeVM.cpp
index 7143dcc19ff10..4b29df764be71 100644
--- a/mlir/lib/Conversion/MathToXeVM/MathToXeVM.cpp
+++ b/mlir/lib/Conversion/MathToXeVM/MathToXeVM.cpp
@@ -145,7 +145,8 @@ struct ConvertNativeFuncPattern final : public OpConversionPattern<Op> {
// convert arith fastmath attrs into attrs recognized by llvm.
arith::AttrConvertFastMathToLLVM<Op, LLVM::CallOp> fastAttrConverter(op);
mlir::NamedAttribute fastAttr = fastAttrConverter.getAttrs()[0];
- callOp->setAttr(fastAttr.getName(), fastAttr.getValue());
+ callOp.setFastmathFlagsAttr(
+ cast<LLVM::FastmathFlagsAttr>(fastAttr.getValue()));
if (unwrapSizeOneVec) {
// Re-wrap the scalar result back into a size-1 vector to preserve types.
diff --git a/mlir/lib/Conversion/MemRefToSPIRV/MapMemRefStorageClassPass.cpp b/mlir/lib/Conversion/MemRefToSPIRV/MapMemRefStorageClassPass.cpp
index 1fbc5a03987e8..6bc49a538bc9e 100644
--- a/mlir/lib/Conversion/MemRefToSPIRV/MapMemRefStorageClassPass.cpp
+++ b/mlir/lib/Conversion/MemRefToSPIRV/MapMemRefStorageClassPass.cpp
@@ -230,9 +230,9 @@ static bool isLegalOp(Operation *op) {
isLegalType);
}
- auto attrs = llvm::map_range(op->getAttrs(), [](const NamedAttribute &attr) {
- return attr.getValue();
- });
+ auto attrs = llvm::map_range(
+ op->getDiscardableAttrDictionary().getValue(),
+ [](const NamedAttribute &attr) { return attr.getValue(); });
return llvm::all_of(op->getOperandTypes(), isLegalType) &&
llvm::all_of(op->getResultTypes(), isLegalType) &&
diff --git a/mlir/lib/Conversion/NVGPUToNVVM/NVGPUToNVVM.cpp b/mlir/lib/Conversion/NVGPUToNVVM/NVGPUToNVVM.cpp
index b155505a2dae1..ae3a5f7e8e97a 100644
--- a/mlir/lib/Conversion/NVGPUToNVVM/NVGPUToNVVM.cpp
+++ b/mlir/lib/Conversion/NVGPUToNVVM/NVGPUToNVVM.cpp
@@ -353,7 +353,7 @@ struct MmaSyncOptoNVVM : public ConvertOpToLLVMPattern<nvgpu::MmaSyncOp> {
std::array<int64_t, 3> gemmShape = op.getMmaShapeAsArray();
// Tensor Cores (mma.sync) on F32 works only with TensorFloat32 (TF32).
- bool tf32Enabled = op->hasAttr(op.getTf32EnabledAttrName());
+ bool tf32Enabled = op.getTf32Enabled().value_or(false);
if (aType.getElementType().isF32() && !tf32Enabled)
return failure();
@@ -599,7 +599,7 @@ struct NVGPUMmaSparseSyncLowering
"could not infer the PTX type for the accumulator/result");
// Same as `mma.sync`, F32 works only with TensorFloat32 (TF32).
- bool tf32Enabled = op->hasAttr(op.getTf32EnabledAttrName());
+ bool tf32Enabled = op.getTf32Enabled().value_or(false);
if (aType.getElementType().isF32() && !tf32Enabled)
return failure();
diff --git a/mlir/lib/Conversion/OpenMPToLLVM/OpenMPToLLVM.cpp b/mlir/lib/Conversion/OpenMPToLLVM/OpenMPToLLVM.cpp
index 2ab1575a510ac..69d5b57609edd 100644
--- a/mlir/lib/Conversion/OpenMPToLLVM/OpenMPToLLVM.cpp
+++ b/mlir/lib/Conversion/OpenMPToLLVM/OpenMPToLLVM.cpp
@@ -28,6 +28,13 @@ using namespace mlir;
namespace {
+static NamedAttrList getAttrsForConversion(Operation *op) {
+ NamedAttrList attrs;
+ op->getName().populateInherentAttrs(op, attrs);
+ attrs.append(op->getDiscardableAttrDictionary().getValue());
+ return attrs;
+}
+
/// A pattern that converts the result and operand types, attributes, and region
/// arguments of an OpenMP operation to the LLVM dialect.
///
@@ -63,7 +70,7 @@ struct OpenMPOpConversion : public ConvertOpToLLVMPattern<T> {
// Translate type attributes.
// They are kept unmodified except if they are type attributes.
SmallVector<NamedAttribute> convertedAttrs;
- for (NamedAttribute attr : op->getAttrs()) {
+ for (NamedAttribute attr : getAttrsForConversion(op)) {
if (auto typeAttr = dyn_cast<TypeAttr>(attr.getValue())) {
Type convertedType = converter->convertType(typeAttr.getValue());
if (!convertedType)
@@ -131,7 +138,7 @@ void mlir::configureOpenMPToLLVMConversionLegality(
[&](Region ®ion) {
return typeConverter.isLegal(®ion);
}) &&
- llvm::all_of(op->getAttrs(), [&](NamedAttribute attr) {
+ llvm::all_of(getAttrsForConversion(op), [&](NamedAttribute attr) {
auto typeAttr = dyn_cast<TypeAttr>(attr.getValue());
return !typeAttr || typeConverter.isLegal(typeAttr.getValue());
});
diff --git a/mlir/lib/Conversion/RaiseWasm/RaiseWasmMLIR.cpp b/mlir/lib/Conversion/RaiseWasm/RaiseWasmMLIR.cpp
index c26a3b038e918..f6c1c748b2e89 100644
--- a/mlir/lib/Conversion/RaiseWasm/RaiseWasmMLIR.cpp
+++ b/mlir/lib/Conversion/RaiseWasm/RaiseWasmMLIR.cpp
@@ -649,8 +649,8 @@ struct WasmGlobalWithGetGlobalInitConversion
auto globalInitializer =
func::FuncOp::create(rewriter, loc, initializerName,
FunctionType::get(getContext(), {}, {}));
- globalInitializer->setAttr(rewriter.getStringAttr("initializer"),
- rewriter.getUnitAttr());
+ globalInitializer->setDiscardableAttr(rewriter.getStringAttr("initializer"),
+ rewriter.getUnitAttr());
auto *initializerBody = globalInitializer.addEntryBlock();
auto sip = rewriter.saveInsertionPoint();
rewriter.setInsertionPointToStart(initializerBody);
@@ -717,8 +717,8 @@ struct WasmMemoryOpConversion : OpConversionPattern<MemOp> {
auto memInitializer =
func::FuncOp::create(rewriter, loc, initializerName,
FunctionType::get(getContext(), {}, {}));
- memInitializer->setAttr(rewriter.getStringAttr("initializer"),
- rewriter.getUnitAttr());
+ memInitializer->setDiscardableAttr(rewriter.getStringAttr("initializer"),
+ rewriter.getUnitAttr());
auto *initializerBody = memInitializer.addEntryBlock();
auto sip = rewriter.saveInsertionPoint();
rewriter.setInsertionPointToStart(initializerBody);
diff --git a/mlir/lib/Conversion/SCFToControlFlow/SCFToControlFlow.cpp b/mlir/lib/Conversion/SCFToControlFlow/SCFToControlFlow.cpp
index 2972d79c4302f..eba6ef8c48fa2 100644
--- a/mlir/lib/Conversion/SCFToControlFlow/SCFToControlFlow.cpp
+++ b/mlir/lib/Conversion/SCFToControlFlow/SCFToControlFlow.cpp
@@ -319,8 +319,8 @@ static void propagateLoopAttrs(Operation *scfOp, Operation *brOp) {
// LLVM requires the loop metadata to be attached on the "latch" block. Which
// is the back-edge to the header block (conditionBlock)
SmallVector<NamedAttribute> llvmAttrs;
- llvm::copy_if(scfOp->getAttrs(), std::back_inserter(llvmAttrs),
- [](auto attr) {
+ llvm::copy_if(scfOp->getDiscardableAttrDictionary().getValue(),
+ std::back_inserter(llvmAttrs), [](auto attr) {
return isa<LLVM::LLVMDialect>(attr.getValue().getDialect());
});
brOp->setDiscardableAttrs(llvmAttrs);
diff --git a/mlir/lib/Conversion/SCFToGPU/SCFToGPU.cpp b/mlir/lib/Conversion/SCFToGPU/SCFToGPU.cpp
index 370457c85e797..26b2f537e91a7 100644
--- a/mlir/lib/Conversion/SCFToGPU/SCFToGPU.cpp
+++ b/mlir/lib/Conversion/SCFToGPU/SCFToGPU.cpp
@@ -41,7 +41,7 @@ using namespace mlir::scf;
// Name of internal attribute to mark visited operations during conversion.
//
// NOTE: The conversion originally used the following legality criteria:
-// `!parallelOp->hasAttr(gpu::getMappingAttrName())`
+// `!parallelOp->hasDiscardableAttr(gpu::getMappingAttrName())`
// But the provided pattern might reject some cases based on more detailed
// analysis of the `mapping` attribute.
// To avoid dialect conversion failure due to non-converted illegal operation
@@ -408,8 +408,8 @@ static LogicalResult processParallelLoop(
DenseMap<gpu::Processor, Value> &bounds, PatternRewriter &rewriter) {
// TODO: Verify that this is a valid GPU mapping.
// processor ids: 0-2 block [x/y/z], 3-5 -> thread [x/y/z], 6-> sequential
- ArrayAttr mapping =
- parallelOp->getAttrOfType<ArrayAttr>(gpu::getMappingAttrName());
+ ArrayAttr mapping = parallelOp->getDiscardableAttrOfType<ArrayAttr>(
+ gpu::getMappingAttrName());
// TODO: Support multiple reductions.
if (!mapping || parallelOp.getNumResults() > 1)
@@ -562,11 +562,12 @@ static LogicalResult processParallelLoop(
// Propagate custom user defined optional attributes, that can be used at
// later stage, such as extension data for GPU kernel dispatch
- for (const auto &namedAttr : parallelOp->getAttrs()) {
+ for (const auto &namedAttr :
+ parallelOp->getDiscardableAttrDictionary().getValue()) {
if (namedAttr.getName() == gpu::getMappingAttrName() ||
namedAttr.getName() == ParallelOp::getOperandSegmentSizeAttr())
continue;
- launchOp->setAttr(namedAttr.getName(), namedAttr.getValue());
+ launchOp->setDiscardableAttr(namedAttr.getName(), namedAttr.getValue());
}
Block *body = parallelOp.getBody();
@@ -614,7 +615,7 @@ LogicalResult
ParallelToGpuLaunchLowering::matchAndRewrite(ParallelOp parallelOp,
PatternRewriter &rewriter) const {
// Mark the operation as visited for recursive legality check.
- parallelOp->setAttr(kVisitedAttrName, rewriter.getUnitAttr());
+ parallelOp->setDiscardableAttr(kVisitedAttrName, rewriter.getUnitAttr());
// We can only transform starting at the outer-most loop. Launches inside of
// parallel loops are not supported.
@@ -775,13 +776,13 @@ void mlir::populateParallelLoopToGPUPatterns(RewritePatternSet &patterns) {
void mlir::configureParallelLoopToGPULegality(ConversionTarget &target) {
target.addLegalDialect<memref::MemRefDialect>();
target.addDynamicallyLegalOp<scf::ParallelOp>([](scf::ParallelOp parallelOp) {
- return !parallelOp->hasAttr(gpu::getMappingAttrName()) ||
- parallelOp->hasAttr(kVisitedAttrName);
+ return !parallelOp->hasDiscardableAttr(gpu::getMappingAttrName()) ||
+ parallelOp->hasDiscardableAttr(kVisitedAttrName);
});
}
void mlir::finalizeParallelLoopToGPUConversion(Operation *op) {
op->walk([](scf::ParallelOp parallelOp) {
- parallelOp->removeAttr(kVisitedAttrName);
+ parallelOp->removeDiscardableAttr(kVisitedAttrName);
});
}
diff --git a/mlir/lib/Conversion/SCFToSPIRV/SCFToSPIRV.cpp b/mlir/lib/Conversion/SCFToSPIRV/SCFToSPIRV.cpp
index fc6b37798e42d..0821e8e96a9d0 100644
--- a/mlir/lib/Conversion/SCFToSPIRV/SCFToSPIRV.cpp
+++ b/mlir/lib/Conversion/SCFToSPIRV/SCFToSPIRV.cpp
@@ -137,7 +137,7 @@ struct ForOpConversion final : SCFToSPIRVPattern<scf::ForOp> {
// from header to merge.
auto loc = forOp.getLoc();
auto loopControl = spirv::LoopControl::None;
- if (auto attr = forOp->getAttrOfType<spirv::LoopControlAttr>(
+ if (auto attr = forOp->getDiscardableAttrOfType<spirv::LoopControlAttr>(
spirv::getLoopControlAttrName()))
loopControl = attr.getValue();
auto loopOp = spirv::LoopOp::create(rewriter, loc, loopControl);
@@ -260,7 +260,7 @@ struct IfOpConversion : SCFToSPIRVPattern<scf::IfOp> {
// Create `spirv.selection` operation, selection header block and merge
// block.
auto selectionControl = spirv::SelectionControl::None;
- if (auto attr = ifOp->getAttrOfType<spirv::SelectionControlAttr>(
+ if (auto attr = ifOp->getDiscardableAttrOfType<spirv::SelectionControlAttr>(
spirv::getSelectionControlAttrName()))
selectionControl = attr.getValue();
auto selectionOp =
@@ -339,8 +339,9 @@ struct IndexSwitchOpConversion final : SCFToSPIRVPattern<scf::IndexSwitchOp> {
// Create the `spirv.mlir.selection` op, its header block, and merge block.
auto selectionControl = spirv::SelectionControl::None;
- if (auto attr = switchOp->getAttrOfType<spirv::SelectionControlAttr>(
- spirv::getSelectionControlAttrName()))
+ if (auto attr =
+ switchOp->getDiscardableAttrOfType<spirv::SelectionControlAttr>(
+ spirv::getSelectionControlAttrName()))
selectionControl = attr.getValue();
auto selectionOp =
spirv::SelectionOp::create(rewriter, loc, selectionControl);
@@ -451,7 +452,7 @@ struct WhileOpConversion final : SCFToSPIRVPattern<scf::WhileOp> {
ConversionPatternRewriter &rewriter) const override {
auto loc = whileOp.getLoc();
auto loopControl = spirv::LoopControl::None;
- if (auto attr = whileOp->getAttrOfType<spirv::LoopControlAttr>(
+ if (auto attr = whileOp->getDiscardableAttrOfType<spirv::LoopControlAttr>(
spirv::getLoopControlAttrName()))
loopControl = attr.getValue();
auto loopOp = spirv::LoopOp::create(rewriter, loc, loopControl);
diff --git a/mlir/lib/Conversion/SPIRVToLLVM/ConvertLaunchFuncToLLVMCalls.cpp b/mlir/lib/Conversion/SPIRVToLLVM/ConvertLaunchFuncToLLVMCalls.cpp
index 2491c7cbd3d22..54a24004cfc75 100644
--- a/mlir/lib/Conversion/SPIRVToLLVM/ConvertLaunchFuncToLLVMCalls.cpp
+++ b/mlir/lib/Conversion/SPIRVToLLVM/ConvertLaunchFuncToLLVMCalls.cpp
@@ -44,24 +44,13 @@ static constexpr const char kSPIRVModule[] = "__spv__";
// Utility functions
//===----------------------------------------------------------------------===//
-/// Returns the string name of the `DescriptorSet` decoration.
-static std::string descriptorSetName() {
- return spirv::getDecorationString(spirv::Decoration::DescriptorSet);
-}
-
-/// Returns the string name of the `Binding` decoration.
-static std::string bindingName() {
- return spirv::getDecorationString(spirv::Decoration::Binding);
-}
-
/// Calculates the index of the kernel's operand that is represented by the
/// given global variable with the `bind` attribute. We assume that the index of
/// each kernel's operand is mapped to (descriptorSet, binding) by the map:
/// i -> (0, i)
/// which is implemented under `LowerABIAttributesPass`.
static unsigned calculateGlobalIndex(spirv::GlobalVariableOp op) {
- IntegerAttr binding = op->getAttrOfType<IntegerAttr>(bindingName());
- return binding.getInt();
+ return *op.getBinding();
}
/// Copies the given number of bytes from src to dst pointers.
@@ -78,22 +67,16 @@ static void copy(Location loc, Value dst, Value src, Value size,
static std::string
createGlobalVariableWithBindName(spirv::GlobalVariableOp op,
StringRef kernelModuleName) {
- IntegerAttr descriptorSet =
- op->getAttrOfType<IntegerAttr>(descriptorSetName());
- IntegerAttr binding = op->getAttrOfType<IntegerAttr>(bindingName());
return llvm::formatv("{0}_{1}_descriptor_set{2}_binding{3}",
kernelModuleName.str(), op.getSymName().str(),
- std::to_string(descriptorSet.getInt()),
- std::to_string(binding.getInt()));
+ std::to_string(*op.getDescriptorSet()),
+ std::to_string(*op.getBinding()));
}
/// Returns true if the given global variable has both a descriptor set number
/// and a binding number.
static bool hasDescriptorSetAndBinding(spirv::GlobalVariableOp op) {
- IntegerAttr descriptorSet =
- op->getAttrOfType<IntegerAttr>(descriptorSetName());
- IntegerAttr binding = op->getAttrOfType<IntegerAttr>(bindingName());
- return descriptorSet && binding;
+ return op.getDescriptorSetAttr() && op.getBindingAttr();
}
/// Fills `globalVariableMap` with SPIR-V global variables that represent kernel
@@ -289,8 +272,8 @@ class LowerHostCodeToLLVM
// Request C wrapper emission.
for (auto func : module.getOps<func::FuncOp>()) {
- func->setAttr(LLVM::LLVMDialect::getEmitCWrapperAttrName(),
- UnitAttr::get(&getContext()));
+ func->setDiscardableAttr(LLVM::LLVMDialect::getEmitCWrapperAttrName(),
+ UnitAttr::get(&getContext()));
}
// Specify options to lower to LLVM and pull in the conversion patterns.
diff --git a/mlir/lib/Conversion/SPIRVToLLVM/SPIRVToLLVM.cpp b/mlir/lib/Conversion/SPIRVToLLVM/SPIRVToLLVM.cpp
index 63f9188a4e464..5b74f4e1bb5e9 100644
--- a/mlir/lib/Conversion/SPIRVToLLVM/SPIRVToLLVM.cpp
+++ b/mlir/lib/Conversion/SPIRVToLLVM/SPIRVToLLVM.cpp
@@ -303,6 +303,15 @@ static Type convertStructType(spirv::StructType type,
namespace {
+template <typename OpTy>
+static NamedAttrList collectAttrsForConversion(OpTy op) {
+ NamedAttrList attrs(op->getDiscardableAttrDictionary());
+ if (auto properties =
+ dyn_cast_or_null<DictionaryAttr>(op->getPropertiesAsAttribute()))
+ attrs.append(properties.getValue());
+ return attrs;
+}
+
class AccessChainPattern : public SPIRVToLLVMConversion<spirv::AccessChainOp> {
public:
using SPIRVToLLVMConversion<spirv::AccessChainOp>::SPIRVToLLVMConversion;
@@ -434,7 +443,8 @@ class ConstantScalarAndVectorPattern
return success();
}
rewriter.replaceOpWithNewOp<LLVM::ConstantOp>(
- constOp, dstType, adaptor.getOperands(), constOp->getAttrs());
+ constOp, dstType, adaptor.getOperands(),
+ collectAttrsForConversion(constOp));
return success();
}
};
@@ -644,7 +654,7 @@ class DirectConversionPattern : public SPIRVToLLVMConversion<SPIRVOp> {
if (!dstType)
return rewriter.notifyMatchFailure(op, "type conversion failed");
rewriter.template replaceOpWithNewOp<LLVMOp>(
- op, dstType, adaptor.getOperands(), op->getAttrs());
+ op, dstType, adaptor.getOperands(), collectAttrsForConversion(op));
return success();
}
};
@@ -828,7 +838,7 @@ class GlobalVariablePattern
// Attach location attribute if applicable
if (locationAttr)
- newGlobalOp->setAttr(locationAttrName, locationAttr);
+ newGlobalOp->setDiscardableAttr(locationAttrName, locationAttr);
return success();
}
@@ -879,7 +889,8 @@ class FunctionCallPattern
ConversionPatternRewriter &rewriter) const override {
if (callOp.getNumResults() == 0) {
auto newOp = rewriter.replaceOpWithNewOp<LLVM::CallOp>(
- callOp, TypeRange(), adaptor.getOperands(), callOp->getAttrs());
+ callOp, TypeRange(), adaptor.getOperands(),
+ collectAttrsForConversion(callOp));
newOp.getProperties().operandSegmentSizes = {
static_cast<int32_t>(adaptor.getOperands().size()), 0};
newOp.getProperties().op_bundle_sizes = rewriter.getDenseI32ArrayAttr({});
@@ -891,7 +902,8 @@ class FunctionCallPattern
if (!dstType)
return rewriter.notifyMatchFailure(callOp, "type conversion failed");
auto newOp = rewriter.replaceOpWithNewOp<LLVM::CallOp>(
- callOp, dstType, adaptor.getOperands(), callOp->getAttrs());
+ callOp, dstType, adaptor.getOperands(),
+ collectAttrsForConversion(callOp));
newOp.getProperties().operandSegmentSizes = {
static_cast<int32_t>(adaptor.getOperands().size()), 0};
newOp.getProperties().op_bundle_sizes = rewriter.getDenseI32ArrayAttr({});
@@ -1940,7 +1952,8 @@ class BitcastConversionPattern
}
rewriter.replaceOpWithNewOp<LLVM::BitcastOp>(
- bitcastOp, dstType, adaptor.getOperands(), bitcastOp->getAttrs());
+ bitcastOp, dstType, adaptor.getOperands(),
+ collectAttrsForConversion(bitcastOp));
return success();
}
};
@@ -1986,7 +1999,8 @@ class FuncConversionPattern : public SPIRVToLLVMConversion<spirv::FuncOp> {
#define DISPATCH(functionControl, llvmAttr) \
case functionControl: \
- newFuncOp->setAttr("passthrough", ArrayAttr::get(context, {llvmAttr})); \
+ newFuncOp->setDiscardableAttr("passthrough", \
+ ArrayAttr::get(context, {llvmAttr})); \
break;
DISPATCH(spirv::FunctionControl::Pure,
@@ -2388,9 +2402,8 @@ void mlir::encodeBindAttribute(ModuleOp module) {
auto spvModules = module.getOps<spirv::ModuleOp>();
for (auto spvModule : spvModules) {
spvModule.walk([&](spirv::GlobalVariableOp op) {
- IntegerAttr descriptorSet =
- op->getAttrOfType<IntegerAttr>(kDescriptorSet);
- IntegerAttr binding = op->getAttrOfType<IntegerAttr>(kBinding);
+ IntegerAttr descriptorSet = op.getDescriptorSetAttr();
+ IntegerAttr binding = op.getBindingAttr();
// For every global variable in the module, get the ones with descriptor
// set and binding numbers.
if (descriptorSet && binding) {
@@ -2411,8 +2424,8 @@ void mlir::encodeBindAttribute(ModuleOp module) {
if (failed(SymbolTable::replaceAllSymbolUses(op, nameAttr, spvModule)))
op.emitError("unable to replace all symbol uses for ") << name;
SymbolTable::setSymbolName(op, nameAttr);
- op->removeAttr(kDescriptorSet);
- op->removeAttr(kBinding);
+ op.removeDescriptorSetAttr();
+ op.removeBindingAttr();
}
});
}
diff --git a/mlir/lib/Conversion/TosaToLinalg/TosaToLinalg.cpp b/mlir/lib/Conversion/TosaToLinalg/TosaToLinalg.cpp
index e3f40c57eb312..b7eb0a3aed546 100644
--- a/mlir/lib/Conversion/TosaToLinalg/TosaToLinalg.cpp
+++ b/mlir/lib/Conversion/TosaToLinalg/TosaToLinalg.cpp
@@ -291,7 +291,7 @@ static Value createLinalgBodyCalculationForElementwiseOp(
// tosa::ArithmeticRightShiftOp
if (isa<tosa::ArithmeticRightShiftOp>(op) && isa<IntegerType>(elementTy)) {
auto result = arith::ShRSIOp::create(rewriter, loc, resultTypes, args);
- auto round = cast<BoolAttr>(op->getAttr("round")).getValue();
+ bool round = cast<tosa::ArithmeticRightShiftOp>(op).getRound();
if (!round) {
return result;
}
@@ -451,8 +451,9 @@ static Value createLinalgBodyCalculationForElementwiseOp(
// tosa::ClampOp
if (isa<tosa::ClampOp>(op) && isa<FloatType>(elementTy)) {
bool losesInfo = false;
- APFloat minApf = cast<FloatAttr>(op->getAttr("min_val")).getValue();
- APFloat maxApf = cast<FloatAttr>(op->getAttr("max_val")).getValue();
+ auto clampOp = cast<tosa::ClampOp>(op);
+ APFloat minApf = cast<FloatAttr>(clampOp.getMinValAttr()).getValue();
+ APFloat maxApf = cast<FloatAttr>(clampOp.getMaxValAttr()).getValue();
minApf.convert(cast<FloatType>(elementTy).getFloatSemantics(),
APFloat::rmNearestTiesToEven, &losesInfo);
maxApf.convert(cast<FloatType>(elementTy).getFloatSemantics(),
@@ -463,7 +464,6 @@ static Value createLinalgBodyCalculationForElementwiseOp(
rewriter, loc, elementTy, rewriter.getFloatAttr(elementTy, maxApf));
auto result = clampFloatHelper(loc, args[0], min, max, rewriter);
- auto clampOp = llvm::cast<tosa::ClampOp>(op);
const auto nanMode = clampOp.getNanMode();
// NaN propagation has no meaning for non floating point types.
@@ -495,10 +495,11 @@ static Value createLinalgBodyCalculationForElementwiseOp(
if (isa<tosa::ClampOp>(op) && isa<IntegerType>(elementTy)) {
auto intTy = cast<IntegerType>(elementTy);
+ auto clampOp = cast<tosa::ClampOp>(op);
int64_t min =
- cast<IntegerAttr>(op->getAttr("min_val")).getValue().getSExtValue();
+ cast<IntegerAttr>(clampOp.getMinValAttr()).getValue().getSExtValue();
int64_t max =
- cast<IntegerAttr>(op->getAttr("max_val")).getValue().getSExtValue();
+ cast<IntegerAttr>(clampOp.getMaxValAttr()).getValue().getSExtValue();
int64_t minRepresentable = std::numeric_limits<int64_t>::min();
int64_t maxRepresentable = std::numeric_limits<int64_t>::max();
diff --git a/mlir/lib/Conversion/TosaToLinalg/TosaToLinalgNamed.cpp b/mlir/lib/Conversion/TosaToLinalg/TosaToLinalgNamed.cpp
index 058b3de3a3788..ee57a5a781c5f 100644
--- a/mlir/lib/Conversion/TosaToLinalg/TosaToLinalgNamed.cpp
+++ b/mlir/lib/Conversion/TosaToLinalg/TosaToLinalgNamed.cpp
@@ -445,9 +445,9 @@ class DepthwiseConvConverter
Type inputETy = inputTy.getElementType();
Type resultETy = resultTy.getElementType();
- auto padAttr = cast<DenseI64ArrayAttr>(op->getAttr("pad"));
- auto strideTosaAttr = cast<DenseI64ArrayAttr>(op->getAttr("stride"));
- auto dilationTosaAttr = cast<DenseI64ArrayAttr>(op->getAttr("dilation"));
+ auto padAttr = op.getPadAttr();
+ auto strideTosaAttr = op.getStrideAttr();
+ auto dilationTosaAttr = op.getDilationAttr();
Type accETy = op.getAccType();
diff --git a/mlir/lib/Conversion/TosaToSPIRVTosa/TosaToSPIRVTosa.cpp b/mlir/lib/Conversion/TosaToSPIRVTosa/TosaToSPIRVTosa.cpp
index 3ef57c1e2cd22..45a7b0e68b793 100644
--- a/mlir/lib/Conversion/TosaToSPIRVTosa/TosaToSPIRVTosa.cpp
+++ b/mlir/lib/Conversion/TosaToSPIRVTosa/TosaToSPIRVTosa.cpp
@@ -34,7 +34,7 @@ void copyFuncAttrsToGraph(func::FuncOp funcOp, func::FuncOpAdaptor adaptor,
attrName))
continue;
- graphOp->setAttr(attr.getName(), attr.getValue());
+ graphOp->setDiscardableAttr(attr.getName(), attr.getValue());
}
}
@@ -109,7 +109,7 @@ struct FuncGraphConvert final : OpConversionPattern<func::FuncOp> {
rewriter, funcOp.getLoc(), spirv::AddressingModel::Logical,
spirv::MemoryModel::Vulkan, std::nullopt,
("_spirv_tosa_" + name).str());
- spvModule->setAttr(spirv::getTargetEnvAttrName(), targetAttr);
+ spvModule->setDiscardableAttr(spirv::getTargetEnvAttrName(), targetAttr);
rewriter.setInsertionPoint(spvModule.getBody(), spvModule.begin());
diff --git a/mlir/lib/Conversion/TosaToSPIRVTosa/TosaToSPIRVTosaConstants.cpp b/mlir/lib/Conversion/TosaToSPIRVTosa/TosaToSPIRVTosaConstants.cpp
index c7174fd930782..b1496a776fa89 100644
--- a/mlir/lib/Conversion/TosaToSPIRVTosa/TosaToSPIRVTosaConstants.cpp
+++ b/mlir/lib/Conversion/TosaToSPIRVTosa/TosaToSPIRVTosaConstants.cpp
@@ -51,7 +51,8 @@ bool shouldMarkGraphConstant(Operation *op) {
void setGraphConstantId(Operation *op, uint32_t id) {
auto i32Type = IntegerType::get(op->getContext(), 32);
- op->setAttr(graphARMGraphConstantIdAttrName, IntegerAttr::get(i32Type, id));
+ op->setDiscardableAttr(graphARMGraphConstantIdAttrName,
+ IntegerAttr::get(i32Type, id));
}
struct TosaToSPIRVTosaMarkGraphConstants final
@@ -64,7 +65,7 @@ struct TosaToSPIRVTosaMarkGraphConstants final
if (!isa<tosa::ConstOp, tosa::ConstShapeOp>(op))
return WalkResult::advance();
- if (op->hasAttr(graphARMGraphConstantIdAttrName)) {
+ if (op->hasDiscardableAttr(graphARMGraphConstantIdAttrName)) {
op->emitOpError()
<< "already has `" << graphARMGraphConstantIdAttrName
<< "`; this pass assigns graph constant IDs automatically and "
diff --git a/mlir/lib/Conversion/TosaToSPIRVTosa/TosaToSPIRVTosaPass.cpp b/mlir/lib/Conversion/TosaToSPIRVTosa/TosaToSPIRVTosaPass.cpp
index 815f2db74ffa6..937d1d0e6f2ee 100644
--- a/mlir/lib/Conversion/TosaToSPIRVTosa/TosaToSPIRVTosaPass.cpp
+++ b/mlir/lib/Conversion/TosaToSPIRVTosa/TosaToSPIRVTosaPass.cpp
@@ -145,8 +145,8 @@ LogicalResult verifyGraphConstantIdAttrs(Operation *op) {
if (!isa<tosa::ConstOp, tosa::ConstShapeOp>(op))
return WalkResult::advance();
- auto graphConstantId =
- op->getAttrOfType<IntegerAttr>(graphARMGraphConstantIdAttrName);
+ auto graphConstantId = op->getDiscardableAttrOfType<IntegerAttr>(
+ graphARMGraphConstantIdAttrName);
if (!graphConstantId)
return WalkResult::advance();
diff --git a/mlir/lib/Conversion/VectorToArmSME/VectorToArmSME.cpp b/mlir/lib/Conversion/VectorToArmSME/VectorToArmSME.cpp
index 778c616f1bf44..6ec404e982577 100644
--- a/mlir/lib/Conversion/VectorToArmSME/VectorToArmSME.cpp
+++ b/mlir/lib/Conversion/VectorToArmSME/VectorToArmSME.cpp
@@ -300,9 +300,9 @@ struct TransposeOpToArmSMELowering
// Fold transpose into transfer_read to enable in-flight transpose when
// converting to arm_sme.tile_load.
rewriter.modifyOpInPlace(xferOp, [&]() {
- xferOp->setAttr(xferOp.getPermutationMapAttrName(),
- AffineMapAttr::get(AffineMap::getPermutationMap(
- permutation, transposeOp.getContext())));
+ xferOp.setPermutationMapAttr(
+ AffineMapAttr::get(AffineMap::getPermutationMap(
+ permutation, transposeOp.getContext())));
});
rewriter.replaceOp(transposeOp, xferOp);
return success();
diff --git a/mlir/lib/Conversion/VectorToSCF/VectorToSCF.cpp b/mlir/lib/Conversion/VectorToSCF/VectorToSCF.cpp
index c9eba6962e6a4..3a48e2e6abf6a 100644
--- a/mlir/lib/Conversion/VectorToSCF/VectorToSCF.cpp
+++ b/mlir/lib/Conversion/VectorToSCF/VectorToSCF.cpp
@@ -272,7 +272,7 @@ template <typename OpTy>
static void maybeApplyPassLabel(OpBuilder &b, OpTy newXferOp,
unsigned targetRank) {
if (newXferOp.getVectorType().getRank() > targetRank)
- newXferOp->setAttr(kPassLabel, b.getUnitAttr());
+ newXferOp->setDiscardableAttr(kPassLabel, b.getUnitAttr());
}
namespace lowering_n_d {
@@ -550,7 +550,7 @@ struct Strategy<TransferWriteOp> {
template <typename OpTy>
static LogicalResult checkPrepareXferOp(OpTy xferOp, PatternRewriter &rewriter,
VectorTransferToSCFOptions options) {
- if (xferOp->hasAttr(kPassLabel))
+ if (xferOp->hasDiscardableAttr(kPassLabel))
return rewriter.notifyMatchFailure(
xferOp, "kPassLabel is present (vector-to-scf lowering in progress)");
if (xferOp.getVectorType().getRank() <= options.targetRank)
@@ -606,7 +606,7 @@ struct PrepareTransferReadConversion
auto buffers = allocBuffers(rewriter, xferOp);
auto *newXfer = rewriter.clone(*xferOp.getOperation());
- newXfer->setAttr(kPassLabel, rewriter.getUnitAttr());
+ newXfer->setDiscardableAttr(kPassLabel, rewriter.getUnitAttr());
if (xferOp.getMask()) {
dyn_cast<TransferReadOp>(newXfer).getMaskMutable().assign(
buffers.maskBuffer);
@@ -661,7 +661,7 @@ struct PrepareTransferWriteConversion
auto loadedVec = memref::LoadOp::create(rewriter, loc, buffers.dataBuffer);
rewriter.modifyOpInPlace(xferOp, [&]() {
xferOp.getValueToStoreMutable().assign(loadedVec);
- xferOp->setAttr(kPassLabel, rewriter.getUnitAttr());
+ xferOp->setDiscardableAttr(kPassLabel, rewriter.getUnitAttr());
});
if (xferOp.getMask()) {
@@ -906,7 +906,7 @@ struct TransferOpConversion : public VectorToSCFPattern<OpTy> {
LogicalResult matchAndRewrite(OpTy xferOp,
PatternRewriter &rewriter) const override {
- if (!xferOp->hasAttr(kPassLabel))
+ if (!xferOp->hasDiscardableAttr(kPassLabel))
return rewriter.notifyMatchFailure(
xferOp, "kPassLabel is present (progressing lowering in progress)");
diff --git a/mlir/lib/Conversion/XeGPUToXeVM/XeGPUToXeVM.cpp b/mlir/lib/Conversion/XeGPUToXeVM/XeGPUToXeVM.cpp
index 78d99cf88b768..c1c7ddfbdd237 100644
--- a/mlir/lib/Conversion/XeGPUToXeVM/XeGPUToXeVM.cpp
+++ b/mlir/lib/Conversion/XeGPUToXeVM/XeGPUToXeVM.cpp
@@ -678,7 +678,7 @@ class LoadStoreToXeVMPattern : public OpConversionPattern<OpType> {
Value loaded =
LLVM::LoadOp::create(rewriter, loc, valOrResTy, basePtrLLVM);
// Set cache control attribute on the load operation.
- loaded.getDefiningOp()->setAttr(
+ loaded.getDefiningOp()->setDiscardableAttr(
"cache_control", xevm::LoadCacheControlAttr::get(
ctxt, translateLoadXeGPUCacheHint(
op.getL1Hint(), op.getL3Hint())));
@@ -706,7 +706,7 @@ class LoadStoreToXeVMPattern : public OpConversionPattern<OpType> {
auto storeOp =
LLVM::StoreOp::create(rewriter, loc, adaptor.getValue(), basePtrLLVM);
// Set cache control attribute on the store operation.
- storeOp.getOperation()->setAttr(
+ storeOp.getOperation()->setDiscardableAttr(
"cache_control", xevm::StoreCacheControlAttr::get(
ctxt, translateStoreXeGPUCacheHint(
op.getL1Hint(), op.getL3Hint())));
diff --git a/mlir/lib/Conversion/XeVMToLLVM/XeVMToLLVM.cpp b/mlir/lib/Conversion/XeVMToLLVM/XeVMToLLVM.cpp
index c51da4d5d4d3d..231bbea0eb212 100644
--- a/mlir/lib/Conversion/XeVMToLLVM/XeVMToLLVM.cpp
+++ b/mlir/lib/Conversion/XeVMToLLVM/XeVMToLLVM.cpp
@@ -241,8 +241,9 @@ static std::optional<StoreCacheControl> getCacheControl(BlockStoreOp op) {
}
static std::optional<LoadCacheControl> getCacheControl(LLVM::LoadOp op) {
- if (op->hasAttr("cache_control")) {
- auto attr = op->getAttrOfType<xevm::LoadCacheControlAttr>("cache_control");
+ if (op->hasDiscardableAttr("cache_control")) {
+ auto attr = op->getDiscardableAttrOfType<xevm::LoadCacheControlAttr>(
+ "cache_control");
if (!attr)
return std::nullopt;
return std::optional<LoadCacheControl>(attr.getValue());
@@ -251,8 +252,9 @@ static std::optional<LoadCacheControl> getCacheControl(LLVM::LoadOp op) {
}
static std::optional<StoreCacheControl> getCacheControl(LLVM::StoreOp op) {
- if (op->hasAttr("cache_control")) {
- auto attr = op->getAttrOfType<xevm::StoreCacheControlAttr>("cache_control");
+ if (op->hasDiscardableAttr("cache_control")) {
+ auto attr = op->getDiscardableAttrOfType<xevm::StoreCacheControlAttr>(
+ "cache_control");
if (!attr)
return std::nullopt;
return std::optional<StoreCacheControl>(attr.getValue());
@@ -533,7 +535,15 @@ static LLVM::CallOp createDeviceFunctionCall(
funcOp.setArgAttr(idx, attrName, rewriter.getUnitAttr());
auto callOp = LLVM::CallOp::create(rewriter, loc, funcOp, args);
- callOp->setAttrs(funcOp->getAttrs());
+ NamedAttrList attrs(funcOp->getDiscardableAttrDictionary());
+ funcOp->getName().populateInherentAttrs(funcOp, attrs);
+ for (NamedAttribute attr :
+ attrs.getDictionary(funcOp.getContext()).getValue()) {
+ if (callOp->getInherentAttr(attr.getName()).has_value())
+ callOp->setInherentAttr(attr.getName(), attr.getValue());
+ else
+ callOp->setDiscardableAttr(attr.getName(), attr.getValue());
+ }
return callOp;
}
@@ -968,14 +978,15 @@ class LLVMLoadStoreToOCLPattern : public OpConversionPattern<OpType> {
LogicalResult
matchAndRewrite(OpType op, typename OpType::Adaptor adaptor,
ConversionPatternRewriter &rewriter) const override {
- if (!op->hasAttr("cache_control"))
+ if (!op->hasDiscardableAttr("cache_control"))
return failure();
auto *moduleOp = op->template getParentWithTrait<OpTrait::SymbolTable>();
std::optional<ArrayAttr> optCacheControls =
getCacheControlMetadata(rewriter, op);
if (!optCacheControls) {
- rewriter.modifyOpInPlace(op, [&]() { op->removeAttr("cache_control"); });
+ rewriter.modifyOpInPlace(
+ op, [&]() { op->removeDiscardableAttr("cache_control"); });
return success();
}
@@ -991,7 +1002,7 @@ class LLVMLoadStoreToOCLPattern : public OpConversionPattern<OpType> {
// Replace the pointer operand with the annotated one.
rewriter.modifyOpInPlace(op, [&]() {
op->setOperand(ptrIdx, annotatedPtr);
- op->removeAttr("cache_control");
+ op->removeDiscardableAttr("cache_control");
});
return success();
}
@@ -1784,7 +1795,7 @@ void ::mlir::populateXeVMToLLVMConversionPatterns(ConversionTarget &target,
return addrSpace != 3;
}
// cache_control attribute should be converted.
- return !op->hasAttr("cache_control");
+ return !op->hasDiscardableAttr("cache_control");
});
target.addIllegalDialect<XeVMDialect>();
patterns
diff --git a/mlir/lib/Dialect/AMDGPU/Transforms/EmulateAtomics.cpp b/mlir/lib/Dialect/AMDGPU/Transforms/EmulateAtomics.cpp
index 332ac8cdb60c0..b2483426b8ee8 100644
--- a/mlir/lib/Dialect/AMDGPU/Transforms/EmulateAtomics.cpp
+++ b/mlir/lib/Dialect/AMDGPU/Transforms/EmulateAtomics.cpp
@@ -110,7 +110,8 @@ LogicalResult RawBufferAtomicByCasPattern<AtomicOp, ArithOp>::matchAndRewrite(
ConversionPatternRewriter &rewriter) const {
Location loc = atomicOp.getLoc();
- ArrayRef<NamedAttribute> origAttrs = atomicOp->getAttrs();
+ NamedAttrList origAttrs(atomicOp->getDiscardableAttrDictionary());
+ atomicOp->getName().populateInherentAttrs(atomicOp, origAttrs);
ValueRange operands = adaptor.getOperands();
Value data = operands.take_front()[0];
ValueRange invariantArgs = operands.drop_front();
diff --git a/mlir/lib/Dialect/AMDGPU/Transforms/MaskedloadToLoad.cpp b/mlir/lib/Dialect/AMDGPU/Transforms/MaskedloadToLoad.cpp
index 89ef51f922cad..8c2d697632e20 100644
--- a/mlir/lib/Dialect/AMDGPU/Transforms/MaskedloadToLoad.cpp
+++ b/mlir/lib/Dialect/AMDGPU/Transforms/MaskedloadToLoad.cpp
@@ -81,7 +81,7 @@ struct MaskedLoadLowering final : OpRewritePattern<vector::MaskedLoadOp> {
LogicalResult matchAndRewrite(vector::MaskedLoadOp maskedOp,
PatternRewriter &rewriter) const override {
- if (maskedOp->hasAttr(kMaskedloadNeedsMask))
+ if (maskedOp->hasDiscardableAttr(kMaskedloadNeedsMask))
return rewriter.notifyMatchFailure(maskedOp, "already rewritten");
if (failed(hasBufferAddressSpace(maskedOp.getBase().getType()))) {
@@ -150,7 +150,7 @@ struct MaskedLoadLowering final : OpRewritePattern<vector::MaskedLoadOp> {
auto thenBuilder = [&](OpBuilder &builder, Location loc) {
Operation *read = builder.clone(*maskedOp.getOperation());
- read->setAttr(kMaskedloadNeedsMask, builder.getUnitAttr());
+ read->setDiscardableAttr(kMaskedloadNeedsMask, builder.getUnitAttr());
Value readResult = read->getResult(0);
scf::YieldOp::create(builder, loc, readResult);
};
diff --git a/mlir/lib/Dialect/Affine/Analysis/Utils.cpp b/mlir/lib/Dialect/Affine/Analysis/Utils.cpp
index 321c8e34d907c..4f65b392da603 100644
--- a/mlir/lib/Dialect/Affine/Analysis/Utils.cpp
+++ b/mlir/lib/Dialect/Affine/Analysis/Utils.cpp
@@ -1945,7 +1945,8 @@ void mlir::affine::getComputationSliceState(
for (unsigned i = 0; i < numSliceLoopIVs; ++i) {
Value iv = getSliceLoop(i).getInductionVar();
if (sequentialLoops.count(iv) == 0 &&
- getSliceLoop(i)->getAttr(kSliceFusionBarrierAttrName) == nullptr)
+ getSliceLoop(i)->getDiscardableAttr(kSliceFusionBarrierAttrName) ==
+ nullptr)
continue;
// Skip reset of bounds of reduction loop inserted in the destination loop
// that meets the following conditions:
diff --git a/mlir/lib/Dialect/Affine/IR/AffineOps.cpp b/mlir/lib/Dialect/Affine/IR/AffineOps.cpp
index b1f7b987703a5..aa24cb0d3d3c8 100644
--- a/mlir/lib/Dialect/Affine/IR/AffineOps.cpp
+++ b/mlir/lib/Dialect/Affine/IR/AffineOps.cpp
@@ -574,7 +574,8 @@ void AffineApplyOp::print(OpAsmPrinter &p) {
p << " " << getMapAttr();
printDimAndSymbolList(operand_begin(), operand_end(),
getAffineMap().getNumDims(), p);
- p.printOptionalAttrDict((*this)->getAttrs(), /*elidedAttrs=*/{"map"});
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue(),
+ /*elidedAttrs=*/{"map"});
}
LogicalResult AffineApplyOp::verify() {
@@ -2507,7 +2508,7 @@ void AffineForOp::print(OpAsmPrinter &p) {
p.printRegion(getRegion(), /*printEntryBlockArgs=*/false,
printBlockTerminators);
p.printOptionalAttrDict(
- (*this)->getAttrs(),
+ (*this)->getDiscardableAttrDictionary().getValue(),
/*elidedAttrs=*/{getLowerBoundMapAttrName(getOperation()->getName()),
getUpperBoundMapAttrName(getOperation()->getName()),
getStepAttrName(getOperation()->getName()),
@@ -3199,8 +3200,7 @@ ValueRange AffineIfOp::getSuccessorInputs(RegionSuccessor successor) {
LogicalResult AffineIfOp::verify() {
// Verify that we have a condition attribute.
// FIXME: This should be specified in the arguments list in ODS.
- auto conditionAttr =
- (*this)->getAttrOfType<IntegerSetAttr>(getConditionAttrStrName());
+ auto conditionAttr = getConditionAttr();
if (!conditionAttr)
return emitOpError("requires an integer set attribute named 'condition'");
@@ -3270,8 +3270,7 @@ ParseResult AffineIfOp::parse(OpAsmParser &parser, OperationState &result) {
}
void AffineIfOp::print(OpAsmPrinter &p) {
- auto conditionAttr =
- (*this)->getAttrOfType<IntegerSetAttr>(getConditionAttrStrName());
+ auto conditionAttr = getConditionAttr();
p << " " << conditionAttr;
printDimAndSymbolList(operand_begin(), operand_end(),
conditionAttr.getValue().getNumDims(), p);
@@ -3290,18 +3289,14 @@ void AffineIfOp::print(OpAsmPrinter &p) {
}
// Print the attribute list.
- p.printOptionalAttrDict((*this)->getAttrs(),
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue(),
/*elidedAttrs=*/getConditionAttrStrName());
}
-IntegerSet AffineIfOp::getIntegerSet() {
- return (*this)
- ->getAttrOfType<IntegerSetAttr>(getConditionAttrStrName())
- .getValue();
-}
+IntegerSet AffineIfOp::getIntegerSet() { return getConditionAttr().getValue(); }
void AffineIfOp::setIntegerSet(IntegerSet newSet) {
- (*this)->setAttr(getConditionAttrStrName(), IntegerSetAttr::get(newSet));
+ setConditionAttr(IntegerSetAttr::get(newSet));
}
void AffineIfOp::setConditional(IntegerSet set, ValueRange operands) {
@@ -3451,12 +3446,13 @@ ParseResult AffineLoadOp::parse(OpAsmParser &parser, OperationState &result) {
void AffineLoadOp::print(OpAsmPrinter &p) {
p << " " << getMemRef() << '[';
- if (AffineMapAttr mapAttr =
- (*this)->getAttrOfType<AffineMapAttr>(getMapAttrStrName()))
+ if (AffineMapAttr mapAttr = getMapAttr())
p.printAffineMapOfSSAIds(mapAttr, getMapOperands());
p << ']';
- p.printOptionalAttrDict((*this)->getAttrs(),
- /*elidedAttrs=*/{getMapAttrStrName()});
+ NamedAttrList attrs((*this)->getDiscardableAttrDictionary());
+ if (IntegerAttr alignment = getAlignmentAttr())
+ attrs.append(getAlignmentAttrName(), alignment);
+ p.printOptionalAttrDict(attrs, /*elidedAttrs=*/{getMapAttrStrName()});
p << " : " << getMemRefType();
}
@@ -3488,10 +3484,9 @@ LogicalResult AffineLoadOp::verify() {
if (getType() != memrefType.getElementType())
return emitOpError("result type must match element type of memref");
- if (failed(verifyMemoryOpIndexing(
- *this, (*this)->getAttrOfType<AffineMapAttr>(getMapAttrStrName()),
- getMapOperands(), memrefType,
- /*numIndexOperands=*/getNumOperands() - 1)))
+ if (failed(verifyMemoryOpIndexing(*this, getMapAttr(), getMapOperands(),
+ memrefType,
+ /*numIndexOperands=*/getNumOperands() - 1)))
return failure();
return success();
@@ -3587,12 +3582,13 @@ ParseResult AffineStoreOp::parse(OpAsmParser &parser, OperationState &result) {
void AffineStoreOp::print(OpAsmPrinter &p) {
p << " " << getValueToStore();
p << ", " << getMemRef() << '[';
- if (AffineMapAttr mapAttr =
- (*this)->getAttrOfType<AffineMapAttr>(getMapAttrStrName()))
+ if (AffineMapAttr mapAttr = getMapAttr())
p.printAffineMapOfSSAIds(mapAttr, getMapOperands());
p << ']';
- p.printOptionalAttrDict((*this)->getAttrs(),
- /*elidedAttrs=*/{getMapAttrStrName()});
+ NamedAttrList attrs((*this)->getDiscardableAttrDictionary());
+ if (IntegerAttr alignment = getAlignmentAttr())
+ attrs.append(getAlignmentAttrName(), alignment);
+ p.printOptionalAttrDict(attrs, /*elidedAttrs=*/{getMapAttrStrName()});
p << " : " << getMemRefType();
}
@@ -3603,10 +3599,9 @@ LogicalResult AffineStoreOp::verify() {
return emitOpError(
"value to store must have the same type as memref element type");
- if (failed(verifyMemoryOpIndexing(
- *this, (*this)->getAttrOfType<AffineMapAttr>(getMapAttrStrName()),
- getMapOperands(), memrefType,
- /*numIndexOperands=*/getNumOperands() - 2)))
+ if (failed(verifyMemoryOpIndexing(*this, getMapAttr(), getMapOperands(),
+ memrefType,
+ /*numIndexOperands=*/getNumOperands() - 2)))
return failure();
return success();
@@ -3642,14 +3637,14 @@ static LogicalResult verifyAffineMinMaxOp(T op) {
template <typename T>
static void printAffineMinMaxOp(OpAsmPrinter &p, T op) {
- p << ' ' << op->getAttr(T::getMapAttrStrName());
+ p << ' ' << op.getMapAttr();
auto operands = op.getOperands();
unsigned numDims = op.getMap().getNumDims();
p << '(' << operands.take_front(numDims) << ')';
if (operands.size() != numDims)
p << '[' << operands.drop_front(numDims) << ']';
- p.printOptionalAttrDict(op->getAttrs(),
+ p.printOptionalAttrDict(op->getDiscardableAttrDictionary().getValue(),
/*elidedAttrs=*/{T::getMapAttrStrName()});
}
@@ -3695,7 +3690,7 @@ static OpFoldResult foldMinMaxOp(T op, ArrayRef<Attribute> operands) {
// If the map is the same, report that folding did not happen.
if (foldedMap == op.getMap())
return {};
- op->setAttr("map", AffineMapAttr::get(foldedMap));
+ op.setMapAttr(AffineMapAttr::get(foldedMap));
return op.getResult();
}
@@ -4033,21 +4028,20 @@ ParseResult AffinePrefetchOp::parse(OpAsmParser &parser,
void AffinePrefetchOp::print(OpAsmPrinter &p) {
p << " " << getMemref() << '[';
- AffineMapAttr mapAttr =
- (*this)->getAttrOfType<AffineMapAttr>(getMapAttrStrName());
+ AffineMapAttr mapAttr = getMapAttr();
if (mapAttr)
p.printAffineMapOfSSAIds(mapAttr, getMapOperands());
p << ']' << ", " << (getIsWrite() ? "write" : "read") << ", " << "locality<"
<< getLocalityHint() << ">, " << (getIsDataCache() ? "data" : "instr");
p.printOptionalAttrDict(
- (*this)->getAttrs(),
+ (*this)->getDiscardableAttrDictionary().getValue(),
/*elidedAttrs=*/{getMapAttrStrName(), getLocalityHintAttrStrName(),
getIsDataCacheAttrStrName(), getIsWriteAttrStrName()});
p << " : " << getMemRefType();
}
LogicalResult AffinePrefetchOp::verify() {
- auto mapAttr = (*this)->getAttrOfType<AffineMapAttr>(getMapAttrStrName());
+ auto mapAttr = getMapAttr();
if (mapAttr) {
AffineMap map = mapAttr.getValue();
if (map.getNumResults() != getMemRefType().getRank())
@@ -4475,7 +4469,7 @@ void AffineParallelOp::print(OpAsmPrinter &p) {
p.printRegion(getRegion(), /*printEntryBlockArgs=*/false,
/*printBlockTerminators=*/getNumResults());
p.printOptionalAttrDict(
- (*this)->getAttrs(),
+ (*this)->getDiscardableAttrDictionary().getValue(),
/*elidedAttrs=*/{AffineParallelOp::getReductionsAttrStrName(),
AffineParallelOp::getLowerBoundsMapAttrStrName(),
AffineParallelOp::getLowerBoundsGroupsAttrStrName(),
@@ -4818,12 +4812,13 @@ ParseResult AffineVectorLoadOp::parse(OpAsmParser &parser,
void AffineVectorLoadOp::print(OpAsmPrinter &p) {
p << " " << getMemRef() << '[';
- if (AffineMapAttr mapAttr =
- (*this)->getAttrOfType<AffineMapAttr>(getMapAttrStrName()))
+ if (AffineMapAttr mapAttr = getMapAttr())
p.printAffineMapOfSSAIds(mapAttr, getMapOperands());
p << ']';
- p.printOptionalAttrDict((*this)->getAttrs(),
- /*elidedAttrs=*/{getMapAttrStrName()});
+ NamedAttrList attrs((*this)->getDiscardableAttrDictionary());
+ if (IntegerAttr alignment = getAlignmentAttr())
+ attrs.append(getAlignmentAttrName(), alignment);
+ p.printOptionalAttrDict(attrs, /*elidedAttrs=*/{getMapAttrStrName()});
p << " : " << getMemRefType() << ", " << getType();
}
@@ -4839,10 +4834,9 @@ static LogicalResult verifyVectorMemoryOp(Operation *op, MemRefType memrefType,
LogicalResult AffineVectorLoadOp::verify() {
MemRefType memrefType = getMemRefType();
- if (failed(verifyMemoryOpIndexing(
- *this, (*this)->getAttrOfType<AffineMapAttr>(getMapAttrStrName()),
- getMapOperands(), memrefType,
- /*numIndexOperands=*/getNumOperands() - 1)))
+ if (failed(verifyMemoryOpIndexing(*this, getMapAttr(), getMapOperands(),
+ memrefType,
+ /*numIndexOperands=*/getNumOperands() - 1)))
return failure();
if (failed(verifyVectorMemoryOp(getOperation(), memrefType, getVectorType())))
@@ -4913,21 +4907,21 @@ ParseResult AffineVectorStoreOp::parse(OpAsmParser &parser,
void AffineVectorStoreOp::print(OpAsmPrinter &p) {
p << " " << getValueToStore();
p << ", " << getMemRef() << '[';
- if (AffineMapAttr mapAttr =
- (*this)->getAttrOfType<AffineMapAttr>(getMapAttrStrName()))
+ if (AffineMapAttr mapAttr = getMapAttr())
p.printAffineMapOfSSAIds(mapAttr, getMapOperands());
p << ']';
- p.printOptionalAttrDict((*this)->getAttrs(),
- /*elidedAttrs=*/{getMapAttrStrName()});
+ NamedAttrList attrs((*this)->getDiscardableAttrDictionary());
+ if (IntegerAttr alignment = getAlignmentAttr())
+ attrs.append(getAlignmentAttrName(), alignment);
+ p.printOptionalAttrDict(attrs, /*elidedAttrs=*/{getMapAttrStrName()});
p << " : " << getMemRefType() << ", " << getValueToStore().getType();
}
LogicalResult AffineVectorStoreOp::verify() {
MemRefType memrefType = getMemRefType();
- if (failed(verifyMemoryOpIndexing(
- *this, (*this)->getAttrOfType<AffineMapAttr>(getMapAttrStrName()),
- getMapOperands(), memrefType,
- /*numIndexOperands=*/getNumOperands() - 2)))
+ if (failed(verifyMemoryOpIndexing(*this, getMapAttr(), getMapOperands(),
+ memrefType,
+ /*numIndexOperands=*/getNumOperands() - 2)))
return failure();
if (failed(verifyVectorMemoryOp(*this, memrefType, getVectorType())))
diff --git a/mlir/lib/Dialect/Affine/Transforms/PipelineDataTransfer.cpp b/mlir/lib/Dialect/Affine/Transforms/PipelineDataTransfer.cpp
index 9a1c731b5a97e..97258afd18024 100644
--- a/mlir/lib/Dialect/Affine/Transforms/PipelineDataTransfer.cpp
+++ b/mlir/lib/Dialect/Affine/Transforms/PipelineDataTransfer.cpp
@@ -368,7 +368,7 @@ void PipelineDataTransfer::runOnAffineForOp(AffineForOp forOp) {
// Tagging operations with shifts for debugging purposes.
LLVM_DEBUG({
OpBuilder b(&op);
- op.setAttr("shift", b.getI64IntegerAttr(shifts[s - 1]));
+ op.setDiscardableAttr("shift", b.getI64IntegerAttr(shifts[s - 1]));
});
}
diff --git a/mlir/lib/Dialect/Affine/Transforms/SimplifyAffineStructures.cpp b/mlir/lib/Dialect/Affine/Transforms/SimplifyAffineStructures.cpp
index c09afc03c5257..e4509b9ba5463 100644
--- a/mlir/lib/Dialect/Affine/Transforms/SimplifyAffineStructures.cpp
+++ b/mlir/lib/Dialect/Affine/Transforms/SimplifyAffineStructures.cpp
@@ -64,7 +64,10 @@ struct SimplifyAffineStructures
}
// Simplification was successful, so update the attribute.
- op->setAttr(name, simplified);
+ if (op->getInherentAttr(name).has_value())
+ op->setInherentAttr(name, simplified);
+ else
+ op->setDiscardableAttr(name, simplified);
}
IntegerSet simplify(IntegerSet set) { return simplifyIntegerSet(set); }
@@ -99,7 +102,9 @@ void SimplifyAffineStructures::runOnOperation() {
// fold/apply canonicalization patterns when we have affine dialect ops.
SmallVector<Operation *> opsToSimplify;
func.walk([&](Operation *op) {
- for (auto attr : op->getAttrs()) {
+ NamedAttrList attrs(op->getDiscardableAttrDictionary());
+ op->getName().populateInherentAttrs(op, attrs);
+ for (auto attr : attrs) {
if (auto mapAttr = dyn_cast<AffineMapAttr>(attr.getValue()))
simplifyAndUpdateAttribute(op, attr.getName(), mapAttr);
else if (auto setAttr = dyn_cast<IntegerSetAttr>(attr.getValue()))
diff --git a/mlir/lib/Dialect/Affine/Transforms/SuperVectorize.cpp b/mlir/lib/Dialect/Affine/Transforms/SuperVectorize.cpp
index 6c0cf507de5b8..6c6e8ed979d23 100644
--- a/mlir/lib/Dialect/Affine/Transforms/SuperVectorize.cpp
+++ b/mlir/lib/Dialect/Affine/Transforms/SuperVectorize.cpp
@@ -1504,9 +1504,11 @@ static Operation *widenOp(Operation *op, VectorizationState &state) {
// name that works both in scalar mode and vector mode.
// TODO: Is it worth considering an Operation.clone operation which
// changes the type so we can promote an Operation with less boilerplate?
- Operation *vecOp =
- state.builder.create(op->getLoc(), op->getName().getIdentifier(),
- vectorOperands, vectorTypes, op->getAttrs());
+ OperationState vecState(op->getLoc(), op->getName(), vectorOperands,
+ vectorTypes,
+ op->getDiscardableAttrDictionary().getValue());
+ vecState.propertiesAttr = op->getPropertiesAsAttribute();
+ Operation *vecOp = state.builder.create(vecState);
state.registerOpVectorReplacement(op, vecOp);
return vecOp;
}
diff --git a/mlir/lib/Dialect/Affine/Utils/Utils.cpp b/mlir/lib/Dialect/Affine/Utils/Utils.cpp
index 7043083298615..e2ad3151a934c 100644
--- a/mlir/lib/Dialect/Affine/Utils/Utils.cpp
+++ b/mlir/lib/Dialect/Affine/Utils/Utils.cpp
@@ -312,7 +312,7 @@ static AffineIfOp hoistAffineIfOp(AffineIfOp ifOp, Operation *hoistOverOp) {
operandMap.clear();
b.setInsertionPointAfter(hoistOverOp);
// We'll set an attribute to identify this op in a clone of this sub-tree.
- ifOp->setAttr(idForIfOp, b.getBoolAttr(true));
+ ifOp->setDiscardableAttr(idForIfOp, b.getBoolAttr(true));
hoistOverOpClone = b.clone(*hoistOverOp, operandMap);
// Promote the 'then' block of the original affine.if in the then version.
@@ -327,7 +327,7 @@ static AffineIfOp hoistAffineIfOp(AffineIfOp ifOp, Operation *hoistOverOp) {
// Find the clone of the original affine.if op in the else version.
AffineIfOp ifCloneInElse;
hoistOverOpClone->walk([&](AffineIfOp ifClone) {
- if (!ifClone->getAttr(idForIfOp))
+ if (!ifClone->getDiscardableAttr(idForIfOp))
return WalkResult::advance();
ifCloneInElse = ifClone;
return WalkResult::interrupt();
@@ -1298,17 +1298,16 @@ LogicalResult mlir::affine::replaceAllMemRefUsesWith(
// Add attribute for 'newMap', other Attributes do not change.
auto newMapAttr = AffineMapAttr::get(newMap);
- for (auto namedAttr : op->getAttrs()) {
- if (affMapAccInterface &&
- namedAttr.getName() ==
- affMapAccInterface.getAffineMapAttrForMemRef(oldMemRef).getName())
- state.attributes.push_back({namedAttr.getName(), newMapAttr});
- else
- state.attributes.push_back(namedAttr);
- }
+ state.addAttributes(op->getDiscardableAttrDictionary().getValue());
+ state.propertiesAttr = op->getPropertiesAsAttribute();
// Create the new operation.
auto *repOp = builder.create(state);
+ if (affMapAccInterface) {
+ StringAttr mapAttrName =
+ affMapAccInterface.getAffineMapAttrForMemRef(oldMemRef).getName();
+ repOp->setInherentAttr(mapAttrName, newMapAttr);
+ }
op->replaceAllUsesWith(repOp);
op->erase();
diff --git a/mlir/lib/Dialect/Arith/IR/ArithOps.cpp b/mlir/lib/Dialect/Arith/IR/ArithOps.cpp
index 7157e29800db0..bf2ab29caad4b 100644
--- a/mlir/lib/Dialect/Arith/IR/ArithOps.cpp
+++ b/mlir/lib/Dialect/Arith/IR/ArithOps.cpp
@@ -1461,9 +1461,14 @@ struct NarrowExtremum final : OpRewritePattern<TruncOp> {
return failure();
}
- rewriter.replaceOpWithNewOp<ExtremumOp>(truncOp, TypeRange{narrowType},
- ValueRange{lhs, rhs},
- extremumOp->getAttrs());
+ SmallVector<NamedAttribute> discardableAttrs(
+ extremumOp->getDiscardableAttrs());
+ OperationState state(truncOp.getLoc(), ExtremumOp::getOperationName(),
+ ValueRange{lhs, rhs}, TypeRange{narrowType},
+ discardableAttrs);
+ state.propertiesAttr = extremumOp->getPropertiesAsAttribute();
+ Operation *newExtremum = rewriter.create(state);
+ rewriter.replaceOp(truncOp, newExtremum->getResults());
return success();
}
};
@@ -3061,7 +3066,7 @@ ParseResult SelectOp::parse(OpAsmParser &parser, OperationState &result) {
void arith::SelectOp::print(OpAsmPrinter &p) {
p << " " << getOperands();
- p.printOptionalAttrDict((*this)->getAttrs());
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue());
p << " : ";
if (ShapedType condType = dyn_cast<ShapedType>(getCondition().getType()))
p << condType << ", ";
diff --git a/mlir/lib/Dialect/Arith/Transforms/EmulateUnsupportedFloats.cpp b/mlir/lib/Dialect/Arith/Transforms/EmulateUnsupportedFloats.cpp
index b6e101952676a..23659d8010f45 100644
--- a/mlir/lib/Dialect/Arith/Transforms/EmulateUnsupportedFloats.cpp
+++ b/mlir/lib/Dialect/Arith/Transforms/EmulateUnsupportedFloats.cpp
@@ -68,9 +68,11 @@ LogicalResult EmulateFloatPattern::matchAndRewrite(
// If you're seeing it, there's a bug.
return op->emitOpError("type conversion failed in float emulation");
}
- Operation *expandedOp =
- rewriter.create(loc, op->getName().getIdentifier(), operands, resultTypes,
- op->getAttrs(), op->getSuccessors(), /*regions=*/{});
+ OperationState state(loc, op->getName(), operands, resultTypes,
+ op->getDiscardableAttrDictionary().getValue(),
+ op->getSuccessors());
+ state.propertiesAttr = op->getPropertiesAsAttribute();
+ Operation *expandedOp = rewriter.create(state);
SmallVector<Value> newResults(expandedOp->getResults());
for (auto [res, oldType, newType] : llvm::zip_equal(
MutableArrayRef{newResults}, op->getResultTypes(), resultTypes)) {
diff --git a/mlir/lib/Dialect/Arith/Transforms/IntRangeOptimizations.cpp b/mlir/lib/Dialect/Arith/Transforms/IntRangeOptimizations.cpp
index 298c0dc2f3bda..8b66ba6855b68 100644
--- a/mlir/lib/Dialect/Arith/Transforms/IntRangeOptimizations.cpp
+++ b/mlir/lib/Dialect/Arith/Transforms/IntRangeOptimizations.cpp
@@ -542,7 +542,7 @@ struct NarrowLoopBounds final : OpInterfaceRewritePattern<LoopLikeOpInterface> {
LogicalResult matchAndRewrite(LoopLikeOpInterface loopLike,
PatternRewriter &rewriter) const override {
// Skip ops where bounds narrowing previously failed.
- if (loopLike->hasAttr(boundsNarrowingFailedAttr))
+ if (loopLike->hasDiscardableAttr(boundsNarrowingFailedAttr))
return rewriter.notifyMatchFailure(loopLike,
"bounds narrowing previously failed");
@@ -669,7 +669,8 @@ struct NarrowLoopBounds final : OpInterfaceRewritePattern<LoopLikeOpInterface> {
failed(loopLike.setLoopSteps(newSteps))) {
// Mark op to prevent future attempts. IR was modified (attribute
// added), so we must return success() from the pattern.
- loopLike->setAttr(boundsNarrowingFailedAttr, rewriter.getUnitAttr());
+ loopLike->setDiscardableAttr(boundsNarrowingFailedAttr,
+ rewriter.getUnitAttr());
updateFailed = true;
return;
}
diff --git a/mlir/lib/Dialect/Arith/Transforms/UnsignedWhenEquivalent.cpp b/mlir/lib/Dialect/Arith/Transforms/UnsignedWhenEquivalent.cpp
index c9eaa66d6ea49..0b900b42863b5 100644
--- a/mlir/lib/Dialect/Arith/Transforms/UnsignedWhenEquivalent.cpp
+++ b/mlir/lib/Dialect/Arith/Transforms/UnsignedWhenEquivalent.cpp
@@ -92,8 +92,9 @@ struct ConvertOpToUnsigned final : OpRewritePattern<Signed> {
staticallyNonNegative(this->solver, static_cast<Operation *>(op))))
return failure();
- rw.replaceOpWithNewOp<Unsigned>(op, op->getResultTypes(), op->getOperands(),
- op->getAttrs());
+ rw.replaceOpWithNewOp<Unsigned>(
+ op, op->getResultTypes(), op->getOperands(),
+ op->getDiscardableAttrDictionary().getValue());
return success();
}
diff --git a/mlir/lib/Dialect/ArmSME/Transforms/EnableArmStreaming.cpp b/mlir/lib/Dialect/ArmSME/Transforms/EnableArmStreaming.cpp
index c5c90762eaa92..e85e62099bf40 100644
--- a/mlir/lib/Dialect/ArmSME/Transforms/EnableArmStreaming.cpp
+++ b/mlir/lib/Dialect/ArmSME/Transforms/EnableArmStreaming.cpp
@@ -122,7 +122,7 @@ struct EnableArmStreamingPass
return;
}
- if (function->getAttr(kEnableArmStreamingIgnoreAttr) ||
+ if (function->getDiscardableAttr(kEnableArmStreamingIgnoreAttr) ||
streamingMode == ArmStreamingMode::Disabled)
return;
@@ -137,8 +137,8 @@ struct EnableArmStreamingPass
// streaming-mode (see section B1.1.1, IDGNQM of spec [1]). It may be worth
// supporting this later.
if (zaMode != ArmZaMode::Disabled)
- function->setAttr((Twine("llvm.") + stringifyArmZaMode(zaMode)).str(),
- unitAttr);
+ function->setDiscardableAttr(
+ (Twine("llvm.") + stringifyArmZaMode(zaMode)).str(), unitAttr);
}
};
} // namespace
diff --git a/mlir/lib/Dialect/ArmSVE/Transforms/LegalizeVectorStorage.cpp b/mlir/lib/Dialect/ArmSVE/Transforms/LegalizeVectorStorage.cpp
index 3a409ad9ed9d6..c1af8a5c80fcf 100644
--- a/mlir/lib/Dialect/ArmSVE/Transforms/LegalizeVectorStorage.cpp
+++ b/mlir/lib/Dialect/ArmSVE/Transforms/LegalizeVectorStorage.cpp
@@ -83,7 +83,7 @@ void replaceOpWithUnrealizedConversion(PatternRewriter &rewriter, TOp op,
/// `unrealized_conversion_cast`s added by this pass.
static FailureOr<Value> getSVELegalizedMemref(Value illegalMemref) {
Operation *definingOp = illegalMemref.getDefiningOp();
- if (!definingOp || !definingOp->hasAttr(kSVELegalizerTag))
+ if (!definingOp || !definingOp->hasDiscardableAttr(kSVELegalizerTag))
return failure();
auto unrealizedConversion =
llvm::cast<UnrealizedConversionCastOp>(definingOp);
@@ -464,7 +464,7 @@ struct LegalizeVectorStorage
ConversionTarget target(getContext());
target.addDynamicallyLegalOp<UnrealizedConversionCastOp>(
[](UnrealizedConversionCastOp unrealizedConversion) {
- return !unrealizedConversion->hasAttr(kSVELegalizerTag);
+ return !unrealizedConversion->hasDiscardableAttr(kSVELegalizerTag);
});
// This detects if we failed to completely legalize the IR.
if (failed(applyPartialConversion(getOperation(), target, {})))
diff --git a/mlir/lib/Dialect/Async/IR/Async.cpp b/mlir/lib/Dialect/Async/IR/Async.cpp
index c11400c061584..4d533e1579480 100644
--- a/mlir/lib/Dialect/Async/IR/Async.cpp
+++ b/mlir/lib/Dialect/Async/IR/Async.cpp
@@ -127,8 +127,9 @@ void ExecuteOp::print(OpAsmPrinter &p) {
// -> (!async.value<!return.type>, ...)
p.printOptionalArrowTypeList(llvm::drop_begin(getResultTypes()));
- p.printOptionalAttrDictWithKeyword((*this)->getAttrs(),
- {kOperandSegmentSizesAttr});
+ p.printOptionalAttrDictWithKeyword(
+ (*this)->getDiscardableAttrDictionary().getValue(),
+ {kOperandSegmentSizesAttr});
p << ' ';
p.printRegion(getBodyRegion(), /*printEntryBlockArgs=*/false);
}
@@ -367,7 +368,7 @@ LogicalResult FuncOp::verify() {
LogicalResult CallOp::verifySymbolUses(SymbolTableCollection &symbolTable) {
// Check that the callee attribute was specified.
- auto fnAttr = (*this)->getAttrOfType<FlatSymbolRefAttr>("callee");
+ auto fnAttr = getCalleeAttr();
if (!fnAttr)
return emitOpError("requires a 'callee' symbol reference attribute");
FuncOp fn = symbolTable.lookupNearestSymbolFrom<FuncOp>(*this, fnAttr);
diff --git a/mlir/lib/Dialect/Async/Transforms/AsyncToAsyncRuntime.cpp b/mlir/lib/Dialect/Async/Transforms/AsyncToAsyncRuntime.cpp
index f4d37bd0e8f34..401851dd594de 100644
--- a/mlir/lib/Dialect/Async/Transforms/AsyncToAsyncRuntime.cpp
+++ b/mlir/lib/Dialect/Async/Transforms/AsyncToAsyncRuntime.cpp
@@ -244,8 +244,9 @@ static CoroMachinery setupCoroMachinery(func::FuncOp func) {
// The switch-resumed API based coroutine should be marked with
// presplitcoroutine attribute to mark the function as a coroutine.
- func->setAttr("llvm.passthrough", builder.getArrayAttr(StringAttr::get(
- ctx, "presplitcoroutine")));
+ func->setDiscardableAttr(
+ "llvm.passthrough",
+ builder.getArrayAttr(StringAttr::get(ctx, "presplitcoroutine")));
CoroMachinery machinery;
machinery.func = func;
@@ -475,9 +476,11 @@ class AsyncFuncOpLowering : public OpConversionPattern<async::FuncOp> {
SymbolTable::setSymbolVisibility(newFuncOp,
SymbolTable::getSymbolVisibility(op));
// Copy over all attributes other than the name.
- for (const auto &namedAttr : op->getAttrs()) {
+ for (const auto &namedAttr :
+ op->getDiscardableAttrDictionary().getValue()) {
if (namedAttr.getName() != SymbolTable::getSymbolAttrName())
- newFuncOp->setAttr(namedAttr.getName(), namedAttr.getValue());
+ newFuncOp->setDiscardableAttr(namedAttr.getName(),
+ namedAttr.getValue());
}
rewriter.inlineRegionBefore(op.getBody(), newFuncOp.getBody(),
diff --git a/mlir/lib/Dialect/Bufferization/IR/BufferizationOps.cpp b/mlir/lib/Dialect/Bufferization/IR/BufferizationOps.cpp
index 9b9e631e7cebd..84c44fb89afd8 100644
--- a/mlir/lib/Dialect/Bufferization/IR/BufferizationOps.cpp
+++ b/mlir/lib/Dialect/Bufferization/IR/BufferizationOps.cpp
@@ -328,8 +328,11 @@ void AllocTensorOp::print(OpAsmPrinter &p) {
p << " copy(" << getCopy() << ")";
if (getSizeHint())
p << " size_hint=" << getSizeHint();
- p.printOptionalAttrDict((*this)->getAttrs(), /*elidedAttrs=*/{
- AllocTensorOp::getOperandSegmentSizeAttr()});
+ NamedAttrList attrs((*this)->getDiscardableAttrDictionary());
+ if (Attribute memorySpace = getMemorySpaceAttr())
+ attrs.append(getMemorySpaceAttrName(), memorySpace);
+ p.printOptionalAttrDict(
+ attrs, /*elidedAttrs=*/{AllocTensorOp::getOperandSegmentSizeAttr()});
p << " : ";
auto type = getResult().getType();
if (auto validType = llvm::dyn_cast<::mlir::TensorType>(type))
diff --git a/mlir/lib/Dialect/Bufferization/Transforms/FuncBufferizableOpInterfaceImpl.cpp b/mlir/lib/Dialect/Bufferization/Transforms/FuncBufferizableOpInterfaceImpl.cpp
index 8ca968367b026..73d3312021d87 100644
--- a/mlir/lib/Dialect/Bufferization/Transforms/FuncBufferizableOpInterfaceImpl.cpp
+++ b/mlir/lib/Dialect/Bufferization/Transforms/FuncBufferizableOpInterfaceImpl.cpp
@@ -332,10 +332,12 @@ struct CallOpInterface
}
// 3. Create the new CallOp.
- Operation *newCallOp =
+ func::CallOp newCallOp =
func::CallOp::create(rewriter, callOp.getLoc(), funcOp.getSymName(),
resultTypes, newOperands);
- newCallOp->setAttrs(callOp->getAttrs());
+ newCallOp.setArgAttrsAttr(callOp.getArgAttrsAttr());
+ newCallOp.setResAttrsAttr(callOp.getResAttrsAttr());
+ newCallOp->setDiscardableAttrs(callOp->getDiscardableAttrDictionary());
// 4. Replace the old op with the new op.
replaceOpWithBufferizedValues(rewriter, callOp, newCallOp->getResults());
diff --git a/mlir/lib/Dialect/Bufferization/Transforms/OneShotAnalysis.cpp b/mlir/lib/Dialect/Bufferization/Transforms/OneShotAnalysis.cpp
index 57ef3b88b291c..937a765d49ad8 100644
--- a/mlir/lib/Dialect/Bufferization/Transforms/OneShotAnalysis.cpp
+++ b/mlir/lib/Dialect/Bufferization/Transforms/OneShotAnalysis.cpp
@@ -89,7 +89,7 @@ constexpr StringLiteral kBbArgAliasSetAttrName = "__bbarg_alias_set_attr__";
static void setInPlaceOpOperand(OpOperand &opOperand, bool inPlace) {
Operation *op = opOperand.getOwner();
SmallVector<StringRef> inPlaceVector;
- if (auto attr = op->getAttr(kInPlaceOperandsAttrName)) {
+ if (auto attr = op->getDiscardableAttr(kInPlaceOperandsAttrName)) {
inPlaceVector = SmallVector<StringRef>(llvm::to_vector<4>(
cast<ArrayAttr>(attr).getAsValueRange<StringAttr>()));
// The existing attribute may have fewer entries than the current operand
@@ -104,8 +104,8 @@ static void setInPlaceOpOperand(OpOperand &opOperand, bool inPlace) {
inPlaceVector[opOperand.getOperandNumber()] = "false";
}
inPlaceVector[opOperand.getOperandNumber()] = inPlace ? "true" : "false";
- op->setAttr(kInPlaceOperandsAttrName,
- OpBuilder(op).getStrArrayAttr(inPlaceVector));
+ op->setDiscardableAttr(kInPlaceOperandsAttrName,
+ OpBuilder(op).getStrArrayAttr(inPlaceVector));
}
//===----------------------------------------------------------------------===//
@@ -446,21 +446,23 @@ static void annotateConflict(OpOperand *uRead, OpOperand *uConflictingWrite,
id +
"[CONFL-WRITE: " + std::to_string(uConflictingWrite->getOperandNumber()) +
"]";
- conflictingWritingOp->setAttr(conflictingWriteAttr, b.getUnitAttr());
+ conflictingWritingOp->setDiscardableAttr(conflictingWriteAttr,
+ b.getUnitAttr());
std::string readAttr =
id + "[READ: " + std::to_string(uRead->getOperandNumber()) + "]";
- readingOp->setAttr(readAttr, b.getUnitAttr());
+ readingOp->setDiscardableAttr(readAttr, b.getUnitAttr());
if (auto opResult = dyn_cast<OpResult>(definition)) {
std::string defAttr =
id + "[DEF: result " + std::to_string(opResult.getResultNumber()) + "]";
- opResult.getDefiningOp()->setAttr(defAttr, b.getUnitAttr());
+ opResult.getDefiningOp()->setDiscardableAttr(defAttr, b.getUnitAttr());
} else {
auto bbArg = cast<BlockArgument>(definition);
std::string defAttr =
id + "[DEF: bbArg " + std::to_string(bbArg.getArgNumber()) + "]";
- bbArg.getOwner()->getParentOp()->setAttr(defAttr, b.getUnitAttr());
+ bbArg.getOwner()->getParentOp()->setDiscardableAttr(defAttr,
+ b.getUnitAttr());
}
}
@@ -908,12 +910,12 @@ static void annotateNonWritableTensor(Value value) {
if (auto opResult = dyn_cast<OpResult>(value)) {
std::string attr = id + "[NOT-WRITABLE: result " +
std::to_string(opResult.getResultNumber()) + "]";
- opResult.getDefiningOp()->setAttr(attr, b.getUnitAttr());
+ opResult.getDefiningOp()->setDiscardableAttr(attr, b.getUnitAttr());
} else {
auto bbArg = cast<BlockArgument>(value);
std::string attr = id + "[NOT-WRITABLE: bbArg " +
std::to_string(bbArg.getArgNumber()) + "]";
- bbArg.getOwner()->getParentOp()->setAttr(attr, b.getUnitAttr());
+ bbArg.getOwner()->getParentOp()->setDiscardableAttr(attr, b.getUnitAttr());
}
}
@@ -1299,7 +1301,8 @@ static void annotateOpsWithAliasSets(Operation *op,
}
}
if (!opResultAliasSets.empty())
- op->setAttr(kOpResultAliasSetAttrName, b.getArrayAttr(opResultAliasSets));
+ op->setDiscardableAttr(kOpResultAliasSetAttrName,
+ b.getArrayAttr(opResultAliasSets));
// Build alias set array for every BlockArgument.
SmallVector<Attribute> regionAliasSets;
@@ -1319,7 +1322,8 @@ static void annotateOpsWithAliasSets(Operation *op,
regionAliasSets.push_back(b.getArrayAttr(blockAliasSets));
}
if (hasTensorBbArg)
- op->setAttr(kBbArgAliasSetAttrName, b.getArrayAttr(regionAliasSets));
+ op->setDiscardableAttr(kBbArgAliasSetAttrName,
+ b.getArrayAttr(regionAliasSets));
});
}
diff --git a/mlir/lib/Dialect/Bufferization/Transforms/OneShotModuleBufferize.cpp b/mlir/lib/Dialect/Bufferization/Transforms/OneShotModuleBufferize.cpp
index 4d044bbb74df1..ed8c3f919488c 100644
--- a/mlir/lib/Dialect/Bufferization/Transforms/OneShotModuleBufferize.cpp
+++ b/mlir/lib/Dialect/Bufferization/Transforms/OneShotModuleBufferize.cpp
@@ -99,8 +99,8 @@ static void annotateEquivalentReturnBbArg(OpOperand &returnVal,
Operation *op = returnVal.getOwner();
SmallVector<int64_t> equivBbArgs;
- if (op->hasAttr(kEquivalentArgsAttr)) {
- auto attr = cast<ArrayAttr>(op->getAttr(kEquivalentArgsAttr));
+ if (op->hasDiscardableAttr(kEquivalentArgsAttr)) {
+ auto attr = cast<ArrayAttr>(op->getDiscardableAttr(kEquivalentArgsAttr));
equivBbArgs = llvm::map_to_vector<4>(attr, [](Attribute a) {
return cast<IntegerAttr>(a).getValue().getSExtValue();
});
@@ -110,7 +110,7 @@ static void annotateEquivalentReturnBbArg(OpOperand &returnVal,
equivBbArgs[returnVal.getOperandNumber()] = bbArg.getArgNumber();
OpBuilder b(op->getContext());
- op->setAttr(kEquivalentArgsAttr, b.getI64ArrayAttr(equivBbArgs));
+ op->setDiscardableAttr(kEquivalentArgsAttr, b.getI64ArrayAttr(equivBbArgs));
}
/// Store function BlockArguments that are equivalent to/aliasing a returned
diff --git a/mlir/lib/Dialect/Bufferization/Transforms/OwnershipBasedBufferDeallocation.cpp b/mlir/lib/Dialect/Bufferization/Transforms/OwnershipBasedBufferDeallocation.cpp
index 7b8340e363e39..d7aba40313a47 100644
--- a/mlir/lib/Dialect/Bufferization/Transforms/OwnershipBasedBufferDeallocation.cpp
+++ b/mlir/lib/Dialect/Bufferization/Transforms/OwnershipBasedBufferDeallocation.cpp
@@ -674,10 +674,10 @@ Operation *BufferDeallocation::appendOpResults(Operation *op,
SmallVector<Value> oldResults(op->getResults());
newTypes.append(types.begin(), types.end());
- auto *newOp = Operation::create(op->getLoc(), op->getName(), newTypes,
- op->getOperands(), op->getAttrDictionary(),
- op->getPropertiesStorage(),
- op->getSuccessors(), op->getNumRegions());
+ auto *newOp = Operation::create(
+ op->getLoc(), op->getName(), newTypes, op->getOperands(),
+ op->getDiscardableAttrDictionary(), op->getPropertiesStorage(),
+ op->getSuccessors(), op->getNumRegions());
for (auto [oldRegion, newRegion] :
llvm::zip(op->getRegions(), newOp->getRegions()))
newRegion.takeBody(oldRegion);
@@ -875,7 +875,7 @@ BufferDeallocation::handleInterface(MemoryEffectOpInterface op) {
// usually forbidden in the input IR (not supported by the buffer
// deallocation pass). However, if they are under manual deallocation,
// they can be safely ignored by the buffer deallocation pass.
- if (!op->hasAttr(BufferizationDialect::kManualDeallocation))
+ if (!op->hasDiscardableAttr(BufferizationDialect::kManualDeallocation))
return op->emitError(
"memory free side-effect on MemRef value not supported!");
@@ -913,7 +913,7 @@ BufferDeallocation::handleInterface(MemoryEffectOpInterface op) {
continue;
}
- if (op->hasAttr(BufferizationDialect::kManualDeallocation)) {
+ if (op->hasDiscardableAttr(BufferizationDialect::kManualDeallocation)) {
// This allocation will be deallocated manually. Assign an ownership of
// "false", so that it will never be deallocated by the buffer
// deallocation pass.
diff --git a/mlir/lib/Dialect/DLTI/DLTI.cpp b/mlir/lib/Dialect/DLTI/DLTI.cpp
index da572f123fdc1..d6adf8f21aded 100644
--- a/mlir/lib/Dialect/DLTI/DLTI.cpp
+++ b/mlir/lib/Dialect/DLTI/DLTI.cpp
@@ -525,7 +525,7 @@ getClosestQueryable(Operation *op) {
// Search op and its ancestors for the first attached DLTIQueryInterface attr.
do {
- for (NamedAttribute attr : op->getAttrs())
+ for (NamedAttribute attr : op->getDiscardableAttrDictionary().getValue())
if ((queryable = dyn_cast<DLTIQueryInterface>(attr.getValue())))
break;
} while (!queryable && (op = op->getParentOp()));
diff --git a/mlir/lib/Dialect/DLTI/Traits.cpp b/mlir/lib/Dialect/DLTI/Traits.cpp
index 3f6dd2900a915..400ff40c3d368 100644
--- a/mlir/lib/Dialect/DLTI/Traits.cpp
+++ b/mlir/lib/Dialect/DLTI/Traits.cpp
@@ -24,11 +24,11 @@ LogicalResult mlir::impl::verifyHasDefaultDLTIDataLayoutTrait(Operation *op) {
}
DataLayoutSpecInterface mlir::impl::getDataLayoutSpec(Operation *op) {
- return op->getAttrOfType<DataLayoutSpecInterface>(
+ return op->getDiscardableAttrOfType<DataLayoutSpecInterface>(
DLTIDialect::kDataLayoutAttrName);
}
TargetSystemSpecInterface mlir::impl::getTargetSystemSpec(Operation *op) {
- return op->getAttrOfType<TargetSystemSpecAttr>(
+ return op->getDiscardableAttrOfType<TargetSystemSpecAttr>(
DLTIDialect::kTargetSystemDescAttrName);
}
diff --git a/mlir/lib/Dialect/EmitC/IR/EmitC.cpp b/mlir/lib/Dialect/EmitC/IR/EmitC.cpp
index f40b6e67b30fc..4c1db1ff45306 100644
--- a/mlir/lib/Dialect/EmitC/IR/EmitC.cpp
+++ b/mlir/lib/Dialect/EmitC/IR/EmitC.cpp
@@ -717,7 +717,7 @@ void ForOp::print(OpAsmPrinter &p) {
p.printRegion(getRegion(),
/*printEntryBlockArgs=*/false,
/*printBlockTerminators=*/false);
- p.printOptionalAttrDict((*this)->getAttrs());
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue());
}
LogicalResult ForOp::verifyRegions() {
@@ -740,7 +740,7 @@ LogicalResult ForOp::verifyRegions() {
LogicalResult CallOp::verifySymbolUses(SymbolTableCollection &symbolTable) {
// Check that the callee attribute was specified.
- auto fnAttr = (*this)->getAttrOfType<FlatSymbolRefAttr>("callee");
+ auto fnAttr = getCalleeAttr();
if (!fnAttr)
return emitOpError("requires a 'callee' symbol reference attribute");
FuncOp fn = symbolTable.lookupNearestSymbolFrom<FuncOp>(*this, fnAttr);
@@ -955,7 +955,7 @@ void IfOp::print(OpAsmPrinter &p) {
/*printBlockTerminators=*/printBlockTerminators);
}
- p.printOptionalAttrDict((*this)->getAttrs());
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue());
}
/// Given the region at `index`, or the parent operation if `index` is None,
@@ -1747,7 +1747,8 @@ void DoOp::print(OpAsmPrinter &p) {
p.printRegion(getBodyRegion(), /*printEntryBlockArgs=*/false);
p << " while ";
p.printRegion(getConditionRegion());
- p.printOptionalAttrDictWithKeyword(getOperation()->getAttrs());
+ p.printOptionalAttrDictWithKeyword(
+ getOperation()->getDiscardableAttrDictionary().getValue());
}
LogicalResult emitc::DoOp::verify() {
diff --git a/mlir/lib/Dialect/EmitC/Transforms/MLGOAddReflectionMap.cpp b/mlir/lib/Dialect/EmitC/Transforms/MLGOAddReflectionMap.cpp
index 6900e0d989b92..1caf379dc5f37 100644
--- a/mlir/lib/Dialect/EmitC/Transforms/MLGOAddReflectionMap.cpp
+++ b/mlir/lib/Dialect/EmitC/Transforms/MLGOAddReflectionMap.cpp
@@ -147,7 +147,8 @@ class MLGOAddReflectionMapClass : public OpRewritePattern<ClassOp> {
std::vector<std::pair<StringRef, StringRef>> fieldNames;
classOp.walk([&](FieldOp fieldOp) {
for (const auto &attr : includedFieldAttrs) {
- auto arrayAttr = dyn_cast_if_present<ArrayAttr>(fieldOp->getAttr(attr));
+ auto arrayAttr =
+ dyn_cast_if_present<ArrayAttr>(fieldOp->getDiscardableAttr(attr));
if (!arrayAttr)
continue;
diff --git a/mlir/lib/Dialect/Func/IR/FuncOps.cpp b/mlir/lib/Dialect/Func/IR/FuncOps.cpp
index 54eb8cac737e8..2493243e24b8d 100644
--- a/mlir/lib/Dialect/Func/IR/FuncOps.cpp
+++ b/mlir/lib/Dialect/Func/IR/FuncOps.cpp
@@ -62,7 +62,7 @@ Operation *FuncDialect::materializeConstant(OpBuilder &builder, Attribute value,
LogicalResult CallOp::verifySymbolUses(SymbolTableCollection &symbolTable) {
// Check that the callee attribute was specified.
- auto fnAttr = (*this)->getAttrOfType<FlatSymbolRefAttr>("callee");
+ auto fnAttr = getCalleeAttr();
if (!fnAttr)
return emitOpError("requires a 'callee' symbol reference attribute");
FuncOp fn = symbolTable.lookupNearestSymbolFrom<FuncOp>(*this, fnAttr);
@@ -196,16 +196,16 @@ void FuncOp::print(OpAsmPrinter &p) {
void FuncOp::cloneInto(FuncOp dest, IRMapping &mapper) {
// Add the attributes of this function to dest.
llvm::MapVector<StringAttr, Attribute> newAttrMap;
- for (const auto &attr : dest->getAttrs())
+ for (const auto &attr : dest->getDiscardableAttrDictionary().getValue())
newAttrMap.insert({attr.getName(), attr.getValue()});
- for (const auto &attr : (*this)->getAttrs())
+ for (const auto &attr : (*this)->getDiscardableAttrDictionary().getValue())
newAttrMap.insert({attr.getName(), attr.getValue()});
auto newAttrs = llvm::map_to_vector(
newAttrMap, [](std::pair<StringAttr, Attribute> attrPair) {
return NamedAttribute(attrPair.first, attrPair.second);
});
- dest->setAttrs(DictionaryAttr::get(getContext(), newAttrs));
+ dest->setDiscardableAttrs(DictionaryAttr::get(getContext(), newAttrs));
// Clone the body.
getBody().cloneInto(&dest.getBody(), mapper);
diff --git a/mlir/lib/Dialect/Func/Transforms/DuplicateFunctionElimination.cpp b/mlir/lib/Dialect/Func/Transforms/DuplicateFunctionElimination.cpp
index c480e469fdcc8..d91474dd8ed91 100644
--- a/mlir/lib/Dialect/Func/Transforms/DuplicateFunctionElimination.cpp
+++ b/mlir/lib/Dialect/Func/Transforms/DuplicateFunctionElimination.cpp
@@ -31,7 +31,8 @@ struct DuplicateFuncOpEquivalenceInfo
llvm::hash_code hash = {};
func::FuncOp func = const_cast<func::FuncOp &>(cFunc);
StringAttr symNameAttrName = func.getSymNameAttrName();
- for (NamedAttribute namedAttr : cFunc->getAttrs()) {
+ for (NamedAttribute namedAttr :
+ cFunc->getDiscardableAttrDictionary().getValue()) {
StringAttr attrName = namedAttr.getName();
if (attrName == symNameAttrName)
continue;
diff --git a/mlir/lib/Dialect/GPU/IR/GPUDialect.cpp b/mlir/lib/Dialect/GPU/IR/GPUDialect.cpp
index 22c5e3c9b86ad..4250f06c6a12d 100644
--- a/mlir/lib/Dialect/GPU/IR/GPUDialect.cpp
+++ b/mlir/lib/Dialect/GPU/IR/GPUDialect.cpp
@@ -266,7 +266,7 @@ bool GPUDialect::isKernel(Operation *op) {
if (auto gpuFunc = dyn_cast<GPUFuncOp>(op))
return gpuFunc.isKernel();
return static_cast<bool>(
- op->getAttrOfType<UnitAttr>(getKernelFuncAttrName()));
+ op->getDiscardableAttrOfType<UnitAttr>(getKernelFuncAttrName()));
}
namespace {
@@ -695,7 +695,8 @@ void gpu::addAsyncDependency(Operation *op, Value token) {
return;
auto attrName =
OpTrait::AttrSizedOperandSegments<void>::getOperandSegmentSizeAttr();
- auto sizeAttr = op->template getAttrOfType<DenseI32ArrayAttr>(attrName);
+ auto sizeAttr = dyn_cast_or_null<DenseI32ArrayAttr>(
+ op->getInherentAttr(attrName).value_or(Attribute{}));
// Async dependencies is the only variadic operand.
if (!sizeAttr)
@@ -703,7 +704,8 @@ void gpu::addAsyncDependency(Operation *op, Value token) {
SmallVector<int32_t, 8> sizes(sizeAttr.asArrayRef());
++sizes.front();
- op->setAttr(attrName, Builder(op->getContext()).getDenseI32ArrayAttr(sizes));
+ op->setInherentAttr(StringAttr::get(op->getContext(), attrName),
+ Builder(op->getContext()).getDenseI32ArrayAttr(sizes));
}
//===----------------------------------------------------------------------===//
@@ -961,11 +963,11 @@ void LaunchOp::print(OpAsmPrinter &p) {
p << ' ';
p.printRegion(getBody(), /*printEntryBlockArgs=*/false);
- p.printOptionalAttrDict((*this)->getAttrs(), /*elidedAttrs=*/{
- LaunchOp::getOperandSegmentSizeAttr(),
- getWorkgroupAttributionsAttrName(),
- getCooperativeAttrName(), moduleAttrName,
- functionAttrName});
+ p.printOptionalAttrDict(
+ (*this)->getDiscardableAttrDictionary().getValue(), /*elidedAttrs=*/{
+ LaunchOp::getOperandSegmentSizeAttr(),
+ getWorkgroupAttributionsAttrName(), getCooperativeAttrName(),
+ moduleAttrName, functionAttrName});
}
// Parse the size assignment blocks for blocks and threads. These have the form
@@ -1346,7 +1348,7 @@ LogicalResult LaunchFuncOp::verify() {
if (!module)
return emitOpError("expected to belong to a module");
- if (!module->getAttrOfType<UnitAttr>(
+ if (!module->getDiscardableAttrOfType<UnitAttr>(
GPUDialect::getContainerModuleAttrName()))
return emitOpError("expected the closest surrounding module to have the '" +
GPUDialect::getContainerModuleAttrName() +
@@ -1378,8 +1380,7 @@ LaunchFuncOp::verifySymbolUses(SymbolTableCollection &symbolTable) {
// Ignore launch ops with missing attributes here. The errors will be
// reported by the verifiers of those ops.
- if (!launchOp->getAttrOfType<SymbolRefAttr>(
- LaunchFuncOp::getKernelAttrName(launchOp->getName())))
+ if (!launchOp.getKernelAttr())
return success();
// Check that `launch_func` refers to a well-formed GPU kernel container.
@@ -1813,7 +1814,9 @@ void GPUFuncOp::print(OpAsmPrinter &p) {
static DictionaryAttr getAttributionAttrs(GPUFuncOp op, unsigned index,
StringAttr attrName) {
- auto allAttrs = llvm::dyn_cast_or_null<ArrayAttr>(op->getAttr(attrName));
+ ArrayAttr allAttrs = attrName == op.getWorkgroupAttribAttrsAttrName()
+ ? op.getWorkgroupAttribAttrsAttr()
+ : op.getPrivateAttribAttrsAttr();
if (!allAttrs || index >= allAttrs.size())
return DictionaryAttr();
return llvm::cast<DictionaryAttr>(allAttrs[index]);
@@ -1830,7 +1833,9 @@ DictionaryAttr GPUFuncOp::getPrivateAttributionAttrs(unsigned index) {
static void setAttributionAttrs(GPUFuncOp op, unsigned index,
DictionaryAttr value, StringAttr attrName) {
MLIRContext *ctx = op.getContext();
- auto allAttrs = llvm::dyn_cast_or_null<ArrayAttr>(op->getAttr(attrName));
+ ArrayAttr allAttrs = attrName == op.getWorkgroupAttribAttrsAttrName()
+ ? op.getWorkgroupAttribAttrsAttr()
+ : op.getPrivateAttribAttrsAttr();
SmallVector<Attribute> elements;
if (allAttrs)
elements.append(allAttrs.begin(), allAttrs.end());
@@ -1841,7 +1846,10 @@ static void setAttributionAttrs(GPUFuncOp op, unsigned index,
else
elements[index] = value;
ArrayAttr newValue = ArrayAttr::get(ctx, elements);
- op->setAttr(attrName, newValue);
+ if (attrName == op.getWorkgroupAttribAttrsAttrName())
+ op.setWorkgroupAttribAttrsAttr(newValue);
+ else
+ op.setPrivateAttribAttrsAttr(newValue);
}
void GPUFuncOp::setworkgroupAttributionAttrs(unsigned index,
@@ -2027,7 +2035,7 @@ void GPUModuleOp::setTargets(ArrayRef<TargetAttrInterface> targets) {
}
LogicalResult GPUModuleOp::verify() {
- auto targets = getOperation()->getAttrOfType<ArrayAttr>("targets");
+ auto targets = getTargetsAttr();
if (!targets)
return success();
@@ -2453,8 +2461,7 @@ void WarpExecuteOnLane0Op::print(OpAsmPrinter &p) {
p << "(" << getLaneid() << ")";
SmallVector<StringRef> coreAttr = {getWarpSizeAttrName()};
- auto warpSizeAttr = getOperation()->getAttr(getWarpSizeAttrName());
- p << "[" << llvm::cast<IntegerAttr>(warpSizeAttr).getInt() << "]";
+ p << "[" << getWarpSize() << "]";
if (!getArgs().empty())
p << " args(" << getArgs() << " : " << getArgs().getTypes() << ")";
@@ -2464,7 +2471,8 @@ void WarpExecuteOnLane0Op::print(OpAsmPrinter &p) {
p.printRegion(getRegion(),
/*printEntryBlockArgs=*/true,
/*printBlockTerminators=*/!getResults().empty());
- p.printOptionalAttrDict(getOperation()->getAttrs(), coreAttr);
+ p.printOptionalAttrDict(
+ getOperation()->getDiscardableAttrDictionary().getValue(), coreAttr);
}
ParseResult WarpExecuteOnLane0Op::parse(OpAsmParser &parser,
diff --git a/mlir/lib/Dialect/GPU/IR/InferIntRangeInterfaceImpls.cpp b/mlir/lib/Dialect/GPU/IR/InferIntRangeInterfaceImpls.cpp
index 33695833b1ad8..b15deed706076 100644
--- a/mlir/lib/Dialect/GPU/IR/InferIntRangeInterfaceImpls.cpp
+++ b/mlir/lib/Dialect/GPU/IR/InferIntRangeInterfaceImpls.cpp
@@ -68,7 +68,9 @@ getKnownLaunchAttr(GPUFuncOp func, DimensionKind dims, Dimension dim) {
static std::optional<uint32_t> getKnownLaunchAttr(FunctionOpInterface func,
StringRef attrName,
Dimension dim) {
- auto bounds = func.getOperation()->getAttrOfType<DenseI32ArrayAttr>(attrName);
+ auto bounds =
+ func.getOperation()->getDiscardableAttrOfType<DenseI32ArrayAttr>(
+ attrName);
if (!bounds)
return std::nullopt;
if (bounds.size() <= static_cast<uint32_t>(dim))
diff --git a/mlir/lib/Dialect/GPU/Transforms/EliminateBarriers.cpp b/mlir/lib/Dialect/GPU/Transforms/EliminateBarriers.cpp
index 21162546fe1b2..05ede7b017031 100644
--- a/mlir/lib/Dialect/GPU/Transforms/EliminateBarriers.cpp
+++ b/mlir/lib/Dialect/GPU/Transforms/EliminateBarriers.cpp
@@ -45,7 +45,7 @@ using namespace mlir::gpu;
/// Returns `true` if the op is defines the parallel region that is subject to
/// barrier synchronization.
static bool isParallelRegionBoundary(Operation *op) {
- if (op->hasAttr("__parallel_region_boundary_for_test"))
+ if (op->hasDiscardableAttr("__parallel_region_boundary_for_test"))
return true;
return isa<GPUFuncOp, LaunchOp>(op);
diff --git a/mlir/lib/Dialect/GPU/Transforms/KernelOutlining.cpp b/mlir/lib/Dialect/GPU/Transforms/KernelOutlining.cpp
index 831ac7fb0354e..0ee3d425f66be 100644
--- a/mlir/lib/Dialect/GPU/Transforms/KernelOutlining.cpp
+++ b/mlir/lib/Dialect/GPU/Transforms/KernelOutlining.cpp
@@ -394,8 +394,9 @@ class GpuKernelOutliningPass
// If any new module was inserted in this module, annotate this module as
// a container module.
if (modified)
- getOperation()->setAttr(gpu::GPUDialect::getContainerModuleAttrName(),
- UnitAttr::get(&getContext()));
+ getOperation()->setDiscardableAttr(
+ gpu::GPUDialect::getContainerModuleAttrName(),
+ UnitAttr::get(&getContext()));
}
private:
@@ -429,7 +430,8 @@ class GpuKernelOutliningPass
// If a valid data layout spec was provided, attach it to the kernel module.
// Otherwise, the default data layout will be used.
if (dataLayoutSpec)
- kernelModule->setAttr(DLTIDialect::kDataLayoutAttrName, dataLayoutSpec);
+ kernelModule->setDiscardableAttr(DLTIDialect::kDataLayoutAttrName,
+ dataLayoutSpec);
SymbolTable symbolTable(kernelModule);
symbolTable.insert(kernelFunc);
diff --git a/mlir/lib/Dialect/GPU/Transforms/ParallelLoopMapper.cpp b/mlir/lib/Dialect/GPU/Transforms/ParallelLoopMapper.cpp
index 594c7a265667e..07b6dd482f172 100644
--- a/mlir/lib/Dialect/GPU/Transforms/ParallelLoopMapper.cpp
+++ b/mlir/lib/Dialect/GPU/Transforms/ParallelLoopMapper.cpp
@@ -44,8 +44,9 @@ gpu::setMappingAttr(ParallelOp ploopOp,
specifiedMappings.insert(processor);
}
ArrayRef<Attribute> mappingAsAttrs(mapping.data(), mapping.size());
- ploopOp->setAttr(getMappingAttrName(),
- ArrayAttr::get(ploopOp.getContext(), mappingAsAttrs));
+ ploopOp->setDiscardableAttr(
+ getMappingAttrName(),
+ ArrayAttr::get(ploopOp.getContext(), mappingAsAttrs));
return success();
}
@@ -126,7 +127,7 @@ static void
mapParallelOp(ParallelOp parallelOp, MappingLevel mappingLevel = MapGrid,
MappingPolicy mappingPolicy = MappingPolicy::OutermostFirst) {
// Do not try to add a mapping to already mapped loops or nested loops.
- if (parallelOp->getAttr(getMappingAttrName()) ||
+ if (parallelOp->getDiscardableAttr(getMappingAttrName()) ||
((mappingLevel == MapGrid) && parallelOp->getParentOfType<ParallelOp>()))
return;
diff --git a/mlir/lib/Dialect/IRDL/IRDLLoading.cpp b/mlir/lib/Dialect/IRDL/IRDLLoading.cpp
index 54c7d17a97b50..b9652a3c85cfa 100644
--- a/mlir/lib/Dialect/IRDL/IRDLLoading.cpp
+++ b/mlir/lib/Dialect/IRDL/IRDLLoading.cpp
@@ -54,7 +54,7 @@ LogicalResult getSegmentSizesFromAttr(Operation *op, StringRef elemName,
ArrayRef<Variadicity> variadicities,
SmallVectorImpl<int> &segmentSizes) {
// Get the segment sizes attribute, and check that it is of the right type.
- Attribute segmentSizesAttr = op->getAttr(attrName);
+ Attribute segmentSizesAttr = op->getDiscardableAttr(attrName);
if (!segmentSizesAttr) {
return op->emitError() << "'" << attrName
<< "' attribute is expected but not provided";
@@ -209,7 +209,7 @@ static LogicalResult irdlOpVerifier(
/// Сheck that we have all needed attributes passed
/// and they satisfy the constraints.
- DictionaryAttr actualAttrs = op->getAttrDictionary();
+ DictionaryAttr actualAttrs = op->getDiscardableAttrDictionary();
for (auto [name, constraint] : attributeConstrs) {
/// First, check if the attribute actually passed.
diff --git a/mlir/lib/Dialect/LLVMIR/IR/LLVMAttrs.cpp b/mlir/lib/Dialect/LLVMIR/IR/LLVMAttrs.cpp
index b3a7d2e46030d..2bf6bbd74755f 100644
--- a/mlir/lib/Dialect/LLVMIR/IR/LLVMAttrs.cpp
+++ b/mlir/lib/Dialect/LLVMIR/IR/LLVMAttrs.cpp
@@ -503,8 +503,8 @@ TargetFeaturesAttr TargetFeaturesAttr::featuresAt(Operation *op) {
auto parentFunction = op->getParentOfType<FunctionOpInterface>();
if (!parentFunction)
return {};
- return parentFunction.getOperation()->getAttrOfType<TargetFeaturesAttr>(
- getAttributeName());
+ return parentFunction.getOperation()
+ ->getDiscardableAttrOfType<TargetFeaturesAttr>(getAttributeName());
}
FailureOr<Attribute> TargetFeaturesAttr::query(DataLayoutEntryKey key) {
diff --git a/mlir/lib/Dialect/LLVMIR/IR/LLVMDialect.cpp b/mlir/lib/Dialect/LLVMIR/IR/LLVMDialect.cpp
index 374ad4a9dcb83..1c724d16a19a9 100644
--- a/mlir/lib/Dialect/LLVMIR/IR/LLVMDialect.cpp
+++ b/mlir/lib/Dialect/LLVMIR/IR/LLVMDialect.cpp
@@ -50,6 +50,15 @@ using mlir::LLVM::tailcallkind::getMaxEnumValForTailCallKind;
static constexpr const char kElemTypeAttrName[] = "elem_type";
+static NamedAttrList getAttrsForPrinting(Operation *op) {
+ NamedAttrList attrs(op->getRawDictionaryAttrs());
+ NamedAttrList inherentAttrs;
+ op->getName().populateInherentAttrs(op, inherentAttrs);
+ for (NamedAttribute attr : inherentAttrs)
+ attrs.set(attr.getName(), attr.getValue());
+ return NamedAttrList(attrs.getDictionary(op->getContext()));
+}
+
static auto processFMFAttr(ArrayRef<NamedAttribute> attrs) {
SmallVector<NamedAttribute, 8> filteredAttrs(
llvm::make_filter_range(attrs, [&](NamedAttribute attr) {
@@ -278,14 +287,15 @@ static std::optional<ParseResult> parseOpBundles(
void ICmpOp::print(OpAsmPrinter &p) {
p << " \"" << stringifyICmpPredicate(getPredicate()) << "\" " << getOperand(0)
<< ", " << getOperand(1);
- p.printOptionalAttrDict((*this)->getAttrs(), {"predicate"});
+ p.printOptionalAttrDict(getAttrsForPrinting(*this).getAttrs(), {"predicate"});
p << " : " << getLhs().getType();
}
void FCmpOp::print(OpAsmPrinter &p) {
p << " \"" << stringifyFCmpPredicate(getPredicate()) << "\" " << getOperand(0)
<< ", " << getOperand(1);
- p.printOptionalAttrDict(processFMFAttr((*this)->getAttrs()), {"predicate"});
+ p.printOptionalAttrDict(processFMFAttr(getAttrsForPrinting(*this).getAttrs()),
+ {"predicate"});
p << " : " << getLhs().getType();
}
@@ -397,13 +407,10 @@ void AllocaOp::print(OpAsmPrinter &p) {
p << " inalloca";
p << ' ' << getArraySize() << " x " << getElemType();
+ NamedAttrList attrs((*this)->getDiscardableAttrDictionary().getValue());
if (getAlignment() && *getAlignment() != 0)
- p.printOptionalAttrDict((*this)->getAttrs(),
- {kElemTypeAttrName, getInallocaAttrName()});
- else
- p.printOptionalAttrDict(
- (*this)->getAttrs(),
- {getAlignmentAttrName(), kElemTypeAttrName, getInallocaAttrName()});
+ attrs.append(getAlignmentAttrName(), getAlignmentAttr());
+ p.printOptionalAttrDict(attrs);
p << " : " << funcTy;
}
@@ -1379,7 +1386,7 @@ void CallOp::print(OpAsmPrinter &p) {
getOpBundleOperands().getTypes(), getOpBundleTags());
}
- p.printOptionalAttrDict(processFMFAttr((*this)->getAttrs()),
+ p.printOptionalAttrDict(processFMFAttr(getAttrsForPrinting(*this).getAttrs()),
{getCalleeAttrName(), getTailCallKindAttrName(),
getVarCalleeTypeAttrName(), getCConvAttrName(),
getOperandSegmentSizesAttrName(),
@@ -1707,7 +1714,7 @@ void InvokeOp::print(OpAsmPrinter &p) {
getOpBundleOperands().getTypes(), getOpBundleTags());
}
- p.printOptionalAttrDict((*this)->getAttrs(),
+ p.printOptionalAttrDict(getAttrsForPrinting(*this).getAttrs(),
{getCalleeAttrName(), getOperandSegmentSizeAttr(),
getCConvAttrName(), getVarCalleeTypeAttrName(),
getOpBundleSizesAttrName(),
@@ -1887,7 +1894,7 @@ void LandingpadOp::print(OpAsmPrinter &p) {
<< value.getType() << ") ";
}
- p.printOptionalAttrDict((*this)->getAttrs(), {"cleanup"});
+ p.printOptionalAttrDict(getAttrsForPrinting(*this).getAttrs(), {"cleanup"});
p << ": " << getType();
}
@@ -2480,7 +2487,7 @@ void GlobalOp::print(OpAsmPrinter &p) {
// Note that the alignment attribute is printed using the
// default syntax here, even though it is an inherent attribute
// (as defined in https://mlir.llvm.org/docs/LangRef/#attributes)
- p.printOptionalAttrDict((*this)->getAttrs(),
+ p.printOptionalAttrDict(getAttrsForPrinting(*this).getAttrs(),
{SymbolTable::getSymbolAttrName(),
getGlobalTypeAttrName(), getConstantAttrName(),
getValueAttrName(), getLinkageAttrName(),
@@ -2841,7 +2848,7 @@ void AliasOp::print(OpAsmPrinter &p) {
printCommonGlobalAndAlias<AliasOp>(p, *this);
p.printSymbolName(getSymName());
- p.printOptionalAttrDict((*this)->getAttrs(),
+ p.printOptionalAttrDict(getAttrsForPrinting(*this).getAttrs(),
{SymbolTable::getSymbolAttrName(),
getAliasTypeAttrName(), getLinkageAttrName(),
getUnnamedAddrAttrName(), getTlsModeAttrName(),
@@ -4204,7 +4211,7 @@ void CallIntrinsicOp::print(OpAsmPrinter &p) {
getOpBundleOperands().getTypes(), getOpBundleTagsAttr());
}
- p.printOptionalAttrDict(processFMFAttr((*this)->getAttrs()),
+ p.printOptionalAttrDict(processFMFAttr(getAttrsForPrinting(*this).getAttrs()),
{getOperandSegmentSizesAttrName(),
getOpBundleSizesAttrName(), getIntrinAttrName(),
getOpBundleTagsAttrName(), getArgAttrsAttrName(),
diff --git a/mlir/lib/Dialect/LLVMIR/IR/NVVMDialect.cpp b/mlir/lib/Dialect/LLVMIR/IR/NVVMDialect.cpp
index 3cb03e297d03c..2786bdf8c9464 100644
--- a/mlir/lib/Dialect/LLVMIR/IR/NVVMDialect.cpp
+++ b/mlir/lib/Dialect/LLVMIR/IR/NVVMDialect.cpp
@@ -810,7 +810,9 @@ void MmaOp::print(OpAsmPrinter &p) {
printMmaOperand(frag);
}
- p.printOptionalAttrDict(this->getOperation()->getAttrs(), ignoreAttrNames);
+ NamedAttrList attrs((*this)->getDiscardableAttrDictionary().getValue());
+ (*this)->getName().populateInherentAttrs(*this, attrs);
+ p.printOptionalAttrDict(attrs, ignoreAttrNames);
// Print the types of the operands and result.
p << " : " << "(";
@@ -1275,7 +1277,9 @@ void MmaSpOp::print(OpAsmPrinter &p) {
for (const auto &frag : frags)
printMmaSpOperand(frag);
- p.printOptionalAttrDict((*this)->getAttrs(), ignoreAttrNames);
+ NamedAttrList attrs((*this)->getDiscardableAttrDictionary().getValue());
+ (*this)->getName().populateInherentAttrs(*this, attrs);
+ p.printOptionalAttrDict(attrs, ignoreAttrNames);
p << " : ";
p << "(";
for (int i = 0; i < 3; ++i) {
@@ -1840,7 +1844,9 @@ void MmaBlockScaleOp::print(OpAsmPrinter &p) {
printOperandList(p, "scaleB",
{getScaleBData(), getByteIdB(), getThreadIdB()});
- p.printOptionalAttrDict(this->getOperation()->getAttrs(), ignoreAttrNames);
+ NamedAttrList attrs((*this)->getDiscardableAttrDictionary().getValue());
+ (*this)->getName().populateInherentAttrs(*this, attrs);
+ p.printOptionalAttrDict(attrs, ignoreAttrNames);
// Print type signature
p << " : (";
@@ -2071,7 +2077,9 @@ void MmaSpBlockScaleOp::print(OpAsmPrinter &p) {
printOperandList(p, "scaleB",
{getScaleBData(), getByteIdB(), getThreadIdB()});
- p.printOptionalAttrDict(this->getOperation()->getAttrs(), ignoreAttrNames);
+ NamedAttrList attrs((*this)->getDiscardableAttrDictionary().getValue());
+ (*this)->getName().populateInherentAttrs(*this, attrs);
+ p.printOptionalAttrDict(attrs, ignoreAttrNames);
// Print type signature
p << " : (";
@@ -5324,12 +5332,13 @@ LogicalResult Tcgen05StOp::verify() {
/// Infer the result ranges for the NVVM SpecialRangeableRegisterOp that might
/// have ConstantRangeAttr.
-static void nvvmInferResultRanges(Operation *op, Value result,
+static void nvvmInferResultRanges(std::optional<LLVM::ConstantRangeAttr> range,
+ Value result,
ArrayRef<::mlir::ConstantIntRanges> argRanges,
SetIntRangeFn setResultRanges) {
- if (auto rangeAttr = op->getAttrOfType<LLVM::ConstantRangeAttr>("range")) {
- setResultRanges(result, {rangeAttr.getLower(), rangeAttr.getUpper(),
- rangeAttr.getLower(), rangeAttr.getUpper()});
+ if (range) {
+ setResultRanges(result, {range->getLower(), range->getUpper(),
+ range->getLower(), range->getUpper()});
} else {
setResultRanges(result, IntegerValueRange::getMaxRange(result).getValue());
}
@@ -6364,8 +6373,8 @@ LogicalResult NVVMDialect::verifyOperationAttribute(Operation *op,
}
// blocksareclusters must be used along with reqntid and cluster_dim
if (attrName == NVVMDialect::getBlocksAreClustersAttrName()) {
- if (!op->hasAttr(NVVMDialect::getReqntidAttrName()) ||
- !op->hasAttr(NVVMDialect::getClusterDimAttrName())) {
+ if (!op->hasDiscardableAttr(NVVMDialect::getReqntidAttrName()) ||
+ !op->hasDiscardableAttr(NVVMDialect::getClusterDimAttrName())) {
return op->emitError()
<< "'" << attrName << "' attribute must be used along with " << "'"
<< NVVMDialect::getReqntidAttrName() << "' and " << "'"
@@ -6384,7 +6393,7 @@ LogicalResult NVVMDialect::verifyRegionArgAttribute(Operation *op,
if (!funcOp)
return success();
- bool isKernel = op->hasAttr(NVVMDialect::getKernelFuncAttrName());
+ bool isKernel = op->hasDiscardableAttr(NVVMDialect::getKernelFuncAttrName());
StringAttr attrName = argAttr.getName();
if (attrName == NVVM::NVVMDialect::getGridConstantAttrName()) {
if (!isKernel) {
diff --git a/mlir/lib/Dialect/LLVMIR/Transforms/InlinerInterfaceImpl.cpp b/mlir/lib/Dialect/LLVMIR/Transforms/InlinerInterfaceImpl.cpp
index 657835ae54149..9409141f6e45a 100644
--- a/mlir/lib/Dialect/LLVMIR/Transforms/InlinerInterfaceImpl.cpp
+++ b/mlir/lib/Dialect/LLVMIR/Transforms/InlinerInterfaceImpl.cpp
@@ -286,7 +286,7 @@ static void createNewAliasScopesFromNoAliasParameter(
continue;
ssaCopies.insert(ssaCopy);
- if (!ssaCopy->hasAttr(LLVM::LLVMDialect::getNoAliasAttrName()))
+ if (!ssaCopy->hasDiscardableAttr(LLVM::LLVMDialect::getNoAliasAttrName()))
continue;
noAliasParams.insert(ssaCopy);
}
diff --git a/mlir/lib/Dialect/LLVMIR/Transforms/RequestCWrappers.cpp b/mlir/lib/Dialect/LLVMIR/Transforms/RequestCWrappers.cpp
index a5fccbdc368fe..10d203c470f1a 100644
--- a/mlir/lib/Dialect/LLVMIR/Transforms/RequestCWrappers.cpp
+++ b/mlir/lib/Dialect/LLVMIR/Transforms/RequestCWrappers.cpp
@@ -25,8 +25,9 @@ class RequestCWrappersPass
: public LLVM::impl::LLVMRequestCWrappersPassBase<RequestCWrappersPass> {
public:
void runOnOperation() override {
- getOperation()->setAttr(LLVM::LLVMDialect::getEmitCWrapperAttrName(),
- UnitAttr::get(&getContext()));
+ getOperation()->setDiscardableAttr(
+ LLVM::LLVMDialect::getEmitCWrapperAttrName(),
+ UnitAttr::get(&getContext()));
}
};
} // namespace
diff --git a/mlir/lib/Dialect/Linalg/IR/LinalgInterfaces.cpp b/mlir/lib/Dialect/Linalg/IR/LinalgInterfaces.cpp
index e3f4988b3ab76..d3a496b6cbb89 100644
--- a/mlir/lib/Dialect/Linalg/IR/LinalgInterfaces.cpp
+++ b/mlir/lib/Dialect/Linalg/IR/LinalgInterfaces.cpp
@@ -898,8 +898,8 @@ mlir::linalg::inferConvolutionDims(LinalgOp linalgOp) {
return inferConvolutionDimsImpl(
indexingMaps, linalgOp.getIteratorTypesArray(), inputExprWalker,
/*allowEmptyConvolvedDims=*/false,
- linalgOp->getAttrOfType<DenseIntElementsAttr>("strides"),
- linalgOp->getAttrOfType<DenseIntElementsAttr>("dilations"));
+ linalgOp->getDiscardableAttrOfType<DenseIntElementsAttr>("strides"),
+ linalgOp->getDiscardableAttrOfType<DenseIntElementsAttr>("dilations"));
}
FailureOr<ConvolutionDimensions>
@@ -1067,8 +1067,8 @@ mlir::linalg::detail::isConvolutionInterfaceImpl(
if (dimensions) {
FailureOr<ConvolutionDimensions> res = inferConvolutionDimsImpl(
indexingMaps, iteratorTypes, inputExprWalker, allowEmptyConvolvedDims,
- linalgOp->getAttrOfType<DenseIntElementsAttr>("strides"),
- linalgOp->getAttrOfType<DenseIntElementsAttr>("dilations"));
+ linalgOp->getDiscardableAttrOfType<DenseIntElementsAttr>("strides"),
+ linalgOp->getDiscardableAttrOfType<DenseIntElementsAttr>("dilations"));
assert(succeeded(res) && "unexpected failure to infer convolution dims");
*dimensions = *res;
}
diff --git a/mlir/lib/Dialect/Linalg/IR/LinalgOps.cpp b/mlir/lib/Dialect/Linalg/IR/LinalgOps.cpp
index 170e1edf8a55d..113552d68fef7 100644
--- a/mlir/lib/Dialect/Linalg/IR/LinalgOps.cpp
+++ b/mlir/lib/Dialect/Linalg/IR/LinalgOps.cpp
@@ -418,7 +418,9 @@ static void printNamedStructuredOpResults(OpAsmPrinter &p,
static void printNamedStructuredOp(OpAsmPrinter &p, Operation *op,
ValueRange inputs, ValueRange outputs,
ArrayRef<StringRef> elidedAttrs = {}) {
- p.printOptionalAttrDict(op->getAttrs(), elidedAttrs);
+ NamedAttrList attrs(op->getDiscardableAttrDictionary().getValue());
+ op->getName().populateInherentAttrs(op, attrs);
+ p.printOptionalAttrDict(attrs, elidedAttrs);
// Printing is shared with generic ops, except for the region and
// attributes.
@@ -1218,7 +1220,11 @@ void GenericOp::print(OpAsmPrinter &p) {
llvm::StringSet<> genericAttrNamesSet;
genericAttrNamesSet.insert_range(genericAttrNames);
SmallVector<NamedAttribute, 8> genericAttrs;
- for (auto attr : (*this)->getAttrs()) {
+ for (StringRef attrName : genericAttrNames) {
+ std::optional<Attribute> value = (*this)->getInherentAttr(attrName);
+ if (!value || !*value)
+ continue;
+ NamedAttribute attr{StringAttr::get(getContext(), attrName), *value};
if (attr.getName() == getIteratorTypesAttrName()) {
auto iteratorTypes =
llvm::cast<ArrayAttr>(attr.getValue())
@@ -1251,13 +1257,13 @@ void GenericOp::print(OpAsmPrinter &p) {
genericAttrNamesSet.insert(genericAttrNames.back());
bool hasExtraAttrs = false;
- for (NamedAttribute n : (*this)->getAttrs()) {
+ for (NamedAttribute n : (*this)->getDiscardableAttrDictionary().getValue()) {
if ((hasExtraAttrs = !genericAttrNamesSet.contains(n.getName().strref())))
break;
}
if (hasExtraAttrs) {
p << " attrs = ";
- p.printOptionalAttrDict((*this)->getAttrs(),
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue(),
/*elidedAttrs=*/genericAttrNames);
}
@@ -1667,8 +1673,10 @@ static bool canUseShortForm(Block *body, bool initFirst = false,
static void printShortForm(OpAsmPrinter &p, Operation *payloadOp) {
SmallVector<StringRef> elidedAttrs;
std::string attrToElide;
+ NamedAttrList attrs(payloadOp->getDiscardableAttrDictionary());
+ payloadOp->getName().populateInherentAttrs(payloadOp, attrs);
p << " { " << payloadOp->getName().getStringRef();
- for (const auto &attr : payloadOp->getAttrs()) {
+ for (const auto &attr : attrs) {
auto fastAttr =
llvm::dyn_cast<mlir::arith::FastMathFlagsAttr>(attr.getValue());
if (fastAttr && fastAttr.getValue() == mlir::arith::FastMathFlags::none) {
@@ -1677,7 +1685,7 @@ static void printShortForm(OpAsmPrinter &p, Operation *payloadOp) {
break;
}
}
- p.printOptionalAttrDict(payloadOp->getAttrs(), elidedAttrs);
+ p.printOptionalAttrDict(attrs, elidedAttrs);
p << " }";
}
@@ -1690,7 +1698,7 @@ void MapOp::print(OpAsmPrinter &p) {
}
printCommonStructuredOpParts(p, getDpsInputs(), getDpsInits());
- p.printOptionalAttrDict((*this)->getAttrs());
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue());
if (!useShortForm) {
// Print region if the payload op was not detected.
@@ -1900,7 +1908,8 @@ void ReduceOp::print(OpAsmPrinter &p) {
printCommonStructuredOpParts(p, getDpsInputs(), getDpsInits());
printDenseI64ArrayAttr(p, getDimensionsAttrName(), getDimensions());
- p.printOptionalAttrDict((*this)->getAttrs(), {getDimensionsAttrName()});
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue(),
+ {getDimensionsAttrName()});
if (!useShortForm) {
// Print region if the payload op was not detected.
p.increaseIndent();
@@ -2079,7 +2088,8 @@ void TransposeOp::getAsmResultNames(
void TransposeOp::print(OpAsmPrinter &p) {
printCommonStructuredOpParts(p, getDpsInputs(), getDpsInits());
printDenseI64ArrayAttr(p, getPermutationAttrName(), getPermutation());
- p.printOptionalAttrDict((*this)->getAttrs(), {getPermutationAttrName()});
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue(),
+ {getPermutationAttrName()});
}
LogicalResult TransposeOp::verify() {
@@ -2327,7 +2337,8 @@ void BroadcastOp::getAsmResultNames(
void BroadcastOp::print(OpAsmPrinter &p) {
printCommonStructuredOpParts(p, getDpsInputs(), getDpsInits());
printDenseI64ArrayAttr(p, getDimensionsAttrName(), getDimensions());
- p.printOptionalAttrDict((*this)->getAttrs(), {getDimensionsAttrName()});
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue(),
+ {getDimensionsAttrName()});
}
LogicalResult BroadcastOp::verify() {
@@ -2475,7 +2486,7 @@ void BroadcastOp::getCanonicalizationPatterns(RewritePatternSet &results,
void linalg::YieldOp::print(OpAsmPrinter &p) {
if (getNumOperands() > 0)
p << ' ' << getOperands();
- p.printOptionalAttrDict((*this)->getAttrs());
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue());
if (getNumOperands() > 0)
p << " : " << getOperandTypes();
}
@@ -2636,7 +2647,9 @@ std::string mlir::linalg::generateLibraryCallName(Operation *op) {
assert(isa<LinalgOp>(op));
std::string name(op->getName().getStringRef().str());
std::string fun = "";
- for (NamedAttribute kv : op->getAttrs()) {
+ NamedAttrList attrs(op->getDiscardableAttrDictionary());
+ op->getName().populateInherentAttrs(op, attrs);
+ for (NamedAttribute kv : attrs) {
if (UnaryFnAttr ufa = llvm::dyn_cast<UnaryFnAttr>(kv.getValue())) {
fun = stringifyEnum(ufa.getValue()).str() + "_";
} else if (BinaryFnAttr bfa = llvm::dyn_cast<BinaryFnAttr>(kv.getValue())) {
@@ -4211,9 +4224,9 @@ MatmulTransposeAOp::create(OpBuilder &builder, Location location,
}
bool MatmulTransposeAOp::classof(Operation *op) {
- return dyn_cast_or_null<linalg::MatmulOp>(op) &&
- MatmulTransposeAOp::isDefaultIndexingMaps(
- op->getAttr("indexing_maps"));
+ auto matmulOp = dyn_cast_or_null<linalg::MatmulOp>(op);
+ return matmulOp && MatmulTransposeAOp::isDefaultIndexingMaps(
+ matmulOp.getIndexingMapsAttr());
}
SmallVector<AffineMap>
@@ -4305,9 +4318,9 @@ MatmulTransposeBOp::create(OpBuilder &builder, Location location,
}
bool MatmulTransposeBOp::classof(Operation *op) {
- return dyn_cast_or_null<linalg::MatmulOp>(op) &&
- MatmulTransposeBOp::isDefaultIndexingMaps(
- op->getAttr("indexing_maps"));
+ auto matmulOp = dyn_cast_or_null<linalg::MatmulOp>(op);
+ return matmulOp && MatmulTransposeBOp::isDefaultIndexingMaps(
+ matmulOp.getIndexingMapsAttr());
}
SmallVector<AffineMap>
@@ -4398,9 +4411,9 @@ BatchMatmulTransposeAOp::create(OpBuilder &builder, Location location,
}
bool BatchMatmulTransposeAOp::classof(Operation *op) {
- return dyn_cast_or_null<linalg::BatchMatmulOp>(op) &&
- BatchMatmulTransposeAOp::isDefaultIndexingMaps(
- op->getAttr("indexing_maps"));
+ auto matmulOp = dyn_cast_or_null<linalg::BatchMatmulOp>(op);
+ return matmulOp && BatchMatmulTransposeAOp::isDefaultIndexingMaps(
+ matmulOp.getIndexingMapsAttr());
}
SmallVector<AffineMap>
@@ -4491,9 +4504,9 @@ BatchMatmulTransposeBOp::create(OpBuilder &builder, Location location,
}
bool BatchMatmulTransposeBOp::classof(Operation *op) {
- return dyn_cast_or_null<linalg::BatchMatmulOp>(op) &&
- BatchMatmulTransposeBOp::isDefaultIndexingMaps(
- op->getAttr("indexing_maps"));
+ auto matmulOp = dyn_cast_or_null<linalg::BatchMatmulOp>(op);
+ return matmulOp && BatchMatmulTransposeBOp::isDefaultIndexingMaps(
+ matmulOp.getIndexingMapsAttr());
}
//===----------------------------------------------------------------------===//
@@ -5547,7 +5560,7 @@ void PackOp::print(OpAsmPrinter &p) {
p << " into " << getDest();
- p.printOptionalAttrDict((*this)->getAttrs(),
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue(),
{"static_inner_tiles", "inner_dims_pos",
"outer_dims_perm", "operandSegmentSizes"});
@@ -6296,7 +6309,7 @@ void UnPackOp::print(OpAsmPrinter &p) {
p << " into " << getDest();
- p.printOptionalAttrDict((*this)->getAttrs(),
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue(),
{"static_inner_tiles", "inner_dims_pos",
"outer_dims_perm", "operandSegmentSizes"});
diff --git a/mlir/lib/Dialect/Linalg/TransformOps/LinalgTransformOps.cpp b/mlir/lib/Dialect/Linalg/TransformOps/LinalgTransformOps.cpp
index 22724e3c31121..697de8446cbd8 100644
--- a/mlir/lib/Dialect/Linalg/TransformOps/LinalgTransformOps.cpp
+++ b/mlir/lib/Dialect/Linalg/TransformOps/LinalgTransformOps.cpp
@@ -1675,9 +1675,13 @@ transform::MatchOp::apply(transform::TransformRewriter &rewriter,
if (attr.getName() == getInterfaceAttrName() ||
attr.getName() == getOpsAttrName())
continue;
- if (!op->hasAttr(attr.getName()))
+ std::optional<Attribute> inherent = op->getInherentAttr(attr.getName());
+ Attribute actual = inherent.has_value()
+ ? *inherent
+ : op->getDiscardableAttr(attr.getName());
+ if (!actual)
return;
- if (op->getAttr(attr.getName()) != attr.getValue())
+ if (actual != attr.getValue())
return;
}
}
@@ -3113,8 +3117,11 @@ void SplitOp::print(OpAsmPrinter &printer) {
else
printer << getDynamicChunkSizes();
printer << " ";
- printer.printOptionalAttrDict(getOperation()->getAttrs(),
- {getStaticChunkSizesAttrName()});
+ NamedAttrList attrs(getOperation()->getDiscardableAttrDictionary());
+ attrs.append(getDimensionAttrName(), getDimensionAttr());
+ if (UnitAttr multiway = getMultiwayAttr())
+ attrs.append(getMultiwayAttrName(), multiway);
+ printer.printOptionalAttrDict(attrs, {getStaticChunkSizesAttrName()});
printer << " : " << getTarget().getType();
if (staticChunkSize == ShapedType::kDynamic)
printer << ", " << getDynamicChunkSizes().getType();
diff --git a/mlir/lib/Dialect/Linalg/Transforms/BufferizableOpInterfaceImpl.cpp b/mlir/lib/Dialect/Linalg/Transforms/BufferizableOpInterfaceImpl.cpp
index ca5ee62e5ffeb..3d5b7cd0ee16c 100644
--- a/mlir/lib/Dialect/Linalg/Transforms/BufferizableOpInterfaceImpl.cpp
+++ b/mlir/lib/Dialect/Linalg/Transforms/BufferizableOpInterfaceImpl.cpp
@@ -75,7 +75,8 @@ static LogicalResult bufferizeDestinationStyleOpInterface(
// return anything.
assert(op->getNumRegions() == 1 && "expected that op has 1 region");
OperationState opState(op->getLoc(), op->getName(), newOperands, TypeRange{},
- op->getAttrs());
+ op->getDiscardableAttrDictionary().getValue());
+ opState.propertiesAttr = op->getPropertiesAsAttribute();
opState.addRegion();
Operation *newOp = Operation::create(opState);
newOp->getRegion(0).getBlocks().splice(newOp->getRegion(0).begin(),
@@ -225,8 +226,11 @@ struct PackOpInterface
operands.push_back(val);
llvm::append_range(operands, packOp.getInnerTiles());
- linalg::PackOp::create(rewriter, packOp.getLoc(), TypeRange{}, operands,
- op->getAttrs());
+ OperationState opState(packOp.getLoc(), packOp->getName(), operands,
+ TypeRange{},
+ op->getDiscardableAttrDictionary().getValue());
+ opState.propertiesAttr = op->getPropertiesAsAttribute();
+ rewriter.create(opState);
replaceOpWithBufferizedValues(rewriter, op, *destBuffer);
return success();
}
@@ -263,8 +267,11 @@ struct UnPackOpInterface
operands.push_back(*destBuffer);
llvm::append_range(operands, unPackOp.getInnerTiles());
- linalg::UnPackOp::create(rewriter, unPackOp.getLoc(), TypeRange{}, operands,
- op->getAttrs());
+ OperationState opState(unPackOp.getLoc(), unPackOp->getName(), operands,
+ TypeRange{},
+ op->getDiscardableAttrDictionary().getValue());
+ opState.propertiesAttr = op->getPropertiesAsAttribute();
+ rewriter.create(opState);
replaceOpWithBufferizedValues(rewriter, op, *destBuffer);
return success();
}
diff --git a/mlir/lib/Dialect/Linalg/Transforms/DropUnitDims.cpp b/mlir/lib/Dialect/Linalg/Transforms/DropUnitDims.cpp
index c3dca148b7f94..9bc6694b38d0d 100644
--- a/mlir/lib/Dialect/Linalg/Transforms/DropUnitDims.cpp
+++ b/mlir/lib/Dialect/Linalg/Transforms/DropUnitDims.cpp
@@ -986,11 +986,11 @@ struct RankReduceContractionOps : OpRewritePattern<FromOpTy> {
auto collapsedOp = ToOpTy::create(rewriter, loc, collapsedResultTy,
ValueRange{collapsedLhs, collapsedRhs},
ValueRange{collapsedInit});
- for (auto attr : contractionOp->getAttrs()) {
+ for (auto attr : contractionOp->getDiscardableAttrDictionary().getValue()) {
if (attr.getName() == LinalgDialect::kMemoizedIndexingMapsAttrName ||
attr.getName() == "indexing_maps")
continue;
- collapsedOp->setAttr(attr.getName(), attr.getValue());
+ collapsedOp->setDiscardableAttr(attr.getName(), attr.getValue());
}
auto results = contractionOp.getResults();
diff --git a/mlir/lib/Dialect/Linalg/Transforms/ElementwiseToLinalg.cpp b/mlir/lib/Dialect/Linalg/Transforms/ElementwiseToLinalg.cpp
index aea17d8de4a76..a991f51732218 100644
--- a/mlir/lib/Dialect/Linalg/Transforms/ElementwiseToLinalg.cpp
+++ b/mlir/lib/Dialect/Linalg/Transforms/ElementwiseToLinalg.cpp
@@ -142,10 +142,11 @@ struct ConvertAnyElementwiseMappableOpOnRankedTensors : public RewritePattern {
llvm::map_to_vector<6>(op->getResultTypes(), [](Type type) {
return cast<TensorType>(type).getElementType();
});
- Operation *scalarOp =
- builder.create(loc, op->getName().getIdentifier(),
- regionArgs.take_front(op->getNumOperands()),
- resultEltTys, op->getAttrs());
+ OperationState state(
+ loc, op->getName(), regionArgs.take_front(op->getNumOperands()),
+ resultEltTys, op->getDiscardableAttrDictionary().getValue());
+ state.propertiesAttr = op->getPropertiesAsAttribute();
+ Operation *scalarOp = builder.create(state);
linalg::YieldOp::create(builder, loc, scalarOp->getResults());
});
return success();
diff --git a/mlir/lib/Dialect/Linalg/Transforms/EraseUnusedOperandsAndResults.cpp b/mlir/lib/Dialect/Linalg/Transforms/EraseUnusedOperandsAndResults.cpp
index cbd63576619b6..ab73f00e9e1ac 100644
--- a/mlir/lib/Dialect/Linalg/Transforms/EraseUnusedOperandsAndResults.cpp
+++ b/mlir/lib/Dialect/Linalg/Transforms/EraseUnusedOperandsAndResults.cpp
@@ -269,9 +269,9 @@ mlir::linalg::deduplicateOperandsAndRemoveDeadResults(
});
// Copy over unknown attributes. They might be load bearing for some flow.
ArrayRef<StringRef> odsAttrs = genericOp.getAttributeNames();
- for (NamedAttribute kv : genericOp->getAttrs())
+ for (NamedAttribute kv : genericOp->getDiscardableAttrDictionary().getValue())
if (!llvm::is_contained(odsAttrs, kv.getName().getValue()))
- newOp->setAttr(kv.getName(), kv.getValue());
+ newOp->setDiscardableAttr(kv.getName(), kv.getValue());
// Fix up the payload of the canonicalized operation.
populateOpPayload(genericOp, newOp, origInsToNewInsPos, origOutsToNewOutsPos,
diff --git a/mlir/lib/Dialect/Linalg/Transforms/FoldIntoElementwise.cpp b/mlir/lib/Dialect/Linalg/Transforms/FoldIntoElementwise.cpp
index 94db259d662d4..bbc6d3968b00c 100644
--- a/mlir/lib/Dialect/Linalg/Transforms/FoldIntoElementwise.cpp
+++ b/mlir/lib/Dialect/Linalg/Transforms/FoldIntoElementwise.cpp
@@ -93,7 +93,8 @@ struct FoldIntoElementwisePattern : public OpInterfaceRewritePattern<LinalgOp> {
rewriter.modifyOpInPlace(op, [&] {
for (auto [index, operand] : llvm::enumerate(op.getDpsInputOperands()))
op->setOperand(operand->getOperandNumber(), newIns[index]);
- op->setAttr("indexing_maps", rewriter.getAffineMapArrayAttr(newMaps));
+ op->setInherentAttr(rewriter.getStringAttr("indexing_maps"),
+ rewriter.getAffineMapArrayAttr(newMaps));
});
return success();
}
diff --git a/mlir/lib/Dialect/Linalg/Transforms/SimplifyDepthwiseConv.cpp b/mlir/lib/Dialect/Linalg/Transforms/SimplifyDepthwiseConv.cpp
index c55a0bf7ef9a3..c6a305d539c10 100644
--- a/mlir/lib/Dialect/Linalg/Transforms/SimplifyDepthwiseConv.cpp
+++ b/mlir/lib/Dialect/Linalg/Transforms/SimplifyDepthwiseConv.cpp
@@ -93,7 +93,7 @@ matchAndReplaceDepthwiseConv(Operation *operation, Value input, Value kernel,
if (!newConv)
return failure();
for (auto attr : preservedAttrs)
- newConv->setAttr(attr.getName(), attr.getValue());
+ newConv->setDiscardableAttr(attr.getName(), attr.getValue());
// Expand dimensions back out to
rewriter.replaceOpWithNewOp<tensor::ExpandShapeOp>(
diff --git a/mlir/lib/Dialect/Linalg/Transforms/TilingInterfaceImpl.cpp b/mlir/lib/Dialect/Linalg/Transforms/TilingInterfaceImpl.cpp
index b00ab8a7d6ee7..43262a6dcc6ab 100644
--- a/mlir/lib/Dialect/Linalg/Transforms/TilingInterfaceImpl.cpp
+++ b/mlir/lib/Dialect/Linalg/Transforms/TilingInterfaceImpl.cpp
@@ -33,6 +33,15 @@
using namespace mlir;
using namespace mlir::linalg;
+static Operation *createWithProperties(OpBuilder &builder, Operation *op,
+ TypeRange resultTypes,
+ ValueRange operands) {
+ OperationState state(op->getLoc(), op->getName(), operands, resultTypes,
+ op->getDiscardableAttrDictionary().getValue());
+ state.propertiesAttr = op->getPropertiesAsAttribute();
+ return builder.create(state);
+}
+
//===----------------------------------------------------------------------===//
// Utility methods for implementation of Tiling Interface for Linalg ops
//===----------------------------------------------------------------------===//
@@ -1149,8 +1158,8 @@ struct PackOpTiling
for (auto tile : packOp.getInnerTiles())
tiledOperands.push_back(tile);
- Operation *tiledPackOp = PackOp::create(
- b, loc, TypeRange{outSlice.getType()}, tiledOperands, op->getAttrs());
+ Operation *tiledPackOp = createWithProperties(
+ b, op, TypeRange{outSlice.getType()}, tiledOperands);
return TilingResult{
{tiledPackOp},
@@ -1486,8 +1495,8 @@ struct PackOpTiling
for (auto tile : packOp.getInnerTiles())
tiledOperands.push_back(tile);
- Operation *tiledPackOp = PackOp::create(
- b, loc, TypeRange{outSlice.getType()}, tiledOperands, op->getAttrs());
+ Operation *tiledPackOp = createWithProperties(
+ b, op, TypeRange{outSlice.getType()}, tiledOperands);
return TilingResult{
{tiledPackOp},
@@ -1727,8 +1736,8 @@ struct UnPackOpTiling
for (auto tile : unpackOp.getInnerTiles())
tiledOperands.push_back(tile);
- Operation *tiledUnpackOp = UnPackOp::create(
- b, loc, TypeRange{sliceDest.getType()}, tiledOperands, op->getAttrs());
+ Operation *tiledUnpackOp = createWithProperties(
+ b, op, TypeRange{sliceDest.getType()}, tiledOperands);
if (isPerfectTilingCase)
return TilingResult{{tiledUnpackOp},
@@ -1986,9 +1995,8 @@ struct UnPackOpTiling
tiledOperands.push_back(tile);
// Create tiled unpack op.
- Operation *tiledUnPackOp =
- UnPackOp::create(b, loc, TypeRange{extractDestSlice.getType()},
- tiledOperands, op->getAttrs());
+ Operation *tiledUnPackOp = createWithProperties(
+ b, op, TypeRange{extractDestSlice.getType()}, tiledOperands);
return TilingResult{{tiledUnPackOp},
SmallVector<Value>(tiledUnPackOp->getResults()),
diff --git a/mlir/lib/Dialect/Linalg/Transforms/Vectorization.cpp b/mlir/lib/Dialect/Linalg/Transforms/Vectorization.cpp
index 21ca3108efcd6..f15f646bbd8b0 100644
--- a/mlir/lib/Dialect/Linalg/Transforms/Vectorization.cpp
+++ b/mlir/lib/Dialect/Linalg/Transforms/Vectorization.cpp
@@ -1442,10 +1442,11 @@ vectorizeOneOp(RewriterBase &rewriter, VectorizationState &state,
: resultType);
}
// d. Build and return the new op.
- return VectorizationHookResult{
- VectorizationHookStatus::NewOp,
- rewriter.create(op->getLoc(), op->getName().getIdentifier(), vecOperands,
- resultTypes, op->getAttrs())};
+ OperationState opState(op->getLoc(), op->getName(), vecOperands, resultTypes,
+ op->getDiscardableAttrDictionary().getValue());
+ opState.propertiesAttr = op->getPropertiesAsAttribute();
+ return VectorizationHookResult{VectorizationHookStatus::NewOp,
+ rewriter.create(opState)};
}
/// Generic vectorization function that rewrites the body of a `linalgOp` into
@@ -2733,8 +2734,8 @@ struct PadOpVectorizationWithTransferReadPattern
rewriter.modifyOpInPlace(xferOp, [&]() {
SmallVector<bool> inBounds(xferOp.getVectorType().getRank(), false);
- xferOp->setAttr(xferOp.getInBoundsAttrName(),
- rewriter.getBoolArrayAttr(inBounds));
+ xferOp->setInherentAttr(xferOp.getInBoundsAttrName(),
+ rewriter.getBoolArrayAttr(inBounds));
xferOp.getBaseMutable().assign(padOp.getSource());
xferOp.getPaddingMutable().assign(padValue);
});
@@ -3794,8 +3795,9 @@ struct Conv1DGenerator
SmallVector<bool> inBounds(maskShape.size(), true);
auto xferOp = cast<VectorTransferOpInterface>(opToMask);
- xferOp->setAttr(xferOp.getInBoundsAttrName(),
- rewriter.getBoolArrayAttr(inBounds));
+ xferOp->setInherentAttr(
+ rewriter.getStringAttr(xferOp.getInBoundsAttrName()),
+ rewriter.getBoolArrayAttr(inBounds));
SmallVector<OpFoldResult> mixedDims = vector::getMixedSizesXfer(
cast<LinalgOp>(op).hasPureTensorSemantics(), opToMask, rewriter);
diff --git a/mlir/lib/Dialect/Math/Transforms/PolynomialApproximation.cpp b/mlir/lib/Dialect/Math/Transforms/PolynomialApproximation.cpp
index 9b367e0f84cb8..9b234ea79df02 100644
--- a/mlir/lib/Dialect/Math/Transforms/PolynomialApproximation.cpp
+++ b/mlir/lib/Dialect/Math/Transforms/PolynomialApproximation.cpp
@@ -345,8 +345,8 @@ LogicalResult insertCasts(Operation *op, PatternRewriter &rewriter) {
SmallVector<Value> operands;
for (auto operand : op->getOperands())
operands.push_back(arith::ExtFOp::create(rewriter, loc, newType, operand));
- auto result =
- T::create(rewriter, loc, TypeRange{newType}, operands, op->getAttrs());
+ auto result = T::create(rewriter, loc, TypeRange{newType}, operands,
+ op->getDiscardableAttrDictionary().getValue());
rewriter.replaceOpWithNewOp<arith::TruncFOp>(op, origType, result);
return success();
}
diff --git a/mlir/lib/Dialect/MemRef/IR/MemRefOps.cpp b/mlir/lib/Dialect/MemRef/IR/MemRefOps.cpp
index 0ef57172e380c..0a93254838082 100644
--- a/mlir/lib/Dialect/MemRef/IR/MemRefOps.cpp
+++ b/mlir/lib/Dialect/MemRef/IR/MemRefOps.cpp
@@ -162,7 +162,8 @@ bubbleDownCastsPassthroughOpImpl(ConcreteOpTy op, OpBuilder &builder,
// Create the new op and results.
auto newOp = ConcreteOpTy::create(
builder, op.getLoc(), TypeRange(resTy), operands, op.getProperties(),
- llvm::to_vector_of<NamedAttribute>(op->getDiscardableAttrs()));
+ llvm::to_vector_of<NamedAttribute>(
+ op->getDiscardableAttrDictionary().getValue()));
// Insert a memory-space cast to the original memory space of the op.
MemorySpaceCastOpInterface result = castOp.cloneMemorySpaceCastOp(
@@ -377,7 +378,7 @@ void AllocaScopeOp::print(OpAsmPrinter &p) {
p.printRegion(getBodyRegion(),
/*printEntryBlockArgs=*/false,
/*printBlockTerminators=*/printBlockTerminators);
- p.printOptionalAttrDict((*this)->getAttrs());
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue());
}
ParseResult AllocaScopeOp::parse(OpAsmParser &parser, OperationState &result) {
@@ -1262,7 +1263,7 @@ void DmaStartOp::print(OpAsmPrinter &p) {
if (isStrided())
p << ", " << getStride() << ", " << getNumElementsPerStride();
- p.printOptionalAttrDict((*this)->getAttrs());
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue());
p << " : " << getSrcMemRef().getType() << ", " << getDstMemRef().getType()
<< ", " << getTagMemRef().getType();
}
@@ -1652,7 +1653,7 @@ void GenericAtomicRMWOp::print(OpAsmPrinter &p) {
p << ' ' << getMemref() << "[" << getIndices()
<< "] : " << getMemref().getType() << ' ';
p.printRegion(getRegion());
- p.printOptionalAttrDict((*this)->getAttrs());
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue());
}
TypedValue<MemRefType> GenericAtomicRMWOp::getAccessedMemref() {
@@ -1926,7 +1927,7 @@ void PrefetchOp::print(OpAsmPrinter &p) {
p << ", locality<" << getLocalityHint();
p << ">, " << (getIsDataCache() ? "data" : "instr");
p.printOptionalAttrDict(
- (*this)->getAttrs(),
+ (*this)->getDiscardableAttrDictionary().getValue(),
/*elidedAttrs=*/{"localityHint", "isWrite", "isDataCache"});
p << " : " << getMemRefType();
}
@@ -3820,7 +3821,8 @@ void TransposeOp::build(OpBuilder &b, OperationState &result, Value in,
// transpose $in $permutation attr-dict : type($in) `to` type(results)
void TransposeOp::print(OpAsmPrinter &p) {
p << " " << getIn() << " " << getPermutation();
- p.printOptionalAttrDict((*this)->getAttrs(), {getPermutationAttrStrName()});
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue(),
+ {getPermutationAttrStrName()});
p << " : " << getIn().getType() << " to " << getType();
}
diff --git a/mlir/lib/Dialect/MemRef/Transforms/AllocationOpInterfaceImpl.cpp b/mlir/lib/Dialect/MemRef/Transforms/AllocationOpInterfaceImpl.cpp
index 75cc39e61656a..b53e3bdf1cf69 100644
--- a/mlir/lib/Dialect/MemRef/Transforms/AllocationOpInterfaceImpl.cpp
+++ b/mlir/lib/Dialect/MemRef/Transforms/AllocationOpInterfaceImpl.cpp
@@ -34,11 +34,12 @@ struct DefaultAllocationInterface
}
static ::std::optional<::mlir::Operation *>
buildPromotedAlloc(OpBuilder &builder, Value alloc) {
- Operation *definingOp = alloc.getDefiningOp();
- return memref::AllocaOp::create(
- builder, definingOp->getLoc(),
- cast<MemRefType>(definingOp->getResultTypes()[0]),
- definingOp->getOperands(), definingOp->getAttrs());
+ auto allocOp = cast<memref::AllocOp>(alloc.getDefiningOp());
+ memref::AllocaOp allocaOp = memref::AllocaOp::create(
+ builder, allocOp.getLoc(), allocOp.getType(), allocOp.getDynamicSizes(),
+ allocOp.getSymbolOperands(), allocOp.getAlignmentAttr());
+ allocaOp->setDiscardableAttrs(allocOp->getDiscardableAttrDictionary());
+ return allocaOp.getOperation();
}
};
diff --git a/mlir/lib/Dialect/MemRef/Transforms/MultiBuffer.cpp b/mlir/lib/Dialect/MemRef/Transforms/MultiBuffer.cpp
index ce45f847ccaed..c9e5f496b91b0 100644
--- a/mlir/lib/Dialect/MemRef/Transforms/MultiBuffer.cpp
+++ b/mlir/lib/Dialect/MemRef/Transforms/MultiBuffer.cpp
@@ -224,8 +224,9 @@ mlir::memref::multiBuffer(RewriterBase &rewriter, memref::AllocOp allocOp,
Location loc = allocOp->getLoc();
OpBuilder::InsertionGuard g(rewriter);
rewriter.setInsertionPoint(allocOp);
- auto mbAlloc = memref::AllocOp::create(rewriter, loc, mbMemRefType,
- ValueRange{}, allocOp->getAttrs());
+ auto mbAlloc = memref::AllocOp::create(
+ rewriter, loc, mbMemRefType, ValueRange{},
+ allocOp->getDiscardableAttrDictionary().getValue());
LLVM_DEBUG(DBGS() << "--multi-buffered alloc: " << mbAlloc << "\n");
// 3. Within the loop, build the modular leading index (i.e. each loop
diff --git a/mlir/lib/Dialect/MemRef/Transforms/NormalizeMemRefs.cpp b/mlir/lib/Dialect/MemRef/Transforms/NormalizeMemRefs.cpp
index d5e0dace3c775..5e3ac56815d0b 100644
--- a/mlir/lib/Dialect/MemRef/Transforms/NormalizeMemRefs.cpp
+++ b/mlir/lib/Dialect/MemRef/Transforms/NormalizeMemRefs.cpp
@@ -514,7 +514,8 @@ Operation *NormalizeMemRefs::createOpResultsNormalized(func::FuncOp funcOp,
// the operation results.
OperationState result(oldOp->getLoc(), oldOp->getName());
result.addOperands(oldOp->getOperands());
- result.addAttributes(oldOp->getAttrs());
+ result.addAttributes(oldOp->getDiscardableAttrDictionary().getValue());
+ result.propertiesAttr = oldOp->getPropertiesAsAttribute();
// Add normalized MemRefType to the OperationState.
SmallVector<Type, 4> resultTypes;
OpBuilder b(funcOp);
diff --git a/mlir/lib/Dialect/NVGPU/IR/NVGPUDialect.cpp b/mlir/lib/Dialect/NVGPU/IR/NVGPUDialect.cpp
index 642e588488641..2649564a7828e 100644
--- a/mlir/lib/Dialect/NVGPU/IR/NVGPUDialect.cpp
+++ b/mlir/lib/Dialect/NVGPU/IR/NVGPUDialect.cpp
@@ -272,7 +272,7 @@ LogicalResult MmaSyncOp::verify() {
return verifyMmaSyncOp(this->getOperation(), getMatrixA(), getMatrixB(),
getMatrixC(), getMmaShapeAsArray(),
- getOperation()->hasAttr(getTf32EnabledAttrName()));
+ getTf32Enabled().value_or(false));
}
//===----------------------------------------------------------------------===//
@@ -296,8 +296,7 @@ LogicalResult MmaSparseSyncOp::verify() {
return verifyMmaSyncOp(this->getOperation(), getMatrixA(), getMatrixB(),
getMatrixC(), getMmaShapeAsArray(),
- getOperation()->hasAttr(getTf32EnabledAttrName()),
- true);
+ getTf32Enabled().value_or(false), true);
}
//===----------------------------------------------------------------------===//
diff --git a/mlir/lib/Dialect/NVGPU/Transforms/MmaSyncTF32Transform.cpp b/mlir/lib/Dialect/NVGPU/Transforms/MmaSyncTF32Transform.cpp
index 7f626a625aaea..118796e23a69a 100644
--- a/mlir/lib/Dialect/NVGPU/Transforms/MmaSyncTF32Transform.cpp
+++ b/mlir/lib/Dialect/NVGPU/Transforms/MmaSyncTF32Transform.cpp
@@ -35,7 +35,7 @@ struct MmaSyncF32ToTF32Pattern : public OpRewritePattern<nvgpu::MmaSyncOp> {
PatternRewriter &rewriter) const override {
Location location = op->getLoc();
- if (op->hasAttr(op.getTf32EnabledAttrName()) ||
+ if (op.getTf32Enabled().value_or(false) ||
!cast<VectorType>(op.getMatrixA().getType()).getElementType().isF32())
return failure();
diff --git a/mlir/lib/Dialect/OpenACC/IR/OpenACC.cpp b/mlir/lib/Dialect/OpenACC/IR/OpenACC.cpp
index cdf34234f06df..69e60410435b6 100644
--- a/mlir/lib/Dialect/OpenACC/IR/OpenACC.cpp
+++ b/mlir/lib/Dialect/OpenACC/IR/OpenACC.cpp
@@ -49,7 +49,7 @@ static void attachVarNameAttr(Operation *op, OpBuilder &builder,
StringRef varName) {
if (!varName.empty()) {
auto varNameAttr = acc::VarNameAttr::get(builder.getContext(), varName);
- op->setAttr(acc::getVarNameAttrName(), varNameAttr);
+ op->setDiscardableAttr(acc::getVarNameAttrName(), varNameAttr);
}
}
diff --git a/mlir/lib/Dialect/OpenACC/IR/OpenACCCG.cpp b/mlir/lib/Dialect/OpenACC/IR/OpenACCCG.cpp
index fbffcb92267d3..eb678fd195b60 100644
--- a/mlir/lib/Dialect/OpenACC/IR/OpenACCCG.cpp
+++ b/mlir/lib/Dialect/OpenACC/IR/OpenACCCG.cpp
@@ -82,10 +82,11 @@ static void updateComputeRegionInputOperandSegments(ComputeRegionOp op,
PatternRewriter &rewriter,
size_t numInput) {
const size_t numLaunch = op.getLaunchArgs().size();
- op->setAttr(ComputeRegionOp::getOperandSegmentSizeAttr(),
- rewriter.getDenseI32ArrayAttr({static_cast<int32_t>(numLaunch),
- static_cast<int32_t>(numInput),
- op.getStream() ? 1 : 0}));
+ op->setInherentAttr(
+ rewriter.getStringAttr(ComputeRegionOp::getOperandSegmentSizeAttr()),
+ rewriter.getDenseI32ArrayAttr({static_cast<int32_t>(numLaunch),
+ static_cast<int32_t>(numInput),
+ op.getStream() ? 1 : 0}));
}
struct ComputeRegionRemoveDuplicateArgs
@@ -734,8 +735,13 @@ void ComputeRegionOp::print(OpAsmPrinter &p) {
p.printOptionalArrowTypeList(getResultTypes());
p << " ";
p.printRegion(getRegion(), /*printEntryBlockArgs=*/false);
- p.printOptionalAttrDict((*this)->getAttrs(),
- /*elidedAttrs=*/getOperandSegmentSizeAttr());
+ NamedAttrList attrs((*this)->getDiscardableAttrDictionary());
+ attrs.set(getOriginAttrName(), getOriginAttr());
+ if (FlatSymbolRefAttr attr = getKernelFuncNameAttr())
+ attrs.set(getKernelFuncNameAttrName(), attr);
+ if (FlatSymbolRefAttr attr = getKernelModuleNameAttr())
+ attrs.set(getKernelModuleNameAttrName(), attr);
+ p.printOptionalAttrDict(attrs, /*elidedAttrs=*/getOperandSegmentSizeAttr());
}
ParseResult ComputeRegionOp::parse(OpAsmParser &parser,
diff --git a/mlir/lib/Dialect/OpenACC/Transforms/ACCBindRoutine.cpp b/mlir/lib/Dialect/OpenACC/Transforms/ACCBindRoutine.cpp
index 81b3cfb627952..88b02f4074ff2 100644
--- a/mlir/lib/Dialect/OpenACC/Transforms/ACCBindRoutine.cpp
+++ b/mlir/lib/Dialect/OpenACC/Transforms/ACCBindRoutine.cpp
@@ -55,12 +55,12 @@ namespace {
static RoutineOp getFirstAccRoutineOp(FunctionOpInterface funcOp,
const SymbolTable &symTab) {
if (isSpecializedAccRoutine(funcOp)) {
- auto attr = funcOp->getAttrOfType<SpecializedRoutineAttr>(
+ auto attr = funcOp->getDiscardableAttrOfType<SpecializedRoutineAttr>(
getSpecializedRoutineAttrName());
return symTab.lookup<RoutineOp>(attr.getRoutine().getLeafReference());
}
- auto routineInfo =
- funcOp->getAttrOfType<RoutineInfoAttr>(getRoutineInfoAttrName());
+ auto routineInfo = funcOp->getDiscardableAttrOfType<RoutineInfoAttr>(
+ getRoutineInfoAttrName());
assert(routineInfo && "expected acc.routine_info for acc routine function");
auto accRoutines = routineInfo.getAccRoutines();
assert(!accRoutines.empty() && "expected at least one acc routine");
@@ -111,7 +111,7 @@ class ACCBindRoutine : public acc::impl::ACCBindRoutineBase<ACCBindRoutine> {
if (!(isAccRoutine(callee) || isSpecializedAccRoutine(callee)))
return;
- if (auto routineInfo = callee->getAttrOfType<RoutineInfoAttr>(
+ if (auto routineInfo = callee->getDiscardableAttrOfType<RoutineInfoAttr>(
getRoutineInfoAttrName())) {
if (routineInfo.getAccRoutines().size() > 1) {
(void)accSupport.emitNYI(callOp.getLoc(), "multiple `acc routine`s");
diff --git a/mlir/lib/Dialect/OpenACC/Transforms/ACCCGToGPU.cpp b/mlir/lib/Dialect/OpenACC/Transforms/ACCCGToGPU.cpp
index b88c4fe33097a..7a762a2f189a2 100644
--- a/mlir/lib/Dialect/OpenACC/Transforms/ACCCGToGPU.cpp
+++ b/mlir/lib/Dialect/OpenACC/Transforms/ACCCGToGPU.cpp
@@ -193,12 +193,14 @@ getAccRoutineParDim(RoutineOp routineOp, MLIRContext *ctx,
static RoutineOp getRoutineOpForAccRoutineFunction(FunctionOpInterface funcOp,
const SymbolTable &symTab) {
if (isSpecializedAccRoutine(funcOp)) {
- SpecializedRoutineAttr attr = funcOp->getAttrOfType<SpecializedRoutineAttr>(
- getSpecializedRoutineAttrName());
+ SpecializedRoutineAttr attr =
+ funcOp->getDiscardableAttrOfType<SpecializedRoutineAttr>(
+ getSpecializedRoutineAttrName());
return symTab.lookup<RoutineOp>(attr.getRoutine().getLeafReference());
}
RoutineInfoAttr routineInfo =
- funcOp->getAttrOfType<RoutineInfoAttr>(getRoutineInfoAttrName());
+ funcOp->getDiscardableAttrOfType<RoutineInfoAttr>(
+ getRoutineInfoAttrName());
if (!routineInfo || routineInfo.getAccRoutines().empty())
return nullptr;
return symTab.lookup<RoutineOp>(
@@ -210,7 +212,7 @@ static GPUParallelDimAttr
getSpecializedRoutineDim(FunctionOpInterface funcOp,
const ACCToGPUMappingPolicy &policy) {
SpecializedRoutineAttr specAttr =
- funcOp->getAttrOfType<SpecializedRoutineAttr>(
+ funcOp->getDiscardableAttrOfType<SpecializedRoutineAttr>(
getSpecializedRoutineAttrName());
assert(specAttr && "expected specialized routine attribute");
return policy.map(funcOp->getContext(), specAttr.getLevel().getValue());
diff --git a/mlir/lib/Dialect/OpenACC/Transforms/ACCComputeLowering.cpp b/mlir/lib/Dialect/OpenACC/Transforms/ACCComputeLowering.cpp
index a275a794c9fd5..a5fbed1d36fd7 100644
--- a/mlir/lib/Dialect/OpenACC/Transforms/ACCComputeLowering.cpp
+++ b/mlir/lib/Dialect/OpenACC/Transforms/ACCComputeLowering.cpp
@@ -94,7 +94,7 @@ static bool isOpInSerialRegion(Operation *op) {
return computeRegion.isEffectivelySerial();
if (auto funcOp = op->getParentOfType<FunctionOpInterface>()) {
if (isSpecializedAccRoutine(funcOp)) {
- auto attr = funcOp->getAttrOfType<SpecializedRoutineAttr>(
+ auto attr = funcOp->getDiscardableAttrOfType<SpecializedRoutineAttr>(
getSpecializedRoutineAttrName());
if (attr && attr.getLevel().getValue() == ParLevel::seq)
return true;
diff --git a/mlir/lib/Dialect/OpenACC/Transforms/ACCDeclareGPUModuleInsertion.cpp b/mlir/lib/Dialect/OpenACC/Transforms/ACCDeclareGPUModuleInsertion.cpp
index fc77accc415d7..f8efb98fb6771 100644
--- a/mlir/lib/Dialect/OpenACC/Transforms/ACCDeclareGPUModuleInsertion.cpp
+++ b/mlir/lib/Dialect/OpenACC/Transforms/ACCDeclareGPUModuleInsertion.cpp
@@ -72,14 +72,16 @@ namespace {
static bool hasAccDeclareGlobals(ModuleOp mod) {
for (Operation &op : mod.getBody()->getOperations())
- if (op.getAttr(acc::getDeclareAttrName()))
+ if (op.getDiscardableAttr(acc::getDeclareAttrName()))
return true;
return false;
}
static void makeDeviceGlobalDeclaration(Operation &globalOp) {
- globalOp.removeAttr("initVal");
- globalOp.removeAttr("linkName");
+ globalOp.setInherentAttr(StringAttr::get(globalOp.getContext(), "initVal"),
+ {});
+ globalOp.setInherentAttr(StringAttr::get(globalOp.getContext(), "linkName"),
+ {});
for (Region ®ion : globalOp.getRegions()) {
region.dropAllReferences();
region.getBlocks().clear();
@@ -98,7 +100,7 @@ class ACCDeclareGPUModuleInsertion
SymbolTable gpuSymTable(gpuMod);
for (Operation &globalOp : mod.getBody()->getOperations()) {
- if (!globalOp.getAttr(acc::getDeclareAttrName()))
+ if (!globalOp.getDiscardableAttr(acc::getDeclareAttrName()))
continue;
auto symOp = dyn_cast<SymbolOpInterface>(&globalOp);
@@ -107,8 +109,8 @@ class ACCDeclareGPUModuleInsertion
StringAttr name = symOp.getNameAttr();
Operation *deviceGlobal = globalOp.clone();
- auto declareAttr =
- globalOp.getAttrOfType<acc::DeclareAttr>(acc::getDeclareAttrName());
+ auto declareAttr = globalOp.getDiscardableAttrOfType<acc::DeclareAttr>(
+ acc::getDeclareAttrName());
auto globalVar = dyn_cast<acc::GlobalVariableOpInterface>(&globalOp);
bool makeUnifiedDeclaration =
cudaUnified &&
@@ -152,10 +154,11 @@ class ACCDeclareGPUModuleInsertion
}
// Propagate acc.declare onto the GPU copy if it was cloned before the
// host global was marked.
- if (!existing->getAttr(acc::getDeclareAttrName()))
+ if (!existing->getDiscardableAttr(acc::getDeclareAttrName()))
if (Attribute declareAttr =
- globalOp.getAttr(acc::getDeclareAttrName()))
- existing->setAttr(acc::getDeclareAttrName(), declareAttr);
+ globalOp.getDiscardableAttr(acc::getDeclareAttrName()))
+ existing->setDiscardableAttr(acc::getDeclareAttrName(),
+ declareAttr);
deviceGlobal->destroy();
continue;
}
diff --git a/mlir/lib/Dialect/OpenACC/Transforms/ACCEmitRemarksData.cpp b/mlir/lib/Dialect/OpenACC/Transforms/ACCEmitRemarksData.cpp
index eda3994d2ab09..fde2def1794ad 100644
--- a/mlir/lib/Dialect/OpenACC/Transforms/ACCEmitRemarksData.cpp
+++ b/mlir/lib/Dialect/OpenACC/Transforms/ACCEmitRemarksData.cpp
@@ -200,7 +200,7 @@ static void emitDataMappingRemarks(ValueRange mappingOperands,
[&]() {
std::string message = "Generating ";
message += directivePrefix.str();
- if (op->getAttr(acc::getFromDefaultClauseAttrName()))
+ if (op->getDiscardableAttr(acc::getFromDefaultClauseAttrName()))
message += "default ";
else if (acc::getImplicitFlag(op))
message += "implicit ";
diff --git a/mlir/lib/Dialect/OpenACC/Transforms/ACCEmitRemarksLoop.cpp b/mlir/lib/Dialect/OpenACC/Transforms/ACCEmitRemarksLoop.cpp
index 29e71fe1e9097..cb082a0708052 100644
--- a/mlir/lib/Dialect/OpenACC/Transforms/ACCEmitRemarksLoop.cpp
+++ b/mlir/lib/Dialect/OpenACC/Transforms/ACCEmitRemarksLoop.cpp
@@ -96,7 +96,7 @@ static void emitLoopMappingRemark(acc::ComputeRegionOp computeRegion,
const acc::ACCToGPUMappingPolicy &policy,
llvm::StringRef gpuDimSeparator) {
acc::GPUParallelDimsAttr parDimsAttr =
- loopOp->getAttrOfType<acc::GPUParallelDimsAttr>(
+ loopOp->getDiscardableAttrOfType<acc::GPUParallelDimsAttr>(
acc::GPUParallelDimsAttr::name);
SmallVector<acc::GPUParallelDimAttr, 1> seqParDims;
diff --git a/mlir/lib/Dialect/OpenACC/Transforms/ACCImplicitData.cpp b/mlir/lib/Dialect/OpenACC/Transforms/ACCImplicitData.cpp
index 628454905b488..8d7d5d3282327 100644
--- a/mlir/lib/Dialect/OpenACC/Transforms/ACCImplicitData.cpp
+++ b/mlir/lib/Dialect/OpenACC/Transforms/ACCImplicitData.cpp
@@ -530,8 +530,8 @@ Operation *ACCImplicitData::generateDataClauseOpForCandidate(
newDataOp = acc::PresentOp::create(builder, loc, var,
/*structured=*/true, /*implicit=*/true,
accSupport.getVariableName(var));
- newDataOp->setAttr(acc::getFromDefaultClauseAttrName(),
- builder.getUnitAttr());
+ newDataOp->setDiscardableAttr(acc::getFromDefaultClauseAttrName(),
+ builder.getUnitAttr());
} else {
auto copyinOp =
acc::CopyinOp::create(builder, loc, var,
diff --git a/mlir/lib/Dialect/OpenACC/Transforms/ACCImplicitDeclare.cpp b/mlir/lib/Dialect/OpenACC/Transforms/ACCImplicitDeclare.cpp
index 4d77353c20f56..28b8e064d7768 100644
--- a/mlir/lib/Dialect/OpenACC/Transforms/ACCImplicitDeclare.cpp
+++ b/mlir/lib/Dialect/OpenACC/Transforms/ACCImplicitDeclare.cpp
@@ -331,9 +331,10 @@ static void collectGlobalsFromDeviceRegion(Region ®ion,
// Adds the declare attribute to the operation `op`.
static void addDeclareAttr(MLIRContext *context, Operation *op,
acc::DataClause clause) {
- op->setAttr(acc::getDeclareAttrName(),
- acc::DeclareAttr::get(context,
- acc::DataClauseAttr::get(context, clause)));
+ op->setDiscardableAttr(
+ acc::getDeclareAttrName(),
+ acc::DeclareAttr::get(context,
+ acc::DataClauseAttr::get(context, clause)));
}
// This pass applies implicit declare actions for globals referenced in
@@ -381,7 +382,7 @@ class ACCImplicitDeclare
symTab);
})
.Case([&](acc::GlobalVariableOpInterface globalVarOp) {
- if (globalVarOp->getAttr(acc::getDeclareAttrName()))
+ if (globalVarOp->getDiscardableAttr(acc::getDeclareAttrName()))
if (Region *initRegion = globalVarOp.getInitRegion())
collectGlobalsFromDeviceRegion(*initRegion, globalsToAccDeclare,
accSupport, symTab);
diff --git a/mlir/lib/Dialect/OpenACC/Transforms/ACCImplicitRoutine.cpp b/mlir/lib/Dialect/OpenACC/Transforms/ACCImplicitRoutine.cpp
index e2ea3f1aed3b5..1ac1d023e1ff4 100644
--- a/mlir/lib/Dialect/OpenACC/Transforms/ACCImplicitRoutine.cpp
+++ b/mlir/lib/Dialect/OpenACC/Transforms/ACCImplicitRoutine.cpp
@@ -119,10 +119,10 @@ class ACCImplicitRoutine
/* gangDimDeviceType=*/nullptr);
// Assert that the callee does not already have routine info attribute
- assert(!callee->hasAttr(acc::getRoutineInfoAttrName()) &&
+ assert(!callee->hasDiscardableAttr(acc::getRoutineInfoAttrName()) &&
"function is already associated with a routine");
- callee->setAttr(
+ callee->setDiscardableAttr(
acc::getRoutineInfoAttrName(),
mlir::acc::RoutineInfoAttr::get(
builder.getContext(),
diff --git a/mlir/lib/Dialect/OpenACC/Transforms/ACCRecipeMaterialization.cpp b/mlir/lib/Dialect/OpenACC/Transforms/ACCRecipeMaterialization.cpp
index 70aacd251c329..e1775ce3706e0 100644
--- a/mlir/lib/Dialect/OpenACC/Transforms/ACCRecipeMaterialization.cpp
+++ b/mlir/lib/Dialect/OpenACC/Transforms/ACCRecipeMaterialization.cpp
@@ -88,12 +88,13 @@ static void saveVarName(StringRef name, Value dst) {
if (name.empty())
return;
if (Operation *dstOp = dst.getDefiningOp()) {
- if (dstOp->getAttrOfType<acc::VarNameAttr>(acc::getVarNameAttrName()))
+ if (dstOp->getDiscardableAttrOfType<acc::VarNameAttr>(
+ acc::getVarNameAttrName()))
return;
if (isa<ACC_DATA_ENTRY_OPS>(dstOp))
return;
- dstOp->setAttr(acc::getVarNameAttrName(),
- acc::VarNameAttr::get(dstOp->getContext(), name));
+ dstOp->setDiscardableAttr(acc::getVarNameAttrName(),
+ acc::VarNameAttr::get(dstOp->getContext(), name));
return;
}
auto blockArg = dyn_cast<BlockArgument>(dst);
@@ -126,13 +127,14 @@ static void resolveVarNamePlaceholders(Block *block, Block::iterator ip,
StringRef name) {
StringRef placeholder = acc::getVarNamePlaceholder();
for (auto it = block->begin(); it != std::next(ip); ++it) {
- auto attr = it->getAttrOfType<acc::VarNameAttr>(acc::getVarNameAttrName());
+ auto attr = it->getDiscardableAttrOfType<acc::VarNameAttr>(
+ acc::getVarNameAttrName());
if (attr && attr.getName() == placeholder) {
if (name.empty())
- it->removeAttr(acc::getVarNameAttrName());
+ it->removeDiscardableAttr(acc::getVarNameAttrName());
else
- it->setAttr(acc::getVarNameAttrName(),
- acc::VarNameAttr::get(it->getContext(), name));
+ it->setDiscardableAttr(acc::getVarNameAttrName(),
+ acc::VarNameAttr::get(it->getContext(), name));
}
}
}
diff --git a/mlir/lib/Dialect/OpenACC/Transforms/ACCRoutineLowering.cpp b/mlir/lib/Dialect/OpenACC/Transforms/ACCRoutineLowering.cpp
index 9d5f0fc434d7e..af970c730e7fe 100644
--- a/mlir/lib/Dialect/OpenACC/Transforms/ACCRoutineLowering.cpp
+++ b/mlir/lib/Dialect/OpenACC/Transforms/ACCRoutineLowering.cpp
@@ -107,13 +107,15 @@ static func::FuncOp createFunctionForDeviceStaging(func::FuncOp hostFunc,
FunctionType funcType = hostFunc.getFunctionType();
func::FuncOp deviceFunc =
func::FuncOp::create(rewriter, loc, hostFunc.getName(), funcType);
- deviceFunc->setAttrs(hostFunc->getAttrs());
- deviceFunc->removeAttr(getRoutineInfoAttrName());
- deviceFunc->setAttr(getSpecializedRoutineAttrName(),
- SpecializedRoutineAttr::get(
- ctx, SymbolRefAttr::get(ctx, routineOp.getSymName()),
- ParLevelAttr::get(ctx, parLevel),
- StringAttr::get(ctx, hostFunc.getName())));
+ deviceFunc->setDiscardableAttrs(
+ hostFunc->getDiscardableAttrDictionary().getValue());
+ deviceFunc->removeDiscardableAttr(getRoutineInfoAttrName());
+ deviceFunc->setDiscardableAttr(
+ getSpecializedRoutineAttrName(),
+ SpecializedRoutineAttr::get(
+ ctx, SymbolRefAttr::get(ctx, routineOp.getSymName()),
+ ParLevelAttr::get(ctx, parLevel),
+ StringAttr::get(ctx, hostFunc.getName())));
Block *sourceBlock = &hostFunc.getBody().front();
Block *newBlock = rewriter.createBlock(&deviceFunc.getRegion());
diff --git a/mlir/lib/Dialect/OpenACC/Transforms/ACCRoutineToGPUFunc.cpp b/mlir/lib/Dialect/OpenACC/Transforms/ACCRoutineToGPUFunc.cpp
index 6bbb4b53cb5bb..c98a7544d5af7 100644
--- a/mlir/lib/Dialect/OpenACC/Transforms/ACCRoutineToGPUFunc.cpp
+++ b/mlir/lib/Dialect/OpenACC/Transforms/ACCRoutineToGPUFunc.cpp
@@ -244,8 +244,9 @@ static LogicalResult cloneFuncsToGPUModule(
gpu::GPUFuncOp deviceFuncOp = createGPUFuncFromFunc(builder, srcFunc);
- if (auto specRoutineAttr = srcFunc->getAttrOfType<SpecializedRoutineAttr>(
- getSpecializedRoutineAttrName())) {
+ if (auto specRoutineAttr =
+ srcFunc->getDiscardableAttrOfType<SpecializedRoutineAttr>(
+ getSpecializedRoutineAttrName())) {
StringAttr funcName = specRoutineAttr.getFuncName();
if (failed(SymbolTable::replaceAllSymbolUses(
StringAttr::get(ctx, deviceFuncOp.getName()), funcName, mod))) {
@@ -253,11 +254,14 @@ static LogicalResult cloneFuncsToGPUModule(
"cannot replace symbol for acc routine");
return failure();
}
- deviceFuncOp->setAttr(SymbolTable::getSymbolAttrName(), funcName);
+ deviceFuncOp->setDiscardableAttr(SymbolTable::getSymbolAttrName(),
+ funcName);
}
- if (auto specAttr = srcFunc->getAttrOfType<SpecializedRoutineAttr>(
- getSpecializedRoutineAttrName()))
- deviceFuncOp->setAttr(getSpecializedRoutineAttrName(), specAttr);
+ if (auto specAttr =
+ srcFunc->getDiscardableAttrOfType<SpecializedRoutineAttr>(
+ getSpecializedRoutineAttrName()))
+ deviceFuncOp->setDiscardableAttr(getSpecializedRoutineAttrName(),
+ specAttr);
gpuSymTab.insert(deviceFuncOp);
}
diff --git a/mlir/lib/Dialect/OpenACC/Utils/OpenACCUtils.cpp b/mlir/lib/Dialect/OpenACC/Utils/OpenACCUtils.cpp
index 5e04a4154adf3..1faba3cc7bebf 100644
--- a/mlir/lib/Dialect/OpenACC/Utils/OpenACCUtils.cpp
+++ b/mlir/lib/Dialect/OpenACC/Utils/OpenACCUtils.cpp
@@ -120,8 +120,8 @@ std::string mlir::acc::getVariableName(mlir::Value v) {
return std::to_string(*constVal);
// Check for `acc.var_name` attribute
- if (auto varNameAttr =
- definingOp->getAttrOfType<VarNameAttr>(getVarNameAttrName()))
+ if (auto varNameAttr = definingOp->getDiscardableAttrOfType<VarNameAttr>(
+ getVarNameAttrName()))
return varNameAttr.getName().str();
// If it is a data entry operation, get name via getVarName
@@ -222,8 +222,8 @@ bool mlir::acc::isValidSymbolUse(mlir::Operation *user,
mlir::dyn_cast_if_present<mlir::FunctionOpInterface>(definingOp)) {
// If this symbol is actually an acc routine or a specialized acc routine -
// then it is expected for it to be offloaded - therefore it is valid.
- if (func->hasAttr(mlir::acc::getRoutineInfoAttrName()) ||
- func->hasAttr(mlir::acc::getSpecializedRoutineAttrName()))
+ if (func->hasDiscardableAttr(mlir::acc::getRoutineInfoAttrName()) ||
+ func->hasDiscardableAttr(mlir::acc::getSpecializedRoutineAttrName()))
return true;
// If this symbol is a call to an LLVM intrinsic, then it is likely valid.
@@ -240,7 +240,8 @@ bool mlir::acc::isValidSymbolUse(mlir::Operation *user,
}
// A declare attribute is needed for symbol references.
- bool hasDeclare = definingOp->hasAttr(mlir::acc::getDeclareAttrName());
+ bool hasDeclare =
+ definingOp->hasDiscardableAttr(mlir::acc::getDeclareAttrName());
return hasDeclare;
}
@@ -261,8 +262,9 @@ bool mlir::acc::isDeviceValue(mlir::Value val) {
// `acc.declare` with deviceptr marks data that is already associated with
// the device.
- if (auto declareAttr = defOp->getAttrOfType<mlir::acc::DeclareAttr>(
- mlir::acc::getDeclareAttrName()))
+ if (auto declareAttr =
+ defOp->getDiscardableAttrOfType<mlir::acc::DeclareAttr>(
+ mlir::acc::getDeclareAttrName()))
if (declareAttr.getDataClause().getValue() ==
mlir::acc::DataClause::acc_deviceptr)
return true;
diff --git a/mlir/lib/Dialect/OpenACC/Utils/OpenACCUtilsCG.cpp b/mlir/lib/Dialect/OpenACC/Utils/OpenACCUtilsCG.cpp
index e97699414fb36..ce11f8b422270 100644
--- a/mlir/lib/Dialect/OpenACC/Utils/OpenACCUtilsCG.cpp
+++ b/mlir/lib/Dialect/OpenACC/Utils/OpenACCUtilsCG.cpp
@@ -171,7 +171,8 @@ GPUParallelDimsAttr getParDimsAttr(Operation *op) {
.Case<ACC_OP_WITH_PAR_DIMS_LIST>(
[](auto parOp) { return parOp.getParDimsAttr(); })
.Default([](Operation *op) -> GPUParallelDimsAttr {
- if (Attribute attr = op->getAttr(GPUParallelDimsAttr::name)) {
+ if (Attribute attr =
+ op->getDiscardableAttr(GPUParallelDimsAttr::name)) {
GPUParallelDimsAttr parDimsAttr = dyn_cast<GPUParallelDimsAttr>(attr);
assert(parDimsAttr && "acc.par_dims must be a GPUParallelDimsAttr");
return parDimsAttr;
@@ -193,8 +194,9 @@ void setParDimsAttr(Operation *op, GPUParallelDimsAttr attr) {
llvm::TypeSwitch<Operation *>(op)
.Case<ACC_OP_WITH_PAR_DIMS_LIST>(
[&](auto parOp) { parOp.setParDimsAttr(attr); })
- .Default(
- [&](Operation *op) { op->setAttr(GPUParallelDimsAttr::name, attr); });
+ .Default([&](Operation *op) {
+ op->setDiscardableAttr(GPUParallelDimsAttr::name, attr);
+ });
}
void updateParDimsAttr(Operation *op, GPUParallelDimsAttr attr) {
@@ -203,19 +205,21 @@ void updateParDimsAttr(Operation *op, GPUParallelDimsAttr attr) {
llvm::TypeSwitch<Operation *>(op)
.Case<ACC_OP_WITH_PAR_DIMS_LIST>(
[&](auto parOp) { parOp.setParDimsAttr(attr); })
- .Default(
- [&](Operation *op) { op->setAttr(GPUParallelDimsAttr::name, attr); });
+ .Default([&](Operation *op) {
+ op->setDiscardableAttr(GPUParallelDimsAttr::name, attr);
+ });
}
#undef ACC_OP_WITH_PAR_DIMS_LIST
bool hasGPUBlockRedundantAttr(Operation *op) {
- return op->hasAttrOfType<GPUBlockRedundantAttr>(GPUBlockRedundantAttr::name);
+ return op->hasDiscardableAttrOfType<GPUBlockRedundantAttr>(
+ GPUBlockRedundantAttr::name);
}
void setGPUBlockRedundantAttr(Operation *op) {
- op->setAttr(GPUBlockRedundantAttr::name,
- GPUBlockRedundantAttr::get(op->getContext()));
+ op->setDiscardableAttr(GPUBlockRedundantAttr::name,
+ GPUBlockRedundantAttr::get(op->getContext()));
}
void copyParDimsAttr(Operation *from, Operation *to) {
@@ -225,7 +229,8 @@ void copyParDimsAttr(Operation *from, Operation *to) {
}
ActiveParDimsAttr getActiveParDimsAttr(Operation *op) {
- return op->getAttrOfType<ActiveParDimsAttr>(ActiveParDimsAttr::name);
+ return op->getDiscardableAttrOfType<ActiveParDimsAttr>(
+ ActiveParDimsAttr::name);
}
bool hasActiveParDimsAttr(Operation *op) {
@@ -233,7 +238,7 @@ bool hasActiveParDimsAttr(Operation *op) {
}
void setActiveParDimsAttr(Operation *op, ActiveParDimsAttr attr) {
- op->setAttr(ActiveParDimsAttr::name, attr);
+ op->setDiscardableAttr(ActiveParDimsAttr::name, attr);
}
void setActiveParDimsAttr(Operation *op, ArrayRef<GPUParallelDimAttr> dims) {
diff --git a/mlir/lib/Dialect/OpenACC/Utils/OpenACCUtilsGPU.cpp b/mlir/lib/Dialect/OpenACC/Utils/OpenACCUtilsGPU.cpp
index d0f454302a2a8..9ec382c67363f 100644
--- a/mlir/lib/Dialect/OpenACC/Utils/OpenACCUtilsGPU.cpp
+++ b/mlir/lib/Dialect/OpenACC/Utils/OpenACCUtilsGPU.cpp
@@ -33,8 +33,8 @@ std::optional<gpu::GPUModuleOp> getOrCreateGPUModule(ModuleOp mod, bool create,
// Create a new GPU module
auto *ctx = mod.getContext();
- mod->setAttr(gpu::GPUDialect::getContainerModuleAttrName(),
- UnitAttr::get(ctx));
+ mod->setDiscardableAttr(gpu::GPUDialect::getContainerModuleAttrName(),
+ UnitAttr::get(ctx));
OpBuilder builder(ctx);
auto gpuMod = gpu::GPUModuleOp::create(builder, mod.getLoc(), moduleName);
diff --git a/mlir/lib/Dialect/OpenACC/Utils/OpenACCUtilsLoop.cpp b/mlir/lib/Dialect/OpenACC/Utils/OpenACCUtilsLoop.cpp
index 52f97e0867ee6..285e02c0e83b1 100644
--- a/mlir/lib/Dialect/OpenACC/Utils/OpenACCUtilsLoop.cpp
+++ b/mlir/lib/Dialect/OpenACC/Utils/OpenACCUtilsLoop.cpp
@@ -340,12 +340,14 @@ convertUnstructuredACCLoopToSCFExecuteRegion(LoopOp loopOp,
}
void setCollapseCountAttr(Operation *op, uint64_t count) {
- op->setAttr(getCollapseCountAttrName(),
- IntegerAttr::get(IntegerType::get(op->getContext(), 64), count));
+ op->setDiscardableAttr(
+ getCollapseCountAttrName(),
+ IntegerAttr::get(IntegerType::get(op->getContext(), 64), count));
}
uint64_t getCollapseCount(Operation *op) {
- if (auto attr = op->getAttrOfType<IntegerAttr>(getCollapseCountAttrName()))
+ if (auto attr =
+ op->getDiscardableAttrOfType<IntegerAttr>(getCollapseCountAttrName()))
return attr.getValue().getZExtValue();
return 1;
}
diff --git a/mlir/lib/Dialect/OpenMP/IR/OpenMPDialect.cpp b/mlir/lib/Dialect/OpenMP/IR/OpenMPDialect.cpp
index 6aabe6e918049..4d6cbef993f94 100644
--- a/mlir/lib/Dialect/OpenMP/IR/OpenMPDialect.cpp
+++ b/mlir/lib/Dialect/OpenMP/IR/OpenMPDialect.cpp
@@ -4364,7 +4364,7 @@ void CanonicalLoopOp::print(OpAsmPrinter &p) {
p.printRegion(getRegion(), /*printEntryBlockArgs=*/false,
/*printBlockTerminators=*/true);
- p.printOptionalAttrDict((*this)->getAttrs());
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue());
}
mlir::ParseResult CanonicalLoopOp::parse(::mlir::OpAsmParser &parser,
@@ -4452,7 +4452,7 @@ void UnrollHeuristicOp::build(::mlir::OpBuilder &odsBuilder,
void UnrollHeuristicOp::print(OpAsmPrinter &p) {
p << '(' << getApplyee() << ')';
- p.printOptionalAttrDict((*this)->getAttrs());
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue());
}
mlir::ParseResult UnrollHeuristicOp::parse(::mlir::OpAsmParser &parser,
@@ -4505,7 +4505,7 @@ void UnrollFullOp::build(::mlir::OpBuilder &odsBuilder,
void UnrollFullOp::print(OpAsmPrinter &p) {
p << '(' << getApplyee() << ')';
- p.printOptionalAttrDict((*this)->getAttrs());
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue());
}
mlir::ParseResult UnrollFullOp::parse(::mlir::OpAsmParser &parser,
@@ -4576,7 +4576,10 @@ void UnrollPartialOp::build(::mlir::OpBuilder &odsBuilder,
void UnrollPartialOp::print(OpAsmPrinter &p) {
p << '(' << getApplyee() << ')';
- p.printOptionalAttrDict((*this)->getAttrs());
+ SmallVector<NamedAttribute> attrs((*this)->getDiscardableAttrs());
+ attrs.emplace_back(getUnrollFactorAttrName(), getUnrollFactorAttr());
+ llvm::sort(attrs);
+ p.printOptionalAttrDict(attrs);
}
mlir::ParseResult UnrollPartialOp::parse(::mlir::OpAsmParser &parser,
@@ -4944,7 +4947,7 @@ LogicalResult AtomicReadOp::verify() {
int64_t version = 50;
if (auto moduleOp = getOperation()->getParentOfType<ModuleOp>())
- if (Attribute verAttr = moduleOp->getAttr("omp.version"))
+ if (Attribute verAttr = moduleOp->getDiscardableAttr("omp.version"))
version = llvm::cast<VersionAttr>(verAttr).getVersion();
if (auto mo = getMemoryOrder()) {
@@ -4970,7 +4973,7 @@ LogicalResult AtomicWriteOp::verify() {
int64_t version = 50;
if (auto moduleOp = getOperation()->getParentOfType<ModuleOp>())
- if (Attribute verAttr = moduleOp->getAttr("omp.version"))
+ if (Attribute verAttr = moduleOp->getDiscardableAttr("omp.version"))
version = llvm::cast<VersionAttr>(verAttr).getVersion();
if (auto mo = getMemoryOrder()) {
@@ -5010,7 +5013,7 @@ LogicalResult AtomicUpdateOp::verify() {
int64_t version = 50;
if (auto moduleOp = getOperation()->getParentOfType<ModuleOp>())
- if (Attribute verAttr = moduleOp->getAttr("omp.version"))
+ if (Attribute verAttr = moduleOp->getDiscardableAttr("omp.version"))
version = llvm::cast<VersionAttr>(verAttr).getVersion();
if (auto mo = getMemoryOrder()) {
@@ -5064,12 +5067,13 @@ LogicalResult AtomicCaptureOp::verifyRegions() {
if (verifyRegionsCommon().failed())
return mlir::failure();
- if (getFirstOp()->getAttr("hint") || getSecondOp()->getAttr("hint"))
+ if (getFirstOp()->getInherentAttr("hint").value_or(Attribute{}) ||
+ getSecondOp()->getInherentAttr("hint").value_or(Attribute{}))
return emitOpError(
"operations inside capture region must not have hint clause");
- if (getFirstOp()->getAttr("memory_order") ||
- getSecondOp()->getAttr("memory_order"))
+ if (getFirstOp()->getInherentAttr("memory_order").value_or(Attribute{}) ||
+ getSecondOp()->getInherentAttr("memory_order").value_or(Attribute{}))
return emitOpError(
"operations inside capture region must not have memory_order clause");
return success();
diff --git a/mlir/lib/Dialect/OpenMP/Utils/Utils.cpp b/mlir/lib/Dialect/OpenMP/Utils/Utils.cpp
index 481efdba89e1e..82ef6611f6dae 100644
--- a/mlir/lib/Dialect/OpenMP/Utils/Utils.cpp
+++ b/mlir/lib/Dialect/OpenMP/Utils/Utils.cpp
@@ -42,20 +42,20 @@ void mlir::omp::setOffloadModuleInterfaceAttributes(
}
void mlir::omp::setOpenMPVersionAttribute(ModuleOp module, int64_t version) {
- module->setAttr(
+ module->setDiscardableAttr(
StringAttr::get(module.getContext(), llvm::Twine{"omp.version"}),
VersionAttr::get(module.getContext(), version));
}
int64_t mlir::omp::getOpenMPVersionAttribute(ModuleOp module,
int64_t fallback) {
- if (Attribute verAttr = module->getAttr("omp.version"))
+ if (Attribute verAttr = module->getDiscardableAttr("omp.version"))
return llvm::cast<VersionAttr>(verAttr).getVersion();
return fallback;
}
bool mlir::omp::isOpenMPModule(ModuleOp module) {
- return module->hasAttr("omp.version");
+ return module->hasDiscardableAttr("omp.version");
}
static bool allocaUseRequiresSharedMem(const OpOperand &use) {
@@ -75,7 +75,7 @@ static bool allocaUseRequiresSharedMem(const OpOperand &use) {
OperandRange privateVars = argIface.getPrivateVars();
auto it = llvm::find(privateVars, use.get());
if (it != privateVars.end()) {
- auto privateSyms = owner->getAttrOfType<ArrayAttr>("private_syms");
+ ArrayAttr privateSyms = argIface.getPrivateSymsAttribute();
size_t idx = std::distance(privateVars.begin(), it);
auto privateOp =
SymbolTable::lookupNearestSymbolFrom<omp::PrivateClauseOp>(
diff --git a/mlir/lib/Dialect/PDLInterp/IR/PDLInterp.cpp b/mlir/lib/Dialect/PDLInterp/IR/PDLInterp.cpp
index 1c713eb6f467c..541f2d64846fc 100644
--- a/mlir/lib/Dialect/PDLInterp/IR/PDLInterp.cpp
+++ b/mlir/lib/Dialect/PDLInterp/IR/PDLInterp.cpp
@@ -183,7 +183,7 @@ void ForEachOp::print(OpAsmPrinter &p) {
BlockArgument arg = getLoopVariable();
p << ' ' << arg << " : " << arg.getType() << " in " << getValues() << ' ';
p.printRegion(getRegion(), /*printEntryBlockArgs=*/false);
- p.printOptionalAttrDict((*this)->getAttrs());
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue());
p << " -> ";
p.printSuccessor(getSuccessor());
}
diff --git a/mlir/lib/Dialect/Quant/Transforms/NormalizeQuantTypes.cpp b/mlir/lib/Dialect/Quant/Transforms/NormalizeQuantTypes.cpp
index 966d7589d42c3..fe7a3e38b5e4f 100644
--- a/mlir/lib/Dialect/Quant/Transforms/NormalizeQuantTypes.cpp
+++ b/mlir/lib/Dialect/Quant/Transforms/NormalizeQuantTypes.cpp
@@ -124,7 +124,8 @@ class ConvertGenericOpwithSubChannelType : public ConversionPattern {
return failure();
auto *newOp = Operation::create(
- op->getLoc(), op->getName(), resultTypes, operands, op->getAttrs(),
+ op->getLoc(), op->getName(), resultTypes, operands,
+ op->getDiscardableAttrDictionary().getValue(),
op->getPropertiesStorage(), op->getSuccessors(), op->getNumRegions());
for (auto regions : llvm::zip(op->getRegions(), newOp->getRegions())) {
Region &before = std::get<0>(regions);
diff --git a/mlir/lib/Dialect/SCF/IR/SCF.cpp b/mlir/lib/Dialect/SCF/IR/SCF.cpp
index 3388fa490f996..9e125af247799 100644
--- a/mlir/lib/Dialect/SCF/IR/SCF.cpp
+++ b/mlir/lib/Dialect/SCF/IR/SCF.cpp
@@ -168,7 +168,8 @@ void ExecuteRegionOp::print(OpAsmPrinter &p) {
p.printRegion(getRegion(),
/*printEntryBlockArgs=*/false,
/*printBlockTerminators=*/true);
- p.printOptionalAttrDict((*this)->getAttrs(), /*elidedAttrs=*/{"no_inline"});
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue(),
+ /*elidedAttrs=*/{"no_inline"});
}
LogicalResult ExecuteRegionOp::verify() {
@@ -530,7 +531,7 @@ void ForOp::print(OpAsmPrinter &p) {
p.printRegion(getRegion(),
/*printEntryBlockArgs=*/false,
/*printBlockTerminators=*/!getInitArgs().empty());
- p.printOptionalAttrDict((*this)->getAttrs(),
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue(),
/*elidedAttrs=*/getUnsignedCmpAttrName().strref());
}
@@ -636,7 +637,7 @@ ForOp::replaceWithAdditionalYields(RewriterBase &rewriter,
scf::ForOp newLoop = scf::ForOp::create(
rewriter, getLoc(), getLowerBound(), getUpperBound(), getStep(), inits,
[](OpBuilder &, Location, Value, ValueRange) {}, getUnsignedCmp());
- newLoop->setAttrs(getPrunedAttributeList(getOperation(), {}));
+ newLoop->setDiscardableAttrs(getPrunedAttributeList(getOperation(), {}));
// Generate the new yield values and append them to the scf.yield operation.
auto yieldOp = cast<scf::YieldOp>(getBody()->getTerminator());
@@ -909,7 +910,8 @@ mlir::scf::replaceAndCastForOpIterArg(RewriterBase &rewriter, scf::ForOp forOp,
rewriter, forOp.getLoc(), forOp.getLowerBound(), forOp.getUpperBound(),
forOp.getStep(), newIterOperands, /*bodyBuilder=*/nullptr,
forOp.getUnsignedCmp());
- newForOp->setAttrs(forOp->getAttrs());
+ newForOp->setDiscardableAttrs(
+ forOp->getDiscardableAttrDictionary().getValue());
Block &newBlock = newForOp.getRegion().front();
SmallVector<Value, 4> newBlockTransferArgs(newBlock.getArguments().begin(),
newBlock.getArguments().end());
@@ -1139,10 +1141,12 @@ void ForallOp::print(OpAsmPrinter &p) {
p.printRegion(getRegion(),
/*printEntryBlockArgs=*/false,
/*printBlockTerminators=*/getNumResults() > 0);
- p.printOptionalAttrDict(op->getAttrs(), {getOperandSegmentSizesAttrName(),
- getStaticLowerBoundAttrName(),
- getStaticUpperBoundAttrName(),
- getStaticStepAttrName()});
+ NamedAttrList attrs(op->getDiscardableAttrDictionary());
+ if (ArrayAttr mapping = getMappingAttr())
+ attrs.append(getMappingAttrName(), mapping);
+ p.printOptionalAttrDict(
+ attrs, {getOperandSegmentSizesAttrName(), getStaticLowerBoundAttrName(),
+ getStaticUpperBoundAttrName(), getStaticStepAttrName()});
}
ParseResult ForallOp::parse(OpAsmParser &parser, OperationState &result) {
@@ -1455,12 +1459,13 @@ class ForallOpControlOperandsFolder : public OpRewritePattern<ForallOp> {
op.getDynamicStepMutable().assign(dynamicStep);
op.setStaticStep(staticStep);
- op->setAttr(ForallOp::getOperandSegmentSizeAttr(),
- rewriter.getDenseI32ArrayAttr(
- {static_cast<int32_t>(dynamicLowerBound.size()),
- static_cast<int32_t>(dynamicUpperBound.size()),
- static_cast<int32_t>(dynamicStep.size()),
- static_cast<int32_t>(op.getNumResults())}));
+ op->setInherentAttr(
+ rewriter.getStringAttr(ForallOp::getOperandSegmentSizeAttr()),
+ rewriter.getDenseI32ArrayAttr(
+ {static_cast<int32_t>(dynamicLowerBound.size()),
+ static_cast<int32_t>(dynamicUpperBound.size()),
+ static_cast<int32_t>(dynamicStep.size()),
+ static_cast<int32_t>(op.getNumResults())}));
});
return success();
}
@@ -1664,6 +1669,7 @@ struct ForallOpSingleOrZeroIterationDimsFolder
newMixedUpperBounds, newMixedSteps,
op.getOutputs(), std::nullopt, nullptr);
newOp.getBodyRegion().getBlocks().clear();
+ newOp.setMappingAttr(op.getMappingAttr());
// The new loop needs to keep all attributes from the old one, except for
// "operandSegmentSizes" and static loop bound attributes which capture
// the outdated information of the old iteration domain.
@@ -1671,11 +1677,12 @@ struct ForallOpSingleOrZeroIterationDimsFolder
newOp.getStaticLowerBoundAttrName(),
newOp.getStaticUpperBoundAttrName(),
newOp.getStaticStepAttrName()};
- for (const auto &namedAttr : op->getAttrs()) {
+ for (const auto &namedAttr :
+ op->getDiscardableAttrDictionary().getValue()) {
if (llvm::is_contained(elidedAttrs, namedAttr.getName()))
continue;
rewriter.modifyOpInPlace(newOp, [&]() {
- newOp->setAttr(namedAttr.getName(), namedAttr.getValue());
+ newOp->setDiscardableAttr(namedAttr.getName(), namedAttr.getValue());
});
}
rewriter.cloneRegionBefore(op.getRegion(), newOp.getRegion(),
@@ -1875,7 +1882,8 @@ void InParallelOp::print(OpAsmPrinter &p) {
p.printRegion(getRegion(),
/*printEntryBlockArgs=*/false,
/*printBlockTerminators=*/false);
- p.printOptionalAttrDict(getOperation()->getAttrs());
+ p.printOptionalAttrDict(
+ getOperation()->getDiscardableAttrDictionary().getValue());
}
ParseResult InParallelOp::parse(OpAsmParser &parser, OperationState &result) {
@@ -2104,7 +2112,7 @@ void IfOp::print(OpAsmPrinter &p) {
/*printBlockTerminators=*/printBlockTerminators);
}
- p.printOptionalAttrDict((*this)->getAttrs());
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue());
}
void IfOp::getSuccessorRegions(RegionBranchPoint point,
@@ -2951,7 +2959,7 @@ void ParallelOp::print(OpAsmPrinter &p) {
p << ' ';
p.printRegion(getRegion(), /*printEntryBlockArgs=*/false);
p.printOptionalAttrDict(
- (*this)->getAttrs(),
+ (*this)->getDiscardableAttrDictionary().getValue(),
/*elidedAttrs=*/ParallelOp::getOperandSegmentSizeAttr());
}
@@ -3371,7 +3379,8 @@ void scf::WhileOp::print(OpAsmPrinter &p) {
p.printRegion(getBefore(), /*printEntryBlockArgs=*/false);
p << " do ";
p.printRegion(getAfter());
- p.printOptionalAttrDictWithKeyword((*this)->getAttrs());
+ p.printOptionalAttrDictWithKeyword(
+ (*this)->getDiscardableAttrDictionary().getValue());
}
/// Verifies that two ranges of types match, i.e. have the same number of
diff --git a/mlir/lib/Dialect/SCF/Transforms/BufferizableOpInterfaceImpl.cpp b/mlir/lib/Dialect/SCF/Transforms/BufferizableOpInterfaceImpl.cpp
index f8302126a4a4e..dad79b19f949a 100644
--- a/mlir/lib/Dialect/SCF/Transforms/BufferizableOpInterfaceImpl.cpp
+++ b/mlir/lib/Dialect/SCF/Transforms/BufferizableOpInterfaceImpl.cpp
@@ -763,7 +763,8 @@ struct ForOpInterface
rewriter, forOp.getLoc(), forOp.getLowerBound(), forOp.getUpperBound(),
forOp.getStep(), castedInitArgs, /*bodyBuilder=*/nullptr,
forOp.getUnsignedCmp());
- newForOp->setAttrs(forOp->getAttrs());
+ newForOp->setDiscardableAttrs(
+ forOp->getDiscardableAttrDictionary().getValue());
Block *loopBody = newForOp.getBody();
// Set up new iter_args. The loop body uses tensors, so wrap the (memref)
diff --git a/mlir/lib/Dialect/SCF/Transforms/ForToWhile.cpp b/mlir/lib/Dialect/SCF/Transforms/ForToWhile.cpp
index ddcbda86cf1f3..cb416cddc1c64 100644
--- a/mlir/lib/Dialect/SCF/Transforms/ForToWhile.cpp
+++ b/mlir/lib/Dialect/SCF/Transforms/ForToWhile.cpp
@@ -49,8 +49,9 @@ struct ForLoopLoweringPattern : public OpRewritePattern<ForOp> {
SmallVector<Value> initArgs;
initArgs.push_back(forOp.getLowerBound());
llvm::append_range(initArgs, forOp.getInitArgs());
- auto whileOp = WhileOp::create(rewriter, forOp.getLoc(), lcvTypes, initArgs,
- forOp->getAttrs());
+ auto whileOp =
+ WhileOp::create(rewriter, forOp.getLoc(), lcvTypes, initArgs,
+ forOp->getDiscardableAttrDictionary().getValue());
// 'before' region contains the loop condition and forwarding of iteration
// arguments to the 'after' region.
diff --git a/mlir/lib/Dialect/SCF/Transforms/ForallToParallel.cpp b/mlir/lib/Dialect/SCF/Transforms/ForallToParallel.cpp
index b95604fa44cb9..3ba51374feb31 100644
--- a/mlir/lib/Dialect/SCF/Transforms/ForallToParallel.cpp
+++ b/mlir/lib/Dialect/SCF/Transforms/ForallToParallel.cpp
@@ -51,7 +51,7 @@ LogicalResult mlir::scf::forallToParallelLoop(RewriterBase &rewriter,
// If the mapping attribute is present, propagate to the new parallelOp.
if (forallOp.getMapping())
- parallelOp->setAttr("mapping", *forallOp.getMapping());
+ parallelOp->setDiscardableAttr("mapping", *forallOp.getMapping());
// Erase the scf.forall op.
rewriter.replaceOp(forallOp, parallelOp);
diff --git a/mlir/lib/Dialect/SCF/Transforms/LoopSpecialization.cpp b/mlir/lib/Dialect/SCF/Transforms/LoopSpecialization.cpp
index a39e5520a144b..c9f20d2026876 100644
--- a/mlir/lib/Dialect/SCF/Transforms/LoopSpecialization.cpp
+++ b/mlir/lib/Dialect/SCF/Transforms/LoopSpecialization.cpp
@@ -272,7 +272,7 @@ struct ForLoopPeelingPattern : public OpRewritePattern<ForOp> {
"unsigned loops are not supported");
// Do not peel already peeled loops.
- if (forOp->hasAttr(kPeeledLoopLabel))
+ if (forOp->hasDiscardableAttr(kPeeledLoopLabel))
return failure();
scf::ForOp partialIteration;
@@ -288,7 +288,7 @@ struct ForLoopPeelingPattern : public OpRewritePattern<ForOp> {
// loop.
Operation *op = forOp.getOperation();
while ((op = op->getParentOfType<scf::ForOp>())) {
- if (op->hasAttr(kPartialIterationLabel))
+ if (op->hasDiscardableAttr(kPartialIterationLabel))
return failure();
}
}
@@ -300,11 +300,13 @@ struct ForLoopPeelingPattern : public OpRewritePattern<ForOp> {
// Apply label, so that the same loop is not rewritten a second time.
rewriter.modifyOpInPlace(partialIteration, [&]() {
- partialIteration->setAttr(kPeeledLoopLabel, rewriter.getUnitAttr());
- partialIteration->setAttr(kPartialIterationLabel, rewriter.getUnitAttr());
+ partialIteration->setDiscardableAttr(kPeeledLoopLabel,
+ rewriter.getUnitAttr());
+ partialIteration->setDiscardableAttr(kPartialIterationLabel,
+ rewriter.getUnitAttr());
});
rewriter.modifyOpInPlace(forOp, [&]() {
- forOp->setAttr(kPeeledLoopLabel, rewriter.getUnitAttr());
+ forOp->setDiscardableAttr(kPeeledLoopLabel, rewriter.getUnitAttr());
});
return success();
}
@@ -351,8 +353,8 @@ struct ForLoopPeeling : public impl::SCFForLoopPeelingBase<ForLoopPeeling> {
// Drop the markers.
parentOp->walk([](Operation *op) {
- op->removeAttr(kPeeledLoopLabel);
- op->removeAttr(kPartialIterationLabel);
+ op->removeDiscardableAttr(kPeeledLoopLabel);
+ op->removeDiscardableAttr(kPartialIterationLabel);
});
}
};
diff --git a/mlir/lib/Dialect/SCF/Transforms/StructuralTypeConversions.cpp b/mlir/lib/Dialect/SCF/Transforms/StructuralTypeConversions.cpp
index 9468927021495..103c03c62b832 100644
--- a/mlir/lib/Dialect/SCF/Transforms/StructuralTypeConversions.cpp
+++ b/mlir/lib/Dialect/SCF/Transforms/StructuralTypeConversions.cpp
@@ -120,7 +120,7 @@ class ConvertForOpTypes
/*bodyBuilder=*/nullptr, op.getUnsignedCmp());
// Reserve whatever attributes in the original op.
- newOp->setAttrs(op->getAttrs());
+ newOp->setDiscardableAttrs(op->getDiscardableAttrDictionary().getValue());
// We do not need the empty block created by rewriter.
rewriter.eraseBlock(newOp.getBody(0));
@@ -145,7 +145,7 @@ class ConvertIfOpTypes
IfOp newOp =
IfOp::create(rewriter, op.getLoc(), dstTypes,
llvm::getSingleElement(adaptor.getCondition()), true);
- newOp->setAttrs(op->getAttrs());
+ newOp->setDiscardableAttrs(op->getDiscardableAttrDictionary().getValue());
// We do not need the empty blocks created by rewriter.
rewriter.eraseBlock(newOp.elseBlock());
diff --git a/mlir/lib/Dialect/SMT/IR/SMTOps.cpp b/mlir/lib/Dialect/SMT/IR/SMTOps.cpp
index 06ad4ab51b88b..1508f73af5a52 100644
--- a/mlir/lib/Dialect/SMT/IR/SMTOps.cpp
+++ b/mlir/lib/Dialect/SMT/IR/SMTOps.cpp
@@ -117,7 +117,8 @@ ParseResult EqOp::parse(OpAsmParser &parser, OperationState &result) {
void EqOp::print(OpAsmPrinter &printer) {
printer << ' ' << getInputs();
- printer.printOptionalAttrDict(getOperation()->getAttrs());
+ printer.printOptionalAttrDict(
+ getOperation()->getDiscardableAttrDictionary().getValue());
printer << " : " << getInputs().front().getType();
}
@@ -139,7 +140,8 @@ ParseResult DistinctOp::parse(OpAsmParser &parser, OperationState &result) {
void DistinctOp::print(OpAsmPrinter &printer) {
printer << ' ' << getInputs();
- printer.printOptionalAttrDict(getOperation()->getAttrs());
+ printer.printOptionalAttrDict(
+ getOperation()->getDiscardableAttrDictionary().getValue());
printer << " : " << getInputs().front().getType();
}
@@ -258,7 +260,8 @@ ParseResult RepeatOp::parse(OpAsmParser &parser, OperationState &result) {
void RepeatOp::print(OpAsmPrinter &printer) {
printer << " " << getCount() << " times " << getInput();
- printer.printOptionalAttrDict((*this)->getAttrs());
+ printer.printOptionalAttrDict(
+ (*this)->getDiscardableAttrDictionary().getValue());
printer << " : " << getInput().getType();
}
@@ -295,7 +298,8 @@ OpFoldResult IntConstantOp::fold(FoldAdaptor adaptor) {
void IntConstantOp::print(OpAsmPrinter &p) {
p << " " << getValue();
- p.printOptionalAttrDict((*this)->getAttrs(), /*elidedAttrs=*/{"value"});
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue(),
+ /*elidedAttrs=*/{"value"});
}
ParseResult IntConstantOp::parse(OpAsmParser &parser, OperationState &result) {
diff --git a/mlir/lib/Dialect/SPIRV/IR/AtomicOps.cpp b/mlir/lib/Dialect/SPIRV/IR/AtomicOps.cpp
index 7029268177128..2c19829106c4c 100644
--- a/mlir/lib/Dialect/SPIRV/IR/AtomicOps.cpp
+++ b/mlir/lib/Dialect/SPIRV/IR/AtomicOps.cpp
@@ -42,11 +42,7 @@ static LogicalResult verifyAtomicUpdateOp(Operation *op) {
<< stringifyTypeName<ExpectedElementType>()
<< " value, found " << elementType;
- StringAttr semanticsAttrName =
- AtomicOpTy::getSemanticsAttrName(op->getName());
- auto memorySemantics =
- op->getAttrOfType<spirv::MemorySemanticsAttr>(semanticsAttrName)
- .getValue();
+ auto memorySemantics = cast<AtomicOpTy>(op).getSemantics();
if (failed(verifyMemorySemantics(op, memorySemantics))) {
return failure();
}
diff --git a/mlir/lib/Dialect/SPIRV/IR/ControlFlowOps.cpp b/mlir/lib/Dialect/SPIRV/IR/ControlFlowOps.cpp
index 0ad88dee9fe9e..44cee60decdbd 100644
--- a/mlir/lib/Dialect/SPIRV/IR/ControlFlowOps.cpp
+++ b/mlir/lib/Dialect/SPIRV/IR/ControlFlowOps.cpp
@@ -204,11 +204,11 @@ FunctionCallOp::verifySymbolUses(SymbolTableCollection &symbolTable) {
}
CallInterfaceCallable FunctionCallOp::getCallableForCallee() {
- return (*this)->getAttrOfType<SymbolRefAttr>(getCalleeAttrName());
+ return getCalleeAttr();
}
void FunctionCallOp::setCalleeFromCallable(CallInterfaceCallable callee) {
- (*this)->setAttr(getCalleeAttrName(), cast<SymbolRefAttr>(callee));
+ setCalleeAttr(cast<FlatSymbolRefAttr>(cast<SymbolRefAttr>(callee)));
}
Operation::operand_range FunctionCallOp::getArgOperands() {
diff --git a/mlir/lib/Dialect/SPIRV/IR/DotProductOps.cpp b/mlir/lib/Dialect/SPIRV/IR/DotProductOps.cpp
index dada8925b88e1..c76f9475f9938 100644
--- a/mlir/lib/Dialect/SPIRV/IR/DotProductOps.cpp
+++ b/mlir/lib/Dialect/SPIRV/IR/DotProductOps.cpp
@@ -72,11 +72,9 @@ static LogicalResult verifyIntegerDotProduct(Operation *op) {
// ODS enforces that vector 1 and vector 2, and result and the accumulator
// have the same types.
Type factorTy = op->getOperand(0).getType();
- StringAttr packedVectorFormatAttrName =
- IntegerDotProductOpTy::getFormatAttrName(op->getName());
+ auto dotOp = cast<IntegerDotProductOpTy>(op);
if (auto intTy = dyn_cast<IntegerType>(factorTy)) {
- auto packedVectorFormat = dyn_cast_or_null<spirv::PackedVectorFormatAttr>(
- op->getAttr(packedVectorFormatAttrName));
+ spirv::PackedVectorFormatAttr packedVectorFormat = dotOp.getFormatAttr();
if (!packedVectorFormat)
return op->emitOpError("requires Packed Vector Format attribute for "
"integer vector operands");
@@ -90,7 +88,7 @@ static LogicalResult verifyIntegerDotProduct(Operation *op) {
"integer vector operands to be 32-bits wide",
packedVectorFormat.getValue()));
} else {
- if (op->hasAttr(packedVectorFormatAttrName))
+ if (dotOp.getFormatAttr())
return op->emitOpError(llvm::formatv(
"with invalid format attribute for vector operands of type '{0}'",
factorTy));
@@ -132,11 +130,9 @@ getIntegerDotProductCapabilities(Operation *op) {
SmallVector<ArrayRef<spirv::Capability>, 1> capabilities = {dotProductCap};
Type factorTy = op->getOperand(0).getType();
- StringAttr packedVectorFormatAttrName =
- IntegerDotProductOpTy::getFormatAttrName(op->getName());
+ auto dotOp = cast<IntegerDotProductOpTy>(op);
if (auto intTy = dyn_cast<IntegerType>(factorTy)) {
- auto formatAttr = cast<spirv::PackedVectorFormatAttr>(
- op->getAttr(packedVectorFormatAttrName));
+ spirv::PackedVectorFormatAttr formatAttr = dotOp.getFormatAttr();
if (formatAttr.getValue() ==
spirv::PackedVectorFormat::PackedVectorFormat4x8Bit)
capabilities.push_back(dotProductInput4x8BitPackedCap);
diff --git a/mlir/lib/Dialect/SPIRV/IR/GroupOps.cpp b/mlir/lib/Dialect/SPIRV/IR/GroupOps.cpp
index fe6f00e9e5bca..b9dde2b2869a8 100644
--- a/mlir/lib/Dialect/SPIRV/IR/GroupOps.cpp
+++ b/mlir/lib/Dialect/SPIRV/IR/GroupOps.cpp
@@ -22,11 +22,7 @@ namespace mlir::spirv {
template <typename OpTy>
static LogicalResult verifyGroupNonUniformArithmeticOp(Operation *groupOp) {
- GroupOperation operation =
- groupOp
- ->getAttrOfType<GroupOperationAttr>(
- OpTy::getGroupOperationAttrName(groupOp->getName()))
- .getValue();
+ GroupOperation operation = cast<OpTy>(groupOp).getGroupOperation();
if (operation == GroupOperation::ClusteredReduce &&
groupOp->getNumOperands() == 1)
return groupOp->emitOpError("cluster size operand must be provided for "
diff --git a/mlir/lib/Dialect/SPIRV/IR/MemoryOps.cpp b/mlir/lib/Dialect/SPIRV/IR/MemoryOps.cpp
index 602ba932f8838..9fb3519a2e5e2 100644
--- a/mlir/lib/Dialect/SPIRV/IR/MemoryOps.cpp
+++ b/mlir/lib/Dialect/SPIRV/IR/MemoryOps.cpp
@@ -177,12 +177,11 @@ static LogicalResult verifyMemoryAccessAttribute(MemoryOpTy memoryOp) {
// ODS checks for attributes values. Just need to verify that if the
// memory-access attribute is Aligned, then the alignment attribute must be
// present.
- auto *op = memoryOp.getOperation();
- auto memAccessAttr = op->getAttr(memoryOp.getMemoryAccessAttrName());
+ auto memAccessAttr = memoryOp.getMemoryAccessAttr();
if (!memAccessAttr) {
// Alignment attribute shouldn't be present if memory access attribute is
// not present.
- if (op->getAttr(memoryOp.getAlignmentAttrName())) {
+ if (memoryOp.getAlignmentAttr()) {
return memoryOp.emitOpError(
"invalid alignment specification without aligned memory access "
"specification");
@@ -190,7 +189,7 @@ static LogicalResult verifyMemoryAccessAttribute(MemoryOpTy memoryOp) {
return success();
}
- auto memAccess = cast<spirv::MemoryAccessAttr>(memAccessAttr);
+ auto memAccess = memAccessAttr;
if (!memAccess) {
return memoryOp.emitOpError("invalid memory access specifier: ")
@@ -199,11 +198,11 @@ static LogicalResult verifyMemoryAccessAttribute(MemoryOpTy memoryOp) {
if (spirv::bitEnumContainsAll(memAccess.getValue(),
spirv::MemoryAccess::Aligned)) {
- if (!op->getAttr(memoryOp.getAlignmentAttrName())) {
+ if (!memoryOp.getAlignmentAttr()) {
return memoryOp.emitOpError("missing alignment value");
}
} else {
- if (op->getAttr(memoryOp.getAlignmentAttrName())) {
+ if (memoryOp.getAlignmentAttr()) {
return memoryOp.emitOpError(
"invalid alignment specification with non-aligned memory access "
"specification");
@@ -221,12 +220,11 @@ static LogicalResult verifySourceMemoryAccessAttribute(MemoryOpTy memoryOp) {
// ODS checks for attributes values. Just need to verify that if the
// memory-access attribute is Aligned, then the alignment attribute must be
// present.
- auto *op = memoryOp.getOperation();
- auto memAccessAttr = op->getAttr(memoryOp.getSourceMemoryAccessAttrName());
+ auto memAccessAttr = memoryOp.getSourceMemoryAccessAttr();
if (!memAccessAttr) {
// Alignment attribute shouldn't be present if memory access attribute is
// not present.
- if (op->getAttr(memoryOp.getSourceAlignmentAttrName())) {
+ if (memoryOp.getSourceAlignmentAttr()) {
return memoryOp.emitOpError(
"invalid alignment specification without aligned memory access "
"specification");
@@ -234,7 +232,7 @@ static LogicalResult verifySourceMemoryAccessAttribute(MemoryOpTy memoryOp) {
return success();
}
- auto memAccess = cast<spirv::MemoryAccessAttr>(memAccessAttr);
+ auto memAccess = memAccessAttr;
if (!memAccess) {
return memoryOp.emitOpError("invalid memory access specifier: ")
@@ -243,11 +241,11 @@ static LogicalResult verifySourceMemoryAccessAttribute(MemoryOpTy memoryOp) {
if (spirv::bitEnumContainsAll(memAccess.getValue(),
spirv::MemoryAccess::Aligned)) {
- if (!op->getAttr(memoryOp.getSourceAlignmentAttrName())) {
+ if (!memoryOp.getSourceAlignmentAttr()) {
return memoryOp.emitOpError("missing alignment value");
}
} else {
- if (op->getAttr(memoryOp.getSourceAlignmentAttrName())) {
+ if (memoryOp.getSourceAlignmentAttr()) {
return memoryOp.emitOpError(
"invalid alignment specification with non-aligned memory access "
"specification");
@@ -406,7 +404,8 @@ void LoadOp::print(OpAsmPrinter &printer) {
printMemoryAccessAttribute(*this, printer, elidedAttrs);
- printer.printOptionalAttrDict((*this)->getAttrs(), elidedAttrs);
+ printer.printOptionalAttrDict(
+ (*this)->getDiscardableAttrDictionary().getValue(), elidedAttrs);
printer << " : " << getType();
}
@@ -454,7 +453,8 @@ void StoreOp::print(OpAsmPrinter &printer) {
printMemoryAccessAttribute(*this, printer, elidedAttrs);
printer << " : " << getValue().getType();
- printer.printOptionalAttrDict((*this)->getAttrs(), elidedAttrs);
+ printer.printOptionalAttrDict(
+ (*this)->getDiscardableAttrDictionary().getValue(), elidedAttrs);
}
LogicalResult StoreOp::verify() {
@@ -486,7 +486,8 @@ void CopyMemoryOp::print(OpAsmPrinter &printer) {
getSourceMemoryAccess(),
getSourceAlignment());
- printer.printOptionalAttrDict((*this)->getAttrs(), elidedAttrs);
+ printer.printOptionalAttrDict(
+ (*this)->getDiscardableAttrDictionary().getValue(), elidedAttrs);
Type pointeeType =
cast<spirv::PointerType>(getTarget().getType()).getPointeeType();
@@ -672,7 +673,7 @@ LogicalResult VariableOp::verify() {
}
auto getDecorationAttr = [op = getOperation()](spirv::Decoration decoration) {
- return op->getAttr(spirv::getDecorationString(decoration));
+ return op->getDiscardableAttr(spirv::getDecorationString(decoration));
};
// TODO: generate these strings using ODS.
diff --git a/mlir/lib/Dialect/SPIRV/IR/SPIRVCanonicalization.cpp b/mlir/lib/Dialect/SPIRV/IR/SPIRVCanonicalization.cpp
index acc38dffe4a2b..d73a87fcd72eb 100644
--- a/mlir/lib/Dialect/SPIRV/IR/SPIRVCanonicalization.cpp
+++ b/mlir/lib/Dialect/SPIRV/IR/SPIRVCanonicalization.cpp
@@ -1284,14 +1284,15 @@ struct ConvertSelectionOpToSelect final : OpRewritePattern<spirv::SelectionOp> {
Value trueValue = getSrcValue(trueBlock);
Value falseValue = getSrcValue(falseBlock);
Value ptrValue = getDstPtr(trueBlock);
- auto storeOpAttributes =
- cast<spirv::StoreOp>(trueBlock->front())->getAttrs();
+ auto storeOp = cast<spirv::StoreOp>(trueBlock->front());
auto selectOp = spirv::SelectOp::create(
rewriter, selectionOp.getLoc(), trueValue.getType(),
brConditionalOp.getCondition(), trueValue, falseValue);
- spirv::StoreOp::create(rewriter, selectOp.getLoc(), ptrValue,
- selectOp.getResult(), storeOpAttributes);
+ auto newStore = spirv::StoreOp::create(
+ rewriter, selectOp.getLoc(), ptrValue, selectOp.getResult(),
+ storeOp.getMemoryAccessAttr(), storeOp.getAlignmentAttr());
+ newStore->setDiscardableAttrs(storeOp->getDiscardableAttrDictionary());
// `spirv.mlir.selection` is not needed anymore.
rewriter.eraseOp(op);
diff --git a/mlir/lib/Dialect/SPIRV/IR/SPIRVOps.cpp b/mlir/lib/Dialect/SPIRV/IR/SPIRVOps.cpp
index fed2764080b01..907e671c43b79 100644
--- a/mlir/lib/Dialect/SPIRV/IR/SPIRVOps.cpp
+++ b/mlir/lib/Dialect/SPIRV/IR/SPIRVOps.cpp
@@ -109,7 +109,7 @@ LogicalResult spirv::verifyPhysicalStorageBufferDecorations(Operation *op,
return success();
auto getDecorationAttr = [op](spirv::Decoration decoration) {
- return op->getAttr(spirv::getDecorationString(decoration));
+ return op->getDiscardableAttr(spirv::getDecorationString(decoration));
};
bool hasAliasedPtr =
@@ -132,13 +132,17 @@ LogicalResult spirv::verifyPhysicalStorageBufferDecorations(Operation *op,
void spirv::printVariableDecorations(Operation *op, OpAsmPrinter &printer,
SmallVectorImpl<StringRef> &elidedAttrs) {
+ NamedAttrList attrs(op->getDiscardableAttrDictionary().getValue());
+ op->getName().populateInherentAttrs(op, attrs);
+
// Print optional descriptor binding
auto descriptorSetName = llvm::convertToSnakeFromCamelCase(
stringifyDecoration(spirv::Decoration::DescriptorSet));
auto bindingName = llvm::convertToSnakeFromCamelCase(
stringifyDecoration(spirv::Decoration::Binding));
- auto descriptorSet = op->getAttrOfType<IntegerAttr>(descriptorSetName);
- auto binding = op->getAttrOfType<IntegerAttr>(bindingName);
+ auto descriptorSet =
+ dyn_cast_or_null<IntegerAttr>(attrs.get(descriptorSetName));
+ auto binding = dyn_cast_or_null<IntegerAttr>(attrs.get(bindingName));
if (descriptorSet && binding) {
elidedAttrs.push_back(descriptorSetName);
elidedAttrs.push_back(bindingName);
@@ -149,12 +153,12 @@ void spirv::printVariableDecorations(Operation *op, OpAsmPrinter &printer,
// Print BuiltIn attribute if present
auto builtInName = llvm::convertToSnakeFromCamelCase(
stringifyDecoration(spirv::Decoration::BuiltIn));
- if (auto builtin = op->getAttrOfType<StringAttr>(builtInName)) {
+ if (auto builtin = dyn_cast_or_null<StringAttr>(attrs.get(builtInName))) {
printer << " " << builtInName << "(\"" << builtin.getValue() << "\")";
elidedAttrs.push_back(builtInName);
}
- printer.printOptionalAttrDict(op->getAttrs(), elidedAttrs);
+ printer.printOptionalAttrDict(attrs, elidedAttrs);
}
static ParseResult parseOneResultSameOperandTypeOp(OpAsmParser &parser,
@@ -200,7 +204,7 @@ static void printOneResultOp(Operation *op, OpAsmPrinter &p) {
p << ' ';
p.printOperands(op->getOperands());
- p.printOptionalAttrDict(op->getAttrs());
+ p.printOptionalAttrDict(op->getDiscardableAttrDictionary().getValue());
// Now we can output only one type for all operands and the result.
p << " : " << resultType;
}
@@ -330,7 +334,7 @@ static ParseResult parseArithmeticExtendedBinaryOp(OpAsmParser &parser,
static void printArithmeticExtendedBinaryOp(Operation *op,
OpAsmPrinter &printer) {
printer << ' ';
- printer.printOptionalAttrDict(op->getAttrs());
+ printer.printOptionalAttrDict(op->getDiscardableAttrDictionary().getValue());
printer.printOperands(op->getOperands());
printer << " : " << op->getResultTypes().front();
}
@@ -1498,8 +1502,7 @@ LogicalResult spirv::GlobalVariableOp::verify() {
}
}
- if (auto init = (*this)->getAttrOfType<FlatSymbolRefAttr>(
- this->getInitializerAttrName())) {
+ if (FlatSymbolRefAttr init = getInitializerAttr()) {
Operation *initOp = SymbolTable::lookupNearestSymbolFrom(
(*this)->getParentOp(), init.getAttr());
// TODO: Currently only variable initialization with specialization
@@ -1753,7 +1756,8 @@ void spirv::ModuleOp::print(OpAsmPrinter &printer) {
elidedAttrs.push_back(spirv::ModuleOp::getVCETripleAttrName());
}
- printer.printOptionalAttrDictWithKeyword((*this)->getAttrs(), elidedAttrs);
+ printer.printOptionalAttrDictWithKeyword(
+ (*this)->getDiscardableAttrDictionary().getValue(), elidedAttrs);
printer << ' ';
printer.printRegion(getRegion());
}
@@ -1889,13 +1893,15 @@ ParseResult spirv::SpecConstantOp::parse(OpAsmParser &parser,
void spirv::SpecConstantOp::print(OpAsmPrinter &printer) {
printer << ' ';
printer.printSymbolName(getSymName());
- if (auto specID = (*this)->getAttrOfType<IntegerAttr>(kSpecIdAttrName))
+ if (auto specID =
+ (*this)->getDiscardableAttrOfType<IntegerAttr>(kSpecIdAttrName))
printer << ' ' << kSpecIdAttrName << '(' << specID.getInt() << ')';
printer << " = " << getDefaultValue();
}
LogicalResult spirv::SpecConstantOp::verify() {
- if (auto specID = (*this)->getAttrOfType<IntegerAttr>(kSpecIdAttrName))
+ if (auto specID =
+ (*this)->getDiscardableAttrOfType<IntegerAttr>(kSpecIdAttrName))
if (specID.getValue().isNegative())
return emitOpError("SpecId cannot be negative");
diff --git a/mlir/lib/Dialect/SPIRV/IR/TargetAndABI.cpp b/mlir/lib/Dialect/SPIRV/IR/TargetAndABI.cpp
index c604fd087ba46..4761a9a3e21aa 100644
--- a/mlir/lib/Dialect/SPIRV/IR/TargetAndABI.cpp
+++ b/mlir/lib/Dialect/SPIRV/IR/TargetAndABI.cpp
@@ -134,7 +134,7 @@ spirv::EntryPointABIAttr spirv::lookupEntryPointABI(Operation *op) {
if (!op)
return {};
- if (auto attr = op->getAttrOfType<spirv::EntryPointABIAttr>(
+ if (auto attr = op->getDiscardableAttrOfType<spirv::EntryPointABIAttr>(
spirv::getEntryPointABIAttrName()))
return attr;
@@ -189,7 +189,7 @@ spirv::TargetEnvAttr spirv::lookupTargetEnv(Operation *op) {
if (!op)
break;
- if (auto attr = op->getAttrOfType<spirv::TargetEnvAttr>(
+ if (auto attr = op->getDiscardableAttrOfType<spirv::TargetEnvAttr>(
spirv::getTargetEnvAttrName()))
return attr;
diff --git a/mlir/lib/Dialect/SPIRV/Linking/ModuleCombiner/ModuleCombiner.cpp b/mlir/lib/Dialect/SPIRV/Linking/ModuleCombiner/ModuleCombiner.cpp
index 2b9c7296830dc..f4467afa1a32c 100644
--- a/mlir/lib/Dialect/SPIRV/Linking/ModuleCombiner/ModuleCombiner.cpp
+++ b/mlir/lib/Dialect/SPIRV/Linking/ModuleCombiner/ModuleCombiner.cpp
@@ -70,10 +70,11 @@ static LogicalResult updateSymbolAndAllUses(SymbolOpInterface op,
/// variable and a spec constant as duplicates because their descriptor set +
/// binding and spec_id, respectively, happen to hash to the same value.
static llvm::hash_code computeHash(SymbolOpInterface symbolOp) {
- auto range =
- llvm::make_filter_range(symbolOp->getAttrs(), [](NamedAttribute attr) {
- return attr.getName() != SymbolTable::getSymbolAttrName();
- });
+ NamedAttrList attrs(symbolOp->getDiscardableAttrDictionary());
+ symbolOp->getName().populateInherentAttrs(symbolOp, attrs);
+ auto range = llvm::make_filter_range(attrs, [](NamedAttribute attr) {
+ return attr.getName() != SymbolTable::getSymbolAttrName();
+ });
return llvm::hash_combine(symbolOp->getName(),
llvm::hash_combine_range(range));
diff --git a/mlir/lib/Dialect/SPIRV/Transforms/DecorateCompositeTypeLayoutPass.cpp b/mlir/lib/Dialect/SPIRV/Transforms/DecorateCompositeTypeLayoutPass.cpp
index a517ca946f3a4..6581f0a822a82 100644
--- a/mlir/lib/Dialect/SPIRV/Transforms/DecorateCompositeTypeLayoutPass.cpp
+++ b/mlir/lib/Dialect/SPIRV/Transforms/DecorateCompositeTypeLayoutPass.cpp
@@ -40,7 +40,8 @@ class SPIRVGlobalVariableOpLayoutInfoDecoration
LogicalResult matchAndRewrite(spirv::GlobalVariableOp op,
PatternRewriter &rewriter) const override {
- SmallVector<NamedAttribute, 4> globalVarAttrs;
+ NamedAttrList globalVarAttrs(op->getDiscardableAttrDictionary());
+ op->getName().populateInherentAttrs(op, globalVarAttrs);
auto ptrType = cast<spirv::PointerType>(op.getType());
auto pointeeType = cast<spirv::StructType>(ptrType.getPointeeType());
@@ -53,12 +54,8 @@ class SPIRVGlobalVariableOpLayoutInfoDecoration
auto decoratedType =
spirv::PointerType::get(structType, ptrType.getStorageClass());
- // Save all named attributes except "type" attribute.
- for (const auto &attr : op->getAttrs()) {
- if (attr.getName() == "type")
- continue;
- globalVarAttrs.push_back(attr);
- }
+ // The new type is passed through the operation-specific builder below.
+ globalVarAttrs.erase("type");
rewriter.replaceOpWithNewOp<spirv::GlobalVariableOp>(
op, TypeAttr::get(decoratedType), globalVarAttrs);
diff --git a/mlir/lib/Dialect/SPIRV/Transforms/LowerABIAttributesPass.cpp b/mlir/lib/Dialect/SPIRV/Transforms/LowerABIAttributesPass.cpp
index b262e6b5d7f75..3b849c5d3ae11 100644
--- a/mlir/lib/Dialect/SPIRV/Transforms/LowerABIAttributesPass.cpp
+++ b/mlir/lib/Dialect/SPIRV/Transforms/LowerABIAttributesPass.cpp
@@ -158,7 +158,8 @@ static LogicalResult lowerEntryPointABIAttr(spirv::FuncOp funcOp,
OpBuilder &builder) {
auto entryPointAttrName = spirv::getEntryPointABIAttrName();
auto entryPointAttr =
- funcOp->getAttrOfType<spirv::EntryPointABIAttr>(entryPointAttrName);
+ funcOp->getDiscardableAttrOfType<spirv::EntryPointABIAttr>(
+ entryPointAttrName);
if (!entryPointAttr) {
return failure();
}
@@ -228,9 +229,9 @@ static LogicalResult lowerEntryPointABIAttr(spirv::FuncOp funcOp,
}
if (entryPointAttr.getWorkgroupSize() || entryPointAttr.getSubgroupSize() ||
entryPointAttr.getTargetWidth())
- funcOp->setAttr(entryPointAttrName, entryPointAttr);
+ funcOp->setDiscardableAttr(entryPointAttrName, entryPointAttr);
else
- funcOp->removeAttr(entryPointAttrName);
+ funcOp->removeDiscardableAttr(entryPointAttrName);
return success();
}
@@ -277,7 +278,7 @@ class LowerABIAttributesPass final
LogicalResult ProcessInterfaceVarABI::matchAndRewrite(
spirv::FuncOp funcOp, OpAdaptor adaptor,
ConversionPatternRewriter &rewriter) const {
- if (!funcOp->getAttrOfType<spirv::EntryPointABIAttr>(
+ if (!funcOp->getDiscardableAttrOfType<spirv::EntryPointABIAttr>(
spirv::getEntryPointABIAttrName())) {
// TODO: Non-entry point functions are not handled.
return failure();
@@ -458,7 +459,8 @@ void LowerABIAttributesPass::runOnOperation() {
SmallVector<spirv::FuncOp, 1> entryPointFns;
auto entryPointAttrName = spirv::getEntryPointABIAttrName();
module.walk([&](spirv::FuncOp funcOp) {
- if (funcOp->getAttrOfType<spirv::EntryPointABIAttr>(entryPointAttrName)) {
+ if (funcOp->getDiscardableAttrOfType<spirv::EntryPointABIAttr>(
+ entryPointAttrName)) {
entryPointFns.push_back(funcOp);
}
});
diff --git a/mlir/lib/Dialect/SPIRV/Transforms/SPIRVConversion.cpp b/mlir/lib/Dialect/SPIRV/Transforms/SPIRVConversion.cpp
index 1c8a22fb35639..a1d714e90ce4e 100644
--- a/mlir/lib/Dialect/SPIRV/Transforms/SPIRVConversion.cpp
+++ b/mlir/lib/Dialect/SPIRV/Transforms/SPIRVConversion.cpp
@@ -868,9 +868,7 @@ static spirv::GlobalVariableOp getBuiltinVariable(Block &body,
// Look through all global variables in the given `body` block and check if
// there is a spirv.GlobalVariable that has the same `builtin` attribute.
for (auto varOp : body.getOps<spirv::GlobalVariableOp>()) {
- if (auto builtinAttr = varOp->getAttrOfType<StringAttr>(
- spirv::SPIRVDialect::getAttributeName(
- spirv::Decoration::BuiltIn))) {
+ if (StringAttr builtinAttr = varOp.getBuiltInAttr()) {
auto varBuiltIn = spirv::symbolizeBuiltIn(builtinAttr.getValue());
if (varBuiltIn == builtin) {
return varOp;
@@ -1023,11 +1021,19 @@ struct FuncOpConversion final : OpConversionPattern<func::FuncOp> {
resultType ? TypeRange(resultType)
: TypeRange()));
+ newFuncOp.setArgAttrsAttr(funcOp.getArgAttrsAttr());
+ newFuncOp.setResAttrsAttr(funcOp.getResAttrsAttr());
+ cast<SymbolOpInterface>(newFuncOp.getOperation())
+ .setVisibility(
+ cast<SymbolOpInterface>(funcOp.getOperation()).getVisibility());
+
// Copy over all attributes other than the function name and type.
- for (NamedAttribute namedAttr : funcOp->getAttrs()) {
+ for (NamedAttribute namedAttr :
+ funcOp->getDiscardableAttrDictionary().getValue()) {
if (namedAttr.getName() != funcOp.getFunctionTypeAttrName() &&
namedAttr.getName() != SymbolTable::getSymbolAttrName())
- newFuncOp->setAttr(namedAttr.getName(), namedAttr.getValue());
+ newFuncOp->setDiscardableAttr(namedAttr.getName(),
+ namedAttr.getValue());
}
rewriter.inlineRegionBefore(funcOp.getBody(), newFuncOp.getBody(),
@@ -1289,11 +1295,13 @@ static void addNoWrapDecorations(Operation *op,
spirv::LinearizedIndexNoWrapFlags flags,
OpBuilder &builder) {
if (flags.noSignedWrap)
- op->setAttr(spirv::getDecorationString(spirv::Decoration::NoSignedWrap),
- builder.getUnitAttr());
+ op->setDiscardableAttr(
+ spirv::getDecorationString(spirv::Decoration::NoSignedWrap),
+ builder.getUnitAttr());
if (flags.noUnsignedWrap)
- op->setAttr(spirv::getDecorationString(spirv::Decoration::NoUnsignedWrap),
- builder.getUnitAttr());
+ op->setDiscardableAttr(
+ spirv::getDecorationString(spirv::Decoration::NoUnsignedWrap),
+ builder.getUnitAttr());
}
static std::optional<uint64_t> getMaxLinearizedIndex(ArrayRef<int64_t> shape,
diff --git a/mlir/lib/Dialect/SPIRV/Transforms/UnifyAliasedResourcePass.cpp b/mlir/lib/Dialect/SPIRV/Transforms/UnifyAliasedResourcePass.cpp
index ecfce68db036b..99eaa3f0b1665 100644
--- a/mlir/lib/Dialect/SPIRV/Transforms/UnifyAliasedResourcePass.cpp
+++ b/mlir/lib/Dialect/SPIRV/Transforms/UnifyAliasedResourcePass.cpp
@@ -47,7 +47,7 @@ using AliasedResourceMap =
static AliasedResourceMap collectAliasedResources(spirv::ModuleOp moduleOp) {
AliasedResourceMap aliasedResources;
moduleOp->walk([&aliasedResources](spirv::GlobalVariableOp varOp) {
- if (varOp->getAttrOfType<UnitAttr>("aliased")) {
+ if (varOp->getDiscardableAttrOfType<UnitAttr>("aliased")) {
std::optional<uint32_t> set = varOp.getDescriptorSet();
std::optional<uint32_t> binding = varOp.getBinding();
if (set && binding)
@@ -559,8 +559,10 @@ struct ConvertStore : public ConvertAliasResource<spirv::StoreOp> {
Value value = adaptor.getValue();
if (srcElemType != dstElemType)
value = spirv::BitcastOp::create(rewriter, loc, dstElemType, value);
- rewriter.replaceOpWithNewOp<spirv::StoreOp>(storeOp, adaptor.getPtr(),
- value, storeOp->getAttrs());
+ auto newStore = rewriter.replaceOpWithNewOp<spirv::StoreOp>(
+ storeOp, adaptor.getPtr(), value, storeOp.getMemoryAccessAttr(),
+ storeOp.getAlignmentAttr());
+ newStore->setDiscardableAttrs(storeOp->getDiscardableAttrDictionary());
return success();
}
};
@@ -626,7 +628,7 @@ void UnifyAliasedResourcePass::runOnOperation() {
for (const auto &dr : resourceMap) {
const auto &resources = dr.second;
if (resources.size() == 1)
- resources.front()->removeAttr("aliased");
+ resources.front()->removeDiscardableAttr("aliased");
}
}
} // namespace
diff --git a/mlir/lib/Dialect/SPIRV/Transforms/UpdateVCEPass.cpp b/mlir/lib/Dialect/SPIRV/Transforms/UpdateVCEPass.cpp
index 68e41838a0952..be8fa3a0b81c3 100644
--- a/mlir/lib/Dialect/SPIRV/Transforms/UpdateVCEPass.cpp
+++ b/mlir/lib/Dialect/SPIRV/Transforms/UpdateVCEPass.cpp
@@ -259,5 +259,5 @@ void UpdateVCEPass::runOnOperation() {
auto triple = spirv::VerCapExtAttr::get(
deducedVersion, deducedCapabilities.getArrayRef(),
deducedExtensions.getArrayRef(), &getContext());
- module->setAttr(spirv::ModuleOp::getVCETripleAttrName(), triple);
+ module.setVceTripleAttr(triple);
}
diff --git a/mlir/lib/Dialect/Shape/IR/Shape.cpp b/mlir/lib/Dialect/Shape/IR/Shape.cpp
index 0bb130eac1bff..6b84acb992590 100644
--- a/mlir/lib/Dialect/Shape/IR/Shape.cpp
+++ b/mlir/lib/Dialect/Shape/IR/Shape.cpp
@@ -269,7 +269,7 @@ void AssumingOp::print(OpAsmPrinter &p) {
p.printRegion(getDoRegion(),
/*printEntryBlockArgs=*/false,
/*printBlockTerminators=*/yieldsResults);
- p.printOptionalAttrDict((*this)->getAttrs());
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue());
}
namespace {
@@ -593,8 +593,9 @@ struct RemoveDuplicateOperandsPattern : public OpRewritePattern<OpTy> {
// Reduce op to equivalent with unique operands.
if (unique.size() < op.getNumOperands()) {
- rewriter.replaceOpWithNewOp<OpTy>(op, op->getResultTypes(),
- unique.takeVector(), op->getAttrs());
+ rewriter.replaceOpWithNewOp<OpTy>(
+ op, op->getResultTypes(), unique.takeVector(),
+ op->getDiscardableAttrDictionary().getValue());
return success();
}
@@ -716,8 +717,9 @@ struct RemoveEmptyShapeOperandsPattern : public OpRewritePattern<OpTy> {
// Reduce op to equivalent without empty shape operands.
if (newOperands.size() < op.getNumOperands()) {
- rewriter.replaceOpWithNewOp<OpTy>(op, op->getResultTypes(), newOperands,
- op->getAttrs());
+ rewriter.replaceOpWithNewOp<OpTy>(
+ op, op->getResultTypes(), newOperands,
+ op->getDiscardableAttrDictionary().getValue());
return success();
}
@@ -891,7 +893,8 @@ OpFoldResult ConcatOp::fold(FoldAdaptor adaptor) {
void ConstShapeOp::print(OpAsmPrinter &p) {
p << " ";
- p.printOptionalAttrDict((*this)->getAttrs(), /*elidedAttrs=*/{"shape"});
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue(),
+ /*elidedAttrs=*/{"shape"});
p << "[";
interleaveComma(getShape().getValues<int64_t>(), p);
p << "] : ";
@@ -1262,7 +1265,8 @@ void FunctionLibraryOp::print(OpAsmPrinter &p) {
p << ' ';
p.printSymbolName(getName());
p.printOptionalAttrDictWithKeyword(
- (*this)->getAttrs(), {mlir::SymbolTable::getSymbolAttrName(), "mapping"});
+ (*this)->getDiscardableAttrDictionary().getValue(),
+ {mlir::SymbolTable::getSymbolAttrName(), "mapping"});
p << ' ';
p.printRegion(getRegion(), /*printEntryBlockArgs=*/false,
/*printBlockTerminators=*/false);
@@ -2055,7 +2059,7 @@ void ReduceOp::print(OpAsmPrinter &p) {
p.printOptionalArrowTypeList(getResultTypes());
p << ' ';
p.printRegion(getRegion());
- p.printOptionalAttrDict((*this)->getAttrs());
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue());
}
#define GET_OP_CLASSES
diff --git a/mlir/lib/Dialect/SparseTensor/IR/SparseTensorDialect.cpp b/mlir/lib/Dialect/SparseTensor/IR/SparseTensorDialect.cpp
index 6c26a31bf88a0..781189210ecd3 100644
--- a/mlir/lib/Dialect/SparseTensor/IR/SparseTensorDialect.cpp
+++ b/mlir/lib/Dialect/SparseTensor/IR/SparseTensorDialect.cpp
@@ -1799,7 +1799,7 @@ static LogicalResult verifyNumBlockArgs(T *op, Region ®ion,
}
LogicalResult BinaryOp::verify() {
- NamedAttrList attrs = (*this)->getAttrs();
+ NamedAttrList attrs = (*this)->getDiscardableAttrDictionary().getValue();
Type leftType = getX().getType();
Type rightType = getY().getType();
Type outputType = getOutput().getType();
diff --git a/mlir/lib/Dialect/SparseTensor/Transforms/SparseAssembler.cpp b/mlir/lib/Dialect/SparseTensor/Transforms/SparseAssembler.cpp
index 4428339b38c5d..a5c74f6941554 100644
--- a/mlir/lib/Dialect/SparseTensor/Transforms/SparseAssembler.cpp
+++ b/mlir/lib/Dialect/SparseTensor/Transforms/SparseAssembler.cpp
@@ -233,12 +233,13 @@ struct SparseFuncAssembler : public OpRewritePattern<func::FuncOp> {
func::ReturnOp::create(rewriter, loc, outputs);
// Finally, migrate a potential c-interface property.
- if (funcOp->getAttrOfType<UnitAttr>(
+ if (funcOp->getDiscardableAttrOfType<UnitAttr>(
LLVM::LLVMDialect::getEmitCWrapperAttrName())) {
- func->setAttr(LLVM::LLVMDialect::getEmitCWrapperAttrName(),
- UnitAttr::get(context));
+ func->setDiscardableAttr(LLVM::LLVMDialect::getEmitCWrapperAttrName(),
+ UnitAttr::get(context));
rewriter.modifyOpInPlace(funcOp, [&]() {
- funcOp->removeAttr(LLVM::LLVMDialect::getEmitCWrapperAttrName());
+ funcOp->removeDiscardableAttr(
+ LLVM::LLVMDialect::getEmitCWrapperAttrName());
});
}
return success();
diff --git a/mlir/lib/Dialect/SparseTensor/Transforms/SparseGPUCodegen.cpp b/mlir/lib/Dialect/SparseTensor/Transforms/SparseGPUCodegen.cpp
index 14418b09f8354..8243bf9317c22 100644
--- a/mlir/lib/Dialect/SparseTensor/Transforms/SparseGPUCodegen.cpp
+++ b/mlir/lib/Dialect/SparseTensor/Transforms/SparseGPUCodegen.cpp
@@ -50,8 +50,8 @@ enum class CuSparseFormat {
/// Marks the given top module as a GPU container module.
static void markAsGPUContainer(ModuleOp topModule) {
- topModule->setAttr(gpu::GPUDialect::getContainerModuleAttrName(),
- UnitAttr::get(topModule->getContext()));
+ topModule->setDiscardableAttr(gpu::GPUDialect::getContainerModuleAttrName(),
+ UnitAttr::get(topModule->getContext()));
}
/// Constructs a new GPU module (for GPU kernels) inside the given top module,
@@ -1189,7 +1189,8 @@ struct ForallRewriter : public OpRewritePattern<scf::ParallelOp> {
// of the form
// forall (i = 0; i < N; i++)
// so that cyclic scheduling over the threads is easy.
- if (!forallOp->hasAttr(LoopEmitter::getLoopEmitterLoopAttrName()) ||
+ if (!forallOp->hasDiscardableAttr(
+ LoopEmitter::getLoopEmitterLoopAttrName()) ||
forallOp.getNumReductions() != 0 || forallOp.getNumLoops() != 1 ||
!matchPattern(forallOp.getLowerBound()[0], m_Zero()) ||
!matchPattern(forallOp.getStep()[0], m_One()))
diff --git a/mlir/lib/Dialect/SparseTensor/Transforms/SparseReinterpretMap.cpp b/mlir/lib/Dialect/SparseTensor/Transforms/SparseReinterpretMap.cpp
index 85f64648c212e..1e2648957a34a 100644
--- a/mlir/lib/Dialect/SparseTensor/Transforms/SparseReinterpretMap.cpp
+++ b/mlir/lib/Dialect/SparseTensor/Transforms/SparseReinterpretMap.cpp
@@ -420,7 +420,7 @@ struct GenericOpScheduler : public OpRewritePattern<linalg::GenericOp> {
}
const StringRef sorted = "sorted";
- if (linalgOp->hasAttr(sorted))
+ if (linalgOp->hasDiscardableAttr(sorted))
return failure();
// Pass strategy to IterationGraphSorter.
@@ -462,7 +462,7 @@ struct GenericOpScheduler : public OpRewritePattern<linalg::GenericOp> {
// Marks the GenericOp to avoid recursive matching.
rewriter.modifyOpInPlace(linalgOp, [&]() {
- linalgOp->setAttr(sorted, rewriter.getBoolAttr(true));
+ linalgOp->setDiscardableAttr(sorted, rewriter.getBoolAttr(true));
});
// Already sorted.
diff --git a/mlir/lib/Dialect/SparseTensor/Transforms/SparseVectorization.cpp b/mlir/lib/Dialect/SparseTensor/Transforms/SparseVectorization.cpp
index c60ca523d81f3..548eef578c4ff 100644
--- a/mlir/lib/Dialect/SparseTensor/Transforms/SparseVectorization.cpp
+++ b/mlir/lib/Dialect/SparseTensor/Transforms/SparseVectorization.cpp
@@ -585,9 +585,9 @@ static bool vectorizeStmt(PatternRewriter &rewriter, scf::ForOp forOp, VL vl,
scf::ForOp::create(rewriter, loc, forOp.getLowerBound(),
forOp.getUpperBound(), step, vinit,
/*bodyBuilder=*/nullptr, forOp.getUnsignedCmp());
- forOpNew->setAttr(
+ forOpNew->setDiscardableAttr(
LoopEmitter::getLoopEmitterLoopAttrName(),
- forOp->getAttr(LoopEmitter::getLoopEmitterLoopAttrName()));
+ forOp->getDiscardableAttr(LoopEmitter::getLoopEmitterLoopAttrName()));
rewriter.setInsertionPointToStart(forOpNew.getBody());
} else {
rewriter.modifyOpInPlace(forOp, [&]() { forOp.setStep(step); });
@@ -666,7 +666,7 @@ struct ForOpRewriter : public OpRewritePattern<scf::ForOp> {
// sparsifier, which means no data dependence analysis is required,
// and its loop-body is very restricted in form.
if (!op.getRegion().hasOneBlock() || !isOneInteger(op.getStep()) ||
- !op->hasAttr(LoopEmitter::getLoopEmitterLoopAttrName()))
+ !op->hasDiscardableAttr(LoopEmitter::getLoopEmitterLoopAttrName()))
return failure();
// Analyze (!codegen) and rewrite (codegen) loop-body.
if (vectorizeStmt(rewriter, op, vl, /*codegen=*/false) &&
@@ -683,7 +683,8 @@ static LogicalResult cleanReducChain(PatternRewriter &rewriter, Operation *op,
Value inp) {
if (auto redOp = inp.getDefiningOp<vector::ReductionOp>()) {
if (auto forOp = redOp.getVector().getDefiningOp<scf::ForOp>()) {
- if (forOp->hasAttr(LoopEmitter::getLoopEmitterLoopAttrName())) {
+ if (forOp->hasDiscardableAttr(
+ LoopEmitter::getLoopEmitterLoopAttrName())) {
rewriter.replaceOp(op, redOp.getVector());
return success();
}
diff --git a/mlir/lib/Dialect/SparseTensor/Transforms/Sparsification.cpp b/mlir/lib/Dialect/SparseTensor/Transforms/Sparsification.cpp
index 6004ab26f4663..860ea68029c3a 100644
--- a/mlir/lib/Dialect/SparseTensor/Transforms/Sparsification.cpp
+++ b/mlir/lib/Dialect/SparseTensor/Transforms/Sparsification.cpp
@@ -876,7 +876,7 @@ static void finalizeWhileOp(CodegenEnv &env, OpBuilder &builder,
while (auto ifOp = dyn_cast_or_null<scf::IfOp>(
builder.getInsertionBlock()->getParentOp())) {
// Break on IfOp for slicing filtering.
- if (ifOp->getAttr(LoopEmitter::getLoopEmitterLoopAttrName()) ==
+ if (ifOp->getDiscardableAttr(LoopEmitter::getLoopEmitterLoopAttrName()) ==
StringAttr::get(ifOp->getContext(), "slice"))
break;
@@ -1411,7 +1411,7 @@ struct GenericOpSparsifier : public OpRewritePattern<linalg::GenericOp> {
return failure();
// Only accept scheduled loops.
- if (!op->hasAttr("sorted")) {
+ if (!op->hasDiscardableAttr("sorted")) {
return rewriter.notifyMatchFailure(
op, "Loops not yet scheduled, try run --sparse-reinterpret-map "
"before sparsification.");
diff --git a/mlir/lib/Dialect/SparseTensor/Transforms/Utils/CodegenUtils.cpp b/mlir/lib/Dialect/SparseTensor/Transforms/Utils/CodegenUtils.cpp
index 3c6a905ebb696..1d9bf51f8d25a 100644
--- a/mlir/lib/Dialect/SparseTensor/Transforms/Utils/CodegenUtils.cpp
+++ b/mlir/lib/Dialect/SparseTensor/Transforms/Utils/CodegenUtils.cpp
@@ -332,8 +332,8 @@ FlatSymbolRefAttr mlir::sparse_tensor::getFunc(ModuleOp module, StringRef name,
FunctionType::get(context, operands.getTypes(), resultType));
func.setPrivate();
if (static_cast<bool>(emitCInterface))
- func->setAttr(LLVM::LLVMDialect::getEmitCWrapperAttrName(),
- UnitAttr::get(context));
+ func->setDiscardableAttr(LLVM::LLVMDialect::getEmitCWrapperAttrName(),
+ UnitAttr::get(context));
}
return result;
}
diff --git a/mlir/lib/Dialect/SparseTensor/Transforms/Utils/LoopEmitter.h b/mlir/lib/Dialect/SparseTensor/Transforms/Utils/LoopEmitter.h
index 355804bcc33fb..a47062987b4b6 100644
--- a/mlir/lib/Dialect/SparseTensor/Transforms/Utils/LoopEmitter.h
+++ b/mlir/lib/Dialect/SparseTensor/Transforms/Utils/LoopEmitter.h
@@ -257,7 +257,8 @@ class LoopEmitter {
: tidLvls(tidLvls), loop(loop), userCodeBlock(userBlock), iv(iv) {
// Attached a special tag to loop emitter generated loop.
if (loopTag)
- loop->setAttr(LoopEmitter::getLoopEmitterLoopAttrName(), loopTag);
+ loop->setDiscardableAttr(LoopEmitter::getLoopEmitterLoopAttrName(),
+ loopTag);
}
// The set of <tensor, lvl>, with *only* trivial index expressions, that are
// used as the condition for the generated loop. Extra information is
diff --git a/mlir/lib/Dialect/Tensor/Transforms/ScalarizeFunctionResult.cpp b/mlir/lib/Dialect/Tensor/Transforms/ScalarizeFunctionResult.cpp
index 60385d0c8b50d..5ed42f278645e 100644
--- a/mlir/lib/Dialect/Tensor/Transforms/ScalarizeFunctionResult.cpp
+++ b/mlir/lib/Dialect/Tensor/Transforms/ScalarizeFunctionResult.cpp
@@ -228,7 +228,8 @@ static void rewriteScalarizableFunction(func::FuncOp func,
rewriter.setInsertionPoint(directCall);
func::CallOp newDirectCall = func::CallOp::create(
rewriter, directCall.getLoc(), func, directCall.getOperands());
- newDirectCall->setAttrs(directCall->getAttrs());
+ newDirectCall->setDiscardableAttrs(
+ directCall->getDiscardableAttrDictionary().getValue());
if (!directCall.getResult(0).use_empty()) {
Value wrappedResult = tensor::FromElementsOp::create(
diff --git a/mlir/lib/Dialect/Tosa/IR/TargetEnv.cpp b/mlir/lib/Dialect/Tosa/IR/TargetEnv.cpp
index 56e4901811dcb..246cb058a91ae 100644
--- a/mlir/lib/Dialect/Tosa/IR/TargetEnv.cpp
+++ b/mlir/lib/Dialect/Tosa/IR/TargetEnv.cpp
@@ -182,7 +182,8 @@ TargetEnvAttr lookupTargetEnv(Operation *op) {
if (!op)
break;
- if (auto attr = op->getAttrOfType<TargetEnvAttr>(TargetEnvAttr::name))
+ if (auto attr =
+ op->getDiscardableAttrOfType<TargetEnvAttr>(TargetEnvAttr::name))
return attr;
op = op->getParentOp();
diff --git a/mlir/lib/Dialect/Tosa/IR/TosaOps.cpp b/mlir/lib/Dialect/Tosa/IR/TosaOps.cpp
index 46f84940d4718..75b2a7472d9b9 100644
--- a/mlir/lib/Dialect/Tosa/IR/TosaOps.cpp
+++ b/mlir/lib/Dialect/Tosa/IR/TosaOps.cpp
@@ -400,10 +400,11 @@ void printWithNanPropagationHandling(OpAsmPrinter &parser, Operation *op) {
parser << " ";
parser.printOperands(op->getOperands());
- NamedAttrList toPrint(op->getAttrs());
+ NamedAttrList toPrint(op->getDiscardableAttrDictionary().getValue());
+ op->getName().populateInherentAttrs(op, toPrint);
// remove default NanPropagate attribute
const auto kDefaultNanValue = NanPropagationMode::PROPAGATE;
- for (auto attr : op->getAttrs()) {
+ for (auto attr : toPrint) {
if (auto nanAttr = dyn_cast<NanPropagationModeAttr>(attr.getValue())) {
if (nanAttr.getValue() == kDefaultNanValue) {
// elide from toPrint
@@ -430,12 +431,13 @@ void printWithEnumHandling(OpAsmPrinter &parser, Operation *op) {
parser << " ";
parser.printOperands(op->getOperands());
- if (!op->getAttrs().empty()) {
+ NamedAttrList toPrint(op->getDiscardableAttrDictionary().getValue());
+ op->getName().populateInherentAttrs(op, toPrint);
+ if (!toPrint.empty()) {
parser << " {";
- llvm::interleaveComma(op->getAttrs(), parser,
- [&](const NamedAttribute namedAttr) {
- printNamedAttr(parser, namedAttr);
- });
+ llvm::interleaveComma(toPrint, parser, [&](NamedAttribute attr) {
+ printNamedAttr(parser, attr);
+ });
parser << "}";
}
@@ -5762,7 +5764,7 @@ void IfOp::print(OpAsmPrinter &p) {
p.printRegion(elseRegion);
}
- p.printOptionalAttrDict((*this)->getAttrs());
+ p.printOptionalAttrDict((*this)->getDiscardableAttrDictionary().getValue());
}
LogicalResult IfOp::verify() {
@@ -5971,7 +5973,8 @@ void WhileOp::print(OpAsmPrinter &parser) {
parser.printRegion(getCondGraph(), /*printEntryBlockArgs=*/false);
parser << " do ";
parser.printRegion(getBodyGraph());
- parser.printOptionalAttrDictWithKeyword((*this)->getAttrs());
+ parser.printOptionalAttrDictWithKeyword(
+ (*this)->getDiscardableAttrDictionary().getValue());
}
// Create a rank-1 const tensor for zero point of the source tensor.
diff --git a/mlir/lib/Dialect/Tosa/Transforms/TosaAttachTarget.cpp b/mlir/lib/Dialect/Tosa/Transforms/TosaAttachTarget.cpp
index 410d55d63e5fd..332409361a1ac 100644
--- a/mlir/lib/Dialect/Tosa/Transforms/TosaAttachTarget.cpp
+++ b/mlir/lib/Dialect/Tosa/Transforms/TosaAttachTarget.cpp
@@ -67,7 +67,7 @@ class TosaAttachTarget
if (failed(TargetEnv::verifyTargetInformation(targetEnvAttr, mod.getLoc())))
return signalPassFailure();
- mod->setAttr(TargetEnvAttr::name, targetEnvAttr);
+ mod->setDiscardableAttr(TargetEnvAttr::name, targetEnvAttr);
}
private:
diff --git a/mlir/lib/Dialect/Tosa/Transforms/TosaConvertIntegerTypeToSignless.cpp b/mlir/lib/Dialect/Tosa/Transforms/TosaConvertIntegerTypeToSignless.cpp
index 5a293087dd5f0..7657993d90c29 100644
--- a/mlir/lib/Dialect/Tosa/Transforms/TosaConvertIntegerTypeToSignless.cpp
+++ b/mlir/lib/Dialect/Tosa/Transforms/TosaConvertIntegerTypeToSignless.cpp
@@ -84,7 +84,8 @@ class ConvertGenericOpWithIntegerTensorType : public ConversionPattern {
// Create new op with replaced operands and results
auto *newOp = Operation::create(
- op->getLoc(), op->getName(), resultTypes, operands, op->getAttrs(),
+ op->getLoc(), op->getName(), resultTypes, operands,
+ op->getDiscardableAttrDictionary().getValue(),
op->getPropertiesStorage(), op->getSuccessors(), op->getNumRegions());
// Handle regions in e.g. tosa.cond_if and tosa.while_loop
diff --git a/mlir/lib/Dialect/Tosa/Transforms/TosaNarrowTypes.cpp b/mlir/lib/Dialect/Tosa/Transforms/TosaNarrowTypes.cpp
index fa58bf3c8c589..78c74132d9e40 100644
--- a/mlir/lib/Dialect/Tosa/Transforms/TosaNarrowTypes.cpp
+++ b/mlir/lib/Dialect/Tosa/Transforms/TosaNarrowTypes.cpp
@@ -371,7 +371,9 @@ LogicalResult convertGenericOp(Operation *op, ValueRange operands,
newResults, {}, op->getSuccessors());
// Keep attribute payloads consistent with the converted element types.
- for (const NamedAttribute &namedAttribute : op->getAttrs()) {
+ NamedAttrList sourceAttrs(op->getDiscardableAttrDictionary().getValue());
+ op->getName().populateInherentAttrs(op, sourceAttrs);
+ for (const NamedAttribute &namedAttribute : sourceAttrs) {
const Attribute attribute = namedAttribute.getValue();
if (isa<IntegerAttr>(attribute) || isa<FloatAttr>(attribute)) {
@@ -501,7 +503,7 @@ class ConvertCastOpWithBoundsChecking
rewriter.replaceOpWithNewOp<tosa::CastOp>(
op, typeConverter->convertType(resultType), adaptor.getInput(),
- op->getAttrs());
+ op->getDiscardableAttrDictionary().getValue());
return success();
}
};
diff --git a/mlir/lib/Dialect/Tosa/Transforms/TosaReduceTransposes.cpp b/mlir/lib/Dialect/Tosa/Transforms/TosaReduceTransposes.cpp
index ffd48e8ab16ae..57069ed74eb99 100644
--- a/mlir/lib/Dialect/Tosa/Transforms/TosaReduceTransposes.cpp
+++ b/mlir/lib/Dialect/Tosa/Transforms/TosaReduceTransposes.cpp
@@ -385,13 +385,13 @@ std::optional<Value> TosaReduceTransposes::buildMappedToValue(
// turn "live" until the transpose being hoisted through this chain
// is replaced with the proper value from the new chain.
- return rewriter
- .create(op->getLoc(), op->getName().getIdentifier(), operands,
- RankedTensorType::get(
- applyTOSAPermutation(resultType.getShape(), hoistedPerms),
- resultType.getElementType()),
- op->getAttrs())
- ->getResult(0);
+ Type newResultType = RankedTensorType::get(
+ applyTOSAPermutation(resultType.getShape(), hoistedPerms),
+ resultType.getElementType());
+ OperationState state(op->getLoc(), op->getName(), operands, newResultType,
+ op->getDiscardableAttrDictionary().getValue());
+ state.propertiesAttr = op->getPropertiesAsAttribute();
+ return rewriter.create(state)->getResult(0);
}
std::optional<Value> TosaReduceTransposes::buildMappedToValue(
diff --git a/mlir/lib/Dialect/Tosa/Transforms/TosaValidation.cpp b/mlir/lib/Dialect/Tosa/Transforms/TosaValidation.cpp
index e4985b8e0c7f0..9a37e57af0d2a 100644
--- a/mlir/lib/Dialect/Tosa/Transforms/TosaValidation.cpp
+++ b/mlir/lib/Dialect/Tosa/Transforms/TosaValidation.cpp
@@ -29,6 +29,7 @@
#include "mlir/Transforms/DialectConversion.h"
#include "llvm/ADT/STLExtras.h"
#include "llvm/ADT/StringExtras.h"
+#include "llvm/ADT/TypeSwitch.h"
#include "llvm/Support/FormatVariadic.h"
namespace mlir {
@@ -1022,7 +1023,10 @@ LogicalResult TosaValidation::CheckVariable(Operation *op) {
LogicalResult TosaValidation::CheckVariableReadOrWrite(Operation *op) {
if (isa<mlir::tosa::VariableReadOp>(op) ||
isa<mlir::tosa::VariableWriteOp>(op)) {
- mlir::StringAttr nameAttr = cast<mlir::StringAttr>(op->getAttr("name"));
+ mlir::StringAttr nameAttr =
+ TypeSwitch<Operation *, mlir::StringAttr>(op)
+ .Case<mlir::tosa::VariableReadOp, mlir::tosa::VariableWriteOp>(
+ [](auto variableOp) { return variableOp.getNameAttr(); });
if (!variablesMap.count(nameAttr))
return op->emitOpError() << "name has not been declared";
diff --git a/mlir/lib/Dialect/Tosa/Utils/ConversionUtils.cpp b/mlir/lib/Dialect/Tosa/Utils/ConversionUtils.cpp
index e0d4b3470c981..0d082a97414a4 100644
--- a/mlir/lib/Dialect/Tosa/Utils/ConversionUtils.cpp
+++ b/mlir/lib/Dialect/Tosa/Utils/ConversionUtils.cpp
@@ -191,8 +191,7 @@ bool mlir::tosa::getConstShapeValues(Operation *op,
return false;
}
if (auto constOp = mlir::dyn_cast<tosa::ConstShapeOp>(op)) {
- Attribute constOpAttr = constOp->getAttr("values");
- DenseElementsAttr elementsAttr = cast<DenseElementsAttr>(constOpAttr);
+ DenseElementsAttr elementsAttr = constOp.getValuesAttr();
for (int i = 0; i < elementsAttr.size(); i++) {
int64_t val = elementsAttr.getValues<int64_t>()[i];
resultShape.push_back(val);
diff --git a/mlir/lib/Dialect/Transform/IR/TransformDialect.cpp b/mlir/lib/Dialect/Transform/IR/TransformDialect.cpp
index f12eab759a583..05820427fac8b 100644
--- a/mlir/lib/Dialect/Transform/IR/TransformDialect.cpp
+++ b/mlir/lib/Dialect/Transform/IR/TransformDialect.cpp
@@ -172,8 +172,8 @@ void transform::TransformDialect::initializeLibraryModule() {
auto loc =
FileLineColLoc::get(context, "<transform-dialect-library-module>", 0, 0);
libraryModule = ModuleOp::create(loc, "__transform_library");
- libraryModule.get()->setAttr(TransformDialect::kWithNamedSequenceAttrName,
- UnitAttr::get(context));
+ libraryModule.get()->setDiscardableAttr(
+ TransformDialect::kWithNamedSequenceAttrName, UnitAttr::get(context));
}
void transform::TransformDialect::reportDuplicateAttributeRegistration(
diff --git a/mlir/lib/Dialect/Transform/IR/TransformOps.cpp b/mlir/lib/Dialect/Transform/IR/TransformOps.cpp
index 2f1648a0b0c30..422836883185b 100644
--- a/mlir/lib/Dialect/Transform/IR/TransformOps.cpp
+++ b/mlir/lib/Dialect/Transform/IR/TransformOps.cpp
@@ -268,13 +268,13 @@ transform::AnnotateOp::apply(transform::TransformRewriter &rewriter,
<< params.size() << " vs " << targets.size() << ")";
}
for (auto &&[target, attr] : llvm::zip_equal(targets, params))
- target->setAttr(getName(), attr);
+ target->setDiscardableAttr(getName(), attr);
return DiagnosedSilenceableFailure::success();
}
attr = params[0];
}
for (auto *target : targets)
- target->setAttr(getName(), attr);
+ target->setDiscardableAttr(getName(), attr);
return DiagnosedSilenceableFailure::success();
}
@@ -2068,8 +2068,7 @@ void transform::IncludeOp::getEffects(
// Bail if the callee is unknown. This may run as part of the verification
// process before we verified the validity of the callee or of this op.
- auto target =
- getOperation()->getAttrOfType<SymbolRefAttr>(getTargetAttrName());
+ auto target = getTargetAttr();
if (!target)
return defaultEffects();
auto callee = SymbolTable::lookupNearestSymbolFrom<NamedSequenceOp>(
@@ -2089,7 +2088,7 @@ LogicalResult
transform::IncludeOp::verifySymbolUses(SymbolTableCollection &symbolTable) {
// Access through indirection and do additional checking because this may be
// running before the main op verifier.
- auto targetAttr = getOperation()->getAttrOfType<SymbolRefAttr>("target");
+ auto targetAttr = getTargetAttr();
if (!targetAttr)
return emitOpError() << "expects a 'target' symbol reference attribute";
@@ -2439,7 +2438,7 @@ verifyYieldingSingleBlockOp(FunctionOpInterface op, bool allowExternal) {
static DiagnosedSilenceableFailure
verifyNamedSequenceOp(transform::NamedSequenceOp op, bool emitWarnings) {
if (Operation *parent = op->getParentWithTrait<OpTrait::SymbolTable>()) {
- if (!parent->getAttr(
+ if (!parent->getDiscardableAttr(
transform::TransformDialect::kWithNamedSequenceAttrName)) {
DiagnosedSilenceableFailure diag =
emitSilenceableFailure(op)
diff --git a/mlir/lib/Dialect/Transform/Interfaces/TransformInterfaces.cpp b/mlir/lib/Dialect/Transform/Interfaces/TransformInterfaces.cpp
index 0084327817075..27ab65b67e8b1 100644
--- a/mlir/lib/Dialect/Transform/Interfaces/TransformInterfaces.cpp
+++ b/mlir/lib/Dialect/Transform/Interfaces/TransformInterfaces.cpp
@@ -939,8 +939,8 @@ transform::TransformState::applyTransform(TransformOpInterface transform) {
DiagnosedSilenceableFailure trackingFailure =
trackingListener.checkAndResetError();
if (!transform->hasTrait<ReportTrackingListenerFailuresOpTrait>() ||
- transform->hasAttr(FindPayloadReplacementOpInterface::
- kSilenceTrackingFailuresAttrName)) {
+ transform->hasDiscardableAttr(FindPayloadReplacementOpInterface::
+ kSilenceTrackingFailuresAttrName)) {
// Only report failures for ReportTrackingListenerFailuresOpTrait ops. Also
// do not report failures if the above mentioned attribute is set.
if (trackingFailure.isSilenceableFailure())
diff --git a/mlir/lib/Dialect/Transform/Transforms/InterpreterPass.cpp b/mlir/lib/Dialect/Transform/Transforms/InterpreterPass.cpp
index 19906f15ae85f..01f6de7c744c8 100644
--- a/mlir/lib/Dialect/Transform/Transforms/InterpreterPass.cpp
+++ b/mlir/lib/Dialect/Transform/Transforms/InterpreterPass.cpp
@@ -34,7 +34,7 @@ static Operation *findPayloadRoot(Operation *passRoot, StringRef tag) {
auto tagAttrName = StringAttr::get(
passRoot->getContext(), transform::TransformDialect::kTargetTagAttrName);
WalkResult walkResult = passRoot->walk([&](Operation *op) {
- auto attr = op->getAttrOfType<StringAttr>(tagAttrName);
+ auto attr = op->getDiscardableAttrOfType<StringAttr>(tagAttrName);
if (!attr || attr.getValue() != tag)
return WalkResult::advance();
diff --git a/mlir/lib/Dialect/Transform/Transforms/TransformInterpreterUtils.cpp b/mlir/lib/Dialect/Transform/Transforms/TransformInterpreterUtils.cpp
index 9ab484ff68078..428bfa75c9f30 100644
--- a/mlir/lib/Dialect/Transform/Transforms/TransformInterpreterUtils.cpp
+++ b/mlir/lib/Dialect/Transform/Transforms/TransformInterpreterUtils.cpp
@@ -237,8 +237,8 @@ LogicalResult transform::detail::assembleTransformLibraryFromPaths(
OwningOpRef<ModuleOp> mergedParsedLibraries =
ModuleOp::create(loc, "__transform");
{
- mergedParsedLibraries.get()->setAttr("transform.with_named_sequence",
- UnitAttr::get(context));
+ mergedParsedLibraries.get()->setDiscardableAttr(
+ "transform.with_named_sequence", UnitAttr::get(context));
// TODO: extend `mergeSymbolsInto` to support multiple `other` modules.
for (OwningOpRef<ModuleOp> &parsedLibrary : parsedLibraries) {
if (failed(transform::detail::mergeSymbolsInto(
diff --git a/mlir/lib/Dialect/Utils/StructuredOpsUtils.cpp b/mlir/lib/Dialect/Utils/StructuredOpsUtils.cpp
index bcff5d32a3d2c..4139b71033780 100644
--- a/mlir/lib/Dialect/Utils/StructuredOpsUtils.cpp
+++ b/mlir/lib/Dialect/Utils/StructuredOpsUtils.cpp
@@ -198,7 +198,8 @@ Operation *mlir::clone(OpBuilder &b, Operation *op, TypeRange newResultTypes,
ValueRange newOperands) {
IRMapping bvm;
OperationState state(op->getLoc(), op->getName(), newOperands, newResultTypes,
- op->getAttrs());
+ op->getDiscardableAttrDictionary().getValue());
+ state.propertiesAttr = op->getPropertiesAsAttribute();
for (Region &r : op->getRegions()) {
Region *newRegion = state.addRegion();
b.cloneRegionBefore(r, *newRegion, newRegion->begin(), bvm);
@@ -210,7 +211,8 @@ Operation *mlir::cloneWithoutRegions(OpBuilder &b, Operation *op,
TypeRange newResultTypes,
ValueRange newOperands) {
OperationState state(op->getLoc(), op->getName(), newOperands, newResultTypes,
- op->getAttrs());
+ op->getDiscardableAttrDictionary().getValue());
+ state.propertiesAttr = op->getPropertiesAsAttribute();
for (size_t cnt = 0, e = op->getNumRegions(); cnt < e; ++cnt)
state.addRegion();
return b.create(state);
@@ -221,7 +223,7 @@ mlir::getPrunedAttributeList(Operation *op, ArrayRef<StringRef> elidedAttrs) {
llvm::StringSet<> elidedAttrsSet;
elidedAttrsSet.insert_range(elidedAttrs);
SmallVector<NamedAttribute> attrs;
- for (auto attr : op->getAttrs()) {
+ for (auto attr : op->getDiscardableAttrDictionary().getValue()) {
if (elidedAttrsSet.count(attr.getName()))
continue;
attrs.push_back(attr);
diff --git a/mlir/lib/Dialect/Vector/IR/VectorOps.cpp b/mlir/lib/Dialect/Vector/IR/VectorOps.cpp
index 7dbe1847f077d..5ecee3c681790 100644
--- a/mlir/lib/Dialect/Vector/IR/VectorOps.cpp
+++ b/mlir/lib/Dialect/Vector/IR/VectorOps.cpp
@@ -971,8 +971,10 @@ void ContractionOp::print(OpAsmPrinter &p) {
auto attrNames = getTraitAttrNames();
llvm::StringSet<> traitAttrsSet;
traitAttrsSet.insert_range(attrNames);
+ NamedAttrList allAttrs(getOperation()->getRawDictionaryAttrs());
+ getOperation()->getName().populateInherentAttrs(getOperation(), allAttrs);
SmallVector<NamedAttribute, 8> attrs;
- for (auto attr : (*this)->getAttrs()) {
+ for (auto attr : allAttrs) {
if (attr.getName() == getIteratorTypesAttrName()) {
auto iteratorTypes =
llvm::cast<ArrayAttr>(attr.getValue())
@@ -1002,7 +1004,7 @@ void ContractionOp::print(OpAsmPrinter &p) {
p << " " << dictAttr << " " << getLhs() << ", ";
p << getRhs() << ", " << getAcc();
- p.printOptionalAttrDict((*this)->getAttrs(), attrNames);
+ p.printOptionalAttrDict(allAttrs.getAttrs(), attrNames);
p << " : " << getLhs().getType() << ", " << getRhs().getType() << " into "
<< getResultType();
}
@@ -4350,7 +4352,10 @@ void OuterProductOp::print(OpAsmPrinter &p) {
p << " " << getLhs() << ", " << getRhs();
if (getAcc()) {
p << ", " << getAcc();
- p.printOptionalAttrDict((*this)->getAttrs());
+ SmallVector<NamedAttribute> attrs((*this)->getDiscardableAttrs());
+ attrs.emplace_back(getKindAttrName(), getKindAttr());
+ llvm::sort(attrs);
+ p.printOptionalAttrDict(attrs);
}
p << " : " << getLhs().getType() << ", " << getRhs().getType();
}
@@ -5123,7 +5128,7 @@ verifyTransferOp(VectorTransferOpInterface op, ShapedType shapedType,
VectorType vectorType, VectorType maskType,
VectorType inferredMaskType, AffineMap permutationMap,
ArrayAttr inBounds) {
- if (op->hasAttr("masked")) {
+ if (op->hasDiscardableAttr("masked")) {
return op->emitOpError("masked attribute has been removed. "
"Use in_bounds instead.");
}
@@ -5199,14 +5204,14 @@ verifyTransferOp(VectorTransferOpInterface op, ShapedType shapedType,
}
static void printTransferAttrs(OpAsmPrinter &p, VectorTransferOpInterface op) {
- SmallVector<StringRef, 3> elidedAttrs;
- elidedAttrs.push_back(TransferReadOp::getOperandSegmentSizeAttr());
- if (op.getPermutationMap().isMinorIdentity())
- elidedAttrs.push_back(op.getPermutationMapAttrName());
+ NamedAttrList attrs(op->getDiscardableAttrDictionary().getValue());
// Elide in_bounds attribute if all dims are out-of-bounds.
- if (llvm::none_of(op.getInBoundsValues(), [](bool b) { return b; }))
- elidedAttrs.push_back(op.getInBoundsAttrName());
- p.printOptionalAttrDict(op->getAttrs(), elidedAttrs);
+ if (llvm::any_of(op.getInBoundsValues(), [](bool b) { return b; }))
+ attrs.append(op.getInBoundsAttrName(), op.getInBounds());
+ if (!op.getPermutationMap().isMinorIdentity())
+ attrs.append(op.getPermutationMapAttrName(),
+ AffineMapAttr::get(op.getPermutationMap()));
+ p.printOptionalAttrDict(attrs);
}
void TransferReadOp::print(OpAsmPrinter &p) {
@@ -7935,7 +7940,8 @@ void mlir::vector::MaskOp::print(OpAsmPrinter &p) {
p.printCustomOrGenericOp(&singleBlock->front());
p << " }";
- p.printOptionalAttrDict(getOperation()->getAttrs());
+ p.printOptionalAttrDict(
+ getOperation()->getDiscardableAttrDictionary().getValue());
p << " : " << getMask().getType();
if (getNumResults() > 0)
diff --git a/mlir/lib/Dialect/Vector/Transforms/VectorDistribute.cpp b/mlir/lib/Dialect/Vector/Transforms/VectorDistribute.cpp
index c500942af7942..522c555da378a 100644
--- a/mlir/lib/Dialect/Vector/Transforms/VectorDistribute.cpp
+++ b/mlir/lib/Dialect/Vector/Transforms/VectorDistribute.cpp
@@ -194,7 +194,8 @@ static Operation *cloneOpWithOperandsAndTypes(RewriterBase &rewriter,
ArrayRef<Value> operands,
ArrayRef<Type> resultTypes) {
OperationState res(loc, op->getName().getStringRef(), operands, resultTypes,
- op->getAttrs());
+ op->getDiscardableAttrDictionary().getValue());
+ res.propertiesAttr = op->getPropertiesAsAttribute();
return rewriter.create(res);
}
diff --git a/mlir/lib/Dialect/Vector/Transforms/VectorDropLeadUnitDim.cpp b/mlir/lib/Dialect/Vector/Transforms/VectorDropLeadUnitDim.cpp
index d86e9f224bf9d..48808ea23f1a3 100644
--- a/mlir/lib/Dialect/Vector/Transforms/VectorDropLeadUnitDim.cpp
+++ b/mlir/lib/Dialect/Vector/Transforms/VectorDropLeadUnitDim.cpp
@@ -49,6 +49,15 @@ static VectorType trimLeadingOneDims(VectorType oldType) {
static SmallVector<int64_t> splatZero(int64_t rank) {
return SmallVector<int64_t>(rank, 0);
}
+
+static Operation *createWithProperties(OpBuilder &builder, Operation *op,
+ ValueRange operands,
+ TypeRange resultTypes) {
+ OperationState state(op->getLoc(), op->getName(), operands, resultTypes,
+ op->getDiscardableAttrDictionary().getValue());
+ state.propertiesAttr = op->getPropertiesAsAttribute();
+ return builder.create(state);
+}
namespace {
// Casts away leading one dimensions in vector.extract_strided_slice's vector
@@ -530,8 +539,7 @@ class CastAwayElementwiseLeadingOneDim : public RewritePattern {
}
}
Operation *newOp =
- rewriter.create(op->getLoc(), op->getName().getIdentifier(),
- newOperands, newVecType, op->getAttrs());
+ createWithProperties(rewriter, op, newOperands, TypeRange{newVecType});
rewriter.replaceOpWithNewOp<vector::BroadcastOp>(op, vecType,
newOp->getResult(0));
return success();
@@ -589,9 +597,8 @@ struct CastAwayLoadLikeLeadingOneDim : public OpRewritePattern<OpTy> {
}
}
- Operation *newOp =
- rewriter.create(loc, op->getName().getIdentifier(), newOperands,
- TypeRange{newResultType}, op->getAttrs());
+ Operation *newOp = createWithProperties(rewriter, op, newOperands,
+ TypeRange{newResultType});
rewriter.replaceOpWithNewOp<vector::BroadcastOp>(op, oldResultType,
newOp->getResult(0));
return success();
@@ -626,8 +633,7 @@ struct CastAwayStoreLikeLeadingOneDim : public OpRewritePattern<OpTy> {
}
Operation *newOp =
- rewriter.create(loc, op->getName().getIdentifier(), newOperands,
- op->getResultTypes(), op->getAttrs());
+ createWithProperties(rewriter, op, newOperands, op->getResultTypes());
rewriter.replaceOp(op, newOp->getResults());
return success();
}
diff --git a/mlir/lib/Dialect/Vector/Transforms/VectorLinearize.cpp b/mlir/lib/Dialect/Vector/Transforms/VectorLinearize.cpp
index e6c28036ea1c5..025bfc0e3d9e2 100644
--- a/mlir/lib/Dialect/Vector/Transforms/VectorLinearize.cpp
+++ b/mlir/lib/Dialect/Vector/Transforms/VectorLinearize.cpp
@@ -67,7 +67,8 @@ struct LinearizeConstantLike final
assert(resType && "expected 1-D vector type");
StringAttr attrName = rewriter.getStringAttr("value");
- Attribute value = op->getAttr(attrName);
+ Attribute value = op->getInherentAttr(attrName).value_or(
+ op->getDiscardableAttr(attrName));
if (!value)
return rewriter.notifyMatchFailure(loc, "no 'value' attr");
@@ -82,7 +83,10 @@ struct LinearizeConstantLike final
return failure();
Operation *newOp = *convertResult;
- newOp->setAttr(attrName, *newValue);
+ if (newOp->getInherentAttr(attrName))
+ newOp->setInherentAttr(attrName, *newValue);
+ else
+ newOp->setDiscardableAttr(attrName, *newValue);
rewriter.replaceOp(op, newOp);
return success();
}
diff --git a/mlir/lib/Dialect/Vector/Transforms/VectorTransferSplitRewritePatterns.cpp b/mlir/lib/Dialect/Vector/Transforms/VectorTransferSplitRewritePatterns.cpp
index bd14e43747f81..d436266654de9 100644
--- a/mlir/lib/Dialect/Vector/Transforms/VectorTransferSplitRewritePatterns.cpp
+++ b/mlir/lib/Dialect/Vector/Transforms/VectorTransferSplitRewritePatterns.cpp
@@ -518,7 +518,8 @@ LogicalResult mlir::vector::splitFullAndPartialTransfer(
auto inBoundsAttr = b.getBoolArrayAttr(bools);
if (options.vectorTransferSplit == VectorTransferSplit::ForceInBounds) {
b.modifyOpInPlace(xferOp, [&]() {
- xferOp->setAttr(xferOp.getInBoundsAttrName(), inBoundsAttr);
+ xferOp->setInherentAttr(b.getStringAttr(xferOp.getInBoundsAttrName()),
+ inBoundsAttr);
});
return success();
}
@@ -591,7 +592,8 @@ LogicalResult mlir::vector::splitFullAndPartialTransfer(
xferReadOp.setOperand(i, fullPartialIfOp.getResult(i));
b.modifyOpInPlace(xferOp, [&]() {
- xferOp->setAttr(xferOp.getInBoundsAttrName(), inBoundsAttr);
+ xferOp->setInherentAttr(b.getStringAttr(xferOp.getInBoundsAttrName()),
+ inBoundsAttr);
});
return success();
@@ -610,7 +612,7 @@ LogicalResult mlir::vector::splitFullAndPartialTransfer(
mapping.map(xferWriteOp.getBase(), memrefAndIndices.front());
mapping.map(xferWriteOp.getIndices(), memrefAndIndices.drop_front());
auto *clone = b.clone(*xferWriteOp, mapping);
- clone->setAttr(xferWriteOp.getInBoundsAttrName(), inBoundsAttr);
+ clone->setInherentAttr(xferWriteOp.getInBoundsAttrName(), inBoundsAttr);
// Create a potential copy from the allocated buffer to the final output in
// the slow path case.
diff --git a/mlir/lib/Dialect/Vector/Transforms/VectorTransforms.cpp b/mlir/lib/Dialect/Vector/Transforms/VectorTransforms.cpp
index d7beb08d3333c..fca71a867b3d9 100644
--- a/mlir/lib/Dialect/Vector/Transforms/VectorTransforms.cpp
+++ b/mlir/lib/Dialect/Vector/Transforms/VectorTransforms.cpp
@@ -41,6 +41,14 @@
using namespace mlir;
using namespace mlir::vector;
+static Operation *createWithProperties(OpBuilder &builder, Operation *op,
+ ValueRange operands, TypeRange types) {
+ OperationState state(op->getLoc(), op->getName(), operands, types,
+ op->getDiscardableAttrDictionary().getValue());
+ state.propertiesAttr = op->getPropertiesAsAttribute();
+ return builder.create(state);
+}
+
template <typename IntType>
static SmallVector<IntType> extractVector(ArrayAttr arrayAttr) {
return llvm::to_vector<4>(llvm::map_range(
@@ -476,8 +484,7 @@ struct ReorderCastOpsOnBroadcast
if (auto vecTy = dyn_cast<VectorType>(bcastOp.getSourceType()))
castResTy = vecTy.clone(castResTy);
auto *castOp =
- rewriter.create(op->getLoc(), op->getName().getIdentifier(),
- bcastOp.getSource(), castResTy, op->getAttrs());
+ createWithProperties(rewriter, op, bcastOp.getSource(), castResTy);
rewriter.replaceOpWithNewOp<vector::BroadcastOp>(
op, op->getResult(0).getType(), castOp->getResult(0));
return success();
@@ -556,8 +563,7 @@ struct ReorderElementwiseOpsOnTranspose final
auto vectorType = srcType.clone(
cast<VectorType>(op->getResultTypes()[0]).getElementType());
Operation *elementwiseOp =
- rewriter.create(op->getLoc(), op->getName().getIdentifier(), srcValues,
- vectorType, op->getAttrs());
+ createWithProperties(rewriter, op, srcValues, vectorType);
rewriter.replaceOpWithNewOp<vector::TransposeOp>(
op, op->getResultTypes()[0], elementwiseOp->getResult(0),
transposeMaps.front());
@@ -1114,8 +1120,7 @@ struct ReorderElementwiseOpsOnBroadcast final
// Create the "elementwise" Op
Operation *elementwiseOp =
- rewriter.create(op->getLoc(), op->getName().getIdentifier(), srcValues,
- unbroadcastResultType, op->getAttrs());
+ createWithProperties(rewriter, op, srcValues, unbroadcastResultType);
// Replace the original Op with the elementwise Op
rewriter.replaceOpWithNewOp<vector::BroadcastOp>(
@@ -2036,8 +2041,7 @@ struct DropUnitDimFromElementwiseOps final
dropNonScalableUnitDimFromType(resultVectorType);
// Create an updated elementwise Op without unit dim.
Operation *elementwiseOp =
- rewriter.create(loc, op->getName().getIdentifier(), newOperands,
- newResultVectorType, op->getAttrs());
+ createWithProperties(rewriter, op, newOperands, newResultVectorType);
// Restore the unit dim by applying vector.shape_cast to the result.
rewriter.replaceOpWithNewOp<ShapeCastOp>(op, resultVectorType,
diff --git a/mlir/lib/Dialect/Vector/Transforms/VectorUnroll.cpp b/mlir/lib/Dialect/Vector/Transforms/VectorUnroll.cpp
index 62869111496d1..aa409e71e7050 100644
--- a/mlir/lib/Dialect/Vector/Transforms/VectorUnroll.cpp
+++ b/mlir/lib/Dialect/Vector/Transforms/VectorUnroll.cpp
@@ -79,8 +79,10 @@ static Operation *cloneOpWithOperandsAndTypes(OpBuilder &builder, Location loc,
Operation *op,
ArrayRef<Value> operands,
ArrayRef<Type> resultTypes) {
- return builder.create(loc, op->getName().getIdentifier(), operands,
- resultTypes, op->getAttrs());
+ OperationState state(loc, op->getName(), operands, resultTypes,
+ op->getDiscardableAttrDictionary().getValue());
+ state.propertiesAttr = op->getPropertiesAsAttribute();
+ return builder.create(state);
}
/// Return the target shape for unrolling for the given `op`. Return
diff --git a/mlir/lib/Dialect/XeGPU/Transforms/XeGPUBlocking.cpp b/mlir/lib/Dialect/XeGPU/Transforms/XeGPUBlocking.cpp
index 9d1686403a431..f70ff26b3d8f7 100644
--- a/mlir/lib/Dialect/XeGPU/Transforms/XeGPUBlocking.cpp
+++ b/mlir/lib/Dialect/XeGPU/Transforms/XeGPUBlocking.cpp
@@ -433,14 +433,15 @@ void XeGPUBlockingPass::runOnOperation() {
if (!isa<scf::ForOp, scf::WhileOp, scf::ConditionOp, scf::IfOp>(loopOp))
return;
SmallVector<StringRef> toRemove;
- for (const NamedAttribute &attr : loopOp->getAttrs()) {
+ for (const NamedAttribute &attr :
+ loopOp->getDiscardableAttrDictionary().getValue()) {
StringRef name = attr.getName().strref();
if (name.starts_with("layout_operand_") ||
name.starts_with("layout_result_"))
toRemove.push_back(name);
}
for (StringRef name : toRemove)
- loopOp->removeAttr(name);
+ loopOp->removeDiscardableAttr(name);
});
// Source (N:1) and target (1:1) materializations using
@@ -524,15 +525,16 @@ void XeGPUBlockingPass::runOnOperation() {
// Remove the layout attributes cached per operands.
for (OpOperand &opr : op->getOpOperands()) {
std::string name = xegpu::getTemporaryLayoutName(opr);
- if (op->hasAttrOfType<xegpu::DistributeLayoutAttr>(name))
- op->removeAttr(name);
+ if (op->hasDiscardableAttrOfType<xegpu::DistributeLayoutAttr>(name))
+ op->removeDiscardableAttr(name);
}
// Update the layout attributes per result.
for (OpResult result : op->getOpResults()) {
std::string name = xegpu::getTemporaryLayoutName(result);
- if (auto layout = op->getAttrOfType<xegpu::DistributeLayoutAttr>(name)) {
- op->removeAttr(name);
+ if (auto layout =
+ op->getDiscardableAttrOfType<xegpu::DistributeLayoutAttr>(name)) {
+ op->removeDiscardableAttr(name);
if (!isa<LoopLikeOpInterface>(op))
xegpu::setDistributeLayoutAttr(result, layout.dropInstData());
}
@@ -540,9 +542,9 @@ void XeGPUBlockingPass::runOnOperation() {
// Drop left-over inst_data if the unroll pattern does not being applied,
// say, inst_data just matches their shape.
- SmallVector<NamedAttribute> newAttrs =
- xegpu::dropInstDataOnAttrs(op->getAttrs());
- op->setAttrs(newAttrs);
+ SmallVector<NamedAttribute> newAttrs = xegpu::dropInstDataOnAttrs(
+ op->getDiscardableAttrDictionary().getValue());
+ op->setDiscardableAttrs(newAttrs);
});
// Resolve UnrealizedConversionCastOps generated by SCF structural type
diff --git a/mlir/lib/Dialect/XeGPU/Transforms/XeGPULayoutImpl.cpp b/mlir/lib/Dialect/XeGPU/Transforms/XeGPULayoutImpl.cpp
index eb3c3faf75572..7fa3060c6e1ba 100644
--- a/mlir/lib/Dialect/XeGPU/Transforms/XeGPULayoutImpl.cpp
+++ b/mlir/lib/Dialect/XeGPU/Transforms/XeGPULayoutImpl.cpp
@@ -377,8 +377,8 @@ template <typename T, typename>
void xegpu::removeLayoutAttr(const T &operandOrResult) {
Operation *owner = operandOrResult.getOwner();
std::string name = xegpu::getTemporaryLayoutName(operandOrResult);
- if (owner->hasAttrOfType<DistributeLayoutAttr>(name))
- owner->removeAttr(name);
+ if (owner->hasDiscardableAttrOfType<DistributeLayoutAttr>(name))
+ owner->removeDiscardableAttr(name);
}
// Explicit instantiation for OpResult
@@ -393,19 +393,19 @@ void xegpu::removeLayoutAttrs(Operation *op) {
op->walk([&](Operation *nestOp) {
// Remove all attributes of DistributeLayoutAttr type
SmallVector<StringAttr> attrsToRemove;
- for (auto namedAttr : nestOp->getAttrs()) {
+ for (auto namedAttr : nestOp->getDiscardableAttrDictionary().getValue()) {
if (isa<DistributeLayoutAttr>(namedAttr.getValue()))
attrsToRemove.push_back(namedAttr.getName());
}
for (auto attrName : attrsToRemove)
- nestOp->removeAttr(attrName);
+ nestOp->removeDiscardableAttr(attrName);
});
}
void xegpu::removeTemporaryLayoutAttrs(Operation *op) {
op->walk([&](Operation *nestOp) {
SmallVector<StringAttr> attrsToRemove;
- for (auto namedAttr : nestOp->getDiscardableAttrs()) {
+ for (auto namedAttr : nestOp->getDiscardableAttrDictionary().getValue()) {
if (isa<xegpu::DistributeLayoutAttr>(namedAttr.getValue()))
attrsToRemove.push_back(namedAttr.getName());
}
diff --git a/mlir/lib/Dialect/XeGPU/Transforms/XeGPUPropagateLayout.cpp b/mlir/lib/Dialect/XeGPU/Transforms/XeGPUPropagateLayout.cpp
index c4a103fad6c56..1e909319e19e8 100644
--- a/mlir/lib/Dialect/XeGPU/Transforms/XeGPUPropagateLayout.cpp
+++ b/mlir/lib/Dialect/XeGPU/Transforms/XeGPUPropagateLayout.cpp
@@ -1736,10 +1736,12 @@ ResolveLayoutConflicts::resolveTensorDescConsumer(OpOperand &operand) {
conflictingCreateNdOp.getContext(), currTDescType.getShape(),
currTDescType.getElementType(), currTDescType.getEncoding(),
expectedLayout);
- xegpu::CreateNdDescOp newOp = xegpu::CreateNdDescOp::create(
- builder, consumerOp->getLoc(), newTensorDescType,
- conflictingCreateNdOp->getOperands(),
- conflictingCreateNdOp->getAttrs());
+ OperationState state(
+ consumerOp->getLoc(), conflictingCreateNdOp->getName(),
+ conflictingCreateNdOp->getOperands(), TypeRange{newTensorDescType},
+ conflictingCreateNdOp->getDiscardableAttrDictionary().getValue());
+ state.propertiesAttr = conflictingCreateNdOp->getPropertiesAsAttribute();
+ auto newOp = cast<xegpu::CreateNdDescOp>(builder.create(state));
// Replace the tensor descriptor operand in the consumer op with the new
// tensor descriptor.
consumerOp->replaceUsesOfWith(tdescValue, newOp.getResult());
diff --git a/mlir/lib/Dialect/XeGPU/Transforms/XeGPUSgToLaneDistribute.cpp b/mlir/lib/Dialect/XeGPU/Transforms/XeGPUSgToLaneDistribute.cpp
index bc85140f9f121..b84fe9aa97b5c 100644
--- a/mlir/lib/Dialect/XeGPU/Transforms/XeGPUSgToLaneDistribute.cpp
+++ b/mlir/lib/Dialect/XeGPU/Transforms/XeGPUSgToLaneDistribute.cpp
@@ -127,10 +127,12 @@ struct SgToLaneCreateNdDesc
if (!resultType.getLayout())
return failure();
- auto newOp = xegpu::CreateNdDescOp::create(
- rewriter, op.getLoc(), resultType.dropLayouts(), op.getOperands(),
- op->getAttrs());
- rewriter.replaceOp(op, newOp.getResult());
+ OperationState state(op.getLoc(), op->getName(), op.getOperands(),
+ TypeRange{resultType.dropLayouts()},
+ op->getDiscardableAttrDictionary().getValue());
+ state.propertiesAttr = op->getPropertiesAsAttribute();
+ Operation *newOp = rewriter.create(state);
+ rewriter.replaceOp(op, newOp->getResult(0));
return success();
}
};
@@ -345,10 +347,11 @@ struct SgToLaneElementWise : public ConversionPattern {
state.addOperands(operands);
state.addTypes(newResultType);
// Copy all attributes except for DistributeLayoutAttr.
- for (auto attr : op->getAttrs()) {
+ for (auto attr : op->getDiscardableAttrDictionary().getValue()) {
if (!isa<xegpu::DistributeLayoutAttr>(attr.getValue()))
state.addAttribute(attr.getName(), attr.getValue());
}
+ state.propertiesAttr = op->getPropertiesAsAttribute();
Operation *newOp = rewriter.create(state);
rewriter.replaceOp(op, newOp->getResult(0));
diff --git a/mlir/lib/Dialect/XeGPU/Transforms/XeGPUUnroll.cpp b/mlir/lib/Dialect/XeGPU/Transforms/XeGPUUnroll.cpp
index 14061ab24ffe0..c3873c916b647 100644
--- a/mlir/lib/Dialect/XeGPU/Transforms/XeGPUUnroll.cpp
+++ b/mlir/lib/Dialect/XeGPU/Transforms/XeGPUUnroll.cpp
@@ -564,9 +564,12 @@ struct UnrollDpasOp : public UnrollPattern<xegpu::DpasOp> {
if (tmpC)
operands.push_back(tmpC);
- tmpC = xegpu::DpasOp::create(
- rewriter, loc, vecTy, operands,
- xegpu::dropInstDataOnAttrs(op->getAttrs()));
+ OperationState state(
+ loc, op->getName(), operands, TypeRange{vecTy},
+ xegpu::dropInstDataOnAttrs(
+ op->getDiscardableAttrDictionary().getValue()));
+ state.propertiesAttr = op->getPropertiesAsAttribute();
+ tmpC = rewriter.create(state)->getResult(0);
}
newOps.push_back(tmpC);
}
@@ -666,9 +669,12 @@ struct UnrollDpasMxOp : public UnrollPattern<xegpu::DpasMxOp> {
operands.push_back(
bScaleVals[batch * (kIters * nIters) + k * nIters + j]);
- newDpasMxOp = xegpu::DpasMxOp::create(
- rewriter, loc, vecTy, operands,
- xegpu::dropInstDataOnAttrs(op->getAttrs()));
+ OperationState state(
+ loc, op->getName(), operands, TypeRange{vecTy},
+ xegpu::dropInstDataOnAttrs(
+ op->getDiscardableAttrDictionary().getValue()));
+ state.propertiesAttr = op->getPropertiesAsAttribute();
+ newDpasMxOp = cast<xegpu::DpasMxOp>(rewriter.create(state));
tmpC = newDpasMxOp.getResult();
}
newOps.push_back(newDpasMxOp);
@@ -699,11 +705,7 @@ struct UnrollLoadGatherOp : public UnrollPattern<xegpu::LoadGatherOp> {
return failure();
SmallVector<int64_t> targetMaskShape(*targetShape);
- int64_t chunkSize = 1;
- if (auto chunkSizeAttr = op->getAttr("chunk_size")) {
- if (auto intAttr = llvm::dyn_cast<IntegerAttr>(chunkSizeAttr))
- chunkSize = intAttr.getInt();
- }
+ int64_t chunkSize = op.getChunkSize().value_or(1);
// Unroll mask and offsets with correct shape
VectorType maskTy = llvm::dyn_cast<VectorType>(mask.getType());
@@ -793,11 +795,7 @@ struct UnrollStoreScatterOp : public UnrollPattern<xegpu::StoreScatterOp> {
if (!targetShape)
return failure();
- int64_t chunkSize = 1;
- if (auto chunkSizeAttr = op->getAttr("chunk_size")) {
- if (auto intAttr = llvm::dyn_cast<IntegerAttr>(chunkSizeAttr))
- chunkSize = intAttr.getInt();
- }
+ int64_t chunkSize = op.getChunkSize().value_or(1);
SmallVector<int64_t> targetMaskShape(*targetShape);
VectorType maskTy = llvm::dyn_cast<VectorType>(mask.getType());
diff --git a/mlir/lib/Dialect/XeGPU/Transforms/XeGPUWgToSgDistribute.cpp b/mlir/lib/Dialect/XeGPU/Transforms/XeGPUWgToSgDistribute.cpp
index a24e9b2fd7e0f..4886eeff13bac 100644
--- a/mlir/lib/Dialect/XeGPU/Transforms/XeGPUWgToSgDistribute.cpp
+++ b/mlir/lib/Dialect/XeGPU/Transforms/XeGPUWgToSgDistribute.cpp
@@ -41,7 +41,7 @@ static xegpu::RangeAttr getRangeSpecAttr(Operation *op) {
Operation *parent = op->getParentOfType<scf::IfOp>();
while (parent) {
if (auto attr = llvm::dyn_cast_if_present<xegpu::RangeAttr>(
- parent->getAttr("sg_id_range")))
+ parent->getDiscardableAttr("sg_id_range")))
return attr;
parent = parent->getParentOfType<scf::IfOp>();
}
@@ -485,7 +485,8 @@ struct WgToSgElementwiseOp : public ConversionPattern {
OperationState state(op->getLoc(), op->getName());
state.addOperands(opOperands);
state.addTypes(newResultType);
- state.addAttributes(op->getAttrs());
+ state.addAttributes(op->getDiscardableAttrDictionary().getValue());
+ state.propertiesAttr = op->getPropertiesAsAttribute();
Operation *newOp = rewriter.create(state);
xegpu::removeLayoutAttrs(newOp);
newResults.push_back(newOp->getResult(0));
diff --git a/mlir/lib/Dialect/XeGPU/Utils/XeGPUUtils.cpp b/mlir/lib/Dialect/XeGPU/Utils/XeGPUUtils.cpp
index 07dcb438ca553..01d39f9ec638d 100644
--- a/mlir/lib/Dialect/XeGPU/Utils/XeGPUUtils.cpp
+++ b/mlir/lib/Dialect/XeGPU/Utils/XeGPUUtils.cpp
@@ -160,9 +160,10 @@ xegpu::DistributeLayoutAttr xegpu::getDistributeLayoutAttr(const Value value) {
}
std::string layoutName = getTemporaryLayoutName(result);
- if (defOp->hasAttr(layoutName)) {
+ if (defOp->hasDiscardableAttr(layoutName)) {
auto layout =
- defOp->getAttrOfType<xegpu::DistributeLayoutAttr>(layoutName);
+ defOp->getDiscardableAttrOfType<xegpu::DistributeLayoutAttr>(
+ layoutName);
return layout;
}
}
@@ -254,8 +255,9 @@ xegpu::getDistributeLayoutAttr(const OpOperand &opr) {
}
std::string layoutName = xegpu::getTemporaryLayoutName(opr);
- if (op->hasAttr(layoutName)) {
- auto layout = op->getAttrOfType<xegpu::DistributeLayoutAttr>(layoutName);
+ if (op->hasDiscardableAttr(layoutName)) {
+ auto layout =
+ op->getDiscardableAttrOfType<xegpu::DistributeLayoutAttr>(layoutName);
return layout;
}
@@ -312,11 +314,11 @@ void xegpu::setDistributeLayoutAttr(
}
std::string name = xegpu::getTemporaryLayoutName(result);
- if (owner->hasAttrOfType<DistributeLayoutAttr>(name)) {
+ if (owner->hasDiscardableAttrOfType<DistributeLayoutAttr>(name)) {
return;
}
if (layout) {
- owner->setAttr(name, layout);
+ owner->setDiscardableAttr(name, layout);
}
}
@@ -360,11 +362,11 @@ void xegpu::setDistributeLayoutAttr(const OpOperand &operand,
}
std::string name = xegpu::getTemporaryLayoutName(operand);
- if (owner->hasAttrOfType<DistributeLayoutAttr>(name)) {
+ if (owner->hasDiscardableAttrOfType<DistributeLayoutAttr>(name)) {
return;
}
if (layout) {
- owner->setAttr(name, layout);
+ owner->setDiscardableAttr(name, layout);
}
}
@@ -374,8 +376,9 @@ xegpu::getTemporaryLayout(const T &operandOrResult) {
Operation *op = operandOrResult.getOwner();
std::string layoutName = xegpu::getTemporaryLayoutName(operandOrResult);
- if (op->hasAttr(layoutName)) {
- auto layout = op->getAttrOfType<xegpu::DistributeLayoutAttr>(layoutName);
+ if (op->hasDiscardableAttr(layoutName)) {
+ auto layout =
+ op->getDiscardableAttrOfType<xegpu::DistributeLayoutAttr>(layoutName);
return layout;
}
@@ -392,11 +395,11 @@ void xegpu::setTemporaryLayout(const T &operandOrResult,
const xegpu::DistributeLayoutAttr layout) {
Operation *owner = operandOrResult.getOwner();
std::string name = xegpu::getTemporaryLayoutName(operandOrResult);
- if (owner->hasAttrOfType<xegpu::DistributeLayoutAttr>(name)) {
+ if (owner->hasDiscardableAttrOfType<xegpu::DistributeLayoutAttr>(name)) {
return;
}
if (layout) {
- owner->setAttr(name, layout);
+ owner->setDiscardableAttr(name, layout);
}
}
diff --git a/mlir/lib/IR/AsmPrinter.cpp b/mlir/lib/IR/AsmPrinter.cpp
index c94cf8f77bf6b..ece1fdf3eab33 100644
--- a/mlir/lib/IR/AsmPrinter.cpp
+++ b/mlir/lib/IR/AsmPrinter.cpp
@@ -762,7 +762,11 @@ class DummyAliasOperationPrinter : private OpAsmPrinter {
printType(type);
// Consider the attributes of the operation for aliases.
- for (const NamedAttribute &attr : op->getAttrs())
+ for (const NamedAttribute &attr : op->getDiscardableAttrs())
+ printAttribute(attr.getValue());
+ NamedAttrList inherentAttrs;
+ op->getName().populateInherentAttrs(op, inherentAttrs);
+ for (const NamedAttribute &attr : inherentAttrs)
printAttribute(attr.getValue());
}
@@ -3834,9 +3838,10 @@ void OperationPrinter::printGenericOp(Operation *op, bool printOpName) {
os << ')';
}
- printOptionalAttrDict(op->getPropertiesStorage()
- ? llvm::to_vector(op->getDiscardableAttrs())
- : op->getAttrs());
+ printOptionalAttrDict(
+ op->getPropertiesStorage()
+ ? llvm::to_vector(op->getDiscardableAttrDictionary().getValue())
+ : op->getRawDictionaryAttrs().getValue());
// Print the type signature of the operation.
os << " : ";
diff --git a/mlir/lib/IR/AttrTypeSubElements.cpp b/mlir/lib/IR/AttrTypeSubElements.cpp
index 863e1aa95f2fb..bbc86c4507f9c 100644
--- a/mlir/lib/IR/AttrTypeSubElements.cpp
+++ b/mlir/lib/IR/AttrTypeSubElements.cpp
@@ -94,8 +94,17 @@ void detail::AttrTypeReplacerBase<Concrete>::replaceElementsIn(
// Update the attribute dictionary.
if (replaceAttrs) {
- if (auto newAttrs = replaceIfDifferent(op->getAttrDictionary()))
- op->setAttrs(cast<DictionaryAttr>(newAttrs));
+ if (auto newAttrs = replaceIfDifferent(op->getDiscardableAttrDictionary()))
+ op->setDiscardableAttrs(cast<DictionaryAttr>(newAttrs));
+
+ if (op->getPropertiesStorageSize()) {
+ NamedAttrList inherentAttrs;
+ op->getName().populateInherentAttrs(op, inherentAttrs);
+ for (NamedAttribute attr : inherentAttrs) {
+ if (Attribute replacement = replaceIfDifferent(attr.getValue()))
+ op->setInherentAttr(attr.getName(), replacement);
+ }
+ }
}
// If we aren't updating locations or types, we're done.
diff --git a/mlir/lib/IR/BuiltinAttributes.cpp b/mlir/lib/IR/BuiltinAttributes.cpp
index 0f84f7a682fcf..3a24a77267112 100644
--- a/mlir/lib/IR/BuiltinAttributes.cpp
+++ b/mlir/lib/IR/BuiltinAttributes.cpp
@@ -348,10 +348,9 @@ FlatSymbolRefAttr SymbolRefAttr::get(StringAttr value) {
}
FlatSymbolRefAttr SymbolRefAttr::get(Operation *symbol) {
- auto symName =
- symbol->getAttrOfType<StringAttr>(SymbolTable::getSymbolAttrName());
- assert(symName && "value does not have a valid symbol name");
- return SymbolRefAttr::get(symName);
+ auto symbolOp = dyn_cast<SymbolOpInterface>(symbol);
+ assert(symbolOp && "value does not have a valid symbol name");
+ return SymbolRefAttr::get(symbolOp.getNameAttr());
}
StringAttr SymbolRefAttr::getLeafReference() const {
diff --git a/mlir/lib/IR/BuiltinDialect.cpp b/mlir/lib/IR/BuiltinDialect.cpp
index c88b328282275..f2a84134616e5 100644
--- a/mlir/lib/IR/BuiltinDialect.cpp
+++ b/mlir/lib/IR/BuiltinDialect.cpp
@@ -139,7 +139,8 @@ DataLayoutSpecInterface ModuleOp::getDataLayoutSpec() {
// Take the first and only (if present) attribute that implements the
// interface. This needs a linear search, but is called only once per data
// layout object construction that is used for repeated queries.
- for (NamedAttribute attr : getOperation()->getAttrs())
+ for (NamedAttribute attr :
+ getOperation()->getDiscardableAttrDictionary().getValue())
if (auto spec = llvm::dyn_cast<DataLayoutSpecInterface>(attr.getValue()))
return spec;
return {};
@@ -149,7 +150,8 @@ TargetSystemSpecInterface ModuleOp::getTargetSystemSpec() {
// Take the first and only (if present) attribute that implements the
// interface. This needs a linear search, but is called only once per data
// layout object construction that is used for repeated queries.
- for (NamedAttribute attr : getOperation()->getAttrs())
+ for (NamedAttribute attr :
+ getOperation()->getDiscardableAttrDictionary().getValue())
if (auto spec = llvm::dyn_cast<TargetSystemSpecInterface>(attr.getValue()))
return spec;
return {};
@@ -158,7 +160,7 @@ TargetSystemSpecInterface ModuleOp::getTargetSystemSpec() {
LogicalResult ModuleOp::verify() {
// Check that none of the attributes are non-dialect attributes, except for
// the symbol related attributes.
- for (auto attr : (*this)->getAttrs()) {
+ for (auto attr : (*this)->getDiscardableAttrDictionary().getValue()) {
if (!attr.getName().strref().contains('.') &&
!llvm::is_contained(
ArrayRef<StringRef>{mlir::SymbolTable::getSymbolAttrName(),
@@ -172,7 +174,8 @@ LogicalResult ModuleOp::verify() {
// Check that there is at most one data layout spec attribute.
StringRef layoutSpecAttrName;
DataLayoutSpecInterface layoutSpec;
- for (const NamedAttribute &na : (*this)->getAttrs()) {
+ for (const NamedAttribute &na :
+ (*this)->getDiscardableAttrDictionary().getValue()) {
if (auto spec = llvm::dyn_cast<DataLayoutSpecInterface>(na.getValue())) {
if (layoutSpec) {
InFlightDiagnostic diag =
diff --git a/mlir/lib/IR/Operation.cpp b/mlir/lib/IR/Operation.cpp
index b7227d0802ea8..52ccce03e3c87 100644
--- a/mlir/lib/IR/Operation.cpp
+++ b/mlir/lib/IR/Operation.cpp
@@ -143,7 +143,9 @@ Operation *Operation::create(Location location, OperationName name,
new (&blockOperands[i]) BlockOperand(op, successors[i]);
// This must be done after properties are initialized.
+ LLVM_SUPPRESS_DEPRECATED_DECLARATIONS_PUSH
op->setAttrs(attributes);
+ LLVM_SUPPRESS_DEPRECATED_DECLARATIONS_POP
return op;
}
@@ -1269,7 +1271,10 @@ LogicalResult OpTrait::impl::verifyValueSizeAttr(Operation *op,
StringRef attrName,
StringRef valueGroupName,
size_t expectedCount) {
- auto sizeAttr = op->getAttrOfType<DenseI32ArrayAttr>(attrName);
+ Attribute rawSizeAttr = op->getDiscardableAttr(attrName);
+ if (op->getPropertiesStorageSize())
+ rawSizeAttr = op->getInherentAttr(attrName).value_or(rawSizeAttr);
+ auto sizeAttr = dyn_cast_or_null<DenseI32ArrayAttr>(rawSizeAttr);
if (!sizeAttr)
return op->emitOpError("requires dense i32 array attribute '")
<< attrName << "'";
diff --git a/mlir/lib/IR/OperationSupport.cpp b/mlir/lib/IR/OperationSupport.cpp
index 32c6426429ae8..1b964d9a38f95 100644
--- a/mlir/lib/IR/OperationSupport.cpp
+++ b/mlir/lib/IR/OperationSupport.cpp
@@ -523,7 +523,13 @@ void MutableOperandRange::updateLength(unsigned newLength) {
segments[segment.first] += diff;
segment.second.setValue(
DenseI32ArrayAttr::get(attr.getContext(), segments));
- owner->setAttr(segment.second.getName(), segment.second.getValue());
+ if (owner->getPropertiesStorageSize() &&
+ owner->getInherentAttr(segment.second.getName()))
+ owner->setInherentAttr(segment.second.getName(),
+ segment.second.getValue());
+ else
+ owner->setDiscardableAttr(segment.second.getName(),
+ segment.second.getValue());
}
}
diff --git a/mlir/lib/IR/PatternMatch.cpp b/mlir/lib/IR/PatternMatch.cpp
index cd067f2cc25b3..0b080d2920230 100644
--- a/mlir/lib/IR/PatternMatch.cpp
+++ b/mlir/lib/IR/PatternMatch.cpp
@@ -260,7 +260,9 @@ Operation *RewriterBase::eraseOpResults(Operation *op,
InsertionGuard g(*this);
setInsertionPoint(op);
OperationState state(op->getLoc(), op->getName().getStringRef(),
- op->getOperands(), newResultTypes, op->getAttrs());
+ op->getOperands(), newResultTypes,
+ op->getDiscardableAttrDictionary().getValue());
+ state.propertiesAttr = op->getPropertiesAsAttribute();
for ([[maybe_unused]] auto i : llvm::seq<unsigned>(0, op->getNumRegions()))
state.addRegion();
Operation *newOp = create(state);
diff --git a/mlir/lib/IR/SymbolTable.cpp b/mlir/lib/IR/SymbolTable.cpp
index 100eba7146d81..0c9b21f6dcf8a 100644
--- a/mlir/lib/IR/SymbolTable.cpp
+++ b/mlir/lib/IR/SymbolTable.cpp
@@ -22,13 +22,21 @@ static bool isPotentiallyUnknownSymbolTable(Operation *op) {
return op->getNumRegions() == 1 && !op->getDialect();
}
+static Attribute getSymbolAttribute(Operation *op, StringRef name) {
+ if (op->getPropertiesStorageSize())
+ if (std::optional<Attribute> inherent = op->getInherentAttr(name))
+ return *inherent;
+ return op->getDiscardableAttr(name);
+}
+
/// Returns the string name of the given symbol, or null if this is not a
/// symbol.
static StringAttr getNameIfSymbol(Operation *op) {
- return op->getAttrOfType<StringAttr>(SymbolTable::getSymbolAttrName());
+ return dyn_cast_or_null<StringAttr>(
+ getSymbolAttribute(op, SymbolTable::getSymbolAttrName()));
}
static StringAttr getNameIfSymbol(Operation *op, StringAttr symbolAttrNameId) {
- return op->getAttrOfType<StringAttr>(symbolAttrNameId);
+ return dyn_cast_or_null<StringAttr>(getSymbolAttribute(op, symbolAttrNameId));
}
/// Computes the nested symbol reference attribute for the symbol 'symbolName'
@@ -299,13 +307,19 @@ StringAttr SymbolTable::getSymbolName(Operation *symbol) {
/// Sets the name of the given symbol operation.
void SymbolTable::setSymbolName(Operation *symbol, StringAttr name) {
- symbol->setAttr(getSymbolAttrName(), name);
+ StringAttr attrName =
+ StringAttr::get(symbol->getContext(), getSymbolAttrName());
+ if (symbol->getPropertiesStorageSize() && symbol->getInherentAttr(attrName))
+ symbol->setInherentAttr(attrName, name);
+ else
+ symbol->setDiscardableAttr(attrName, name);
}
/// Returns the visibility of the given symbol operation.
SymbolTable::Visibility SymbolTable::getSymbolVisibility(Operation *symbol) {
// If the attribute doesn't exist, assume public.
- StringAttr vis = symbol->getAttrOfType<StringAttr>(getVisibilityAttrName());
+ StringAttr vis = dyn_cast_or_null<StringAttr>(
+ getSymbolAttribute(symbol, getVisibilityAttrName()));
if (!vis)
return Visibility::Public;
@@ -322,7 +336,11 @@ void SymbolTable::setSymbolVisibility(Operation *symbol, Visibility vis) {
// If the visibility is public, just drop the attribute as this is the
// default.
if (vis == Visibility::Public) {
- symbol->removeAttr(StringAttr::get(ctx, getVisibilityAttrName()));
+ StringAttr attrName = StringAttr::get(ctx, getVisibilityAttrName());
+ if (symbol->getPropertiesStorageSize() && symbol->getInherentAttr(attrName))
+ symbol->setInherentAttr(attrName, {});
+ else
+ symbol->removeDiscardableAttr(attrName);
return;
}
@@ -331,7 +349,11 @@ void SymbolTable::setSymbolVisibility(Operation *symbol, Visibility vis) {
"unknown symbol visibility kind");
StringRef visName = vis == Visibility::Private ? "private" : "nested";
- symbol->setAttr(getVisibilityAttrName(), StringAttr::get(ctx, visName));
+ StringAttr attrName = StringAttr::get(ctx, getVisibilityAttrName());
+ if (symbol->getPropertiesStorageSize() && symbol->getInherentAttr(attrName))
+ symbol->setInherentAttr(attrName, StringAttr::get(ctx, visName));
+ else
+ symbol->setDiscardableAttr(attrName, StringAttr::get(ctx, visName));
}
/// Returns the nearest symbol table from a given operation `from`. Returns
@@ -512,13 +534,19 @@ static LogicalResult verifyOpTypeSymbolUses(Operation *op,
return failure();
// Verify types nested within the operation's attributes.
- WalkResult attrResult =
- op->getAttrDictionary().walk<WalkOrder::PreOrder>([&](Type type) {
- if (verify(type).wasInterrupted())
- return WalkResult::interrupt();
- return WalkResult::advance();
- });
- return failure(attrResult.wasInterrupted());
+ auto verifyTypes = [&](Attribute attr) {
+ return attr.walk<WalkOrder::PreOrder>([&](Type type) {
+ if (verify(type).wasInterrupted())
+ return WalkResult::interrupt();
+ return WalkResult::advance();
+ });
+ };
+ if (verifyTypes(op->getRawDictionaryAttrs()).wasInterrupted())
+ return failure();
+ if (Attribute properties = op->getPropertiesAsAttribute())
+ if (verifyTypes(properties).wasInterrupted())
+ return failure();
+ return success();
}
LogicalResult detail::verifySymbolTable(Operation *op) {
@@ -534,8 +562,7 @@ LogicalResult detail::verifySymbolTable(Operation *op) {
for (auto &block : op->getRegion(0)) {
for (auto &op : block) {
// Check for a symbol name attribute.
- auto nameAttr =
- op.getAttrOfType<StringAttr>(mlir::SymbolTable::getSymbolAttrName());
+ StringAttr nameAttr = getNameIfSymbol(&op);
if (!nameAttr)
continue;
@@ -562,7 +589,7 @@ LogicalResult detail::verifySymbolTable(Operation *op) {
if (SymbolUserOpInterface user = dyn_cast<SymbolUserOpInterface>(op))
if (failed(user.verifySymbolUses(symbolTable)))
return WalkResult::interrupt();
- for (auto &attr : op->getDiscardableAttrs()) {
+ for (auto &attr : op->getDiscardableAttrDictionary().getValue()) {
if (auto user = dyn_cast<SymbolUserAttrInterface>(attr.getValue())) {
if (!verifiedAttrs.insert(attr.getValue()))
continue;
@@ -582,12 +609,13 @@ LogicalResult detail::verifySymbolTable(Operation *op) {
LogicalResult detail::verifySymbol(Operation *op) {
// Verify the name attribute.
- if (!op->getAttrOfType<StringAttr>(mlir::SymbolTable::getSymbolAttrName()))
+ if (!getNameIfSymbol(op))
return op->emitOpError() << "requires string attribute '"
<< mlir::SymbolTable::getSymbolAttrName() << "'";
// Verify the visibility attribute.
- if (Attribute vis = op->getAttr(mlir::SymbolTable::getVisibilityAttrName())) {
+ if (Attribute vis =
+ getSymbolAttribute(op, mlir::SymbolTable::getVisibilityAttrName())) {
StringAttr visStrAttr = llvm::dyn_cast<StringAttr>(vis);
if (!visStrAttr)
return op->emitOpError() << "requires visibility attribute '"
@@ -614,14 +642,20 @@ LogicalResult detail::verifySymbol(Operation *op) {
static WalkResult
walkSymbolRefs(Operation *op,
function_ref<WalkResult(SymbolTable::SymbolUse)> callback) {
- return op->getAttrDictionary().walk<WalkOrder::PreOrder>(
- [&](SymbolRefAttr symbolRef) {
- if (callback({op, symbolRef}).wasInterrupted())
- return WalkResult::interrupt();
+ auto walk = [&](Attribute attr) {
+ return attr.walk<WalkOrder::PreOrder>([&](SymbolRefAttr symbolRef) {
+ if (callback({op, symbolRef}).wasInterrupted())
+ return WalkResult::interrupt();
- // Don't walk nested references.
- return WalkResult::skip();
- });
+ // Don't walk nested references.
+ return WalkResult::skip();
+ });
+ };
+ if (walk(op->getRawDictionaryAttrs()).wasInterrupted())
+ return WalkResult::interrupt();
+ if (Attribute properties = op->getPropertiesAsAttribute())
+ return walk(properties);
+ return WalkResult::advance();
}
/// Walk all of the uses, for any symbol, that are nested within the given
diff --git a/mlir/lib/Interfaces/FunctionImplementation.cpp b/mlir/lib/Interfaces/FunctionImplementation.cpp
index 90f32896e8181..cc4eeedf69352 100644
--- a/mlir/lib/Interfaces/FunctionImplementation.cpp
+++ b/mlir/lib/Interfaces/FunctionImplementation.cpp
@@ -169,21 +169,27 @@ void function_interface_impl::printFunctionAttributes(
SmallVector<StringRef, 8> ignoredAttrs = {SymbolTable::getSymbolAttrName()};
ignoredAttrs.append(elided.begin(), elided.end());
- p.printOptionalAttrDictWithKeyword(op->getAttrs(), ignoredAttrs);
+ NamedAttrList attrs(op->getDiscardableAttrDictionary().getValue());
+ op->getName().populateInherentAttrs(op, attrs);
+ p.printOptionalAttrDictWithKeyword(attrs, ignoredAttrs);
}
void function_interface_impl::printFunctionOp(
OpAsmPrinter &p, FunctionOpInterface op, bool isVariadic,
StringRef typeAttrName, StringAttr argAttrsName, StringAttr resAttrsName) {
// Print the operation and the function name.
- auto funcName =
- op->getAttrOfType<StringAttr>(SymbolTable::getSymbolAttrName())
- .getValue();
+ auto symbol = cast<SymbolOpInterface>(op.getOperation());
+ StringRef funcName = symbol.getName();
p << ' ';
StringRef visibilityAttrName = SymbolTable::getVisibilityAttrName();
- if (auto visibility = op->getAttrOfType<StringAttr>(visibilityAttrName))
- p << visibility.getValue() << ' ';
+ std::optional<Attribute> inherentVisibility =
+ op->getInherentAttr(visibilityAttrName);
+ Attribute visibility = inherentVisibility.has_value()
+ ? *inherentVisibility
+ : op->getDiscardableAttr(visibilityAttrName);
+ if (auto value = dyn_cast_or_null<StringAttr>(visibility))
+ p << value.getValue() << ' ';
p.printSymbolName(funcName);
ArrayRef<Type> argTypes = op.getArgumentTypes();
diff --git a/mlir/lib/Interfaces/Utils/MemorySlotUtils.cpp b/mlir/lib/Interfaces/Utils/MemorySlotUtils.cpp
index c497970b8b188..9beadc1a13c4a 100644
--- a/mlir/lib/Interfaces/Utils/MemorySlotUtils.cpp
+++ b/mlir/lib/Interfaces/Utils/MemorySlotUtils.cpp
@@ -31,7 +31,8 @@ Operation *mlir::memoryslot::replaceWithNewResults(RewriterBase &rewriter,
RewriterBase::InsertionGuard guard(rewriter);
rewriter.setInsertionPoint(op);
OperationState state(op->getLoc(), op->getName(), op->getOperands(),
- resultTypes, op->getAttrs());
+ resultTypes,
+ op->getDiscardableAttrDictionary().getValue());
state.propertiesAttr = op->getPropertiesAsAttribute();
unsigned numRegions = op->getNumRegions();
for (unsigned i = 0; i < numRegions; ++i)
diff --git a/mlir/lib/Pass/IRPrinting.cpp b/mlir/lib/Pass/IRPrinting.cpp
index 006ce3cbe794a..61a6adb0f1a24 100644
--- a/mlir/lib/Pass/IRPrinting.cpp
+++ b/mlir/lib/Pass/IRPrinting.cpp
@@ -70,9 +70,8 @@ static void printIRHeader(raw_ostream &out, StringRef title, Pass *pass,
pass->printAsTextualPipeline(out);
if (printModuleScope) {
out << " ('" << op->getName() << "' operation";
- if (auto symbolName =
- op->getAttrOfType<StringAttr>(SymbolTable::getSymbolAttrName()))
- out << ": @" << symbolName.getValue();
+ if (auto symbol = dyn_cast<SymbolOpInterface>(op))
+ out << ": @" << symbol.getName();
out << ")";
}
out << " //----- //\n";
@@ -230,10 +229,8 @@ getOpAndSymbolNames(Operation *op, StringRef passName,
++counters.try_emplace(op, -1).first->second;
while (iter) {
countPrefix.push_back(counters[iter]);
- StringAttr symbolNameAttr =
- iter->getAttrOfType<StringAttr>(SymbolTable::getSymbolAttrName());
- std::string symbolName =
- symbolNameAttr ? symbolNameAttr.str() : "no-symbol-name";
+ auto symbol = dyn_cast<SymbolOpInterface>(iter);
+ std::string symbolName = symbol ? symbol.getName().str() : "no-symbol-name";
llvm::replace(symbolName, '/', '_');
llvm::replace(symbolName, '\\', '_');
diff --git a/mlir/lib/Rewrite/ByteCode.cpp b/mlir/lib/Rewrite/ByteCode.cpp
index 2daf2635d96d5..27cacbbb07749 100644
--- a/mlir/lib/Rewrite/ByteCode.cpp
+++ b/mlir/lib/Rewrite/ByteCode.cpp
@@ -1788,7 +1788,9 @@ void ByteCodeExecutor::executeGetAttribute() {
unsigned memIndex = read();
Operation *op = read<Operation *>();
StringAttr attrName = read<StringAttr>();
- Attribute attr = op->getAttr(attrName);
+ Attribute attr = op->getDiscardableAttr(attrName);
+ if (op->getPropertiesStorageSize())
+ attr = op->getInherentAttr(attrName).value_or(attr);
LDBG() << " * Operation: " << *op << "\n * Attribute: " << attrName
<< "\n * Result: " << attr;
@@ -1857,7 +1859,11 @@ executeGetOperandsResults(RangeT values, Operation *op, unsigned index,
} else if (op->hasTrait<AttrSizedSegmentsT>()) {
LDBG() << " * Extracting values from `" << attrSizedSegments << "`";
- auto segmentAttr = op->getAttrOfType<DenseI32ArrayAttr>(attrSizedSegments);
+ Attribute rawSegmentAttr = op->getDiscardableAttr(attrSizedSegments);
+ if (op->getPropertiesStorageSize())
+ rawSegmentAttr =
+ op->getInherentAttr(attrSizedSegments).value_or(rawSegmentAttr);
+ auto segmentAttr = dyn_cast_or_null<DenseI32ArrayAttr>(rawSegmentAttr);
if (!segmentAttr || segmentAttr.asArrayRef().size() <= index)
return nullptr;
diff --git a/mlir/lib/Target/Cpp/TranslateToCpp.cpp b/mlir/lib/Target/Cpp/TranslateToCpp.cpp
index d5815fafcd6a7..8ec07bdae0ec2 100644
--- a/mlir/lib/Target/Cpp/TranslateToCpp.cpp
+++ b/mlir/lib/Target/Cpp/TranslateToCpp.cpp
@@ -1836,9 +1836,11 @@ CppEmitter::emitOperandsAndAttributes(Operation &op,
ArrayRef<StringRef> exclude) {
if (failed(emitOperands(op)))
return failure();
+ NamedAttrList attrs(op.getRawDictionaryAttrs());
+ op.getName().populateInherentAttrs(&op, attrs);
// Insert comma in between operands and non-filtered attributes if needed.
if (op.getNumOperands() > 0) {
- for (NamedAttribute attr : op.getAttrs()) {
+ for (NamedAttribute attr : attrs) {
if (!llvm::is_contained(exclude, attr.getName().strref())) {
os << ", ";
break;
@@ -1854,7 +1856,7 @@ CppEmitter::emitOperandsAndAttributes(Operation &op,
return failure();
return success();
};
- return interleaveCommaWithError(op.getAttrs(), os, emitNamedAttribute);
+ return interleaveCommaWithError(attrs, os, emitNamedAttribute);
}
LogicalResult CppEmitter::emitVariableAssignment(OpResult result) {
diff --git a/mlir/lib/Target/LLVM/XeVM/Target.cpp b/mlir/lib/Target/LLVM/XeVM/Target.cpp
index 18f6b7b3e67c8..731ac4bd677f9 100644
--- a/mlir/lib/Target/LLVM/XeVM/Target.cpp
+++ b/mlir/lib/Target/LLVM/XeVM/Target.cpp
@@ -619,7 +619,8 @@ XeVMTargetAttrImpl::serializeToObject(Attribute attribute, Operation *module,
auto xeTarget = cast<XeVMTargetAttr>(attribute);
if (xeTarget.getTriple().starts_with("spirv")) {
gpuMod.walk([&](LLVM::LLVMFuncOp funcOp) {
- if (funcOp->hasAttr(gpu::GPUDialect::getKernelFuncAttrName())) {
+ if (funcOp->hasDiscardableAttr(
+ gpu::GPUDialect::getKernelFuncAttrName())) {
funcOp.setIntelReqdSubGroupSize(16);
return WalkResult::interrupt();
}
diff --git a/mlir/lib/Target/LLVMIR/Dialect/LLVMIR/LLVMIRToLLVMTranslation.cpp b/mlir/lib/Target/LLVMIR/Dialect/LLVMIR/LLVMIRToLLVMTranslation.cpp
index b6dee4e89ee4c..6733d6ee3ceb0 100644
--- a/mlir/lib/Target/LLVMIR/Dialect/LLVMIR/LLVMIRToLLVMTranslation.cpp
+++ b/mlir/lib/Target/LLVMIR/Dialect/LLVMIR/LLVMIRToLLVMTranslation.cpp
@@ -285,7 +285,7 @@ static LogicalResult setMmraAttr(llvm::MDNode *node, Operation *op,
}
mlirMmra = ArrayAttr::get(ctx, tags);
}
- op->setAttr(LLVMDialect::getMmraAttrName(), mlirMmra);
+ op->setDiscardableAttr(LLVMDialect::getMmraAttrName(), mlirMmra);
return success();
}
diff --git a/mlir/lib/Target/LLVMIR/Dialect/LLVMIR/LLVMToLLVMIRTranslation.cpp b/mlir/lib/Target/LLVMIR/Dialect/LLVMIR/LLVMToLLVMIRTranslation.cpp
index 3e0a228c773d5..aa62d0d0db4b1 100644
--- a/mlir/lib/Target/LLVMIR/Dialect/LLVMIR/LLVMToLLVMIRTranslation.cpp
+++ b/mlir/lib/Target/LLVMIR/Dialect/LLVMIR/LLVMToLLVMIRTranslation.cpp
@@ -639,7 +639,7 @@ convertOperationImpl(Operation &opInst, llvm::IRBuilderBase &builder,
invOp.getOpBundleTags(), moduleTranslation);
ArrayRef<llvm::Value *> operandsRef(operands);
llvm::InvokeInst *result;
- if (auto attr = opInst.getAttrOfType<FlatSymbolRefAttr>("callee")) {
+ if (auto attr = invOp.getCalleeAttr()) {
if (llvm::Function *function =
moduleTranslation.lookupFunction(attr.getValue())) {
result = builder.CreateInvoke(
diff --git a/mlir/lib/Target/LLVMIR/Dialect/OpenMP/OpenMPToLLVMIRTranslation.cpp b/mlir/lib/Target/LLVMIR/Dialect/OpenMP/OpenMPToLLVMIRTranslation.cpp
index 1a861767b5512..bb20290b86822 100644
--- a/mlir/lib/Target/LLVMIR/Dialect/OpenMP/OpenMPToLLVMIRTranslation.cpp
+++ b/mlir/lib/Target/LLVMIR/Dialect/OpenMP/OpenMPToLLVMIRTranslation.cpp
@@ -5715,8 +5715,7 @@ static void extractAtomicControlFlags(omp::AtomicUpdateOp atomicUpdateOp,
isIgnoreDenormalMode = false;
isFineGrainedMemory = false;
isRemoteMemory = false;
- if (atomicUpdateOp &&
- atomicUpdateOp->hasAttr(atomicUpdateOp.getAtomicControlAttrName())) {
+ if (atomicUpdateOp && atomicUpdateOp.getAtomicControlAttr()) {
mlir::omp::AtomicControlAttr atomicControlAttr =
atomicUpdateOp.getAtomicControlAttr();
isIgnoreDenormalMode = atomicControlAttr.getIgnoreDenormalMode();
@@ -9827,7 +9826,7 @@ convertDeclareTargetAttr(Operation *op, mlir::omp::DeclareTargetAttr attribute,
std::vector<llvm::Triple> targetTriple;
auto targetTripleAttr = dyn_cast_or_null<mlir::StringAttr>(
- op->getParentOfType<mlir::ModuleOp>()->getAttr(
+ op->getParentOfType<mlir::ModuleOp>()->getDiscardableAttr(
LLVM::LLVMDialect::getTargetTripleAttrName()));
if (targetTripleAttr)
targetTriple.emplace_back(targetTripleAttr.data());
diff --git a/mlir/lib/Target/LLVMIR/Dialect/ROCDL/ROCDLToLLVMIRTranslation.cpp b/mlir/lib/Target/LLVMIR/Dialect/ROCDL/ROCDLToLLVMIRTranslation.cpp
index 42393218f8705..18eb07a9e17df 100644
--- a/mlir/lib/Target/LLVMIR/Dialect/ROCDL/ROCDLToLLVMIRTranslation.cpp
+++ b/mlir/lib/Target/LLVMIR/Dialect/ROCDL/ROCDLToLLVMIRTranslation.cpp
@@ -195,8 +195,8 @@ class ROCDLDialectLLVMIRTranslationInterface
StringRef flatAttrName =
dialect->getFlatWorkGroupSizeAttrHelper().getName();
- if (auto flatAttr =
- dyn_cast_if_present<StringAttr>(op->getAttr(flatAttrName))) {
+ if (auto flatAttr = dyn_cast_if_present<StringAttr>(
+ op->getDiscardableAttr(flatAttrName))) {
if (flatAttr.getValue() != expectedFlatWorkGroupSize)
return op->emitOpError(Twine(flatAttrName) +
" must match rocdl.reqd_work_group_size");
@@ -204,8 +204,8 @@ class ROCDLDialectLLVMIRTranslationInterface
StringRef maxFlatAttrName =
dialect->getMaxFlatWorkGroupSizeAttrHelper().getName();
- if (auto maxFlatAttr =
- dyn_cast_if_present<IntegerAttr>(op->getAttr(maxFlatAttrName))) {
+ if (auto maxFlatAttr = dyn_cast_if_present<IntegerAttr>(
+ op->getDiscardableAttr(maxFlatAttrName))) {
llvm::SmallString<16> expectedMaxFlatWorkGroupSize;
llvm::raw_svector_ostream maxAttrValueStream(
expectedMaxFlatWorkGroupSize);
diff --git a/mlir/lib/Target/LLVMIR/ModuleImport.cpp b/mlir/lib/Target/LLVMIR/ModuleImport.cpp
index 2ab4529ddef53..a22b3524a3c89 100644
--- a/mlir/lib/Target/LLVMIR/ModuleImport.cpp
+++ b/mlir/lib/Target/LLVMIR/ModuleImport.cpp
@@ -1025,8 +1025,9 @@ LogicalResult ModuleImport::convertDependentLibrariesMetadata() {
libraries.push_back(mdString->getString());
}
if (!libraries.empty())
- mlirModule->setAttr(LLVM::LLVMDialect::getDependentLibrariesAttrName(),
- builder.getStrArrayAttr(libraries));
+ mlirModule->setDiscardableAttr(
+ LLVM::LLVMDialect::getDependentLibrariesAttrName(),
+ builder.getStrArrayAttr(libraries));
}
return success();
}
@@ -1042,8 +1043,9 @@ LogicalResult ModuleImport::convertIdentMetadata() {
if (auto *md = dyn_cast<llvm::MDNode>(named.getOperand(0)))
if (md->getNumOperands() == 1)
if (auto *mdStr = dyn_cast<llvm::MDString>(md->getOperand(0)))
- mlirModule->setAttr(LLVMDialect::getIdentAttrName(),
- builder.getStringAttr(mdStr->getString()));
+ mlirModule->setDiscardableAttr(
+ LLVMDialect::getIdentAttrName(),
+ builder.getStringAttr(mdStr->getString()));
}
return success();
}
@@ -1059,8 +1061,9 @@ LogicalResult ModuleImport::convertCommandlineMetadata() {
if (auto *md = dyn_cast<llvm::MDNode>(nmd.getOperand(0)))
if (md->getNumOperands() == 1)
if (auto *mdStr = dyn_cast<llvm::MDString>(md->getOperand(0)))
- mlirModule->setAttr(LLVMDialect::getCommandlineAttrName(),
- builder.getStringAttr(mdStr->getString()));
+ mlirModule->setDiscardableAttr(
+ LLVMDialect::getCommandlineAttrName(),
+ builder.getStringAttr(mdStr->getString()));
}
return success();
}
@@ -1179,13 +1182,13 @@ LogicalResult ModuleImport::convertDataLayout() {
for (StringRef token : dataLayoutImporter.getUnhandledTokens())
emitWarning(loc, "unhandled data layout token: ") << token;
- mlirModule->setAttr(DLTIDialect::kDataLayoutAttrName,
- dataLayoutImporter.getDataLayoutSpec());
+ mlirModule->setDiscardableAttr(DLTIDialect::kDataLayoutAttrName,
+ dataLayoutImporter.getDataLayoutSpec());
return success();
}
void ModuleImport::convertTargetTriple() {
- mlirModule->setAttr(
+ mlirModule->setDiscardableAttr(
LLVM::LLVMDialect::getTargetTripleAttrName(),
builder.getStringAttr(llvmModule->getTargetTriple().str()));
}
@@ -1201,8 +1204,8 @@ void ModuleImport::convertModuleLevelAsm() {
asmArrayAttr.push_back(builder.getStringAttr(line));
}
- mlirModule->setAttr(LLVM::LLVMDialect::getModuleLevelAsmAttrName(),
- builder.getArrayAttr(asmArrayAttr));
+ mlirModule->setDiscardableAttr(LLVM::LLVMDialect::getModuleLevelAsmAttrName(),
+ builder.getArrayAttr(asmArrayAttr));
}
LogicalResult ModuleImport::convertFunctions() {
@@ -1284,7 +1287,7 @@ void ModuleImport::setFastmathFlagsAttr(llvm::Instruction *inst,
value = bitEnumSet(value, FastmathFlags::afn, flags.approxFunc());
value = bitEnumSet(value, FastmathFlags::reassoc, flags.allowReassoc());
FastmathFlagsAttr attr = FastmathFlagsAttr::get(builder.getContext(), value);
- iface->setAttr(iface.getFastmathAttrName(), attr);
+ iface.setFastmathAttr(attr);
}
/// Returns `type` if it is a builtin integer or floating-point vector type that
diff --git a/mlir/lib/Target/LLVMIR/ModuleTranslation.cpp b/mlir/lib/Target/LLVMIR/ModuleTranslation.cpp
index b87a581a5185e..eed0ee3f8f1d2 100644
--- a/mlir/lib/Target/LLVMIR/ModuleTranslation.cpp
+++ b/mlir/lib/Target/LLVMIR/ModuleTranslation.cpp
@@ -949,9 +949,11 @@ llvm::CallInst *mlir::LLVM::detail::createIntrinsicCall(
SmallVector<llvm::OperandBundleDef> opBundles;
size_t numOpBundleOperands = 0;
auto opBundleSizesAttr = cast_if_present<DenseI32ArrayAttr>(
- intrOp->getAttr(LLVMDialect::getOpBundleSizesAttrName()));
+ intrOp->getInherentAttr(LLVMDialect::getOpBundleSizesAttrName())
+ .value_or(Attribute{}));
auto opBundleTagsAttr = cast_if_present<ArrayAttr>(
- intrOp->getAttr(LLVMDialect::getOpBundleTagsAttrName()));
+ intrOp->getInherentAttr(LLVMDialect::getOpBundleTagsAttrName())
+ .value_or(Attribute{}));
if (opBundleSizesAttr && opBundleTagsAttr) {
ArrayRef<int> opBundleSizes = opBundleSizesAttr.asArrayRef();
@@ -982,7 +984,7 @@ llvm::CallInst *mlir::LLVM::detail::createIntrinsicCall(
SmallVector<llvm::Value *> args(immArgPositions.size() + operands.size());
for (auto [immArgPos, immArgName] :
llvm::zip(immArgPositions, immArgAttrNames)) {
- Attribute attr = intrOp->getAttr(immArgName);
+ Attribute attr = intrOp->getInherentAttr(immArgName).value_or(Attribute{});
if (auto intrinsicIntegerAttr =
dyn_cast<LLVM::IntrinsicIntegerAttrInterface>(attr))
attr = intrinsicIntegerAttr.getIntegerAttr();
@@ -2426,7 +2428,7 @@ LogicalResult ModuleTranslation::createTBAAMetadata() {
}
LogicalResult ModuleTranslation::createIdentMetadata() {
- if (auto attr = mlirModule->getAttrOfType<StringAttr>(
+ if (auto attr = mlirModule->getDiscardableAttrOfType<StringAttr>(
LLVMDialect::getIdentAttrName())) {
StringRef ident = attr;
llvm::LLVMContext &ctx = llvmModule->getContext();
@@ -2440,7 +2442,7 @@ LogicalResult ModuleTranslation::createIdentMetadata() {
}
LogicalResult ModuleTranslation::createCommandlineMetadata() {
- if (auto attr = mlirModule->getAttrOfType<StringAttr>(
+ if (auto attr = mlirModule->getDiscardableAttrOfType<StringAttr>(
LLVMDialect::getCommandlineAttrName())) {
StringRef cmdLine = attr;
llvm::LLVMContext &ctx = llvmModule->getContext();
diff --git a/mlir/lib/Target/LLVMIR/Transforms/TargetToDataLayout.cpp b/mlir/lib/Target/LLVMIR/Transforms/TargetToDataLayout.cpp
index c0f9ceb6313d0..1246c9cacf98f 100644
--- a/mlir/lib/Target/LLVMIR/Transforms/TargetToDataLayout.cpp
+++ b/mlir/lib/Target/LLVMIR/Transforms/TargetToDataLayout.cpp
@@ -33,7 +33,7 @@ struct TargetToDataLayoutPass
if (initializeLLVMTargets)
LLVM::detail::initializeBackendsOnce();
- auto targetAttr = op->getAttrOfType<LLVM::TargetAttrInterface>(
+ auto targetAttr = op->getDiscardableAttrOfType<LLVM::TargetAttrInterface>(
LLVM::LLVMDialect::getTargetAttrName());
if (!targetAttr) {
op->emitError()
@@ -52,11 +52,12 @@ struct TargetToDataLayoutPass
DataLayoutSpecInterface dataLayoutSpec =
mlir::translateDataLayout(dataLayout.value(), &getContext());
- if (auto existingDlSpec = op->getAttrOfType<DataLayoutSpecInterface>(
- DLTIDialect::kDataLayoutAttrName)) {
+ if (auto existingDlSpec =
+ op->getDiscardableAttrOfType<DataLayoutSpecInterface>(
+ DLTIDialect::kDataLayoutAttrName)) {
dataLayoutSpec = existingDlSpec.combineWith({dataLayoutSpec});
}
- op->setAttr(DLTIDialect::kDataLayoutAttrName, dataLayoutSpec);
+ op->setDiscardableAttr(DLTIDialect::kDataLayoutAttrName, dataLayoutSpec);
}
};
diff --git a/mlir/lib/Target/LLVMIR/Transforms/TargetToTargetFeatures.cpp b/mlir/lib/Target/LLVMIR/Transforms/TargetToTargetFeatures.cpp
index 24f37cce513af..0cc5f5aabb630 100644
--- a/mlir/lib/Target/LLVMIR/Transforms/TargetToTargetFeatures.cpp
+++ b/mlir/lib/Target/LLVMIR/Transforms/TargetToTargetFeatures.cpp
@@ -37,7 +37,7 @@ struct TargetToTargetFeaturesPass
if (initializeLLVMTargets)
LLVM::detail::initializeBackendsOnce();
- auto targetAttr = op->getAttrOfType<LLVM::TargetAttr>(
+ auto targetAttr = op->getDiscardableAttrOfType<LLVM::TargetAttr>(
LLVM::LLVMDialect::getTargetAttrName());
if (!targetAttr) {
op->emitError() << "no LLVM::TargetAttr attribute at key \""
@@ -74,6 +74,7 @@ struct TargetToTargetFeaturesPass
LLVM::TargetAttr::get(&getContext(), targetAttr.getTriple(),
targetAttr.getChip(), fullTargetFeaturesAttr);
- op->setAttr(LLVM::LLVMDialect::getTargetAttrName(), updatedTargetAttr);
+ op->setDiscardableAttr(LLVM::LLVMDialect::getTargetAttrName(),
+ updatedTargetAttr);
}
};
diff --git a/mlir/lib/Target/SPIRV/Deserialization/Deserializer.cpp b/mlir/lib/Target/SPIRV/Deserialization/Deserializer.cpp
index 9e44f43ad889d..8e02d070c0cfa 100644
--- a/mlir/lib/Target/SPIRV/Deserialization/Deserializer.cpp
+++ b/mlir/lib/Target/SPIRV/Deserialization/Deserializer.cpp
@@ -44,6 +44,15 @@ static inline bool isFnEntryBlock(Block *block) {
isa_and_nonnull<spirv::FuncOp>(block->getParentOp());
}
+static void setInherentOrDiscardableAttr(Operation *op, StringAttr name,
+ Attribute value) {
+ if (op->getName().getInherentAttr(op, name).has_value()) {
+ op->getName().setInherentAttr(op, name, value);
+ return;
+ }
+ op->setDiscardableAttr(name, value);
+}
+
//===----------------------------------------------------------------------===//
// Deserializer Method Definitions
//===----------------------------------------------------------------------===//
@@ -208,10 +217,8 @@ spirv::Deserializer::processExtInstImport(ArrayRef<uint32_t> words) {
}
void spirv::Deserializer::attachVCETriple() {
- (*module)->setAttr(
- spirv::ModuleOp::getVCETripleAttrName(),
- spirv::VerCapExtAttr::get(version, capabilities.getArrayRef(),
- extensions.getArrayRef(), context));
+ module->setVceTripleAttr(spirv::VerCapExtAttr::get(
+ version, capabilities.getArrayRef(), extensions.getArrayRef(), context));
}
LogicalResult
@@ -219,14 +226,10 @@ spirv::Deserializer::processMemoryModel(ArrayRef<uint32_t> operands) {
if (operands.size() != 2)
return emitError(unknownLoc, "OpMemoryModel must have two operands");
- (*module)->setAttr(
- module->getAddressingModelAttrName(),
- opBuilder.getAttr<spirv::AddressingModelAttr>(
- static_cast<spirv::AddressingModel>(operands.front())));
+ module->setAddressingModel(
+ static_cast<spirv::AddressingModel>(operands.front()));
- (*module)->setAttr(module->getMemoryModelAttrName(),
- opBuilder.getAttr<spirv::MemoryModelAttr>(
- static_cast<spirv::MemoryModel>(operands.back())));
+ module->setMemoryModel(static_cast<spirv::MemoryModel>(operands.back()));
return success();
}
@@ -438,7 +441,7 @@ LogicalResult spirv::Deserializer::resolveDeferredIdDecorations() {
<< decorationName << " references unknown target <id> "
<< entry.targetID;
- targetOp->setAttr(symbol, symRef);
+ setInherentOrDiscardableAttr(targetOp, symbol, symRef);
}
return success();
}
@@ -580,7 +583,7 @@ spirv::Deserializer::processFunction(ArrayRef<uint32_t> operands) {
// Processing other function attributes.
if (decorations.count(fnID)) {
for (auto attr : decorations[fnID].getAttrs()) {
- funcOp->setAttr(attr.getName(), attr.getValue());
+ setInherentOrDiscardableAttr(funcOp, attr.getName(), attr.getValue());
}
}
curFunction = funcMap[fnID] = funcOp;
@@ -986,7 +989,7 @@ spirv::Deserializer::createSpecConstant(Location loc, uint32_t resultID,
defaultValue);
if (decorations.count(resultID)) {
for (auto attr : decorations[resultID].getAttrs())
- op->setAttr(attr.getName(), attr.getValue());
+ setInherentOrDiscardableAttr(op, attr.getName(), attr.getValue());
}
specConstMap[resultID] = op;
return op;
@@ -1073,7 +1076,7 @@ spirv::Deserializer::processGlobalVariable(ArrayRef<uint32_t> operands) {
// Decorations.
if (decorations.count(variableID)) {
for (auto attr : decorations[variableID].getAttrs())
- varOp->setAttr(attr.getName(), attr.getValue());
+ setInherentOrDiscardableAttr(varOp, attr.getName(), attr.getValue());
}
globalVariableMap[variableID] = varOp;
return success();
diff --git a/mlir/lib/Target/SPIRV/Serialization/SerializeOps.cpp b/mlir/lib/Target/SPIRV/Serialization/SerializeOps.cpp
index 32fa603e6c23d..9ed2401ac4099 100644
--- a/mlir/lib/Target/SPIRV/Serialization/SerializeOps.cpp
+++ b/mlir/lib/Target/SPIRV/Serialization/SerializeOps.cpp
@@ -109,7 +109,7 @@ LogicalResult Serializer::processSpecConstantOp(spirv::SpecConstantOp op) {
if (auto resultID = prepareConstantScalar(op.getLoc(), op.getDefaultValue(),
/*isSpec=*/true)) {
// Emit the OpDecorate instruction for SpecId.
- if (auto specID = op->getAttrOfType<IntegerAttr>("spec_id")) {
+ if (auto specID = op->getDiscardableAttrOfType<IntegerAttr>("spec_id")) {
auto val = static_cast<uint32_t>(specID.getInt());
if (failed(emitDecoration(resultID, spirv::Decoration::SpecId, {val})))
return failure();
@@ -393,7 +393,9 @@ LogicalResult Serializer::processFuncOp(spirv::FuncOp op) {
// Only attributes we should be considering for decoration are the
// ::mlir::spirv::Decoration attributes.
- for (auto attr : op->getAttrs()) {
+ NamedAttrList attrs(op->getDiscardableAttrDictionary().getValue());
+ op->getName().populateInherentAttrs(op, attrs);
+ for (auto attr : attrs) {
// Only generate OpDecorate op for spirv::Decoration attributes.
auto isValidDecoration = mlir::spirv::symbolizeEnum<spirv::Decoration>(
llvm::convertToCamelFromSnakeCase(attr.getName().strref(),
@@ -669,11 +671,7 @@ LogicalResult Serializer::processVariableOp(spirv::VariableOp op) {
resultID = getNextID();
valueIDMap[op.getResult()] = resultID;
operands.push_back(resultID);
- auto attr = op->getAttr(spirv::attributeName<spirv::StorageClass>());
- if (attr) {
- operands.push_back(
- static_cast<uint32_t>(cast<spirv::StorageClassAttr>(attr).getValue()));
- }
+ operands.push_back(static_cast<uint32_t>(op.getStorageClass()));
elidedAttrs.push_back(spirv::attributeName<spirv::StorageClass>());
for (auto arg : op.getODSOperands(0)) {
auto argID = getValueID(arg);
@@ -685,7 +683,7 @@ LogicalResult Serializer::processVariableOp(spirv::VariableOp op) {
if (failed(emitDebugLine(functionHeader, op.getLoc())))
return failure();
encodeInstructionInto(functionHeader, spirv::Opcode::OpVariable, operands);
- for (auto attr : op->getAttrs()) {
+ for (auto attr : op->getDiscardableAttrDictionary().getValue()) {
if (llvm::any_of(elidedAttrs, [&](StringRef elided) {
return attr.getName() == elided;
})) {
@@ -728,7 +726,7 @@ Serializer::processGlobalVariableOp(spirv::GlobalVariableOp varOp) {
StringRef initAttrName = varOp.getInitializerAttrName().getValue();
if (std::optional<StringRef> initSymbolName = varOp.getInitializer()) {
uint32_t initializerID = 0;
- auto initRef = varOp->getAttrOfType<FlatSymbolRefAttr>(initAttrName);
+ FlatSymbolRefAttr initRef = varOp.getInitializerAttr();
Operation *initOp = SymbolTable::lookupNearestSymbolFrom(
varOp->getParentOp(), initRef.getAttr());
@@ -752,7 +750,9 @@ Serializer::processGlobalVariableOp(spirv::GlobalVariableOp varOp) {
elidedAttrs.push_back(initAttrName);
// Encode decorations.
- for (auto attr : varOp->getAttrs()) {
+ NamedAttrList attrs(varOp->getDiscardableAttrDictionary().getValue());
+ varOp->getName().populateInherentAttrs(varOp, attrs);
+ for (auto attr : attrs) {
if (llvm::any_of(elidedAttrs, [&](StringRef elided) {
return attr.getName() == elided;
})) {
@@ -1111,34 +1111,26 @@ Serializer::processOp<spirv::CopyMemoryOp>(spirv::CopyMemoryOp op) {
}
StringAttr memoryAccess = op.getMemoryAccessAttrName();
- if (auto attr = op->getAttr(memoryAccess)) {
- operands.push_back(
- static_cast<uint32_t>(cast<spirv::MemoryAccessAttr>(attr).getValue()));
- }
+ if (std::optional<spirv::MemoryAccess> value = op.getMemoryAccess())
+ operands.push_back(static_cast<uint32_t>(*value));
elidedAttrs.push_back(memoryAccess.strref());
StringAttr alignment = op.getAlignmentAttrName();
- if (auto attr = op->getAttr(alignment)) {
- operands.push_back(static_cast<uint32_t>(
- cast<IntegerAttr>(attr).getValue().getZExtValue()));
- }
+ if (std::optional<uint32_t> value = op.getAlignment())
+ operands.push_back(*value);
elidedAttrs.push_back(alignment.strref());
StringAttr sourceMemoryAccess = op.getSourceMemoryAccessAttrName();
- if (auto attr = op->getAttr(sourceMemoryAccess)) {
- operands.push_back(
- static_cast<uint32_t>(cast<spirv::MemoryAccessAttr>(attr).getValue()));
- }
+ if (std::optional<spirv::MemoryAccess> value = op.getSourceMemoryAccess())
+ operands.push_back(static_cast<uint32_t>(*value));
elidedAttrs.push_back(sourceMemoryAccess.strref());
StringAttr sourceAlignment = op.getSourceAlignmentAttrName();
- if (auto attr = op->getAttr(sourceAlignment)) {
- operands.push_back(static_cast<uint32_t>(
- cast<IntegerAttr>(attr).getValue().getZExtValue()));
- }
+ if (std::optional<uint32_t> value = op.getSourceAlignment())
+ operands.push_back(*value);
elidedAttrs.push_back(sourceAlignment.strref());
if (failed(emitDebugLine(functionBody, op.getLoc())))
diff --git a/mlir/lib/Target/SPIRV/Serialization/Serializer.cpp b/mlir/lib/Target/SPIRV/Serialization/Serializer.cpp
index c3c065b693623..3919c3ed5ec36 100644
--- a/mlir/lib/Target/SPIRV/Serialization/Serializer.cpp
+++ b/mlir/lib/Target/SPIRV/Serialization/Serializer.cpp
@@ -290,15 +290,8 @@ LogicalResult Serializer::processExtension() {
}
void Serializer::processMemoryModel() {
- StringAttr memoryModelName = module.getMemoryModelAttrName();
- auto mm = static_cast<uint32_t>(
- module->getAttrOfType<spirv::MemoryModelAttr>(memoryModelName)
- .getValue());
-
- StringAttr addressingModelName = module.getAddressingModelAttrName();
- auto am = static_cast<uint32_t>(
- module->getAttrOfType<spirv::AddressingModelAttr>(addressingModelName)
- .getValue());
+ auto mm = static_cast<uint32_t>(module.getMemoryModel());
+ auto am = static_cast<uint32_t>(module.getAddressingModel());
encodeInstructionInto(memoryModel, spirv::Opcode::OpMemoryModel, {am, mm});
}
@@ -1738,7 +1731,7 @@ Serializer::processCompositeConstructOp(spirv::CompositeConstructOp op) {
encodeInstructionWithContinuationInto(
functionBody, spirv::Opcode::OpCompositeConstruct, operands);
- for (auto attr : op->getAttrs()) {
+ for (auto attr : op->getDiscardableAttrDictionary().getValue()) {
if (failed(processDecoration(loc, resultID, attr)))
return failure();
}
@@ -1781,7 +1774,7 @@ LogicalResult Serializer::processOpWithoutGrammarAttr(Operation *op,
}
if (op->getNumResults() != 0) {
- for (auto attr : op->getAttrs()) {
+ for (auto attr : op->getDiscardableAttrDictionary().getValue()) {
if (failed(processDecoration(loc, resultID, attr)))
return failure();
}
diff --git a/mlir/lib/Target/Wasm/TranslateFromWasm.cpp b/mlir/lib/Target/Wasm/TranslateFromWasm.cpp
index 96448ed987629..f64a429001399 100644
--- a/mlir/lib/Target/Wasm/TranslateFromWasm.cpp
+++ b/mlir/lib/Target/Wasm/TranslateFromWasm.cpp
@@ -21,6 +21,7 @@
#include "mlir/Support/LLVM.h"
#include "mlir/Target/Wasm/WasmBinaryEncoding.h"
#include "mlir/Target/Wasm/WasmImporter.h"
+#include "llvm/ADT/TypeSwitch.h"
#include "llvm/Support/Debug.h"
#include "llvm/Support/DebugLog.h"
#include "llvm/Support/Endian.h"
@@ -2008,7 +2009,10 @@ WasmBinaryParser::parseSectionItem<WasmSectionType::EXPORT>(ParserHead &ph,
return failure();
Operation *op = SymbolTable::lookupSymbolIn(mOp, *currentSymbol);
- op->setAttr("exported", UnitAttr::get(op->getContext()));
+ TypeSwitch<Operation *>(op)
+ .Case<wasmssa::FuncOp, wasmssa::GlobalOp, wasmssa::MemOp,
+ wasmssa::TableOp>([](auto symbol) { symbol.setExported(true); })
+ .Default([](Operation *) { llvm_unreachable("unexpected export kind"); });
StringAttr symName = SymbolTable::getSymbolName(op);
return SymbolTable{mOp}.rename(symName, *exportName);
}
diff --git a/mlir/lib/Transforms/Utils/DialectConversion.cpp b/mlir/lib/Transforms/Utils/DialectConversion.cpp
index 75d5620f0f298..507f0650169ca 100644
--- a/mlir/lib/Transforms/Utils/DialectConversion.cpp
+++ b/mlir/lib/Transforms/Utils/DialectConversion.cpp
@@ -217,7 +217,7 @@ static Operation *getCommonDefiningOp(const ValueVector &values) {
static bool isPureTypeConversion(const ValueVector &values) {
assert(!values.empty() && "expected non-empty value vector");
Operation *op = getCommonDefiningOp(values);
- return op && op->hasAttr(kPureTypeConversionMarker);
+ return op && op->hasDiscardableAttr(kPureTypeConversionMarker);
}
ValueVector ConversionValueMapping::lookup(const ValueVector &from) const {
@@ -683,7 +683,8 @@ class ModifyOperationRewrite : public OperationRewrite {
ModifyOperationRewrite(ConversionPatternRewriterImpl &rewriterImpl,
Operation *op)
: OperationRewrite(Kind::ModifyOperation, rewriterImpl, op),
- name(op->getName()), loc(op->getLoc()), attrs(op->getAttrDictionary()),
+ name(op->getName()), loc(op->getLoc()),
+ attrs(op->getDiscardableAttrDictionary()),
operands(op->operand_begin(), op->operand_end()),
successors(op->successor_begin(), op->successor_end()) {
if (PropertyRef prop = op->getPropertiesStorage()) {
@@ -721,7 +722,7 @@ class ModifyOperationRewrite : public OperationRewrite {
void rollback() override {
op->setLoc(loc);
- op->setAttrs(attrs);
+ op->setDiscardableAttrs(attrs);
op->setOperands(operands);
for (const auto &it : llvm::enumerate(successors))
op->setSuccessor(it.value(), it.index());
@@ -1723,10 +1724,11 @@ ValueRange ConversionPatternRewriterImpl::buildUnresolvedMaterialization(
if (config.attachDebugMaterializationKind) {
StringRef kindStr =
kind == MaterializationKind::Source ? "source" : "target";
- convertOp->setAttr("__kind__", builder.getStringAttr(kindStr));
+ convertOp->setDiscardableAttr("__kind__", builder.getStringAttr(kindStr));
}
if (isPureTypeConversion)
- convertOp->setAttr(kPureTypeConversionMarker, builder.getUnitAttr());
+ convertOp->setDiscardableAttr(kPureTypeConversionMarker,
+ builder.getUnitAttr());
// Register the materialization.
unresolvedMaterializations[convertOp] =
@@ -3503,7 +3505,7 @@ LogicalResult OperationConverter::applyConversion(ArrayRef<Operation *> ops) {
// Drop markers.
for (UnrealizedConversionCastOp castOp : remainingCastOps)
- castOp->removeAttr(kPureTypeConversionMarker);
+ castOp->removeDiscardableAttr(kPureTypeConversionMarker);
// Try to legalize all unresolved materializations.
if (rewriter.getConfig().buildMaterializations) {
@@ -3947,7 +3949,8 @@ mlir::convertOpResultTypes(Operation *op, ValueRange operands,
return rewriter.notifyMatchFailure(loc, "couldn't convert return types");
newOp.addTypes(newResultTypes);
- newOp.addAttributes(op->getAttrs());
+ newOp.addAttributes(op->getDiscardableAttrDictionary().getValue());
+ newOp.propertiesAttr = op->getPropertiesAsAttribute();
return rewriter.create(newOp);
}
diff --git a/mlir/lib/Transforms/ViewOpGraph.cpp b/mlir/lib/Transforms/ViewOpGraph.cpp
index 2d7e40d18efca..9b4a24861048a 100644
--- a/mlir/lib/Transforms/ViewOpGraph.cpp
+++ b/mlir/lib/Transforms/ViewOpGraph.cpp
@@ -316,7 +316,9 @@ class PrintOpPass : public impl::ViewOpGraphPassBase<PrintOpPass> {
// Print attributes.
if (printAttrs) {
os << "\\l";
- for (const NamedAttribute &attr : op->getAttrs()) {
+ NamedAttrList attrs(op->getDiscardableAttrDictionary());
+ op->getName().populateInherentAttrs(op, attrs);
+ for (const NamedAttribute &attr : attrs) {
os << escapeLabelString(attr.getName().getValue().str()) << ": ";
emitMlirAttr(os, attr.getValue());
os << "\\l";
@@ -344,10 +346,12 @@ class PrintOpPass : public impl::ViewOpGraphPassBase<PrintOpPass> {
os << op->getName() << "\\l";
// Print attributes.
- if (printAttrs && !op->getAttrs().empty()) {
+ NamedAttrList attrs(op->getDiscardableAttrDictionary());
+ op->getName().populateInherentAttrs(op, attrs);
+ if (printAttrs && !attrs.empty()) {
// Extra line break to separate attributes from the operation name.
os << "\\l";
- for (const NamedAttribute &attr : op->getAttrs()) {
+ for (const NamedAttribute &attr : attrs) {
os << attr.getName().getValue() << ": ";
emitMlirAttr(os, attr.getValue());
os << "\\l";
diff --git a/mlir/python/mlir/dialects/gpu/__init__.py b/mlir/python/mlir/dialects/gpu/__init__.py
index b75bd525c9487..2ce4e3a24bf6b 100644
--- a/mlir/python/mlir/dialects/gpu/__init__.py
+++ b/mlir/python/mlir/dialects/gpu/__init__.py
@@ -86,7 +86,10 @@ def __init__(
if not isinstance(function_type, TypeAttr)
else function_type
)
+ if not isinstance(sym_name, (str, StringAttr)):
+ raise ValueError("sym_name must be a string or a StringAttr")
super().__init__(
+ sym_name,
function_type,
arg_attrs=arg_attrs,
res_attrs=res_attrs,
@@ -96,13 +99,6 @@ def __init__(
ip=ip,
)
- if isinstance(sym_name, str):
- self.attributes[self.SYM_NAME_ATTR_NAME] = StringAttr.get(sym_name)
- elif isinstance(sym_name, StringAttr):
- self.attributes[self.SYM_NAME_ATTR_NAME] = sym_name
- else:
- raise ValueError("sym_name must be a string or a StringAttr")
-
if kernel:
self.attributes[self.KERNEL_ATTR_NAME] = UnitAttr.get()
diff --git a/mlir/test/lib/Analysis/DataFlow/TestDeadCodeAnalysis.cpp b/mlir/test/lib/Analysis/DataFlow/TestDeadCodeAnalysis.cpp
index 327e807873714..4ab2a3170ef61 100644
--- a/mlir/test/lib/Analysis/DataFlow/TestDeadCodeAnalysis.cpp
+++ b/mlir/test/lib/Analysis/DataFlow/TestDeadCodeAnalysis.cpp
@@ -19,7 +19,7 @@ using namespace mlir::dataflow;
static void printAnalysisResults(DataFlowSolver &solver, Operation *op,
raw_ostream &os) {
op->walk([&](Operation *op) {
- auto tag = op->getAttrOfType<StringAttr>("tag");
+ auto tag = op->getDiscardableAttrOfType<StringAttr>("tag");
if (!tag)
return;
os << tag.getValue() << ":\n";
diff --git a/mlir/test/lib/Analysis/DataFlow/TestDenseBackwardDataFlowAnalysis.cpp b/mlir/test/lib/Analysis/DataFlow/TestDenseBackwardDataFlowAnalysis.cpp
index e1ea28c06659f..f969869b92482 100644
--- a/mlir/test/lib/Analysis/DataFlow/TestDenseBackwardDataFlowAnalysis.cpp
+++ b/mlir/test/lib/Analysis/DataFlow/TestDenseBackwardDataFlowAnalysis.cpp
@@ -320,7 +320,7 @@ struct TestNextAccessPass
innerAttrs.reserve(nextAcc->get().size());
for (Operation *nextAccOp : nextAcc->get()) {
if (auto nextAccTag =
- nextAccOp->getAttrOfType<StringAttr>(kTagAttrName)) {
+ nextAccOp->getDiscardableAttrOfType<StringAttr>(kTagAttrName)) {
innerAttrs.push_back(nextAccTag);
continue;
}
@@ -356,7 +356,7 @@ struct TestNextAccessPass
LDBG() << " Dataflow solver completed successfully";
LDBG() << " Walking operations to set next access attributes";
op->walk([&](Operation *op) {
- auto tag = op->getAttrOfType<StringAttr>(kTagAttrName);
+ auto tag = op->getDiscardableAttrOfType<StringAttr>(kTagAttrName);
if (!tag)
return;
@@ -364,8 +364,8 @@ struct TestNextAccessPass
<< OpWithFlags(op, OpPrintingFlags().skipRegions());
const NextAccess *nextAccess =
solver.lookupState<NextAccess>(solver.getProgramPointAfter(op));
- op->setAttr(kNextAccessAttrName,
- makeNextAccessAttribute(op, solver, nextAccess));
+ op->setDiscardableAttr(kNextAccessAttrName,
+ makeNextAccessAttribute(op, solver, nextAccess));
auto iface = dyn_cast<RegionBranchOpInterface>(op);
if (!iface)
@@ -383,8 +383,9 @@ struct TestNextAccessPass
entryPointNextAccess.push_back(makeNextAccessAttribute(
op, solver, solver.lookupState<NextAccess>(successorPoint)));
}
- op->setAttr(kAtEntryPointAttrName,
- ArrayAttr::get(op->getContext(), entryPointNextAccess));
+ op->setDiscardableAttr(
+ kAtEntryPointAttrName,
+ ArrayAttr::get(op->getContext(), entryPointNextAccess));
});
}
};
diff --git a/mlir/test/lib/Analysis/DataFlow/TestDenseDataFlowAnalysis.h b/mlir/test/lib/Analysis/DataFlow/TestDenseDataFlowAnalysis.h
index 6012c90f84539..9b0508660e9cd 100644
--- a/mlir/test/lib/Analysis/DataFlow/TestDenseDataFlowAnalysis.h
+++ b/mlir/test/lib/Analysis/DataFlow/TestDenseDataFlowAnalysis.h
@@ -196,7 +196,7 @@ class UnderlyingValueAnalysis
ArrayRef<const UnderlyingValueLattice *> operands,
ArrayRef<UnderlyingValueLattice *> results) override {
// Hook to test error propagation from visitOperation.
- if (op->hasAttr("always_fail"))
+ if (op->hasDiscardableAttr("always_fail"))
return op->emitError("this op is always fails");
setAllToEntryStates(results);
diff --git a/mlir/test/lib/Analysis/DataFlow/TestDenseForwardDataFlowAnalysis.cpp b/mlir/test/lib/Analysis/DataFlow/TestDenseForwardDataFlowAnalysis.cpp
index f2384f32948a2..c8b67b4ba61c0 100644
--- a/mlir/test/lib/Analysis/DataFlow/TestDenseForwardDataFlowAnalysis.cpp
+++ b/mlir/test/lib/Analysis/DataFlow/TestDenseForwardDataFlowAnalysis.cpp
@@ -252,7 +252,7 @@ struct TestLastModifiedPass
// Note that if the underlying value could not be computed or is unknown, we
// conservatively treat the result also unknown.
op->walk([&](Operation *op) {
- auto tag = op->getAttrOfType<StringAttr>("tag");
+ auto tag = op->getDiscardableAttrOfType<StringAttr>("tag");
if (!tag)
return;
os << "test_tag: " << tag.getValue() << ":\n";
@@ -285,7 +285,8 @@ struct TestLastModifiedPass
} else {
for (Operation *lastModifier : lastMod->get()) {
if (auto tagName =
- lastModifier->getAttrOfType<StringAttr>("tag_name")) {
+ lastModifier->getDiscardableAttrOfType<StringAttr>(
+ "tag_name")) {
os << " - " << tagName.getValue() << "\n";
} else {
os << " - " << lastModifier->getName() << "\n";
diff --git a/mlir/test/lib/Analysis/DataFlow/TestIntegerDivisibilityAnalysis.cpp b/mlir/test/lib/Analysis/DataFlow/TestIntegerDivisibilityAnalysis.cpp
index 626cbc0fac7aa..24d01c61e3783 100644
--- a/mlir/test/lib/Analysis/DataFlow/TestIntegerDivisibilityAnalysis.cpp
+++ b/mlir/test/lib/Analysis/DataFlow/TestIntegerDivisibilityAnalysis.cpp
@@ -71,7 +71,8 @@ struct TestIntegerDivisibilityAnalysisPass
const auto *lattice =
solver.lookupState<IntegerDivisibilityLattice>(value);
if (!lattice || lattice->getValue().isUninitialized()) {
- op->setAttr("divisibility", StringAttr::get(context, "uninitialized"));
+ op->setDiscardableAttr("divisibility",
+ StringAttr::get(context, "uninitialized"));
continue;
}
@@ -80,7 +81,7 @@ struct TestIntegerDivisibilityAnalysisPass
std::string result;
llvm::raw_string_ostream os(result);
os << "udiv = " << div.udiv() << ", sdiv = " << div.sdiv();
- op->setAttr("divisibility", StringAttr::get(context, result));
+ op->setDiscardableAttr("divisibility", StringAttr::get(context, result));
}
}
};
diff --git a/mlir/test/lib/Analysis/DataFlow/TestLivenessAnalysis.cpp b/mlir/test/lib/Analysis/DataFlow/TestLivenessAnalysis.cpp
index 2c9f46411f602..22c2a6bffd52a 100644
--- a/mlir/test/lib/Analysis/DataFlow/TestLivenessAnalysis.cpp
+++ b/mlir/test/lib/Analysis/DataFlow/TestLivenessAnalysis.cpp
@@ -38,7 +38,7 @@ struct TestLivenessAnalysisPass
raw_ostream &os = llvm::outs();
op->walk([&](Operation *op) {
- auto tag = op->getAttrOfType<StringAttr>("tag");
+ auto tag = op->getDiscardableAttrOfType<StringAttr>("tag");
if (!tag)
return;
os << "test_tag: " << tag.getValue() << ":\n";
diff --git a/mlir/test/lib/Analysis/DataFlow/TestSparseBackwardDataFlowAnalysis.cpp b/mlir/test/lib/Analysis/DataFlow/TestSparseBackwardDataFlowAnalysis.cpp
index b1978880e2bd6..18c74093e518f 100644
--- a/mlir/test/lib/Analysis/DataFlow/TestSparseBackwardDataFlowAnalysis.cpp
+++ b/mlir/test/lib/Analysis/DataFlow/TestSparseBackwardDataFlowAnalysis.cpp
@@ -104,7 +104,7 @@ WrittenToAnalysis::visitOperation(Operation *op, ArrayRef<WrittenTo *> operands,
ArrayRef<const WrittenTo *> results) {
if (auto store = dyn_cast<memref::StoreOp>(op)) {
SetVector<StringAttr> newWrites;
- newWrites.insert(op->getAttrOfType<StringAttr>("tag_name"));
+ newWrites.insert(op->getDiscardableAttrOfType<StringAttr>("tag_name"));
propagateIfChanged(operands[0],
operands[0]->getValue().addWrites(newWrites));
return success();
@@ -148,7 +148,7 @@ void WrittenToAnalysis::visitExternalCall(CallOpInterface call,
for (WrittenTo *lattice : operands) {
SetVector<StringAttr> newWrites;
- StringAttr name = call->getAttrOfType<StringAttr>("tag_name");
+ StringAttr name = call->getDiscardableAttrOfType<StringAttr>("tag_name");
if (!name) {
name = StringAttr::get(call->getContext(),
call.getOperation()->getName().getStringRef());
@@ -194,7 +194,7 @@ struct TestWrittenToPass
raw_ostream &os = llvm::outs();
op->walk([&](Operation *op) {
- auto tag = op->getAttrOfType<StringAttr>("tag");
+ auto tag = op->getDiscardableAttrOfType<StringAttr>("tag");
if (!tag)
return;
os << "test_tag: " << tag.getValue() << ":\n";
diff --git a/mlir/test/lib/Analysis/TestAliasAnalysis.cpp b/mlir/test/lib/Analysis/TestAliasAnalysis.cpp
index 0125e403272a8..f5eaed98f0268 100644
--- a/mlir/test/lib/Analysis/TestAliasAnalysis.cpp
+++ b/mlir/test/lib/Analysis/TestAliasAnalysis.cpp
@@ -21,14 +21,15 @@ using namespace mlir;
/// Print a value that is used as an operand of an alias query.
static void printAliasOperand(Operation *op) {
- llvm::errs() << op->getAttrOfType<StringAttr>("test.ptr").getValue();
+ llvm::errs()
+ << op->getDiscardableAttrOfType<StringAttr>("test.ptr").getValue();
}
static void printAliasOperand(Value value) {
if (BlockArgument arg = dyn_cast<BlockArgument>(value)) {
Region *region = arg.getParentRegion();
unsigned parentBlockNumber = arg.getOwner()->computeBlockNumber();
llvm::errs() << region->getParentOp()
- ->getAttrOfType<StringAttr>("test.ptr")
+ ->getDiscardableAttrOfType<StringAttr>("test.ptr")
.getValue()
<< ".region" << region->getRegionNumber();
if (parentBlockNumber != 0)
diff --git a/mlir/test/lib/Analysis/TestDataFlowFramework.cpp b/mlir/test/lib/Analysis/TestDataFlowFramework.cpp
index f29136853a9cd..98fbcd8c9b12c 100644
--- a/mlir/test/lib/Analysis/TestDataFlowFramework.cpp
+++ b/mlir/test/lib/Analysis/TestDataFlowFramework.cpp
@@ -238,7 +238,7 @@ void FooAnalysis::visitOperation(Operation *op) {
result |= state->set(*prevState);
// Modify the state with the attribute, if specified.
- if (auto attr = op->getAttrOfType<IntegerAttr>(kFooAttrName)) {
+ if (auto attr = op->getDiscardableAttrOfType<IntegerAttr>(kFooAttrName)) {
uint64_t value = attr.getType().isUnsignedInteger()
? attr.getUInt()
: static_cast<uint64_t>(attr.getInt());
@@ -301,7 +301,7 @@ void BarAnalysis::visitOperation(Operation *op) {
getOrCreateFor<BarState>(point, getProgramPointBefore(op));
result |= state->join(*prevState);
- if (op->hasAttr(kTagAttrName)) {
+ if (op->hasDiscardableAttr(kTagAttrName)) {
const FooState *fooState = getOrCreateFor<FooState>(point, point);
if (fooState->isUninitialized())
return;
@@ -321,7 +321,7 @@ void TestFooAnalysisPass::runOnOperation() {
os << "function: @" << func.getSymName() << "\n";
func.walk([&](Operation *op) {
- auto tag = op->getAttrOfType<StringAttr>(kTagAttrName);
+ auto tag = op->getDiscardableAttrOfType<StringAttr>(kTagAttrName);
if (!tag)
return;
const FooState *state =
@@ -344,7 +344,7 @@ void TestStagedAnalysesPass::runOnOperation() {
return signalPassFailure();
func.walk([&](Operation *op) {
- if (!op->hasAttr(kTagAttrName))
+ if (!op->hasDiscardableAttr(kTagAttrName))
return;
ProgramPoint *point = solver.getProgramPointAfter(op);
@@ -353,9 +353,10 @@ void TestStagedAnalysesPass::runOnOperation() {
assert(fooState && !fooState->isUninitialized());
assert(barState && !barState->isUninitialized());
- op->setAttr(kFooStateAttrName,
- builder.getI64IntegerAttr(fooState->getValue()));
- op->setAttr(kBarStateAttrName, builder.getBoolAttr(barState->getValue()));
+ op->setDiscardableAttr(kFooStateAttrName,
+ builder.getI64IntegerAttr(fooState->getValue()));
+ op->setDiscardableAttr(kBarStateAttrName,
+ builder.getBoolAttr(barState->getValue()));
});
}
diff --git a/mlir/test/lib/Analysis/TestSlice.cpp b/mlir/test/lib/Analysis/TestSlice.cpp
index 7e8320dbf3ec3..5055a7b36265c 100644
--- a/mlir/test/lib/Analysis/TestSlice.cpp
+++ b/mlir/test/lib/Analysis/TestSlice.cpp
@@ -31,14 +31,14 @@ struct TestTopologicalSortPass
void runOnOperation() override {
SetVector<Operation *> toSort;
getOperation().walk([&](Operation *op) {
- if (op->hasAttrOfType<UnitAttr>(kToSortMark))
+ if (op->hasDiscardableAttrOfType<UnitAttr>(kToSortMark))
toSort.insert(op);
});
auto i32Type = IntegerType::get(&getContext(), 32);
SetVector<Operation *> sortedOps = topologicalSort(toSort);
for (auto [index, op] : llvm::enumerate(sortedOps))
- op->setAttr(kOrderIndex, IntegerAttr::get(i32Type, index));
+ op->setDiscardableAttr(kOrderIndex, IntegerAttr::get(i32Type, index));
}
};
diff --git a/mlir/test/lib/Analysis/TestTopologicalSort.cpp b/mlir/test/lib/Analysis/TestTopologicalSort.cpp
index bd7e60f1ecc33..f219c8cf0a341 100644
--- a/mlir/test/lib/Analysis/TestTopologicalSort.cpp
+++ b/mlir/test/lib/Analysis/TestTopologicalSort.cpp
@@ -31,14 +31,14 @@ struct TestTopologicalSortAnalysisPass
OpBuilder builder(op->getContext());
WalkResult result = op->walk([&](Operation *root) {
- if (!root->hasAttr("root"))
+ if (!root->hasDiscardableAttr("root"))
return WalkResult::advance();
SmallVector<Operation *> selectedOps;
root->walk([&](Operation *selected) {
- if (!selected->hasAttr("selected"))
+ if (!selected->hasDiscardableAttr("selected"))
return WalkResult::advance();
- if (root->hasAttr("ordered")) {
+ if (root->hasDiscardableAttr("ordered")) {
// If the root has an "ordered" attribute, we fill the selectedOps
// vector in a certain order.
int64_t pos =
@@ -65,7 +65,7 @@ struct TestTopologicalSortAnalysisPass
}
for (const auto &it : llvm::enumerate(selectedOps))
- it.value()->setAttr("pos", builder.getIndexAttr(it.index()));
+ it.value()->setDiscardableAttr("pos", builder.getIndexAttr(it.index()));
return WalkResult::advance();
});
diff --git a/mlir/test/lib/Dialect/Bufferization/TestTensorLikeAndBufferLike.cpp b/mlir/test/lib/Dialect/Bufferization/TestTensorLikeAndBufferLike.cpp
index 60e60849f3e6c..3e71175a34474 100644
--- a/mlir/test/lib/Dialect/Bufferization/TestTensorLikeAndBufferLike.cpp
+++ b/mlir/test/lib/Dialect/Bufferization/TestTensorLikeAndBufferLike.cpp
@@ -85,7 +85,7 @@ struct TestTensorLikeAndBufferLikePass
op.walk([](func::FuncOp funcOp) {
const auto dict = findAllImplementeesOfTensorOrBufferLike(funcOp);
if (!dict.empty()) {
- funcOp->setAttr("found", dict);
+ funcOp->setDiscardableAttr("found", dict);
}
});
}
diff --git a/mlir/test/lib/Dialect/DLTI/TestDataLayoutQuery.cpp b/mlir/test/lib/Dialect/DLTI/TestDataLayoutQuery.cpp
index 58c77cb94b47f..f6b403799b1da 100644
--- a/mlir/test/lib/Dialect/DLTI/TestDataLayoutQuery.cpp
+++ b/mlir/test/lib/Dialect/DLTI/TestDataLayoutQuery.cpp
@@ -63,7 +63,7 @@ struct TestDataLayoutQuery
});
};
- op->setAttrs(
+ op->setDiscardableAttrs(
{builder.getNamedAttr("size", convertTypeSizeToAttr(size)),
builder.getNamedAttr("bitsize", convertTypeSizeToAttr(bitsize)),
builder.getNamedAttr("alignment", builder.getIndexAttr(alignment)),
diff --git a/mlir/test/lib/Dialect/LLVM/TestPatterns.cpp b/mlir/test/lib/Dialect/LLVM/TestPatterns.cpp
index 69a3d98bc09e4..2252db9bc9802 100644
--- a/mlir/test/lib/Dialect/LLVM/TestPatterns.cpp
+++ b/mlir/test/lib/Dialect/LLVM/TestPatterns.cpp
@@ -79,8 +79,9 @@ struct TestLLVMLegalizePatternsPass
ConversionTarget target(*ctx);
target.addLegalOp(OperationName("test.legal_op", ctx));
target.addLegalDialect<LLVM::LLVMDialect>();
- target.addDynamicallyLegalOp<func::FuncOp>(
- [&](func::FuncOp funcOp) { return funcOp->hasAttr("is_legal"); });
+ target.addDynamicallyLegalOp<func::FuncOp>([&](func::FuncOp funcOp) {
+ return funcOp->hasDiscardableAttr("is_legal");
+ });
// Handle a partial conversion.
DenseSet<Operation *> unlegalizedOps;
diff --git a/mlir/test/lib/Dialect/OpenACC/TestOpenACCSupport.cpp b/mlir/test/lib/Dialect/OpenACC/TestOpenACCSupport.cpp
index 7c8b08489c62e..c0a952658001c 100644
--- a/mlir/test/lib/Dialect/OpenACC/TestOpenACCSupport.cpp
+++ b/mlir/test/lib/Dialect/OpenACC/TestOpenACCSupport.cpp
@@ -49,7 +49,7 @@ void TestOpenACCSupportPass::runOnOperation() {
func.walk([&](Operation *op) {
// Check for test.var_name attribute. This is the marker used to identify
// the operations that need to be tested for getVariableName.
- if (op->hasAttr("test.var_name")) {
+ if (op->hasDiscardableAttr("test.var_name")) {
// For each result of this operation, try to get the variable name
for (auto result : op->getResults()) {
std::string foundName = support.getVariableName(result);
@@ -61,7 +61,7 @@ void TestOpenACCSupportPass::runOnOperation() {
// Check for test.recipe_name attribute. This is the marker used to identify
// the operations that need to be tested for getRecipeName.
if (auto recipeAttr =
- op->getAttrOfType<RecipeKindAttr>("test.recipe_name")) {
+ op->getDiscardableAttrOfType<RecipeKindAttr>("test.recipe_name")) {
RecipeKind kind = recipeAttr.getValue();
// Get the type from the first result if available
if (op->getNumResults() > 0) {
@@ -76,7 +76,8 @@ void TestOpenACCSupportPass::runOnOperation() {
// Check for test.emit_nyi attribute. This is the marker used to
// test whether the not yet implemented case is reported correctly.
- if (auto messageAttr = op->getAttrOfType<StringAttr>("test.emit_nyi")) {
+ if (auto messageAttr =
+ op->getDiscardableAttrOfType<StringAttr>("test.emit_nyi")) {
support.emitNYI(op->getLoc(), messageAttr.getValue());
}
});
diff --git a/mlir/test/lib/Dialect/OpenACC/TestPointerLikeTypeInterface.cpp b/mlir/test/lib/Dialect/OpenACC/TestPointerLikeTypeInterface.cpp
index e45fd104e7331..e43f0724dcc0f 100644
--- a/mlir/test/lib/Dialect/OpenACC/TestPointerLikeTypeInterface.cpp
+++ b/mlir/test/lib/Dialect/OpenACC/TestPointerLikeTypeInterface.cpp
@@ -101,9 +101,10 @@ void TestPointerLikeTypeInterfacePass::runOnOperation() {
if (testMode == "cast") {
func.walk([&](Operation *op) {
- if (!op->hasAttr("test.cast"))
+ if (!op->hasDiscardableAttr("test.cast"))
return;
- auto destAttr = dyn_cast_or_null<TypeAttr>(op->getAttr("cast_dest"));
+ auto destAttr =
+ dyn_cast_or_null<TypeAttr>(op->getDiscardableAttr("cast_dest"));
if (!destAttr || op->getNumResults() == 0)
return;
testGenCast(op, op->getResult(0), destAttr.getValue(), builder);
@@ -118,7 +119,7 @@ void TestPointerLikeTypeInterfacePass::runOnOperation() {
// For store mode, also look for a test value to use
Value testValue;
func.walk([&](Operation *op) {
- if (op->hasAttr("test.ptr")) {
+ if (op->hasDiscardableAttr("test.ptr")) {
for (auto result : op->getResults()) {
if (isa<PointerLikeType>(result.getType())) {
candidates.push_back(
@@ -128,7 +129,7 @@ void TestPointerLikeTypeInterfacePass::runOnOperation() {
}
}
// Collect value marked with test.value for store tests
- if (testMode == "store" && op->hasAttr("test.value")) {
+ if (testMode == "store" && op->hasDiscardableAttr("test.value")) {
if (op->getNumResults() > 0)
testValue = op->getResult(0);
}
@@ -154,7 +155,7 @@ void TestPointerLikeTypeInterfacePass::runOnOperation() {
SmallVector<PointerCandidate> sources, destinations;
func.walk([&](Operation *op) {
- if (op->hasAttr("test.src_ptr")) {
+ if (op->hasDiscardableAttr("test.src_ptr")) {
for (auto result : op->getResults()) {
if (isa<PointerLikeType>(result.getType())) {
sources.push_back(
@@ -163,7 +164,7 @@ void TestPointerLikeTypeInterfacePass::runOnOperation() {
}
}
}
- if (op->hasAttr("test.dest_ptr")) {
+ if (op->hasDiscardableAttr("test.dest_ptr")) {
for (auto result : op->getResults()) {
if (isa<PointerLikeType>(result.getType())) {
destinations.push_back(
@@ -188,8 +189,9 @@ void TestPointerLikeTypeInterfacePass::walkAndPrint() {
func.walk([&](Operation *op) {
// Look for operations marked with "test.ptr", "test.src_ptr", or
// "test.dest_ptr"
- if (op->hasAttr("test.ptr") || op->hasAttr("test.src_ptr") ||
- op->hasAttr("test.dest_ptr")) {
+ if (op->hasDiscardableAttr("test.ptr") ||
+ op->hasDiscardableAttr("test.src_ptr") ||
+ op->hasDiscardableAttr("test.dest_ptr")) {
llvm::errs() << "Operation: ";
op->print(llvm::errs());
llvm::errs() << "\n";
diff --git a/mlir/test/lib/Dialect/OpenACC/TestRecipePopulate.cpp b/mlir/test/lib/Dialect/OpenACC/TestRecipePopulate.cpp
index 7b71f2c5f3b20..6daffb04cd554 100644
--- a/mlir/test/lib/Dialect/OpenACC/TestRecipePopulate.cpp
+++ b/mlir/test/lib/Dialect/OpenACC/TestRecipePopulate.cpp
@@ -62,7 +62,7 @@ void TestRecipePopulatePass::runOnOperation() {
SmallVector<std::tuple<Operation *, Value, std::string>> testVars;
module.walk([&](Operation *op) {
- if (auto varName = op->getAttrOfType<StringAttr>("test.var")) {
+ if (auto varName = op->getDiscardableAttrOfType<StringAttr>("test.var")) {
for (auto result : op->getResults()) {
testVars.push_back({op, result, varName.str()});
}
diff --git a/mlir/test/lib/Dialect/SCF/TestLoopUnrolling.cpp b/mlir/test/lib/Dialect/SCF/TestLoopUnrolling.cpp
index bbeae9d39db8d..f92aa606f018f 100644
--- a/mlir/test/lib/Dialect/SCF/TestLoopUnrolling.cpp
+++ b/mlir/test/lib/Dialect/SCF/TestLoopUnrolling.cpp
@@ -68,7 +68,7 @@ struct TestLoopUnrollingPass
});
auto annotateFn = [this](unsigned i, Operation *op, OpBuilder b) {
if (annotateLoop) {
- op->setAttr("unrolled_iteration", b.getUI32IntegerAttr(i));
+ op->setDiscardableAttr("unrolled_iteration", b.getUI32IntegerAttr(i));
}
};
for (auto loop : loops) {
diff --git a/mlir/test/lib/Dialect/SCF/TestParallelLoopUnrolling.cpp b/mlir/test/lib/Dialect/SCF/TestParallelLoopUnrolling.cpp
index 77a22a1812537..12a6a6af59fa6 100644
--- a/mlir/test/lib/Dialect/SCF/TestParallelLoopUnrolling.cpp
+++ b/mlir/test/lib/Dialect/SCF/TestParallelLoopUnrolling.cpp
@@ -53,7 +53,7 @@ struct TestParallelLoopUnrollingPass
});
auto annotateFn = [this](unsigned i, Operation *op, OpBuilder b) {
if (annotateLoop) {
- op->setAttr("unrolled_iteration", b.getUI32IntegerAttr(i));
+ op->setDiscardableAttr("unrolled_iteration", b.getUI32IntegerAttr(i));
}
};
PatternRewriter rewriter(getOperation()->getContext());
diff --git a/mlir/test/lib/Dialect/SCF/TestSCFUtils.cpp b/mlir/test/lib/Dialect/SCF/TestSCFUtils.cpp
index fafa03b6c089f..6a0f042b9cbe4 100644
--- a/mlir/test/lib/Dialect/SCF/TestSCFUtils.cpp
+++ b/mlir/test/lib/Dialect/SCF/TestSCFUtils.cpp
@@ -152,15 +152,15 @@ struct TestSCFPipeliningPass
static void
getSchedule(scf::ForOp forOp,
std::vector<std::pair<Operation *, unsigned>> &schedule) {
- if (!forOp->hasAttr(kTestPipeliningLoopMarker))
+ if (!forOp->hasDiscardableAttr(kTestPipeliningLoopMarker))
return;
schedule.resize(forOp.getBody()->getOperations().size() - 1);
WalkResult result = forOp.walk([&schedule](Operation *op) {
auto attrStage =
- op->getAttrOfType<IntegerAttr>(kTestPipeliningStageMarker);
- auto attrCycle =
- op->getAttrOfType<IntegerAttr>(kTestPipeliningOpOrderMarker);
+ op->getDiscardableAttrOfType<IntegerAttr>(kTestPipeliningStageMarker);
+ auto attrCycle = op->getDiscardableAttrOfType<IntegerAttr>(
+ kTestPipeliningOpOrderMarker);
if (attrCycle && attrStage) {
const APInt &stage = attrStage.getValue();
if (stage.isNegative() ||
@@ -230,17 +230,20 @@ struct TestSCFPipeliningPass
OpBuilder b(op);
switch (part) {
case mlir::scf::PipeliningOption::PipelinerPart::Prologue:
- op->setAttr(kTestPipeliningAnnotationPart, b.getStringAttr("prologue"));
+ op->setDiscardableAttr(kTestPipeliningAnnotationPart,
+ b.getStringAttr("prologue"));
break;
case mlir::scf::PipeliningOption::PipelinerPart::Kernel:
- op->setAttr(kTestPipeliningAnnotationPart, b.getStringAttr("kernel"));
+ op->setDiscardableAttr(kTestPipeliningAnnotationPart,
+ b.getStringAttr("kernel"));
break;
case mlir::scf::PipeliningOption::PipelinerPart::Epilogue:
- op->setAttr(kTestPipeliningAnnotationPart, b.getStringAttr("epilogue"));
+ op->setDiscardableAttr(kTestPipeliningAnnotationPart,
+ b.getStringAttr("epilogue"));
break;
}
- op->setAttr(kTestPipeliningAnnotationIteration,
- b.getI32IntegerAttr(iteration));
+ op->setDiscardableAttr(kTestPipeliningAnnotationIteration,
+ b.getI32IntegerAttr(iteration));
}
void getDependentDialects(DialectRegistry ®istry) const override {
@@ -262,8 +265,8 @@ struct TestSCFPipeliningPass
(void)applyPatternsGreedily(getOperation(), std::move(patterns));
getOperation().walk([](Operation *op) {
// Clean up the markers.
- op->removeAttr(kTestPipeliningStageMarker);
- op->removeAttr(kTestPipeliningOpOrderMarker);
+ op->removeDiscardableAttr(kTestPipeliningStageMarker);
+ op->removeDiscardableAttr(kTestPipeliningOpOrderMarker);
});
}
};
diff --git a/mlir/test/lib/Dialect/SPIRV/TestAvailability.cpp b/mlir/test/lib/Dialect/SPIRV/TestAvailability.cpp
index ae995a970bade..8cdb9041d196a 100644
--- a/mlir/test/lib/Dialect/SPIRV/TestAvailability.cpp
+++ b/mlir/test/lib/Dialect/SPIRV/TestAvailability.cpp
@@ -208,8 +208,9 @@ struct ConvertToIntegerDotProd : RewritePattern {
LogicalResult matchAndRewrite(Operation *op,
PatternRewriter &rewriter) const override {
- rewriter.replaceOpWithNewOp<SPIRVOp>(op, op->getResultTypes(),
- op->getOperands(), op->getAttrs());
+ rewriter.replaceOpWithNewOp<SPIRVOp>(
+ op, op->getResultTypes(), op->getOperands(),
+ op->getDiscardableAttrDictionary().getValue());
return success();
}
};
diff --git a/mlir/test/lib/Dialect/SPIRV/TestEntryPointAbi.cpp b/mlir/test/lib/Dialect/SPIRV/TestEntryPointAbi.cpp
index f492d7cd87d83..4126071c6b6f6 100644
--- a/mlir/test/lib/Dialect/SPIRV/TestEntryPointAbi.cpp
+++ b/mlir/test/lib/Dialect/SPIRV/TestEntryPointAbi.cpp
@@ -69,13 +69,13 @@ void TestSpirvEntryPointABIPass::runOnOperation() {
SmallVector<int32_t, 3> workgroupSizeVec(workgroupSize.begin(),
workgroupSize.end());
workgroupSizeVec.resize(3, 1);
- gpuFunc->setAttr(attrName,
- spirv::getEntryPointABIAttr(
- context, workgroupSizeVec,
- (subgroupSize == 0) ? std::nullopt
- : std::optional<int>(subgroupSize),
- (targetWidth == 0) ? std::nullopt
- : std::optional<int>(targetWidth)));
+ gpuFunc->setDiscardableAttr(
+ attrName, spirv::getEntryPointABIAttr(
+ context, workgroupSizeVec,
+ (subgroupSize == 0) ? std::nullopt
+ : std::optional<int>(subgroupSize),
+ (targetWidth == 0) ? std::nullopt
+ : std::optional<int>(targetWidth)));
}
}
diff --git a/mlir/test/lib/Dialect/Shape/TestShapeFunctions.cpp b/mlir/test/lib/Dialect/Shape/TestShapeFunctions.cpp
index 5239dc5388951..dc487a63c8400 100644
--- a/mlir/test/lib/Dialect/Shape/TestShapeFunctions.cpp
+++ b/mlir/test/lib/Dialect/Shape/TestShapeFunctions.cpp
@@ -46,7 +46,7 @@ void ReportShapeFnPass::runOnOperation() {
op->emitRemark() << "associated shape function: " << fn.getName();
return true;
}
- if (auto symbol = op->getAttrOfType<SymbolRefAttr>(shapeFnId)) {
+ if (auto symbol = op->getDiscardableAttrOfType<SymbolRefAttr>(shapeFnId)) {
auto fn =
cast<shape::FuncOp>(SymbolTable::lookupSymbolIn(module, symbol));
op->emitRemark() << "associated shape function: " << fn.getName();
diff --git a/mlir/test/lib/Dialect/Tensor/TestTensorTransforms.cpp b/mlir/test/lib/Dialect/Tensor/TestTensorTransforms.cpp
index 687473ebe6d60..95659da666ba4 100644
--- a/mlir/test/lib/Dialect/Tensor/TestTensorTransforms.cpp
+++ b/mlir/test/lib/Dialect/Tensor/TestTensorTransforms.cpp
@@ -305,7 +305,7 @@ static LogicalResult testTrackingListenerReplacements(Operation *rootOp) {
// Find replaced op.
Operation *replaced = nullptr;
WalkResult status = rootOp->walk([&](Operation *op) {
- if (op->hasAttr("replaced")) {
+ if (op->hasDiscardableAttr("replaced")) {
if (replaced) {
op->emitError("only one 'replaced' op is allowed per test case");
replaced->emitRemark("other 'replaced' op");
@@ -326,8 +326,8 @@ static LogicalResult testTrackingListenerReplacements(Operation *rootOp) {
SmallVector<Value> replacements(replaced->getNumResults(), Value());
status = rootOp->walk([&](Operation *op) {
for (int64_t i = 0; i < replaced->getNumResults(); ++i) {
- if (auto attr = op->getAttrOfType<IntegerAttr>("replacement_" +
- std::to_string(i))) {
+ if (auto attr = op->getDiscardableAttrOfType<IntegerAttr>(
+ "replacement_" + std::to_string(i))) {
if (replacements[i]) {
op->emitError("only one 'replacement_" + std::to_string(i) +
"' is allowed per test case");
diff --git a/mlir/test/lib/Dialect/Test/TestDialect.cpp b/mlir/test/lib/Dialect/Test/TestDialect.cpp
index 7c1db3884be10..d4d9aa5c7df79 100644
--- a/mlir/test/lib/Dialect/Test/TestDialect.cpp
+++ b/mlir/test/lib/Dialect/Test/TestDialect.cpp
@@ -315,7 +315,8 @@ void test::testSideEffectOpGetEffect(
Operation *op,
SmallVectorImpl<SideEffects::EffectInstance<TestEffects::Effect>>
&effects) {
- auto effectsAttr = op->getAttrOfType<AffineMapAttr>("effect_parameter");
+ auto effectsAttr =
+ op->getDiscardableAttrOfType<AffineMapAttr>("effect_parameter");
if (!effectsAttr)
return;
@@ -480,7 +481,8 @@ MutableOperandRange CallWithSegmentsOp::getArgOperandsMutable() {
// Obtain the canonical segment size attribute name for this op.
auto segName =
CallWithSegmentsOp::getOperandSegmentSizesAttrName(op->getName());
- auto sizesAttr = op->getAttrOfType<DenseI32ArrayAttr>(segName);
+ auto sizesAttr = dyn_cast_or_null<DenseI32ArrayAttr>(
+ op->getInherentAttr(segName).value_or(Attribute{}));
assert(sizesAttr && "missing operandSegmentSizes attribute on op");
// Compute the start and length of the args segment from the prefix size and
diff --git a/mlir/test/lib/Dialect/Test/TestDialectInterfaces.cpp b/mlir/test/lib/Dialect/Test/TestDialectInterfaces.cpp
index 04d956cce2eea..2b52978fe3636 100644
--- a/mlir/test/lib/Dialect/Test/TestDialectInterfaces.cpp
+++ b/mlir/test/lib/Dialect/Test/TestDialectInterfaces.cpp
@@ -327,7 +327,7 @@ struct TestInlinerInterface : public DialectInlinerInterface {
bool isLegalToInline(Operation *call, Operation *callable,
bool wouldBeCloned) const final {
// Don't allow inlining calls that are marked `noinline`.
- return !call->hasAttr("noinline");
+ return !call->hasDiscardableAttr("noinline");
}
bool isLegalToInline(Region *, Region *, bool, IRMapping &) const final {
// Inlining into test dialect regions is legal.
@@ -420,7 +420,8 @@ struct TestInlinerInterface : public DialectInlinerInterface {
// Set attributed on all ops in the inlined blocks.
for (Block &block : inlinedBlocks) {
block.walk([&](Operation *op) {
- op->setAttr("inlined_conversion", UnitAttr::get(call->getContext()));
+ op->setDiscardableAttr("inlined_conversion",
+ UnitAttr::get(call->getContext()));
});
}
}
diff --git a/mlir/test/lib/Dialect/Test/TestOpDefs.cpp b/mlir/test/lib/Dialect/Test/TestOpDefs.cpp
index 2e8bce9199fd2..734fceeede346 100644
--- a/mlir/test/lib/Dialect/Test/TestOpDefs.cpp
+++ b/mlir/test/lib/Dialect/Test/TestOpDefs.cpp
@@ -82,7 +82,7 @@ SuccessorOperands TestInternalBranchOp::getSuccessorOperands(unsigned index) {
LogicalResult TestCallOp::verifySymbolUses(SymbolTableCollection &symbolTable) {
// Check that the callee attribute was specified.
- auto fnAttr = (*this)->getAttrOfType<FlatSymbolRefAttr>("callee");
+ auto fnAttr = getCalleeAttr();
if (!fnAttr)
return emitOpError("requires a 'callee' symbol reference attribute");
if (!symbolTable.lookupNearestSymbolFrom<FunctionOpInterface>(*this, fnAttr))
@@ -459,7 +459,8 @@ struct TestResource : public SideEffects::Resource::Base<TestResource> {
void SideEffectOp::getEffects(
SmallVectorImpl<MemoryEffects::EffectInstance> &effects) {
// Check for an effects attribute on the op instance.
- ArrayAttr effectsAttr = (*this)->getAttrOfType<ArrayAttr>("effects");
+ ArrayAttr effectsAttr =
+ (*this)->getDiscardableAttrOfType<ArrayAttr>("effects");
if (!effectsAttr)
return;
@@ -520,7 +521,8 @@ void ConditionalSideEffectOp::getEffects(
void SideEffectWithRegionOp::getEffects(
SmallVectorImpl<MemoryEffects::EffectInstance> &effects) {
// Check for an effects attribute on the op instance.
- ArrayAttr effectsAttr = (*this)->getAttrOfType<ArrayAttr>("effects");
+ ArrayAttr effectsAttr =
+ (*this)->getDiscardableAttrOfType<ArrayAttr>("effects");
if (!effectsAttr)
return;
@@ -629,10 +631,15 @@ void StringAttrPrettyNameOp::print(OpAsmPrinter &p) {
}
}
- if (namesDisagree)
- p.printOptionalAttrDictWithKeyword((*this)->getAttrs());
- else
- p.printOptionalAttrDictWithKeyword((*this)->getAttrs(), {"names"});
+ if (namesDisagree) {
+ SmallVector<NamedAttribute> attrs((*this)->getDiscardableAttrs());
+ attrs.emplace_back(getNamesAttrName(), getNamesAttr());
+ llvm::sort(attrs);
+ p.printOptionalAttrDictWithKeyword(attrs);
+ } else {
+ p.printOptionalAttrDictWithKeyword(
+ (*this)->getDiscardableAttrDictionary().getValue(), {"names"});
+ }
}
// We set the SSA name in the asm syntax to the contents of the name
@@ -953,7 +960,13 @@ ParseResult TestWithBoundsRegionOp::parse(OpAsmParser &parser,
}
void TestWithBoundsRegionOp::print(OpAsmPrinter &p) {
- p.printOptionalAttrDict((*this)->getAttrs());
+ SmallVector<NamedAttribute> attrs((*this)->getDiscardableAttrs());
+ attrs.emplace_back(getUminAttrName(), getUminAttr());
+ attrs.emplace_back(getUmaxAttrName(), getUmaxAttr());
+ attrs.emplace_back(getSminAttrName(), getSminAttr());
+ attrs.emplace_back(getSmaxAttrName(), getSmaxAttr());
+ llvm::sort(attrs);
+ p.printOptionalAttrDict(attrs);
p << ' ';
p.printRegionArgument(getRegion().getArgument(0), /*argAttrs=*/{},
/*omitType=*/false);
diff --git a/mlir/test/lib/Dialect/Test/TestOps.td b/mlir/test/lib/Dialect/Test/TestOps.td
index 3cb7f6ce2a054..3acebf1bc1b7f 100644
--- a/mlir/test/lib/Dialect/Test/TestOps.td
+++ b/mlir/test/lib/Dialect/Test/TestOps.td
@@ -714,11 +714,11 @@ def ConversionCallOp : TEST_Op<"conversion_call_op",
}];
let extraClassDefinition = [{
::mlir::CallInterfaceCallable $cppClass::getCallableForCallee() {
- return (*this)->getAttrOfType<::mlir::SymbolRefAttr>("callee");
+ return getCalleeAttr();
}
void $cppClass::setCalleeFromCallable(::mlir::CallInterfaceCallable callee) {
- (*this)->setAttr("callee", cast<SymbolRefAttr>(callee));
+ setCalleeAttr(cast<SymbolRefAttr>(callee));
}
}];
}
@@ -3116,13 +3116,15 @@ def TestLinalgConvOp :
}
llvm::SmallVector<mlir::utils::IteratorType> getIteratorTypesArray() {
- auto attrs = getOperation()->getAttrOfType<mlir::ArrayAttr>("iterator_types");
+ auto attrs = getOperation()->getDiscardableAttrOfType<mlir::ArrayAttr>(
+ "iterator_types");
auto range = attrs.getAsValueRange<IteratorTypeAttr, mlir::utils::IteratorType>();
return {range.begin(), range.end()};
}
mlir::ArrayAttr getIndexingMaps() {
- return getOperation()->getAttrOfType<mlir::ArrayAttr>("indexing_maps");
+ return getOperation()->getDiscardableAttrOfType<mlir::ArrayAttr>(
+ "indexing_maps");
}
std::string getLibraryCallName() {
@@ -3179,13 +3181,15 @@ def TestLinalgFillOp :
}
llvm::SmallVector<mlir::utils::IteratorType> getIteratorTypesArray() {
- auto attrs = getOperation()->getAttrOfType<mlir::ArrayAttr>("iterator_types");
+ auto attrs = getOperation()->getDiscardableAttrOfType<mlir::ArrayAttr>(
+ "iterator_types");
auto range = attrs.getAsValueRange<IteratorTypeAttr, mlir::utils::IteratorType>();
return {range.begin(), range.end()};
}
mlir::ArrayAttr getIndexingMaps() {
- return getOperation()->getAttrOfType<mlir::ArrayAttr>("indexing_maps");
+ return getOperation()->getDiscardableAttrOfType<mlir::ArrayAttr>(
+ "indexing_maps");
}
std::string getLibraryCallName() {
@@ -4423,15 +4427,16 @@ def CallWithSegmentsOp : TEST_Op<"call_with_segments",
let extraClassDefinition = [{
::mlir::CallInterfaceCallable $cppClass::getCallableForCallee() {
- if (auto sym = (*this)->getAttrOfType<::mlir::SymbolRefAttr>("callee"))
+ if (auto sym = (*this)->getDiscardableAttrOfType<::mlir::SymbolRefAttr>(
+ "callee"))
return ::mlir::CallInterfaceCallable(sym);
return ::mlir::CallInterfaceCallable();
}
void $cppClass::setCalleeFromCallable(::mlir::CallInterfaceCallable callee) {
if (auto sym = callee.dyn_cast<::mlir::SymbolRefAttr>())
- (*this)->setAttr("callee", sym);
+ (*this)->setDiscardableAttr("callee", sym);
else
- (*this)->removeAttr("callee");
+ (*this)->removeDiscardableAttr("callee");
}
}];
}
diff --git a/mlir/test/lib/Dialect/Test/TestOpsSyntax.cpp b/mlir/test/lib/Dialect/Test/TestOpsSyntax.cpp
index 5880c2a2302b0..3a971e462e2b8 100644
--- a/mlir/test/lib/Dialect/Test/TestOpsSyntax.cpp
+++ b/mlir/test/lib/Dialect/Test/TestOpsSyntax.cpp
@@ -456,7 +456,8 @@ void PolyForOp::print(OpAsmPrinter &p) {
void PolyForOp::getAsmBlockArgumentNames(Region ®ion,
OpAsmSetValueNameFn setNameFn) {
- auto arrayAttr = getOperation()->getAttrOfType<ArrayAttr>("arg_names");
+ auto arrayAttr =
+ getOperation()->getDiscardableAttrOfType<ArrayAttr>("arg_names");
if (!arrayAttr)
return;
auto args = getRegion().front().getArguments();
diff --git a/mlir/test/lib/Dialect/Test/TestPatterns.cpp b/mlir/test/lib/Dialect/Test/TestPatterns.cpp
index 552a1a473c9fd..58271aab2364a 100644
--- a/mlir/test/lib/Dialect/Test/TestPatterns.cpp
+++ b/mlir/test/lib/Dialect/Test/TestPatterns.cpp
@@ -131,7 +131,7 @@ struct FolderInsertBeforePreviouslyFoldedConstantPattern
LogicalResult matchAndRewrite(TestCastOp op,
PatternRewriter &rewriter) const override {
- if (!op->hasAttr("test_fold_before_previously_folded_op"))
+ if (!op->hasDiscardableAttr("test_fold_before_previously_folded_op"))
return failure();
rewriter.setInsertionPointToStart(op->getBlock());
@@ -192,10 +192,11 @@ struct MakeOpEligible : public RewritePattern {
LogicalResult matchAndRewrite(Operation *op,
PatternRewriter &rewriter) const override {
- if (op->hasAttr("eligible"))
+ if (op->hasDiscardableAttr("eligible"))
return failure();
- rewriter.modifyOpInPlace(
- op, [&]() { op->setAttr("eligible", rewriter.getUnitAttr()); });
+ rewriter.modifyOpInPlace(op, [&]() {
+ op->setDiscardableAttr("eligible", rewriter.getUnitAttr());
+ });
return success();
}
};
@@ -210,7 +211,7 @@ struct HoistEligibleOps : public OpRewritePattern<test::OneRegionOp> {
Operation *toBeHoisted = terminator->getOperands()[0].getDefiningOp();
if (toBeHoisted->getParentOp() != op)
return failure();
- if (!toBeHoisted->hasAttr("eligible"))
+ if (!toBeHoisted->hasDiscardableAttr("eligible"))
return failure();
rewriter.moveOpBefore(toBeHoisted, op);
return success();
@@ -305,7 +306,7 @@ struct MoveAfterParentOp : public RewritePattern {
return failure();
int64_t moveForwardBy = 0;
- if (auto advanceBy = op->getAttrOfType<IntegerAttr>("advance"))
+ if (auto advanceBy = op->getDiscardableAttrOfType<IntegerAttr>("advance"))
moveForwardBy = advanceBy.getInt();
Operation *moveAfter = op->getParentOp();
@@ -363,10 +364,10 @@ struct CloneOp : public RewritePattern {
LogicalResult matchAndRewrite(Operation *op,
PatternRewriter &rewriter) const override {
// Do not clone already cloned ops to avoid going into an infinite loop.
- if (op->hasAttr("was_cloned"))
+ if (op->hasDiscardableAttr("was_cloned"))
return failure();
Operation *cloned = rewriter.clone(*op);
- cloned->setAttr("was_cloned", rewriter.getUnitAttr());
+ cloned->setDiscardableAttr("was_cloned", rewriter.getUnitAttr());
return success();
}
};
@@ -380,11 +381,11 @@ struct CloneRegionBeforeOp : public RewritePattern {
LogicalResult matchAndRewrite(Operation *op,
PatternRewriter &rewriter) const override {
// Do not clone already cloned ops to avoid going into an infinite loop.
- if (op->hasAttr("was_cloned"))
+ if (op->hasDiscardableAttr("was_cloned"))
return failure();
for (Region &r : op->getRegions())
rewriter.cloneRegionBefore(r, op->getBlock());
- op->setAttr("was_cloned", rewriter.getUnitAttr());
+ op->setDiscardableAttr("was_cloned", rewriter.getUnitAttr());
return success();
}
};
@@ -398,7 +399,7 @@ class ReplaceWithNewOp : public RewritePattern {
LogicalResult matchAndRewrite(Operation *op,
PatternRewriter &rewriter) const override {
Operation *newOp;
- if (op->hasAttr("create_erase_op")) {
+ if (op->hasDiscardableAttr("create_erase_op")) {
newOp = rewriter.create(
op->getLoc(),
OperationName("test.erase_op", op->getContext()).getIdentifier(),
@@ -595,9 +596,10 @@ struct TestStrictPatternDriver
(void)applyOpPatternsGreedily(ArrayRef(ops), std::move(patterns), config,
&changed, &allErased);
Builder b(ctx);
- getOperation()->setAttr("pattern_driver_changed", b.getBoolAttr(changed));
- getOperation()->setAttr("pattern_driver_all_erased",
- b.getBoolAttr(allErased));
+ getOperation()->setDiscardableAttr("pattern_driver_changed",
+ b.getBoolAttr(changed));
+ getOperation()->setDiscardableAttr("pattern_driver_all_erased",
+ b.getBoolAttr(allErased));
}
Option<std::string> strictMode{
@@ -614,15 +616,16 @@ struct TestStrictPatternDriver
LogicalResult matchAndRewrite(Operation *op,
PatternRewriter &rewriter) const override {
- if (op->hasAttr("skip"))
+ if (op->hasDiscardableAttr("skip"))
return failure();
Operation *newOp =
rewriter.create(op->getLoc(), op->getName().getIdentifier(),
op->getOperands(), op->getResultTypes());
- rewriter.modifyOpInPlace(
- op, [&]() { op->setAttr("skip", rewriter.getBoolAttr(true)); });
- newOp->setAttr("skip", rewriter.getBoolAttr(true));
+ rewriter.modifyOpInPlace(op, [&]() {
+ op->setDiscardableAttr("skip", rewriter.getBoolAttr(true));
+ });
+ newOp->setDiscardableAttr("skip", rewriter.getBoolAttr(true));
return success();
}
@@ -754,7 +757,8 @@ static void invokeCreateWithInferredReturnType(Operation *op) {
properties, op->getRegions(), inferredReturnTypes))) {
OperationState state(location, OpTy::getOperationName());
// TODO: Expand to regions.
- OpTy::build(b, state, values, op->getAttrs());
+ OpTy::build(b, state, values,
+ op->getDiscardableAttrDictionary().getValue());
(void)b.create(state);
}
}
@@ -981,9 +985,9 @@ struct TestValueReplace : public ConversionPattern {
// Replace the first operand with 2x the second operand.
Value from = op->getOperand(0);
Value repl = op->getOperand(1);
- if (op->hasAttr("conditional")) {
+ if (op->hasDiscardableAttr("conditional")) {
rewriter.replaceUsesWithIf(from, {repl, repl}, [=](OpOperand &use) {
- return use.getOwner()->hasAttr("replace_uses");
+ return use.getOwner()->hasDiscardableAttr("replace_uses");
});
} else {
rewriter.replaceAllUsesWith(from, {repl, repl});
@@ -991,8 +995,8 @@ struct TestValueReplace : public ConversionPattern {
rewriter.modifyOpInPlace(op, [&] {
// If the "trigger_rollback" attribute is set, keep the op illegal, so
// that a rollback is triggered.
- if (!op->hasAttr("trigger_rollback"))
- op->setAttr("is_legal", rewriter.getUnitAttr());
+ if (!op->hasDiscardableAttr("trigger_rollback"))
+ op->setDiscardableAttr("is_legal", rewriter.getUnitAttr());
});
return success();
}
@@ -1038,7 +1042,7 @@ struct TestUndoPropertiesModification : public ConversionPattern {
LogicalResult
matchAndRewrite(Operation *op, ArrayRef<Value> operands,
ConversionPatternRewriter &rewriter) const final {
- if (!op->hasAttr("modify_inplace"))
+ if (!op->hasDiscardableAttr("modify_inplace"))
return failure();
rewriter.modifyOpInPlace(
op, [&]() { cast<TestOpWithProperties>(op).getProperties().setA(42); });
@@ -1255,9 +1259,7 @@ struct TestBoundedRecursiveRewrite
LogicalResult matchAndRewrite(TestRecursiveRewriteOp op,
PatternRewriter &rewriter) const final {
// Decrement the depth of the op in-place.
- rewriter.modifyOpInPlace(op, [&] {
- op->setAttr("depth", rewriter.getI64IntegerAttr(op.getDepth() - 1));
- });
+ rewriter.modifyOpInPlace(op, [&] { op.setDepth(op.getDepth() - 1); });
return success();
}
};
@@ -1324,7 +1326,7 @@ class TestReplaceWithValidProducer : public ConversionPattern {
LogicalResult
matchAndRewrite(Operation *op, ArrayRef<Value> operands,
ConversionPatternRewriter &rewriter) const final {
- auto attr = op->getAttrOfType<TypeAttr>("type");
+ auto attr = op->getDiscardableAttrOfType<TypeAttr>("type");
if (!attr)
return failure();
rewriter.replaceOpWithNewOp<TestValidProducerOp>(op, attr.getValue());
@@ -1349,7 +1351,8 @@ class TestReplaceWithValidConsumer : public ConversionPattern {
// converter.
// with_converter absent: pattern must have been initialized without a type
// converter.
- if (op->hasAttr("with_converter") != static_cast<bool>(getTypeConverter()))
+ if (op->hasDiscardableAttr("with_converter") !=
+ static_cast<bool>(getTypeConverter()))
return failure();
rewriter.replaceOpWithNewOp<TestValidConsumerOp>(op, operands[0]);
return success();
@@ -1426,7 +1429,8 @@ class TestMultiple1ToNReplacement : public ConversionPattern {
types.push_back(t);
}
OperationState state(op->getLoc(), name,
- /*operands=*/{}, types, op->getAttrs());
+ /*operands=*/{}, types,
+ op->getDiscardableAttrDictionary().getValue());
auto *newOp = rewriter.create(state);
SmallVector<ValueRange> repls;
for (size_t i = 0, e = op->getNumResults(); i < e; ++i)
@@ -1470,8 +1474,9 @@ class TestPostOrderLegalization : public ConversionPattern {
for (Region &r : op->getRegions())
if (failed(rewriter.legalize(&r)))
return failure();
- rewriter.modifyOpInPlace(
- op, [&]() { op->setAttr("is_legal", rewriter.getUnitAttr()); });
+ rewriter.modifyOpInPlace(op, [&]() {
+ op->setDiscardableAttr("is_legal", rewriter.getUnitAttr());
+ });
return success();
}
};
@@ -1618,10 +1623,10 @@ struct TestLegalizePatternDriver
[&](func::CallOp op) { return converter.isLegal(op); });
target.addDynamicallyLegalOp(
OperationName("test.value_replace", &getContext()),
- [](Operation *op) { return op->hasAttr("is_legal"); });
+ [](Operation *op) { return op->hasDiscardableAttr("is_legal"); });
target.addDynamicallyLegalOp(
OperationName("test.post_order_legalization", &getContext()),
- [](Operation *op) { return op->hasAttr("is_legal"); });
+ [](Operation *op) { return op->hasDiscardableAttr("is_legal"); });
// TestCreateUnregisteredOp creates `arith.constant` operation,
// which was not added to target intentionally to test
@@ -1638,7 +1643,7 @@ struct TestLegalizePatternDriver
// Check support for marking certain operations as recursively legal.
target.markOpRecursivelyLegal<func::FuncOp, ModuleOp>([](Operation *op) {
return static_cast<bool>(
- op->getAttrOfType<UnitAttr>("test.recursively_legal"));
+ op->getDiscardableAttrOfType<UnitAttr>("test.recursively_legal"));
});
// Mark the bound recursion operation as dynamically legal.
@@ -1679,7 +1684,8 @@ struct TestLegalizePatternDriver
if (mode == ConversionMode::Full) {
// Check support for marking unknown operations as dynamically legal.
target.markUnknownOpDynamicallyLegal([](Operation *op) {
- return (bool)op->getAttrOfType<UnitAttr>("test.dynamically_legal");
+ return (bool)op->getDiscardableAttrOfType<UnitAttr>(
+ "test.dynamically_legal");
});
if (failed(applyFullConversion(getOperation(), target,
@@ -1924,7 +1930,7 @@ struct RewriteDynamicOp : public RewritePattern {
OperationState state(op->getLoc(), "test.dynamic_generic",
op->getOperands(), op->getResultTypes(),
- op->getAttrs());
+ op->getDiscardableAttrDictionary().getValue());
auto *newOp = rewriter.create(state);
rewriter.replaceOp(op, newOp->getResults());
return success();
@@ -2170,7 +2176,8 @@ struct TestTypeConversionDriver
op = op->getParentOfType<FunctionOpInterface>();
if (!op)
return Type();
- auto incrementAttr = op->getAttrOfType<IntegerAttr>("increment");
+ auto incrementAttr =
+ op->getDiscardableAttrOfType<IntegerAttr>("increment");
if (!incrementAttr)
return Type();
return IntegerType::get(v.getContext(),
diff --git a/mlir/test/lib/Dialect/Transform/TestTransformDialectExtension.cpp b/mlir/test/lib/Dialect/Transform/TestTransformDialectExtension.cpp
index faf87316f1466..1b6c3daf89624 100644
--- a/mlir/test/lib/Dialect/Transform/TestTransformDialectExtension.cpp
+++ b/mlir/test/lib/Dialect/Transform/TestTransformDialectExtension.cpp
@@ -415,7 +415,7 @@ mlir::test::TestMixedSuccessAndSilenceableOp::applyToOne(
transform::TransformRewriter &rewriter, Operation *target,
transform::ApplyToEachResultList &results,
transform::TransformState &state) {
- if (target->hasAttr("target_me"))
+ if (target->hasDiscardableAttr("target_me"))
return DiagnosedSilenceableFailure::success();
return emitDefaultSilenceableFailure(target);
}
@@ -663,11 +663,11 @@ mlir::test::TestTrackedRewriteOp::apply(transform::TransformRewriter &rewriter,
// Erase all payload ops. The outer loop should have only one iteration.
for (Operation *op : state.getPayloadOps(getIn())) {
rewriter.setInsertionPoint(op);
- if (op->hasAttr("erase_me")) {
+ if (op->hasDiscardableAttr("erase_me")) {
rewriter.eraseOp(op);
continue;
}
- if (!op->hasAttr("replace_me")) {
+ if (!op->hasDiscardableAttr("replace_me")) {
continue;
}
@@ -695,7 +695,8 @@ class ReplaceWithNewOp : public RewritePattern {
LogicalResult matchAndRewrite(Operation *op,
PatternRewriter &rewriter) const override {
- auto newName = op->getAttrOfType<StringAttr>("replace_with_new_op");
+ auto newName =
+ op->getDiscardableAttrOfType<StringAttr>("replace_with_new_op");
if (!newName)
return failure();
Operation *newOp = rewriter.create(
@@ -844,7 +845,7 @@ class ReplaceWithNewOpConversion : public ConversionPattern {
LogicalResult
matchAndRewrite(Operation *op, ArrayRef<Value> operands,
ConversionPatternRewriter &rewriter) const override {
- if (!op->hasAttr("replace_with_new_op"))
+ if (!op->hasDiscardableAttr("replace_with_new_op"))
return failure();
SmallVector<Type> newResultTypes;
if (failed(getTypeConverter()->convertTypes(op->getResultTypes(),
@@ -939,7 +940,7 @@ mlir::transform::TestCountingNormalFormAttr::checkOperation(
StringAttr counterName =
builder.getStringAttr("test.counting_normal_form_count");
unsigned count = 0;
- if (auto prev = op->getAttrOfType<IntegerAttr>(counterName))
+ if (auto prev = op->getDiscardableAttrOfType<IntegerAttr>(counterName))
count = prev.getValue().getZExtValue();
op->setDiscardableAttr(counterName, builder.getI64IntegerAttr(count + 1));
return DiagnosedSilenceableFailure::success();
diff --git a/mlir/test/lib/Dialect/XeGPU/TestXeGPUTransforms.cpp b/mlir/test/lib/Dialect/XeGPU/TestXeGPUTransforms.cpp
index f6b0c50da91dd..a4813528e98dd 100644
--- a/mlir/test/lib/Dialect/XeGPU/TestXeGPUTransforms.cpp
+++ b/mlir/test/lib/Dialect/XeGPU/TestXeGPUTransforms.cpp
@@ -166,7 +166,7 @@ class TestStepOpPattern : public OpConversionPattern<vector::StepOp> {
ConversionPatternRewriter &rewriter) const override {
auto layoutName = xegpu::getTemporaryLayoutName(op->getResult(0));
- auto sliceAttr = op->getAttrOfType<xegpu::SliceAttr>(layoutName);
+ auto sliceAttr = op->getDiscardableAttrOfType<xegpu::SliceAttr>(layoutName);
if (!sliceAttr || sliceAttr.getRank() != 1)
return failure();
@@ -437,7 +437,8 @@ struct TestXeGPULayoutInterface
target.addDynamicallyLegalOp<vector::StepOp>(
[&](vector::StepOp op) -> bool {
auto layoutName = xegpu::getTemporaryLayoutName(op->getResult(0));
- auto sliceAttr = op->getAttrOfType<xegpu::SliceAttr>(layoutName);
+ auto sliceAttr =
+ op->getDiscardableAttrOfType<xegpu::SliceAttr>(layoutName);
return isLegal(sliceAttr);
});
diff --git a/mlir/test/lib/IR/TestAffineWalk.cpp b/mlir/test/lib/IR/TestAffineWalk.cpp
index e8b836888b459..68806567ad9bb 100644
--- a/mlir/test/lib/IR/TestAffineWalk.cpp
+++ b/mlir/test/lib/IR/TestAffineWalk.cpp
@@ -43,7 +43,7 @@ void TestAffineWalk::runOnOperation() {
auto m = getOperation();
// Test whether the walk is being correctly interrupted.
m.walk([](Operation *op) {
- for (NamedAttribute attr : op->getAttrs()) {
+ for (NamedAttribute attr : op->getDiscardableAttrDictionary().getValue()) {
auto mapAttr = dyn_cast<AffineMapAttr>(attr.getValue());
if (!mapAttr)
return;
diff --git a/mlir/test/lib/IR/TestBuiltinAttributeInterfaces.cpp b/mlir/test/lib/IR/TestBuiltinAttributeInterfaces.cpp
index f44b78673ec5f..6bac095f71734 100644
--- a/mlir/test/lib/IR/TestBuiltinAttributeInterfaces.cpp
+++ b/mlir/test/lib/IR/TestBuiltinAttributeInterfaces.cpp
@@ -35,7 +35,10 @@ struct TestElementsAttrInterface
}
void runOnOperation() override {
getOperation().walk([&](Operation *op) {
- for (NamedAttribute attr : op->getAttrs()) {
+ NamedAttrList attrs(op->getDiscardableAttrDictionary());
+ if (op->getPropertiesStorageSize())
+ op->getName().populateInherentAttrs(op, attrs);
+ for (NamedAttribute attr : attrs) {
auto elementsAttr = dyn_cast<ElementsAttr>(attr.getValue());
if (!elementsAttr)
continue;
diff --git a/mlir/test/lib/IR/TestBuiltinDistinctAttributes.cpp b/mlir/test/lib/IR/TestBuiltinDistinctAttributes.cpp
index 4717ce345fc1f..924a8a91e3903 100644
--- a/mlir/test/lib/IR/TestBuiltinDistinctAttributes.cpp
+++ b/mlir/test/lib/IR/TestBuiltinDistinctAttributes.cpp
@@ -30,11 +30,13 @@ struct DistinctAttributesPass
/// Walk all operations and create a distinct output attribute given a
/// distinct input attribute.
funcOp->walk([](Operation *op) {
- auto distinctAttr = op->getAttrOfType<DistinctAttr>("distinct.input");
+ auto distinctAttr =
+ op->getDiscardableAttrOfType<DistinctAttr>("distinct.input");
if (!distinctAttr)
return;
- op->setAttr("distinct.output",
- DistinctAttr::create(distinctAttr.getReferencedAttr()));
+ op->setDiscardableAttr(
+ "distinct.output",
+ DistinctAttr::create(distinctAttr.getReferencedAttr()));
});
}
};
diff --git a/mlir/test/lib/IR/TestDiagnostics.cpp b/mlir/test/lib/IR/TestDiagnostics.cpp
index 578486c0a3b14..38126b48ea90f 100644
--- a/mlir/test/lib/IR/TestDiagnostics.cpp
+++ b/mlir/test/lib/IR/TestDiagnostics.cpp
@@ -51,7 +51,8 @@ struct TestDiagnosticFilterPass
// Emit a diagnostic for every operation with a valid loc.
getOperation()->walk([&](Operation *op) {
- if (LocationAttr locAttr = op->getAttrOfType<LocationAttr>("test.loc"))
+ if (LocationAttr locAttr =
+ op->getDiscardableAttrOfType<LocationAttr>("test.loc"))
emitError(locAttr, "test diagnostic");
});
}
diff --git a/mlir/test/lib/IR/TestDiagnosticsMetadata.cpp b/mlir/test/lib/IR/TestDiagnosticsMetadata.cpp
index 5cb0193baa171..07dc9cb430128 100644
--- a/mlir/test/lib/IR/TestDiagnosticsMetadata.cpp
+++ b/mlir/test/lib/IR/TestDiagnosticsMetadata.cpp
@@ -43,7 +43,8 @@ struct TestDiagnosticMetadataPass
// Emit a diagnostic for every operation with a valid loc.
getOperation()->walk([&](Operation *op) {
- if (StringAttr strAttr = op->getAttrOfType<StringAttr>("attr")) {
+ if (StringAttr strAttr =
+ op->getDiscardableAttrOfType<StringAttr>("attr")) {
if (strAttr.getValue() == "emit_error")
emitError(op->getLoc(), "test diagnostic metadata")
.getUnderlyingDiagnostic()
diff --git a/mlir/test/lib/IR/TestDominance.cpp b/mlir/test/lib/IR/TestDominance.cpp
index b34149b3e2cbd..60d37476b5bf9 100644
--- a/mlir/test/lib/IR/TestDominance.cpp
+++ b/mlir/test/lib/IR/TestDominance.cpp
@@ -51,12 +51,13 @@ class DominanceTest {
// Helper function that annotates the IR with block IDs.
auto annotateBlockId = [&](Operation *op, int64_t blockId) {
- auto idAttr = op->getAttrOfType<DenseI64ArrayAttr>(kBlockIdsAttrName);
+ auto idAttr =
+ op->getDiscardableAttrOfType<DenseI64ArrayAttr>(kBlockIdsAttrName);
SmallVector<int64_t> ids;
if (idAttr)
ids = llvm::to_vector(idAttr.asArrayRef());
ids.push_back(blockId);
- op->setAttr(kBlockIdsAttrName, b.getDenseI64ArrayAttr(ids));
+ op->setDiscardableAttr(kBlockIdsAttrName, b.getDenseI64ArrayAttr(ids));
};
// Create unique IDs for each block.
diff --git a/mlir/test/lib/IR/TestFunc.cpp b/mlir/test/lib/IR/TestFunc.cpp
index 2d4050d3484d0..7597f06db42f5 100644
--- a/mlir/test/lib/IR/TestFunc.cpp
+++ b/mlir/test/lib/IR/TestFunc.cpp
@@ -26,7 +26,8 @@ struct TestFuncInsertArg
UnknownLoc unknownLoc = UnknownLoc::get(module.getContext());
for (auto func : module.getOps<FunctionOpInterface>()) {
- auto inserts = func->getAttrOfType<ArrayAttr>("test.insert_args");
+ auto inserts =
+ func->getDiscardableAttrOfType<ArrayAttr>("test.insert_args");
if (!inserts || inserts.empty())
continue;
SmallVector<unsigned, 4> indicesToInsert;
@@ -44,7 +45,7 @@ struct TestFuncInsertArg
? Location(cast<LocationAttr>(insert[3]))
: unknownLoc);
}
- func->removeAttr("test.insert_args");
+ func->removeDiscardableAttr("test.insert_args");
if (succeeded(func.insertArguments(indicesToInsert, typesToInsert,
attrsToInsert, locsToInsert)))
continue;
@@ -68,7 +69,8 @@ struct TestFuncInsertResult
auto module = getOperation();
for (auto func : module.getOps<FunctionOpInterface>()) {
- auto inserts = func->getAttrOfType<ArrayAttr>("test.insert_results");
+ auto inserts =
+ func->getDiscardableAttrOfType<ArrayAttr>("test.insert_results");
if (!inserts || inserts.empty())
continue;
SmallVector<unsigned, 4> indicesToInsert;
@@ -82,7 +84,7 @@ struct TestFuncInsertResult
? cast<DictionaryAttr>(insert[2])
: DictionaryAttr::get(&getContext()));
}
- func->removeAttr("test.insert_results");
+ func->removeDiscardableAttr("test.insert_results");
if (succeeded(func.insertResults(indicesToInsert, typesToInsert,
attrsToInsert)))
continue;
@@ -166,7 +168,8 @@ struct TestFuncSetType
SymbolTable symbolTable(module);
for (auto func : module.getOps<FunctionOpInterface>()) {
- auto sym = func->getAttrOfType<FlatSymbolRefAttr>("test.set_type_from");
+ auto sym = func->getDiscardableAttrOfType<FlatSymbolRefAttr>(
+ "test.set_type_from");
if (!sym)
continue;
func.setType(symbolTable.lookup<FunctionOpInterface>(sym.getValue())
diff --git a/mlir/test/lib/IR/TestOperationEquals.cpp b/mlir/test/lib/IR/TestOperationEquals.cpp
index 7cef2e5bd4bfe..6e765e58b1f26 100644
--- a/mlir/test/lib/IR/TestOperationEquals.cpp
+++ b/mlir/test/lib/IR/TestOperationEquals.cpp
@@ -23,7 +23,7 @@ struct TestOperationEqualPass
ModuleOp module = getOperation();
// Expects two operations at the top-level:
int opCount = module.getBody()->getOperations().size();
- if (module->hasAttr("test.includes_setup")) {
+ if (module->hasDiscardableAttr("test.includes_setup")) {
if (opCount < 2) {
module.emitError()
<< "expected at least 2 top-level ops in the module, got "
@@ -41,9 +41,9 @@ struct TestOperationEqualPass
llvm::outs() << first->getName().getStringRef() << " with attr "
<< first->getDiscardableAttrDictionary();
OperationEquivalence::Flags flags{};
- if (!first->hasAttr("strict_loc_check"))
+ if (!first->hasDiscardableAttr("strict_loc_check"))
flags |= OperationEquivalence::IgnoreLocations;
- if (first->hasAttr("ignore_commutativity"))
+ if (first->hasDiscardableAttr("ignore_commutativity"))
flags |= OperationEquivalence::IgnoreCommutativity;
if (OperationEquivalence::isEquivalentTo(first, &module.getBody()->back(),
flags))
diff --git a/mlir/test/lib/IR/TestPrintNesting.cpp b/mlir/test/lib/IR/TestPrintNesting.cpp
index c66149b33371d..b1e878964c49c 100644
--- a/mlir/test/lib/IR/TestPrintNesting.cpp
+++ b/mlir/test/lib/IR/TestPrintNesting.cpp
@@ -35,9 +35,10 @@ struct TestPrintNestingPass
<< op->getNumOperands() << " operands and "
<< op->getNumResults() << " results\n";
// Print the operation attributes
- if (!op->getAttrs().empty()) {
- printIndent() << op->getAttrs().size() << " attributes:\n";
- for (NamedAttribute attr : op->getAttrs())
+ if (!op->getDiscardableAttrDictionary().getValue().empty()) {
+ printIndent() << op->getDiscardableAttrDictionary().getValue().size()
+ << " attributes:\n";
+ for (NamedAttribute attr : op->getDiscardableAttrDictionary().getValue())
printIndent() << " - '" << attr.getName().getValue() << "' : '"
<< attr.getValue() << "'\n";
}
diff --git a/mlir/test/lib/IR/TestSymbolUses.cpp b/mlir/test/lib/IR/TestSymbolUses.cpp
index 6aac9bfc8baa4..e8170b8531d1d 100644
--- a/mlir/test/lib/IR/TestSymbolUses.cpp
+++ b/mlir/test/lib/IR/TestSymbolUses.cpp
@@ -118,7 +118,8 @@ struct SymbolReplacementPass
SymbolTableCollection symbolTable;
SymbolUserMap symbolUsers(symbolTable, module);
module.getBodyRegion().walk([&](Operation *nestedOp) {
- StringAttr newName = nestedOp->getAttrOfType<StringAttr>("sym.new_name");
+ StringAttr newName =
+ nestedOp->getDiscardableAttrOfType<StringAttr>("sym.new_name");
if (!newName)
return;
symbolUsers.replaceAllUsesWith(nestedOp, newName);
diff --git a/mlir/test/lib/IR/TestVisitors.cpp b/mlir/test/lib/IR/TestVisitors.cpp
index 148a57f2a739b..603ee12a1aa46 100644
--- a/mlir/test/lib/IR/TestVisitors.cpp
+++ b/mlir/test/lib/IR/TestVisitors.cpp
@@ -251,7 +251,7 @@ static void testBlockAndRegionWalkers(Operation *op) {
llvm::outs() << "Invoke block pre-order visits on blocks\n";
op->walk([&](Operation *op) {
- if (!op->hasAttr("walk_blocks"))
+ if (!op->hasDiscardableAttr("walk_blocks"))
return;
for (Region ®ion : op->getRegions()) {
for (Block &block : region.getBlocks()) {
@@ -262,7 +262,7 @@ static void testBlockAndRegionWalkers(Operation *op) {
llvm::outs() << "Invoke block post-order visits on blocks\n";
op->walk([&](Operation *op) {
- if (!op->hasAttr("walk_blocks"))
+ if (!op->hasDiscardableAttr("walk_blocks"))
return;
for (Region ®ion : op->getRegions()) {
for (Block &block : region.getBlocks()) {
@@ -273,7 +273,7 @@ static void testBlockAndRegionWalkers(Operation *op) {
llvm::outs() << "Invoke region pre-order visits on region\n";
op->walk([&](Operation *op) {
- if (!op->hasAttr("walk_regions"))
+ if (!op->hasDiscardableAttr("walk_regions"))
return;
for (Region ®ion : op->getRegions()) {
region.walk<WalkOrder::PreOrder>(regionPure);
@@ -282,7 +282,7 @@ static void testBlockAndRegionWalkers(Operation *op) {
llvm::outs() << "Invoke region post-order visits on region\n";
op->walk([&](Operation *op) {
- if (!op->hasAttr("walk_regions"))
+ if (!op->hasDiscardableAttr("walk_regions"))
return;
for (Region ®ion : op->getRegions()) {
region.walk<WalkOrder::PostOrder>(regionPure);
diff --git a/mlir/test/lib/IR/TestVisitorsGeneric.cpp b/mlir/test/lib/IR/TestVisitorsGeneric.cpp
index 4556671df0ba0..20193bd71a6f5 100644
--- a/mlir/test/lib/IR/TestVisitorsGeneric.cpp
+++ b/mlir/test/lib/IR/TestVisitorsGeneric.cpp
@@ -64,31 +64,33 @@ struct TestGenericIRVisitorInterruptPass
auto walker = [&](Operation *op, const WalkStage &stage) {
if (auto interruptBeforeAall =
- op->getAttrOfType<BoolAttr>("interrupt_before_all"))
+ op->getDiscardableAttrOfType<BoolAttr>("interrupt_before_all"))
if (interruptBeforeAall.getValue() && stage.isBeforeAllRegions())
return WalkResult::interrupt();
if (auto interruptAfterAll =
- op->getAttrOfType<BoolAttr>("interrupt_after_all"))
+ op->getDiscardableAttrOfType<BoolAttr>("interrupt_after_all"))
if (interruptAfterAll.getValue() && stage.isAfterAllRegions())
return WalkResult::interrupt();
- if (auto interruptAfterRegion =
- op->getAttrOfType<IntegerAttr>("interrupt_after_region"))
+ if (auto interruptAfterRegion = op->getDiscardableAttrOfType<IntegerAttr>(
+ "interrupt_after_region"))
if (stage.isAfterRegion(
static_cast<int>(interruptAfterRegion.getInt())))
return WalkResult::interrupt();
- if (auto skipBeforeAall = op->getAttrOfType<BoolAttr>("skip_before_all"))
+ if (auto skipBeforeAall =
+ op->getDiscardableAttrOfType<BoolAttr>("skip_before_all"))
if (skipBeforeAall.getValue() && stage.isBeforeAllRegions())
return WalkResult::skip();
- if (auto skipAfterAll = op->getAttrOfType<BoolAttr>("skip_after_all"))
+ if (auto skipAfterAll =
+ op->getDiscardableAttrOfType<BoolAttr>("skip_after_all"))
if (skipAfterAll.getValue() && stage.isAfterAllRegions())
return WalkResult::skip();
if (auto skipAfterRegion =
- op->getAttrOfType<IntegerAttr>("skip_after_region"))
+ op->getDiscardableAttrOfType<IntegerAttr>("skip_after_region"))
if (stage.isAfterRegion(static_cast<int>(skipAfterRegion.getInt())))
return WalkResult::skip();
@@ -131,7 +133,7 @@ struct TestGenericIRBlockVisitorInterruptPass
auto walker = [&](Block *block) {
for (Operation &op : *block)
- if (op.getAttrOfType<BoolAttr>("interrupt"))
+ if (op.getDiscardableAttrOfType<BoolAttr>("interrupt"))
return WalkResult::interrupt();
llvm::outs() << "step " << stepNo++ << "\n";
@@ -162,7 +164,7 @@ struct TestGenericIRRegionVisitorInterruptPass
auto walker = [&](Region *region) {
for (Operation &op : region->getOps())
- if (op.getAttrOfType<BoolAttr>("interrupt"))
+ if (op.getDiscardableAttrOfType<BoolAttr>("interrupt"))
return WalkResult::interrupt();
llvm::outs() << "step " << stepNo++ << "\n";
diff --git a/mlir/test/lib/Transforms/TestControlFlowSink.cpp b/mlir/test/lib/Transforms/TestControlFlowSink.cpp
index ad34b6c2ffdf8..7e4decabb0832 100644
--- a/mlir/test/lib/Transforms/TestControlFlowSink.cpp
+++ b/mlir/test/lib/Transforms/TestControlFlowSink.cpp
@@ -43,8 +43,8 @@ struct TestControlFlowSinkPass
auto moveIntoRegion = [](Operation *op, Region *region) {
Block &entry = region->front();
op->moveBefore(&entry, entry.begin());
- op->setAttr("was_sunk",
- Builder(op).getI32IntegerAttr(region->getRegionNumber()));
+ op->setDiscardableAttr(
+ "was_sunk", Builder(op).getI32IntegerAttr(region->getRegionNumber()));
};
getOperation()->walk([&](Operation *op) {
diff --git a/mlir/test/mlir-linalg-ods-gen/test-linalg-ods-yaml-gen.yaml b/mlir/test/mlir-linalg-ods-gen/test-linalg-ods-yaml-gen.yaml
index 00c70705cbb35..b88c7855b990d 100644
--- a/mlir/test/mlir-linalg-ods-gen/test-linalg-ods-yaml-gen.yaml
+++ b/mlir/test/mlir-linalg-ods-gen/test-linalg-ods-yaml-gen.yaml
@@ -183,7 +183,7 @@ structured_op: !LinalgStructuredOpConfig
# IMPL: Test2Op::hasDynamicIndexingMaps() { return true; }
# IMPL: Test2Op::verifyIndexingMapRequiredAttributes()
-# IMPL: auto attr = op->getAttrOfType<DenseElementsAttr>("strides")
+# IMPL: op->getInherentAttr("strides")
# IMPL: "incorrect element type for index attribute 'strides'"
# IMPL: "incorrect shape for index attribute 'strides'"
# IMPL: void Test2Op::regionBuilder(ImplicitLocOpBuilder &b,
diff --git a/mlir/tools/mlir-linalg-ods-gen/mlir-linalg-ods-yaml-gen.cpp b/mlir/tools/mlir-linalg-ods-gen/mlir-linalg-ods-yaml-gen.cpp
index 67dbab8ca79f9..e4f5143b47bdf 100644
--- a/mlir/tools/mlir-linalg-ods-gen/mlir-linalg-ods-yaml-gen.cpp
+++ b/mlir/tools/mlir-linalg-ods-gen/mlir-linalg-ods-yaml-gen.cpp
@@ -623,7 +623,8 @@ SmallVector<utils::IteratorType> {0}::getIteratorTypesArray() {{
static const char structuredOpIndexingMapsFormat[] = R"FMT(
ArrayAttr {0}::getIndexingMaps() {{
static const char memoizeAttr[] = "linalg.memoized_indexing_maps";
- ArrayAttr cached = getOperation()->getAttrOfType<ArrayAttr>(memoizeAttr);
+ ArrayAttr cached =
+ getOperation()->getDiscardableAttrOfType<ArrayAttr>(memoizeAttr);
if (cached)
return cached;
@@ -632,7 +633,7 @@ ArrayAttr {0}::getIndexingMaps() {{
SmallVector<AffineMap> maps;
{1}
cached = Builder(context).getAffineMapArrayAttr(maps);
- getOperation()->setAttr(memoizeAttr, cached);
+ getOperation()->setDiscardableAttr(memoizeAttr, cached);
return cached;
}
)FMT";
@@ -976,7 +977,8 @@ std::string {0}::getLibraryCallName() {{
// {0}: Attribute name
// {1}: Attribute size
static const char attrFmt[] = R"FMT(
-if (auto attr = op->getAttrOfType<DenseElementsAttr>("{0}")) {{
+if (auto attr = llvm::dyn_cast_or_null<DenseElementsAttr>(
+ op->getInherentAttr("{0}").value_or(Attribute{{}))) {{
if (!attr.getType().getElementType().isInteger(64))
return op->emitError("incorrect element type for index attribute '{0}'");
if (attr.getType().getShape() != ArrayRef<int64_t>{{ {1} })
diff --git a/mlir/tools/mlir-tblgen/DialectGen.cpp b/mlir/tools/mlir-tblgen/DialectGen.cpp
index 8eecad39f49f3..d2f9faa7a9db5 100644
--- a/mlir/tools/mlir-tblgen/DialectGen.cpp
+++ b/mlir/tools/mlir-tblgen/DialectGen.cpp
@@ -215,17 +215,17 @@ static const char *const discardableAttrHelperDecl = R"(
: name(::mlir::StringAttr::get(ctx, getNameStr())) {{}
{2} getAttr(::mlir::Operation *op) const {{
- return op->getAttrOfType<{2}>(name);
+ return op->getDiscardableAttrOfType<{2}>(name);
}
void setAttr(::mlir::Operation *op, {2} val) const {{
- op->setAttr(name, val);
+ op->setDiscardableAttr(name, val);
}
bool isAttrPresent(::mlir::Operation *op) const {{
- return op->hasAttrOfType<{2}>(name);
+ return op->hasDiscardableAttrOfType<{2}>(name);
}
void removeAttr(::mlir::Operation *op) const {{
- assert(op->hasAttrOfType<{2}>(name));
- op->removeAttr(name);
+ assert(op->hasDiscardableAttrOfType<{2}>(name));
+ op->removeDiscardableAttr(name);
}
};
{0}AttrHelper get{0}AttrHelper() {
diff --git a/mlir/tools/mlir-tblgen/OpDefinitionsGen.cpp b/mlir/tools/mlir-tblgen/OpDefinitionsGen.cpp
index d7c119a31795a..6bced8e2c31b0 100644
--- a/mlir/tools/mlir-tblgen/OpDefinitionsGen.cpp
+++ b/mlir/tools/mlir-tblgen/OpDefinitionsGen.cpp
@@ -373,7 +373,7 @@ class OpOrAdaptorHelper {
// Get the code snippet for getting the named attribute range.
StringRef getAttrRange() const {
- return emitForOp ? "(*this)->getAttrs()" : "odsAttrs";
+ return emitForOp ? "(*this)->getRawDictionaryAttrs()" : "odsAttrs";
}
// Get the prefix code for emitting an error.
@@ -2349,11 +2349,10 @@ void OpEmitter::genNamedOperandSetters() {
// MutableOperandRangeRange that provides a range over all of the
// sub-ranges.
if (operand.isVariadicOfVariadic()) {
- body << " return "
- "mutableRange.split(*(*this)->getAttrDictionary().getNamed("
- << op.getGetterName(
- operand.constraint.getVariadicOfVariadicSegmentSizeAttr())
- << "AttrName()));\n";
+ StringRef segmentAttr =
+ operand.constraint.getVariadicOfVariadicSegmentSizeAttr();
+ body << " return mutableRange.split({" << op.getGetterName(segmentAttr)
+ << "AttrName(), " << op.getGetterName(segmentAttr) << "Attr()});\n";
} else {
// Otherwise, we use the full range directly.
body << " return mutableRange;\n";
diff --git a/mlir/tools/mlir-tblgen/OpFormatGen.cpp b/mlir/tools/mlir-tblgen/OpFormatGen.cpp
index 470d27cfc6060..12a50f05bdff3 100644
--- a/mlir/tools/mlir-tblgen/OpFormatGen.cpp
+++ b/mlir/tools/mlir-tblgen/OpFormatGen.cpp
@@ -2063,7 +2063,9 @@ static const char *regionSingleBlockImplicitTerminatorPrinterCode = R"(
{
bool printTerminator = true;
if (auto *term = {0}.empty() ? nullptr : {0}.begin()->getTerminator()) {{
- printTerminator = !term->getAttrDictionary().empty() ||
+ ::mlir::NamedAttrList termAttrs(term->getRawDictionaryAttrs());
+ term->getName().populateInherentAttrs(term, termAttrs);
+ printTerminator = !termAttrs.empty() ||
term->getNumOperands() != 0 ||
term->getNumResults() != 0;
}
@@ -2220,11 +2222,17 @@ static void genAttrDictPrinter(OperationFormat &fmt, Operator &op,
if (fmt.hasPropDict)
body << " _odsPrinter.printOptionalAttrDict"
<< (withKeyword ? "WithKeyword" : "")
- << "(llvm::to_vector((*this)->getDiscardableAttrs()), elidedAttrs);\n";
- else
- body << " _odsPrinter.printOptionalAttrDict"
+ << "(llvm::to_vector((*this)->getDiscardableAttrDictionary().getValue("
+ ")), elidedAttrs);\n";
+ else {
+ body << " ::mlir::NamedAttrList _odsAttrs("
+ "(*this)->getRawDictionaryAttrs());\n"
+ " (*this)->getName().populateInherentAttrs(*this, _odsAttrs);\n"
+ " _odsPrinter.printOptionalAttrDict"
<< (withKeyword ? "WithKeyword" : "")
- << "((*this)->getAttrs(), elidedAttrs);\n";
+ << "(_odsAttrs.getDictionary(getContext()).getValue(), "
+ "elidedAttrs);\n";
+ }
}
/// Generate the printer for a literal value. `shouldEmitSpace` is true if a
@@ -2266,7 +2274,11 @@ static void genCustomDirectiveParameterPrinter(FormatElement *element,
body << op.getGetterName(attr->getVar()->name) << "Attr()";
} else if (isa<AttrDictDirective>(element)) {
- body << "getOperation()->getAttrDictionary()";
+ body << "[&]() { ::mlir::NamedAttrList attrs("
+ "getOperation()->getRawDictionaryAttrs()); "
+ "getOperation()->getName().populateInherentAttrs("
+ "getOperation(), attrs); return attrs.getDictionary("
+ "getOperation()->getContext()); }()";
} else if (isa<PropDictDirective>(element)) {
body << "getProperties()";
diff --git a/mlir/tools/mlir-tblgen/SPIRVUtilsGen.cpp b/mlir/tools/mlir-tblgen/SPIRVUtilsGen.cpp
index 4de8c60dfb55a..f9f25ebb1e663 100644
--- a/mlir/tools/mlir-tblgen/SPIRVUtilsGen.cpp
+++ b/mlir/tools/mlir-tblgen/SPIRVUtilsGen.cpp
@@ -514,9 +514,9 @@ constexpr llvm::StringLiteral constantIdEnumAttrs[] = {
static void emitAttributeSerialization(const Attribute &attr,
ArrayRef<SMLoc> loc, StringRef tabs,
StringRef opVar, StringRef operandList,
- StringRef attrName, raw_ostream &os) {
+ StringRef getterName, raw_ostream &os) {
os << tabs
- << formatv("if (auto attr = {0}->getAttr(\"{1}\")) {{\n", opVar, attrName);
+ << formatv("if (auto attr = {0}.{1}Attr()) {{\n", opVar, getterName);
if (llvm::is_contained(constantIdEnumAttrs, attr.getAttrDefName())) {
EnumInfo baseEnum(attr.getDef().getValueAsDef("enum"));
os << tabs
@@ -628,7 +628,7 @@ static void emitArgumentSerialization(const Operator &op, ArrayRef<SMLoc> loc,
for (const NamedAttribute &attr : op.getAttributes()) {
emitAttributeSerialization(
(attr.attr.isOptional() ? attr.attr.getBaseAttr() : attr.attr), loc,
- tabs, opVar, operands, attr.name, os);
+ tabs, opVar, operands, op.getGetterName(attr.name), os);
os << tabs
<< formatv("{0}.push_back(\"{1}\");\n", elidedAttrs, attr.name);
}
@@ -659,7 +659,7 @@ static void emitArgumentSerialization(const Operator &op, ArrayRef<SMLoc> loc,
auto newtabs = tabs.str() + " ";
emitAttributeSerialization(
(attr->attr.isOptional() ? attr->attr.getBaseAttr() : attr->attr),
- loc, newtabs, opVar, operands, attr->name, os);
+ loc, newtabs, opVar, operands, op.getGetterName(attr->name), os);
os << newtabs
<< formatv("{0}.push_back(\"{1}\");\n", elidedAttrs, attr->name);
}
@@ -702,7 +702,10 @@ static void emitDecorationSerialization(const Operator &op, StringRef tabs,
StringRef resultID, raw_ostream &os) {
if (op.getNumResults() == 1) {
// All non-argument attributes translated into OpDecorate instruction
- os << tabs << formatv("for (auto attr : {0}->getAttrs()) {{\n", opVar);
+ os << tabs
+ << formatv("for (auto attr : "
+ "{0}->getDiscardableAttrDictionary().getValue()) {{\n",
+ opVar);
os << tabs
<< formatv(" if (llvm::is_contained({0}, attr.getName())) {{",
elidedAttrs);
diff --git a/mlir/unittests/Bytecode/BytecodeTest.cpp b/mlir/unittests/Bytecode/BytecodeTest.cpp
index d8f6510924698..7e11aa14fda44 100644
--- a/mlir/unittests/Bytecode/BytecodeTest.cpp
+++ b/mlir/unittests/Bytecode/BytecodeTest.cpp
@@ -222,7 +222,7 @@ TEST(Bytecode, OpWithoutProperties) {
ASSERT_TRUE(succeeded(readBytecodeFile(
llvm::MemoryBufferRef(bytecode, "string-buffer"), block.get(), config)));
Operation *roundtripped = &block->front();
- EXPECT_EQ(roundtripped->getAttrs().size(), 2u);
+ EXPECT_EQ(roundtripped->getRawDictionaryAttrs().size(), 2u);
EXPECT_EQ(roundtripped->getInherentAttr("inherent_attr"), std::nullopt);
EXPECT_NE(roundtripped->getDiscardableAttr("inherent_attr"), Attribute());
EXPECT_NE(roundtripped->getDiscardableAttr("other_attr"), Attribute());
@@ -389,7 +389,7 @@ TEST(Bytecode, LocationElisionPreservesAttributes) {
EXPECT_TRUE(isa<UnknownLoc>(innerOp->getLoc()));
// 2. Verify that the semantic location attribute WAS PRESERVED.
- Attribute semanticLocAttr = innerOp->getAttr("some_loc_attr");
+ Attribute semanticLocAttr = innerOp->getDiscardableAttr("some_loc_attr");
ASSERT_TRUE(semanticLocAttr);
auto locAttr = dyn_cast<LocationAttr>(semanticLocAttr);
ASSERT_TRUE(locAttr);
diff --git a/mlir/unittests/Dialect/OpenACC/OpenACCUtilsCGTest.cpp b/mlir/unittests/Dialect/OpenACC/OpenACCUtilsCGTest.cpp
index 1887405871ff3..33877636b050a 100644
--- a/mlir/unittests/Dialect/OpenACC/OpenACCUtilsCGTest.cpp
+++ b/mlir/unittests/Dialect/OpenACC/OpenACCUtilsCGTest.cpp
@@ -161,7 +161,7 @@ TEST_F(OpenACCUtilsCGTest, getDataLayoutWithSpec) {
auto indexEntry = DataLayoutEntryAttr::get(IndexType::get(&context),
b.getI32IntegerAttr(32));
auto spec = DataLayoutSpecAttr::get(&context, {indexEntry});
- (*module)->setAttr(DLTIDialect::kDataLayoutAttrName, spec);
+ (*module)->setDiscardableAttr(DLTIDialect::kDataLayoutAttrName, spec);
// With explicit spec, should return DataLayout regardless of allowDefault
auto dl1 = getDataLayout(module->getOperation(), /*allowDefault=*/false);
diff --git a/mlir/unittests/Dialect/OpenACC/OpenACCUtilsGPUTest.cpp b/mlir/unittests/Dialect/OpenACC/OpenACCUtilsGPUTest.cpp
index e7ee0655d41f0..e4243ed04f8f1 100644
--- a/mlir/unittests/Dialect/OpenACC/OpenACCUtilsGPUTest.cpp
+++ b/mlir/unittests/Dialect/OpenACC/OpenACCUtilsGPUTest.cpp
@@ -51,8 +51,8 @@ TEST_F(OpenACCUtilsGPUTest, getOrCreateGPUModuleCreatesWhenMissing) {
EXPECT_EQ(gpuMod->getName(), kDefaultGPUModuleName);
// Module should now have the container module attribute
- EXPECT_TRUE(
- (*module)->hasAttr(gpu::GPUDialect::getContainerModuleAttrName()));
+ EXPECT_TRUE((*module)->hasDiscardableAttr(
+ gpu::GPUDialect::getContainerModuleAttrName()));
}
TEST_F(OpenACCUtilsGPUTest, getOrCreateGPUModuleReturnsExisting) {
diff --git a/mlir/unittests/Dialect/OpenACC/OpenACCUtilsLoopTest.cpp b/mlir/unittests/Dialect/OpenACC/OpenACCUtilsLoopTest.cpp
index b71affa8ded11..c7337f4967d4c 100644
--- a/mlir/unittests/Dialect/OpenACC/OpenACCUtilsLoopTest.cpp
+++ b/mlir/unittests/Dialect/OpenACC/OpenACCUtilsLoopTest.cpp
@@ -274,7 +274,7 @@ TEST_F(OpenACCUtilsLoopTest, ConvertLoopToSCFForWithCollapse) {
// Ensure the collapsed loop has an attribute indicating the number
// of collapsed loops
auto collapseAttr =
- forOp->getAttrOfType<IntegerAttr>(getCollapseCountAttrName());
+ forOp->getDiscardableAttrOfType<IntegerAttr>(getCollapseCountAttrName());
ASSERT_TRUE(collapseAttr);
EXPECT_EQ(collapseAttr.getInt(), 2);
@@ -311,7 +311,7 @@ TEST_F(OpenACCUtilsLoopTest, ConvertLoopToSCFForNoCollapse) {
EXPECT_TRUE(hasNestedFor);
// No collapse happened, so no collapse_count attribute is expected
- EXPECT_FALSE(forOp->hasAttr(getCollapseCountAttrName()));
+ EXPECT_FALSE(forOp->hasDiscardableAttr(getCollapseCountAttrName()));
}
TEST_F(OpenACCUtilsLoopTest, ConvertLoopToSCFForWithCollapseAndDynamicBounds) {
diff --git a/mlir/unittests/Dialect/OpenACC/OpenACCUtilsTest.cpp b/mlir/unittests/Dialect/OpenACC/OpenACCUtilsTest.cpp
index 30c6f4312efaf..caa22fa6d9e10 100644
--- a/mlir/unittests/Dialect/OpenACC/OpenACCUtilsTest.cpp
+++ b/mlir/unittests/Dialect/OpenACC/OpenACCUtilsTest.cpp
@@ -425,7 +425,7 @@ TEST_F(OpenACCUtilsTest, getVariableNameDirect) {
// Set the acc.var_name attribute
auto varNameAttr = VarNameAttr::get(&context, "my_variable");
- allocOp.get()->setAttr(getVarNameAttrName(), varNameAttr);
+ allocOp.get()->setDiscardableAttr(getVarNameAttrName(), varNameAttr);
Value varPtr = allocOp->getResult();
@@ -442,7 +442,7 @@ TEST_F(OpenACCUtilsTest, getVariableNameThroughCast) {
// Set the acc.var_name attribute on the alloca
auto varNameAttr = VarNameAttr::get(&context, "casted_variable");
- allocOp.get()->setAttr(getVarNameAttrName(), varNameAttr);
+ allocOp.get()->setDiscardableAttr(getVarNameAttrName(), varNameAttr);
Value allocResult = allocOp->getResult();
@@ -774,8 +774,8 @@ TEST_F(OpenACCUtilsTest, isValidSymbolUseFunctionWithRoutineInfo) {
// Add routine_info attribute with a reference to a routine
SmallVector<SymbolRefAttr> routineRefs = {
SymbolRefAttr::get(&context, "acc_routine")};
- funcOp.get()->setAttr(getRoutineInfoAttrName(),
- RoutineInfoAttr::get(&context, routineRefs));
+ funcOp.get()->setDiscardableAttr(getRoutineInfoAttrName(),
+ RoutineInfoAttr::get(&context, routineRefs));
// Create a call operation that uses the function symbol
SymbolRefAttr funcSymbol = SymbolRefAttr::get(&context, funcName);
@@ -862,7 +862,7 @@ TEST_F(OpenACCUtilsTest, isValidSymbolUseWithDeclareAttr) {
func::FuncOp::create(b, loc, funcName, funcType);
// Add declare attribute
- funcOp.get()->setAttr(
+ funcOp.get()->setDiscardableAttr(
getDeclareAttrName(),
DeclareAttr::get(&context,
DataClauseAttr::get(&context, DataClause::acc_copy)));
@@ -1418,8 +1418,9 @@ static Value memrefViewFromBlockArgWithDeclare(OpBuilder &builder, Location loc,
Value c0 = arith::ConstantIndexOp::create(builder, loc, 0);
memref::ViewOp viewOp =
memref::ViewOp::create(builder, loc, viewTy, buf, c0, ValueRange{});
- viewOp->setAttr(getDeclareAttrName(),
- DeclareAttr::get(ctx, DataClauseAttr::get(ctx, clause)));
+ viewOp->setDiscardableAttr(
+ getDeclareAttrName(),
+ DeclareAttr::get(ctx, DataClauseAttr::get(ctx, clause)));
func::ReturnOp::create(builder, loc);
return viewOp.getResult();
}
diff --git a/mlir/unittests/Dialect/SPIRV/SerializationTest.cpp b/mlir/unittests/Dialect/SPIRV/SerializationTest.cpp
index b0413a8e994ba..626a0f4002641 100644
--- a/mlir/unittests/Dialect/SPIRV/SerializationTest.cpp
+++ b/mlir/unittests/Dialect/SPIRV/SerializationTest.cpp
@@ -531,7 +531,7 @@ TEST_F(SerializationTest, LongCompositeDoesNotDuplicateDeclaredCapability) {
// Pre-declare LongCompositesINTEL / SPV_INTEL_long_composites in the VCE
// triple. The serializer must not emit a second OpCapability/OpExtension
// when a long composite triggers `addLongCompositesCapability()`.
- module->getOperation()->setAttr(
+ module->getOperation()->setDiscardableAttr(
spirv::ModuleOp::getVCETripleAttrName(),
spirv::VerCapExtAttr::get(
spirv::Version::V_1_0, {spirv::Capability::LongCompositesINTEL},
diff --git a/mlir/unittests/IR/BlobManagerTest.cpp b/mlir/unittests/IR/BlobManagerTest.cpp
index d82482ddb7936..b32dc5a59bac4 100644
--- a/mlir/unittests/IR/BlobManagerTest.cpp
+++ b/mlir/unittests/IR/BlobManagerTest.cpp
@@ -49,7 +49,8 @@ TEST(DialectResourceBlobManagerTest, GetBlobMap) {
Block *block = m->getBody();
auto &op = block->getOperations().front();
- auto resourceAttr = op.getAttrOfType<DenseResourceElementsAttr>("attr");
+ auto resourceAttr =
+ op.getDiscardableAttrOfType<DenseResourceElementsAttr>("attr");
ASSERT_NE(resourceAttr, nullptr);
const auto &dialectManager =
diff --git a/mlir/unittests/IR/OpPropertiesTest.cpp b/mlir/unittests/IR/OpPropertiesTest.cpp
index bea69e9e8f107..c9e18c2067366 100644
--- a/mlir/unittests/IR/OpPropertiesTest.cpp
+++ b/mlir/unittests/IR/OpPropertiesTest.cpp
@@ -394,11 +394,15 @@ TEST(OpPropertiesTest, withoutPropertiesDiscardableAttrs) {
ParserConfig config(&context);
OwningOpRef<Operation *> op =
parseSourceString(withoutPropertiesAttrsSrc, config);
- ASSERT_EQ(llvm::range_size(op->getDiscardableAttrs()), 1u);
- EXPECT_EQ(op->getDiscardableAttrs().begin()->getName().getValue(),
+ ASSERT_EQ(llvm::range_size(op->getDiscardableAttrDictionary().getValue()),
+ 1u);
+ EXPECT_EQ(op->getDiscardableAttrDictionary()
+ .getValue()
+ .begin()
+ ->getName()
+ .getValue(),
"other_attr");
- EXPECT_EQ(op->getAttrs().size(), 2u);
EXPECT_EQ(op->getInherentAttr("inherent_attr"), std::nullopt);
EXPECT_NE(op->getDiscardableAttr("inherent_attr"), Attribute());
EXPECT_NE(op->getDiscardableAttr("other_attr"), Attribute());
diff --git a/mlir/unittests/IR/OperationSupportTest.cpp b/mlir/unittests/IR/OperationSupportTest.cpp
index 90e59808c984a..fa5fdfe16fde0 100644
--- a/mlir/unittests/IR/OperationSupportTest.cpp
+++ b/mlir/unittests/IR/OperationSupportTest.cpp
@@ -334,7 +334,7 @@ TEST(OperationEquivalenceTest, HashWorksWithFlags) {
// Check ignore discardable dictionary attributes.
SmallVector<NamedAttribute> newAttrs = {
b.getNamedAttr("foo", b.getStringAttr("f"))};
- op1->setAttrs(newAttrs);
+ op1->setDiscardableAttrs(newAttrs);
EXPECT_EQ(getHash(op1, OperationEquivalence::IgnoreDiscardableAttrs),
getHash(op2, OperationEquivalence::IgnoreDiscardableAttrs));
EXPECT_NE(getHash(op1, OperationEquivalence::None),
diff --git a/mlir/unittests/Interfaces/DataLayoutInterfacesTest.cpp b/mlir/unittests/Interfaces/DataLayoutInterfacesTest.cpp
index 3067cf103590c..f72c00070bd01 100644
--- a/mlir/unittests/Interfaces/DataLayoutInterfacesTest.cpp
+++ b/mlir/unittests/Interfaces/DataLayoutInterfacesTest.cpp
@@ -280,11 +280,12 @@ struct OpWithLayout : public Op<OpWithLayout, DataLayoutOpInterface::Trait> {
static StringRef getOperationName() { return "dltest.op_with_layout"; }
DataLayoutSpecInterface getDataLayoutSpec() {
- return getOperation()->getAttrOfType<DataLayoutSpecInterface>(kAttrName);
+ return getOperation()->getDiscardableAttrOfType<DataLayoutSpecInterface>(
+ kAttrName);
}
TargetSystemSpecInterface getTargetSystemSpec() {
- return getOperation()->getAttrOfType<TargetSystemSpecInterface>(
+ return getOperation()->getDiscardableAttrOfType<TargetSystemSpecInterface>(
kTargetSystemDescAttrName);
}
@@ -332,11 +333,12 @@ struct OpWith7BitByte
static StringRef getOperationName() { return "dltest.op_with_7bit_byte"; }
DataLayoutSpecInterface getDataLayoutSpec() {
- return getOperation()->getAttrOfType<DataLayoutSpecInterface>(kAttrName);
+ return getOperation()->getDiscardableAttrOfType<DataLayoutSpecInterface>(
+ kAttrName);
}
TargetSystemSpecInterface getTargetSystemSpec() {
- return getOperation()->getAttrOfType<TargetSystemSpecInterface>(
+ return getOperation()->getDiscardableAttrOfType<TargetSystemSpecInterface>(
kTargetSystemDescAttrName);
}
@@ -732,7 +734,7 @@ TEST(DataLayout, CacheInvalidation) {
EXPECT_EQ(layout.getTypeSize(Float16Type::get(&ctx)), 6u);
// Replace the data layout spec with a new, empty spec.
- op->setAttr(kAttrName, CustomDataLayoutSpec::get(&ctx, {}));
+ op->setDiscardableAttr(kAttrName, CustomDataLayoutSpec::get(&ctx, {}));
// Data layout is no longer valid and should trigger assertion when queried.
#ifndef NDEBUG
diff --git a/mlir/unittests/Pass/PassManagerTest.cpp b/mlir/unittests/Pass/PassManagerTest.cpp
index 3f5db8ebcbb6d..c0b7dcbb7eaed 100644
--- a/mlir/unittests/Pass/PassManagerTest.cpp
+++ b/mlir/unittests/Pass/PassManagerTest.cpp
@@ -51,8 +51,8 @@ struct AnnotateFunctionPass
auto &ga = getAnalysis<GenericAnalysis>();
auto &sa = getAnalysis<OpSpecificAnalysis>();
- op->setAttr("isFunc", builder.getBoolAttr(ga.isFunc));
- op->setAttr("isSecret", builder.getBoolAttr(sa.isSecret));
+ op->setDiscardableAttr("isFunc", builder.getBoolAttr(ga.isFunc));
+ op->setDiscardableAttr("isSecret", builder.getBoolAttr(sa.isSecret));
}
};
@@ -96,11 +96,11 @@ struct AddAttrFunctionPass
void runOnOperation() override {
func::FuncOp op = getOperation();
Builder builder(op->getParentOfType<ModuleOp>());
- if (op->hasAttr("didProcess"))
- op->setAttr("didProcessAgain", builder.getUnitAttr());
+ if (op->hasDiscardableAttr("didProcess"))
+ op->setDiscardableAttr("didProcessAgain", builder.getUnitAttr());
// We always want to set this one.
- op->setAttr("didProcess", builder.getUnitAttr());
+ op->setDiscardableAttr("didProcess", builder.getUnitAttr());
}
};
@@ -114,7 +114,7 @@ struct AddSecondAttrFunctionPass
void runOnOperation() override {
func::FuncOp op = getOperation();
Builder builder(op->getParentOfType<ModuleOp>());
- op->setAttr("didProcess2", builder.getUnitAttr());
+ op->setDiscardableAttr("didProcess2", builder.getUnitAttr());
}
};
diff --git a/mlir/unittests/TableGen/OpBuildGen.cpp b/mlir/unittests/TableGen/OpBuildGen.cpp
index 09430336de994..5560871f47128 100644
--- a/mlir/unittests/TableGen/OpBuildGen.cpp
+++ b/mlir/unittests/TableGen/OpBuildGen.cpp
@@ -33,6 +33,13 @@ static MLIRContext &getContext() {
/// Test fixture for providing basic utilities for testing.
class OpBuildGenTest : public ::testing::Test {
protected:
+ static NamedAttrList collectAttrs(Operation *op) {
+ NamedAttrList attrs(op->getDiscardableAttrDictionary());
+ if (op->getPropertiesStorageSize())
+ op->getName().populateInherentAttrs(op, attrs);
+ return NamedAttrList(attrs.getDictionary(op->getContext()));
+ }
+
OpBuildGenTest()
: ctx(getContext()), builder(&ctx), loc(builder.getUnknownLoc()),
i32Ty(builder.getI32Type()), f32Ty(builder.getF32Type()),
@@ -60,10 +67,10 @@ class OpBuildGenTest : public ::testing::Test {
for (unsigned idx : llvm::seq(0U, op->getNumOperands()))
EXPECT_EQ(op->getOperand(idx), operands[idx]);
- EXPECT_EQ(op->getAttrs().size(), attrs.size());
+ NamedAttrList actualAttrs = collectAttrs(op);
+ EXPECT_EQ(actualAttrs.getAttrs().size(), attrs.size());
for (unsigned idx : llvm::seq<unsigned>(0U, attrs.size()))
- EXPECT_EQ(op->getAttr(attrs[idx].getName().strref()),
- attrs[idx].getValue());
+ EXPECT_EQ(actualAttrs.get(attrs[idx].getName()), attrs[idx].getValue());
EXPECT_TRUE(mlir::succeeded(concreteOp.verify()));
concreteOp.erase();
@@ -85,11 +92,12 @@ class OpBuildGenTest : public ::testing::Test {
for (unsigned idx : llvm::seq(0U, op->getNumOperands()))
EXPECT_EQ(op->getOperand(idx), operands[idx]);
- EXPECT_EQ(op->getAttrs().size(), attrs.size());
- if (op->getAttrs().size() != attrs.size()) {
+ NamedAttrList actualAttrs = collectAttrs(op);
+ EXPECT_EQ(actualAttrs.getAttrs().size(), attrs.size());
+ if (actualAttrs.getAttrs().size() != attrs.size()) {
// Simple export where there is mismatch count.
llvm::errs() << "Op attrs:\n";
- for (auto it : op->getAttrs())
+ for (auto it : actualAttrs)
llvm::errs() << "\t" << it.getName() << " = " << it.getValue() << "\n";
llvm::errs() << "Expected attrs:\n";
@@ -97,8 +105,7 @@ class OpBuildGenTest : public ::testing::Test {
llvm::errs() << "\t" << it.getName() << " = " << it.getValue() << "\n";
} else {
for (unsigned idx : llvm::seq<unsigned>(0U, attrs.size()))
- EXPECT_EQ(op->getAttr(attrs[idx].getName().strref()),
- attrs[idx].getValue());
+ EXPECT_EQ(actualAttrs.get(attrs[idx].getName()), attrs[idx].getValue());
}
EXPECT_TRUE(mlir::succeeded(concreteOp.verify()));
diff --git a/mlir/unittests/Target/LLVM/SerializeToLLVMBitcode.cpp b/mlir/unittests/Target/LLVM/SerializeToLLVMBitcode.cpp
index 5271923d923e2..c2ca29932014a 100644
--- a/mlir/unittests/Target/LLVM/SerializeToLLVMBitcode.cpp
+++ b/mlir/unittests/Target/LLVM/SerializeToLLVMBitcode.cpp
@@ -105,7 +105,8 @@ std::optional<mlir::gpu::SerializedObject>
TargetAttrImpl::serializeToObject(Attribute attribute, Operation *module,
const gpu::TargetOptions &options) const {
// Set a dummy attr to be retrieved by `createObject`.
- module->setAttr("serialize_attr", UnitAttr::get(module->getContext()));
+ module->setDiscardableAttr("serialize_attr",
+ UnitAttr::get(module->getContext()));
std::string targetTriple = llvm::sys::getProcessTriple();
LLVM::ModuleToObject serializer(
*module, targetTriple, "", "", 3, options.getInitialLlvmIRCallback(),
@@ -124,7 +125,7 @@ TargetAttrImpl::createObject(Attribute attribute, Operation *module,
StringAttr::get(
module->getContext(),
StringRef(object.getObject().data(), object.getObject().size())),
- module->getAttrDictionary(), /*kernels=*/nullptr);
+ module->getDiscardableAttrDictionary(), /*kernels=*/nullptr);
}
// This test checks the correct functioning of `TargetAttrInterface` as an API.
More information about the Mlir-commits
mailing list