Skip to content

Commit 52761cb

Browse files
committed
[mlir][irdl] Add verification of IRDL ops
This patch adds verification on registered IRDL operations, types, and attributes. This is done through an interface implemented by operations from the `irdl` dialect, which translate the operations into `Constraint`. This interface is then use in the `registerDialect` function to generate verifiers for the entire operation/type/attribute. Depends on D145733 Reviewed By: Mogball Differential Revision: https://reviews.llvm.org/D145734
1 parent 1398460 commit 52761cb

File tree

10 files changed

+409
-5
lines changed

10 files changed

+409
-5
lines changed

mlir/include/mlir/Dialect/IRDL/IR/CMakeLists.txt

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,12 @@
11
add_mlir_dialect(IRDL irdl)
22

3+
# Add IRDL interfaces
4+
set(LLVM_TARGET_DEFINITIONS IRDLInterfaces.td)
5+
mlir_tablegen(IRDLInterfaces.h.inc -gen-op-interface-decls)
6+
mlir_tablegen(IRDLInterfaces.cpp.inc -gen-op-interface-defs)
7+
add_public_tablegen_target(MLIRIRDLInterfacesIncGen)
8+
add_dependencies(mlir-generic-headers MLIRIRDLInterfacesIncGen)
9+
310
# Add IRDL operations
411
set(LLVM_TARGET_DEFINITIONS IRDLOps.td)
512
mlir_tablegen(IRDLOps.h.inc -gen-op-decls)

mlir/include/mlir/Dialect/IRDL/IR/IRDL.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@
1313
#ifndef MLIR_DIALECT_IRDL_IR_IRDL_H_
1414
#define MLIR_DIALECT_IRDL_IR_IRDL_H_
1515

16+
#include "mlir/Dialect/IRDL/IR/IRDLInterfaces.h"
1617
#include "mlir/Dialect/IRDL/IR/IRDLTraits.h"
1718
#include "mlir/IR/SymbolTable.h"
1819
#include "mlir/Interfaces/InferTypeOpInterface.h"
Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,38 @@
1+
//===- IRDLInterfaces.h - IRDL interfaces definition ------------*- C++ -*-===//
2+
//
3+
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4+
// See https://llvm.org/LICENSE.txt for license information.
5+
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6+
//
7+
//===----------------------------------------------------------------------===//
8+
//
9+
// This file declares the interfaces used by the IRDL dialect.
10+
//
11+
//===----------------------------------------------------------------------===//
12+
13+
#ifndef MLIR_DIALECT_IRDL_IR_IRDLINTERFACES_H_
14+
#define MLIR_DIALECT_IRDL_IR_IRDLINTERFACES_H_
15+
16+
#include "mlir/Dialect/IRDL/IRDLVerifiers.h"
17+
#include "mlir/IR/BuiltinAttributes.h"
18+
#include "mlir/IR/Diagnostics.h"
19+
#include "mlir/IR/ExtensibleDialect.h"
20+
#include "mlir/IR/OpImplementation.h"
21+
#include "mlir/IR/Types.h"
22+
#include "mlir/Support/LogicalResult.h"
23+
#include <optional>
24+
25+
namespace mlir {
26+
namespace irdl {
27+
class TypeOp;
28+
class AttributeOp;
29+
} // namespace irdl
30+
} // namespace mlir
31+
32+
//===----------------------------------------------------------------------===//
33+
// IRDL Dialect Interfaces
34+
//===----------------------------------------------------------------------===//
35+
36+
#include "mlir/Dialect/IRDL/IR/IRDLInterfaces.h.inc"
37+
38+
#endif // MLIR_DIALECT_IRDL_IR_IRDLINTERFACES_H_
Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
//===- IRDLInterfaces.td - IRDL Attributes -----------------*- tablegen -*-===//
2+
//
3+
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4+
// See https://llvm.org/LICENSE.txt for license information.
5+
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6+
//
7+
//===----------------------------------------------------------------------===//
8+
//
9+
// This file declares the interfaces used by IRDL.
10+
//
11+
//===----------------------------------------------------------------------===//
12+
13+
#ifndef MLIR_DIALECT_IRDL_IR_IRDLINTERFACES
14+
#define MLIR_DIALECT_IRDL_IR_IRDLINTERFACES
15+
16+
include "mlir/IR/OpBase.td"
17+
18+
def VerifyConstraintInterface : OpInterface<"VerifyConstraintInterface"> {
19+
let cppNamespace = "::mlir::irdl";
20+
21+
let description = [{
22+
Interface to get an IRDL constraint verifier from an operation.
23+
}];
24+
25+
let methods = [
26+
InterfaceMethod<
27+
[{
28+
Get an instance of a constraint verifier for the associated operation."
29+
Returns `nullptr` upon failure.
30+
}],
31+
"std::unique_ptr<::mlir::irdl::Constraint>",
32+
"getVerifier",
33+
(ins "::mlir::SmallVector<Value> const&":$valueRes,
34+
"::mlir::DenseMap<::mlir::irdl::TypeOp, std::unique_ptr<::mlir::DynamicTypeDefinition>> &":$types,
35+
"::mlir::DenseMap<::mlir::irdl::AttributeOp, std::unique_ptr<::mlir::DynamicAttrDefinition>> &":$attrs)
36+
>
37+
];
38+
}
39+
40+
#endif // MLIR_DIALECT_IRDL_IR_IRDLINTERFACES

mlir/include/mlir/Dialect/IRDL/IR/IRDLOps.td

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@
1515

1616
include "IRDL.td"
1717
include "IRDLTypes.td"
18+
include "IRDLInterfaces.td"
1819
include "mlir/Interfaces/SideEffectInterfaces.td"
1920
include "mlir/Interfaces/InferTypeOpInterface.td"
2021
include "mlir/IR/SymbolInterfaces.td"
@@ -264,7 +265,8 @@ def IRDL_ResultsOp : IRDL_Op<"results", [HasParent<"OperationOp">]> {
264265
//===----------------------------------------------------------------------===//
265266

266267
class IRDL_ConstraintOp<string mnemonic, list<Trait> traits = []>
267-
: IRDL_Op<mnemonic, traits> {
268+
: IRDL_Op<mnemonic, [VerifyConstraintInterface,
269+
DeclareOpInterfaceMethods<VerifyConstraintInterface>] # traits> {
268270
}
269271

270272
def IRDL_Is : IRDL_ConstraintOp<"is",

mlir/lib/Dialect/IRDL/CMakeLists.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
add_mlir_dialect_library(MLIRIRDL
22
IR/IRDL.cpp
3+
IR/IRDLOps.cpp
34
IRDLLoading.cpp
45
IRDLVerifiers.cpp
56

mlir/lib/Dialect/IRDL/IR/IRDL.cpp

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -71,6 +71,8 @@ LogicalResult DialectOp::verify() {
7171
return success();
7272
}
7373

74+
#include "mlir/Dialect/IRDL/IR/IRDLInterfaces.cpp.inc"
75+
7476
#define GET_TYPEDEF_CLASSES
7577
#include "mlir/Dialect/IRDL/IR/IRDLTypesGen.cpp.inc"
7678

mlir/lib/Dialect/IRDL/IR/IRDLOps.cpp

Lines changed: 61 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,61 @@
1+
//===- IRDLOps.cpp - IRDL dialect -------------------------------*- C++ -*-===//
2+
//
3+
// This file is licensed under the Apache License v2.0 with LLVM Exceptions.
4+
// See https://llvm.org/LICENSE.txt for license information.
5+
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6+
//
7+
//===----------------------------------------------------------------------===//
8+
9+
#include "mlir/Dialect/IRDL/IR/IRDL.h"
10+
11+
using namespace mlir;
12+
using namespace mlir::irdl;
13+
14+
std::unique_ptr<Constraint> Is::getVerifier(
15+
SmallVector<Value> const &valueToConstr,
16+
DenseMap<TypeOp, std::unique_ptr<DynamicTypeDefinition>> &types,
17+
DenseMap<AttributeOp, std::unique_ptr<DynamicAttrDefinition>> &attrs) {
18+
return std::make_unique<IsConstraint>(getExpectedAttr());
19+
}
20+
21+
std::unique_ptr<Constraint> Parametric::getVerifier(
22+
SmallVector<Value> const &valueToConstr,
23+
DenseMap<TypeOp, std::unique_ptr<DynamicTypeDefinition>> &types,
24+
DenseMap<AttributeOp, std::unique_ptr<DynamicAttrDefinition>> &attrs) {
25+
SmallVector<unsigned> constraints;
26+
for (Value arg : getArgs()) {
27+
for (auto [i, value] : enumerate(valueToConstr)) {
28+
if (value == arg) {
29+
constraints.push_back(i);
30+
break;
31+
}
32+
}
33+
}
34+
35+
// Symbol reference case for the base
36+
SymbolRefAttr symRef = getBaseType();
37+
Operation *defOp =
38+
SymbolTable::lookupNearestSymbolFrom(getOperation(), symRef);
39+
if (!defOp) {
40+
emitError() << symRef << " does not refer to any existing symbol";
41+
return nullptr;
42+
}
43+
44+
if (auto typeOp = dyn_cast<TypeOp>(defOp))
45+
return std::make_unique<DynParametricTypeConstraint>(types[typeOp].get(),
46+
constraints);
47+
48+
if (auto attrOp = dyn_cast<AttributeOp>(defOp))
49+
return std::make_unique<DynParametricAttrConstraint>(attrs[attrOp].get(),
50+
constraints);
51+
52+
llvm_unreachable("verifier should ensure that the referenced operation is "
53+
"either a type or an attribute definition");
54+
}
55+
56+
std::unique_ptr<Constraint> Any::getVerifier(
57+
SmallVector<Value> const &valueToConstr,
58+
DenseMap<TypeOp, std::unique_ptr<DynamicTypeDefinition>> &types,
59+
DenseMap<AttributeOp, std::unique_ptr<DynamicAttrDefinition>> &attrs) {
60+
return std::make_unique<AnyAttributeConstraint>();
61+
}

0 commit comments

Comments
 (0)