Skip to content

Commit 875fd9d

Browse files
committed
[flang] Introduce FortranVariableOpInterface for ops creating variable
HLFIR will rely on certain operations to create SSA memory values that correspond to a Fortran variable. They will hold bounds and type parameters information as well as metadata (like Fortran attributes). This patch adds an interface that for such operations so that Fortran variable can be stored, manipulated, and queried regardless of what created them. This is so far intended for fir.declare, hlfir.designate and hlfir.associate operations. It is added to FIR and not HLFIR because fir.declare needs it and it does not itself needs any HLFIR concepts. Unit tests for the interface methods will be added alongside fir.declare in the next patch. Differential Revision: https://reviews.llvm.org/D136151
1 parent fce33e1 commit 875fd9d

File tree

5 files changed

+169
-0
lines changed

5 files changed

+169
-0
lines changed

flang/include/flang/Optimizer/Dialect/CMakeLists.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@ mlir_tablegen(FIROps.h.inc -gen-op-decls)
1212
mlir_tablegen(FIROps.cpp.inc -gen-op-defs)
1313
mlir_tablegen(FIROpsTypes.h.inc --gen-typedef-decls)
1414
mlir_tablegen(FIROpsTypes.cpp.inc --gen-typedef-defs)
15+
add_mlir_interface(FortranVariableInterface)
1516
add_public_tablegen_target(FIROpsIncGen)
1617

1718
set(LLVM_TARGET_DEFINITIONS CanonicalizationPatterns.td)
Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
//===- FortranVariableInterface.h -------------------------------*- 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 contains a set of interfaces for operations defining Fortran
10+
// variables.
11+
//
12+
//===----------------------------------------------------------------------===//
13+
14+
#ifndef FORTRAN_OPTIMIZER_DIALECT_FORTRANVARIABLEINTERFACE_H
15+
#define FORTRAN_OPTIMIZER_DIALECT_FORTRANVARIABLEINTERFACE_H
16+
17+
#include "flang/Optimizer/Dialect/FIRAttr.h"
18+
#include "flang/Optimizer/Dialect/FIRType.h"
19+
#include "mlir/IR/BuiltinTypes.h"
20+
#include "mlir/IR/OpDefinition.h"
21+
22+
namespace fir {
23+
#include "flang/Optimizer/Dialect/FortranVariableInterface.h.inc"
24+
} // namespace fir
25+
26+
#endif // FORTRAN_OPTIMIZER_DIALECT_FORTRANVARIABLEINTERFACE_H
Lines changed: 124 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,124 @@
1+
//===- FortranVariableInterface.td -------------------------*- 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 defines an interface for operations defining Fortran variables.
10+
//
11+
//===----------------------------------------------------------------------===//
12+
13+
#ifndef FORTRANVARIABLEINTERFACE
14+
#define FORTRANVARIABLEINTERFACE
15+
16+
include "mlir/IR/OpBase.td"
17+
18+
19+
def FortranVariableOpInterface : OpInterface<"FortranVariableOpInterface"> {
20+
let description = [{
21+
Interface for operations that create Fortran like variables in order to
22+
query about all their Fortran properties.
23+
}];
24+
25+
let methods = [
26+
InterfaceMethod<
27+
/*desc=*/"Get the address produced by the definition",
28+
/*retTy=*/"mlir::Value",
29+
/*methodName=*/"getBase",
30+
/*args=*/(ins),
31+
/*methodBody=*/[{}],
32+
/*defaultImplementation=*/[{
33+
ConcreteOp op = mlir::cast<ConcreteOp>(this->getOperation());
34+
return op.getResult();
35+
}]
36+
>,
37+
InterfaceMethod<
38+
/*desc=*/"Get Fortran attributes",
39+
/*retTy=*/"llvm::Optional<fir::FortranVariableFlagsEnum>",
40+
/*methodName=*/"getFortranAttrs",
41+
/*args=*/(ins),
42+
/*methodBody=*/[{}],
43+
/*defaultImplementation=*/[{
44+
ConcreteOp op = mlir::cast<ConcreteOp>(this->getOperation());
45+
return op.getFortran_attrs();
46+
}]
47+
>,
48+
InterfaceMethod<
49+
/*desc=*/"Get the shape of the variable",
50+
/*retTy=*/"llvm::Optional<mlir::Value>",
51+
/*methodName=*/"getShape",
52+
/*args=*/(ins),
53+
/*methodBody=*/[{}],
54+
/*defaultImplementation=*/[{
55+
ConcreteOp op = mlir::cast<ConcreteOp>(this->getOperation());
56+
return op.getShape();
57+
}]
58+
>,
59+
InterfaceMethod<
60+
/*desc=*/"Get explicit type parameters of the variable",
61+
/*retTy=*/"mlir::OperandRange",
62+
/*methodName=*/"getExplicitTypeParams",
63+
/*args=*/(ins),
64+
/*methodBody=*/[{}],
65+
/*defaultImplementation=*/[{
66+
ConcreteOp op = mlir::cast<ConcreteOp>(this->getOperation());
67+
return op.getTypeparams();
68+
}]
69+
>,
70+
];
71+
72+
let extraClassDeclaration = [{
73+
74+
/// Get the sequence type or scalar value type corresponding to this
75+
/// variable.
76+
mlir::Type getElementOrSequenceType() {
77+
return fir::unwrapPassByRefType(getBase().getType());
78+
}
79+
80+
/// Get the scalar value type corresponding to this variable.
81+
mlir::Type getElementType() {
82+
return fir::unwrapSequenceType(getElementOrSequenceType());
83+
}
84+
85+
/// Is the variable an array ?
86+
bool isArray() {
87+
return getElementOrSequenceType().isa<fir::SequenceType>();
88+
}
89+
90+
/// Is this variable a Fortran pointer ?
91+
bool isPointer() {
92+
auto attrs = getFortranAttrs();
93+
return attrs && bitEnumContainsAny(*attrs,
94+
fir::FortranVariableFlagsEnum::pointer);
95+
}
96+
97+
/// Is this variable a Fortran allocatable ?
98+
bool isAllocatable() {
99+
auto attrs = getFortranAttrs();
100+
return attrs && bitEnumContainsAny(*attrs,
101+
fir::FortranVariableFlagsEnum::allocatable);
102+
}
103+
104+
/// Is this a Fortran character variable ?
105+
bool isCharacter() {
106+
return getElementType().isa<fir::CharacterType>();
107+
}
108+
109+
/// Is this a Fortran character variable with an explicit length ?
110+
bool hasExplicitCharLen() {
111+
return isCharacter() && !getExplicitTypeParams().empty();
112+
}
113+
114+
/// Return the length of explicit length character variable.
115+
mlir::Value getExplicitCharLen() {
116+
assert(hasExplicitCharLen() && "must be an explicit length character");
117+
return getExplicitTypeParams()[0];
118+
}
119+
120+
}];
121+
122+
}
123+
124+
#endif // FORTRANVARIABLEINTERFACE

flang/lib/Optimizer/Dialect/CMakeLists.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@ add_flang_library(FIRDialect
33
FIRDialect.cpp
44
FIROps.cpp
55
FIRType.cpp
6+
FortranVariableInterface.cpp
67
Inliner.cpp
78

89
DEPENDS
Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
//===-- FortranVariableInterface.cpp.cpp ----------------------------------===//
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+
// Coding style: https://mlir.llvm.org/getting_started/DeveloperGuide/
10+
//
11+
//===----------------------------------------------------------------------===//
12+
13+
#include "flang/Optimizer/Dialect/FortranVariableInterface.h"
14+
15+
namespace fir {
16+
#include "flang/Optimizer/Dialect/FortranVariableInterface.cpp.inc"
17+
}

0 commit comments

Comments
 (0)