23 #define GEN_PASS_DEF_CONVERTOPENMPTOLLVMPASS
24 #include "mlir/Conversion/Passes.h.inc"
34 template <
typename OpType>
39 matchAndRewrite(OpType curOp,
typename OpType::Adaptor adaptor,
41 auto newOp = rewriter.
create<OpType>(
42 curOp.getLoc(),
TypeRange(), adaptor.getOperands(), curOp->getAttrs());
44 newOp.getRegion().end());
46 *this->getTypeConverter())))
55 struct RegionLessOpWithVarOperandsConversion
59 matchAndRewrite(T curOp,
typename T::Adaptor adaptor,
63 if (failed(converter->
convertTypes(curOp->getResultTypes(), resTypes)))
66 assert(curOp.getNumVariableOperands() ==
67 curOp.getOperation()->getNumOperands() &&
68 "unexpected non-variable operands");
69 for (
unsigned idx = 0; idx < curOp.getNumVariableOperands(); ++idx) {
70 Value originalVariableOperand = curOp.getVariableOperand(idx);
71 if (!originalVariableOperand)
73 if (isa<MemRefType>(originalVariableOperand.
getType())) {
76 "memref is not supported yet");
78 convertedOperands.emplace_back(adaptor.getOperands()[idx]);
91 matchAndRewrite(T curOp,
typename T::Adaptor adaptor,
95 if (failed(converter->
convertTypes(curOp->getResultTypes(), resTypes)))
98 assert(curOp.getNumVariableOperands() ==
99 curOp.getOperation()->getNumOperands() &&
100 "unexpected non-variable operands");
101 for (
unsigned idx = 0; idx < curOp.getNumVariableOperands(); ++idx) {
102 Value originalVariableOperand = curOp.getVariableOperand(idx);
103 if (!originalVariableOperand)
105 if (isa<MemRefType>(originalVariableOperand.
getType())) {
108 "memref is not supported yet");
110 convertedOperands.emplace_back(adaptor.getOperands()[idx]);
112 auto newOp = rewriter.
create<T>(curOp.getLoc(), resTypes, convertedOperands,
115 newOp.getRegion().end());
117 *this->getTypeConverter())))
125 template <
typename T>
129 matchAndRewrite(T curOp,
typename T::Adaptor adaptor,
133 if (failed(converter->
convertTypes(curOp->getResultTypes(), resTypes)))
142 struct AtomicReadOpConversion
146 matchAndRewrite(omp::AtomicReadOp curOp, OpAdaptor adaptor,
149 Type curElementType = curOp.getElementType();
150 auto newOp = rewriter.
create<omp::AtomicReadOp>(
151 curOp.getLoc(),
TypeRange(), adaptor.getOperands(), curOp->getAttrs());
153 newOp.setElementTypeAttr(typeAttr);
162 matchAndRewrite(omp::MapInfoOp curOp, OpAdaptor adaptor,
167 if (failed(converter->
convertTypes(curOp->getResultTypes(), resTypes)))
174 if (
auto typeAttr = dyn_cast<TypeAttr>(attr.getValue())) {
176 newAttrs.emplace_back(attr.getName(),
TypeAttr::get(newAttr));
178 newAttrs.push_back(attr);
183 curOp, resTypes, adaptor.getOperands(), newAttrs);
188 template <
typename OpType>
192 void forwardOpAttrs(OpType curOp, OpType newOp)
const {}
195 matchAndRewrite(OpType curOp,
typename OpType::Adaptor adaptor,
197 auto newOp = rewriter.
create<OpType>(
198 curOp.getLoc(),
TypeRange(), curOp.getSymNameAttr(),
200 curOp.getTypeAttr().getValue())));
201 forwardOpAttrs(curOp, newOp);
203 for (
unsigned idx = 0; idx < curOp.getNumRegions(); idx++) {
205 newOp.getRegion(idx).end());
207 *this->getTypeConverter())))
217 void MultiRegionOpConversion<omp::PrivateClauseOp>::forwardOpAttrs(
218 omp::PrivateClauseOp curOp, omp::PrivateClauseOp newOp)
const {
219 newOp.setDataSharingType(curOp.getDataSharingType());
226 mlir::omp::AtomicReadOp, mlir::omp::AtomicWriteOp, mlir::omp::FlushOp,
227 mlir::omp::ThreadprivateOp, mlir::omp::YieldOp,
228 mlir::omp::TargetEnterDataOp, mlir::omp::TargetExitDataOp,
229 mlir::omp::TargetUpdateOp, mlir::omp::MapBoundsOp, mlir::omp::MapInfoOp>(
235 mlir::omp::AtomicUpdateOp, mlir::omp::CriticalOp, mlir::omp::TargetOp,
236 mlir::omp::TargetDataOp, mlir::omp::LoopNestOp,
237 mlir::omp::OrderedRegionOp, mlir::omp::ParallelOp, mlir::omp::WsloopOp,
238 mlir::omp::SimdOp, mlir::omp::MasterOp, mlir::omp::SectionOp,
239 mlir::omp::SectionsOp, mlir::omp::SingleOp, mlir::omp::TaskgroupOp,
240 mlir::omp::TaskOp, mlir::omp::DeclareReductionOp,
241 mlir::omp::PrivateClauseOp>([&](
Operation *op) {
244 return typeConverter.isLegal(®ion);
257 [&](omp::MapBoundsType type) ->
Type {
return type; });
260 AtomicReadOpConversion, MapInfoOpConversion,
261 MultiRegionOpConversion<omp::DeclareReductionOp>,
262 MultiRegionOpConversion<omp::PrivateClauseOp>,
263 RegionOpConversion<omp::CriticalOp>, RegionOpConversion<omp::LoopNestOp>,
264 RegionOpConversion<omp::MasterOp>,
265 RegionOpConversion<omp::OrderedRegionOp>,
266 RegionOpConversion<omp::ParallelOp>, RegionOpConversion<omp::WsloopOp>,
267 RegionOpConversion<omp::SectionsOp>, RegionOpConversion<omp::SectionOp>,
268 RegionOpConversion<omp::SimdOp>, RegionOpConversion<omp::SingleOp>,
269 RegionOpConversion<omp::TaskgroupOp>, RegionOpConversion<omp::TaskOp>,
270 RegionOpConversion<omp::TargetDataOp>, RegionOpConversion<omp::TargetOp>,
271 RegionLessOpWithVarOperandsConversion<omp::AtomicWriteOp>,
272 RegionOpWithVarOperandsConversion<omp::AtomicUpdateOp>,
273 RegionLessOpWithVarOperandsConversion<omp::FlushOp>,
274 RegionLessOpWithVarOperandsConversion<omp::ThreadprivateOp>,
275 RegionLessOpConversion<omp::YieldOp>,
276 RegionLessOpConversion<omp::TargetEnterDataOp>,
277 RegionLessOpConversion<omp::TargetExitDataOp>,
278 RegionLessOpConversion<omp::TargetUpdateOp>,
279 RegionLessOpWithVarOperandsConversion<omp::MapBoundsOp>>(converter);
283 struct ConvertOpenMPToLLVMPass
284 :
public impl::ConvertOpenMPToLLVMPassBase<ConvertOpenMPToLLVMPass> {
287 void runOnOperation()
override;
291 void ConvertOpenMPToLLVMPass::runOnOperation() {
292 auto module = getOperation();
304 target.addLegalOp<omp::TerminatorOp, omp::TaskyieldOp, omp::FlushOp,
305 omp::BarrierOp, omp::TaskwaitOp>();
static MLIRContext * getContext(OpFoldResult val)
This class implements a pattern rewriter for use with ConversionPatterns.
FailureOr< Block * > convertRegionTypes(Region *region, const TypeConverter &converter, TypeConverter::SignatureConversion *entryConversion=nullptr)
Apply a signature conversion to each block in the given region.
void eraseOp(Operation *op) override
PatternRewriter hook for erasing a dead operation.
This class describes a specific conversion target.
void addDynamicallyLegalOp(OperationName op, const DynamicLegalityCallbackFn &callback)
Register the given operation as dynamically legal and set the dynamic legalization callback to the on...
Utility class for operation conversions targeting the LLVM dialect that match exactly one source oper...
const LLVMTypeConverter * getTypeConverter() const
Derived class that automatically populates legalization information for different LLVM ops.
Conversion from types to the LLVM IR dialect.
NamedAttribute represents a combination of a name and an Attribute value.
Operation * create(const OperationState &state)
Creates an operation given the fields represented as an OperationState.
Operation is the basic unit of execution within MLIR.
MutableArrayRef< Region > getRegions()
Returns the regions held by this operation.
operand_type_range getOperandTypes()
result_type_range getResultTypes()
This class contains a list of basic blocks and a link to the parent operation it is attached to.
RewritePatternSet & add(ConstructorArg &&arg, ConstructorArgs &&...args)
Add an instance of each of the pattern types 'Ts' to the pattern list with the given arguments.
std::enable_if_t<!std::is_convertible< CallbackT, Twine >::value, LogicalResult > notifyMatchFailure(Location loc, CallbackT &&reasonCallback)
Used to notify the listener that the IR failed to be rewritten because of a match failure,...
void inlineRegionBefore(Region ®ion, Region &parent, Region::iterator before)
Move the blocks that belong to "region" before the given position in another region "parent".
OpTy replaceOpWithNewOp(Operation *op, Args &&...args)
Replace the results of the given (original) op with a new op that is created without verification (re...
void addConversion(FnT &&callback)
Register a conversion function.
bool isLegal(Type type) const
Return true if the given type is legal for this type converter, i.e.
LogicalResult convertType(Type t, SmallVectorImpl< Type > &results) const
Convert the given type.
LogicalResult convertTypes(TypeRange types, SmallVectorImpl< Type > &results) const
Convert the given set of types, filling 'results' as necessary.
This class provides an abstraction over the various different ranges of value types.
Instances of the Type class are uniqued, have an immutable identifier and an optional mutable compone...
This class represents an instance of an SSA value in the MLIR system, representing a computable value...
Type getType() const
Return the type of this value.
void populateArithToLLVMConversionPatterns(LLVMTypeConverter &converter, RewritePatternSet &patterns)
void populateControlFlowToLLVMConversionPatterns(LLVMTypeConverter &converter, RewritePatternSet &patterns)
Collect the patterns to convert from the ControlFlow dialect to LLVM.
Include the generated interface declarations.
void populateOpenMPToLLVMConversionPatterns(LLVMTypeConverter &converter, RewritePatternSet &patterns)
Populate the given list with patterns that convert from OpenMP to LLVM.
void populateFuncToLLVMConversionPatterns(LLVMTypeConverter &converter, RewritePatternSet &patterns, const SymbolTable *symbolTable=nullptr)
Collect the patterns to convert from the Func dialect to LLVM.
void populateFinalizeMemRefToLLVMConversionPatterns(LLVMTypeConverter &converter, RewritePatternSet &patterns)
Collect a set of patterns to convert memory-related operations from the MemRef dialect to the LLVM di...
void configureOpenMPToLLVMConversionLegality(ConversionTarget &target, LLVMTypeConverter &typeConverter)
Configure dynamic conversion legality of regionless operations from OpenMP to LLVM.
auto get(MLIRContext *context, Ts &&...params)
Helper method that injects context only if needed, this helps unify some of the attribute constructio...
LogicalResult applyPartialConversion(ArrayRef< Operation * > ops, const ConversionTarget &target, const FrozenRewritePatternSet &patterns, ConversionConfig config=ConversionConfig())
Below we define several entry points for operation conversion.