[Mlir-commits] [mlir] [Flang][OpenMP] Fix update operation not found issue (PR #92165)
Kiran Chandramohan
llvmlistbot at llvm.org
Tue May 14 12:09:28 PDT 2024
https://github.com/kiranchandramohan created https://github.com/llvm/llvm-project/pull/92165
If there is only one non-terminator operation in the update region then the update operation can be found and we can try to generate an atomicrmw instruction. Otherwise use the cmpxchg loop.
Fixes #91929
>From 8b036c930e4a98244a812a59e67a7b74882980b6 Mon Sep 17 00:00:00 2001
From: Kiran Chandramohan <kiran.chandramohan at arm.com>
Date: Tue, 14 May 2024 18:57:45 +0000
Subject: [PATCH] [Flang][OpenMP] Fix update operation not found issue
If there is only one non-terminator operation in the update region
then the update operation can be found and we can try to generate
an atomicrmw instruction. Otherwise use the cmpxchg loop.
Fixes #91929
---
.../OpenMP/OpenMPToLLVMIRTranslation.cpp | 44 ++++++++++---------
1 file changed, 23 insertions(+), 21 deletions(-)
diff --git a/mlir/lib/Target/LLVMIR/Dialect/OpenMP/OpenMPToLLVMIRTranslation.cpp b/mlir/lib/Target/LLVMIR/Dialect/OpenMP/OpenMPToLLVMIRTranslation.cpp
index a7294632d6667..ed9fb44cf08ed 100644
--- a/mlir/lib/Target/LLVMIR/Dialect/OpenMP/OpenMPToLLVMIRTranslation.cpp
+++ b/mlir/lib/Target/LLVMIR/Dialect/OpenMP/OpenMPToLLVMIRTranslation.cpp
@@ -1623,31 +1623,33 @@ convertOmpAtomicUpdate(omp::AtomicUpdateOp &opInst,
// Convert values and types.
auto &innerOpList = opInst.getRegion().front().getOperations();
- bool isRegionArgUsed{false}, isXBinopExpr{false};
+ bool isXBinopExpr{false};
llvm::AtomicRMWInst::BinOp binop;
mlir::Value mlirExpr;
- // Find the binary update operation that uses the region argument
- // and get the expression to update
- for (Operation &innerOp : innerOpList) {
- if (innerOp.getNumOperands() == 2) {
- binop = convertBinOpToAtomic(innerOp);
- if (!llvm::is_contained(innerOp.getOperands(),
- opInst.getRegion().getArgument(0)))
- continue;
- isRegionArgUsed = true;
- isXBinopExpr = innerOp.getNumOperands() > 0 &&
- innerOp.getOperand(0) == opInst.getRegion().getArgument(0);
- mlirExpr = (isXBinopExpr ? innerOp.getOperand(1) : innerOp.getOperand(0));
- break;
+ llvm::Value *llvmExpr = nullptr;
+ llvm::Value *llvmX = nullptr;
+ llvm::Type *llvmXElementType = nullptr;
+ if (innerOpList.size() == 2) {
+ // The two operations here are the update and the terminator.
+ // Since we can identify the update operation, there is a possibility
+ // that we can generate the atomicrmw instruction.
+ mlir::Operation &innerOp = *opInst.getRegion().front().begin();
+ if (!llvm::is_contained(innerOp.getOperands(),
+ opInst.getRegion().getArgument(0))) {
+ return opInst.emitError("no atomic update operation with region argument"
+ " as operand found inside atomic.update region");
}
+ binop = convertBinOpToAtomic(innerOp);
+ isXBinopExpr = innerOp.getOperand(0) == opInst.getRegion().getArgument(0);
+ mlirExpr = (isXBinopExpr ? innerOp.getOperand(1) : innerOp.getOperand(0));
+ llvmExpr = moduleTranslation.lookupValue(mlirExpr);
+ } else {
+ // Since the update region includes more than one operation
+ // we will resort to generating a cmpxchg loop.
+ binop = llvm::AtomicRMWInst::BinOp::BAD_BINOP;
}
- if (!isRegionArgUsed)
- return opInst.emitError("no atomic update operation with region argument"
- " as operand found inside atomic.update region");
-
- llvm::Value *llvmExpr = moduleTranslation.lookupValue(mlirExpr);
- llvm::Value *llvmX = moduleTranslation.lookupValue(opInst.getX());
- llvm::Type *llvmXElementType = moduleTranslation.convertType(
+ llvmX = moduleTranslation.lookupValue(opInst.getX());
+ llvmXElementType = moduleTranslation.convertType(
opInst.getRegion().getArgument(0).getType());
llvm::OpenMPIRBuilder::AtomicOpValue llvmAtomicX = {llvmX, llvmXElementType,
/*isSigned=*/false,
More information about the Mlir-commits
mailing list