r295473 - [OpenMP] Remove barriers at cancel and cancellation point
Jonas Hahnfeld via cfe-commits
cfe-commits at lists.llvm.org
Fri Feb 17 10:32:52 PST 2017
Author: hahnfeld
Date: Fri Feb 17 12:32:51 2017
New Revision: 295473
URL: http://llvm.org/viewvc/llvm-project?rev=295473&view=rev
Log:
[OpenMP] Remove barriers at cancel and cancellation point
This resolves a deadlock with the cancel directive when there is no explicit
cancellation point. In that case, the implicit barrier acts as cancellation
point. After removing the barrier after cancel, the now unmatched barrier for
the explicit cancellation point has to go as well.
This has probably worked before rL255992: With the calls for the explicit
barrier, it was sure that all threads passed a barrier before exiting.
Reported by Simon Convent and Joachim Protze!
Differential Revision: https://reviews.llvm.org/D30088
Modified:
cfe/trunk/lib/CodeGen/CGOpenMPRuntime.cpp
cfe/trunk/test/OpenMP/cancel_codegen.cpp
cfe/trunk/test/OpenMP/cancellation_point_codegen.cpp
Modified: cfe/trunk/lib/CodeGen/CGOpenMPRuntime.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CGOpenMPRuntime.cpp?rev=295473&r1=295472&r2=295473&view=diff
==============================================================================
--- cfe/trunk/lib/CodeGen/CGOpenMPRuntime.cpp (original)
+++ cfe/trunk/lib/CodeGen/CGOpenMPRuntime.cpp Fri Feb 17 12:32:51 2017
@@ -4724,7 +4724,6 @@ void CGOpenMPRuntime::emitCancellationPo
auto *Result = CGF.EmitRuntimeCall(
createRuntimeFunction(OMPRTL__kmpc_cancellationpoint), Args);
// if (__kmpc_cancellationpoint()) {
- // __kmpc_cancel_barrier();
// exit from construct;
// }
auto *ExitBB = CGF.createBasicBlock(".cancel.exit");
@@ -4732,8 +4731,6 @@ void CGOpenMPRuntime::emitCancellationPo
auto *Cmp = CGF.Builder.CreateIsNotNull(Result);
CGF.Builder.CreateCondBr(Cmp, ExitBB, ContBB);
CGF.EmitBlock(ExitBB);
- // __kmpc_cancel_barrier();
- emitBarrierCall(CGF, Loc, OMPD_unknown, /*EmitChecks=*/false);
// exit from construct;
auto CancelDest =
CGF.getOMPCancelDestination(OMPRegionInfo->getDirectiveKind());
@@ -4762,7 +4759,6 @@ void CGOpenMPRuntime::emitCancelCall(Cod
auto *Result = CGF.EmitRuntimeCall(
RT.createRuntimeFunction(OMPRTL__kmpc_cancel), Args);
// if (__kmpc_cancel()) {
- // __kmpc_cancel_barrier();
// exit from construct;
// }
auto *ExitBB = CGF.createBasicBlock(".cancel.exit");
@@ -4770,8 +4766,6 @@ void CGOpenMPRuntime::emitCancelCall(Cod
auto *Cmp = CGF.Builder.CreateIsNotNull(Result);
CGF.Builder.CreateCondBr(Cmp, ExitBB, ContBB);
CGF.EmitBlock(ExitBB);
- // __kmpc_cancel_barrier();
- RT.emitBarrierCall(CGF, Loc, OMPD_unknown, /*EmitChecks=*/false);
// exit from construct;
auto CancelDest =
CGF.getOMPCancelDestination(OMPRegionInfo->getDirectiveKind());
Modified: cfe/trunk/test/OpenMP/cancel_codegen.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/OpenMP/cancel_codegen.cpp?rev=295473&r1=295472&r2=295473&view=diff
==============================================================================
--- cfe/trunk/test/OpenMP/cancel_codegen.cpp (original)
+++ cfe/trunk/test/OpenMP/cancel_codegen.cpp Fri Feb 17 12:32:51 2017
@@ -12,6 +12,8 @@ int main (int argc, char **argv) {
{
#pragma omp cancel parallel if(flag)
argv[0][0] = argc;
+#pragma omp barrier
+ argv[0][0] += argc;
}
// CHECK: call void (%ident_t*, i32, void (i32*, i32*, ...)*, ...) @__kmpc_fork_call(
#pragma omp sections
@@ -20,7 +22,6 @@ int main (int argc, char **argv) {
}
// CHECK: call void @__kmpc_for_static_init_4(
// CHECK: call i32 @__kmpc_cancel(
-// CHECK: call i32 @__kmpc_cancel_barrier(%ident_t*
// CHECK: call void @__kmpc_for_static_fini(
// CHECK: call void @__kmpc_barrier(%ident_t*
#pragma omp sections
@@ -36,7 +37,6 @@ int main (int argc, char **argv) {
// CHECK: [[CMP:%.+]] = icmp ne i32 [[RES]], 0
// CHECK: br i1 [[CMP]], label %[[EXIT:[^,].+]], label %[[CONTINUE:.+]]
// CHECK: [[EXIT]]
-// CHECK: call i32 @__kmpc_cancel_barrier(%ident_t*
// CHECK: br label
// CHECK: [[CONTINUE]]
// CHECK: br label
@@ -44,7 +44,6 @@ int main (int argc, char **argv) {
// CHECK: [[CMP:%.+]] = icmp ne i32 [[RES]], 0
// CHECK: br i1 [[CMP]], label %[[EXIT:[^,].+]], label %[[CONTINUE:.+]]
// CHECK: [[EXIT]]
-// CHECK: call i32 @__kmpc_cancel_barrier(%ident_t*
// CHECK: br label
// CHECK: [[CONTINUE]]
// CHECK: br label
@@ -62,7 +61,6 @@ for (int i = 0; i < argc; ++i) {
// CHECK: [[CMP:%.+]] = icmp ne i32 [[RES]], 0
// CHECK: br i1 [[CMP]], label %[[EXIT:[^,].+]], label %[[CONTINUE:.+]]
// CHECK: [[EXIT]]
-// CHECK: call i32 @__kmpc_cancel_barrier(%ident_t*
// CHECK: br label
// CHECK: [[CONTINUE]]
// CHECK: br label
@@ -109,9 +107,10 @@ for (int i = 0; i < argc; ++i) {
// CHECK: [[CMP:%.+]] = icmp ne i32 [[RES]], 0
// CHECK: br i1 [[CMP]], label %[[EXIT:[^,]+]],
// CHECK: [[EXIT]]
-// CHECK: call i32 @__kmpc_cancel_barrier(%ident_t*
// CHECK: br label %[[RETURN:.+]]
// CHECK: [[ELSE]]
+// The barrier directive should now call __kmpc_cancel_barrier
+// CHECK: call i32 @__kmpc_cancel_barrier(%ident_t*
// CHECK: br label
// CHECK: [[RETURN]]
// CHECK: ret void
@@ -121,7 +120,6 @@ for (int i = 0; i < argc; ++i) {
// CHECK: [[CMP:%.+]] = icmp ne i32 [[RES]], 0
// CHECK: br i1 [[CMP]], label %[[EXIT:[^,]+]],
// CHECK: [[EXIT]]
-// CHECK: call i32 @__kmpc_cancel_barrier(%ident_t*
// CHECK: br label %[[RETURN:.+]]
// CHECK: [[RETURN]]
// CHECK: ret i32 0
@@ -129,7 +127,6 @@ for (int i = 0; i < argc; ++i) {
// CHECK: define internal void @{{[^(]+}}(i32* {{[^,]+}}, i32* {{[^,]+}})
// CHECK: call void @__kmpc_for_static_init_4(
// CHECK: call i32 @__kmpc_cancel(
-// CHECK: call i32 @__kmpc_cancel_barrier(%ident_t*
// CHECK: call void @__kmpc_for_static_fini(
// CHECK: ret void
@@ -139,7 +136,6 @@ for (int i = 0; i < argc; ++i) {
// CHECK: [[CMP:%.+]] = icmp ne i32 [[RES]], 0
// CHECK: br i1 [[CMP]], label %[[EXIT:[^,].+]], label %[[CONTINUE:.+]]
// CHECK: [[EXIT]]
-// CHECK: call i32 @__kmpc_cancel_barrier(%ident_t*
// CHECK: br label
// CHECK: [[CONTINUE]]
// CHECK: br label
@@ -147,7 +143,6 @@ for (int i = 0; i < argc; ++i) {
// CHECK: [[CMP:%.+]] = icmp ne i32 [[RES]], 0
// CHECK: br i1 [[CMP]], label %[[EXIT:[^,].+]], label %[[CONTINUE:.+]]
// CHECK: [[EXIT]]
-// CHECK: call i32 @__kmpc_cancel_barrier(%ident_t*
// CHECK: br label
// CHECK: [[CONTINUE]]
// CHECK: br label
@@ -160,7 +155,6 @@ for (int i = 0; i < argc; ++i) {
// CHECK: [[CMP:%.+]] = icmp ne i32 [[RES]], 0
// CHECK: br i1 [[CMP]], label %[[EXIT:[^,].+]], label %[[CONTINUE:.+]]
// CHECK: [[EXIT]]
-// CHECK: call i32 @__kmpc_cancel_barrier(%ident_t*
// CHECK: br label
// CHECK: [[CONTINUE]]
// CHECK: br label
Modified: cfe/trunk/test/OpenMP/cancellation_point_codegen.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/OpenMP/cancellation_point_codegen.cpp?rev=295473&r1=295472&r2=295473&view=diff
==============================================================================
--- cfe/trunk/test/OpenMP/cancellation_point_codegen.cpp (original)
+++ cfe/trunk/test/OpenMP/cancellation_point_codegen.cpp Fri Feb 17 12:32:51 2017
@@ -26,7 +26,6 @@ int main (int argc, char **argv) {
// CHECK: [[CMP:%.+]] = icmp ne i32 [[RES]], 0
// CHECK: br i1 [[CMP]], label %[[EXIT:[^,].+]], label %[[CONTINUE:.+]]
// CHECK: [[EXIT]]
-// CHECK: call i32 @__kmpc_cancel_barrier(%ident_t*
// CHECK: br label
// CHECK: [[CONTINUE]]
// CHECK: br label
@@ -46,7 +45,6 @@ int main (int argc, char **argv) {
// CHECK: [[CMP:%.+]] = icmp ne i32 [[RES]], 0
// CHECK: br i1 [[CMP]], label %[[EXIT:[^,].+]], label %[[CONTINUE:.+]]
// CHECK: [[EXIT]]
-// CHECK: call i32 @__kmpc_cancel_barrier(%ident_t*
// CHECK: br label
// CHECK: [[CONTINUE]]
// CHECK: br label
@@ -54,7 +52,6 @@ int main (int argc, char **argv) {
// CHECK: [[CMP:%.+]] = icmp ne i32 [[RES]], 0
// CHECK: br i1 [[CMP]], label %[[EXIT:[^,].+]], label %[[CONTINUE:.+]]
// CHECK: [[EXIT]]
-// CHECK: call i32 @__kmpc_cancel_barrier(%ident_t*
// CHECK: br label
// CHECK: [[CONTINUE]]
// CHECK: br label
@@ -69,7 +66,6 @@ for (int i = 0; i < argc; ++i) {
// CHECK: [[CMP:%.+]] = icmp ne i32 [[RES]], 0
// CHECK: br i1 [[CMP]], label %[[EXIT:[^,].+]], label %[[CONTINUE:.+]]
// CHECK: [[EXIT]]
-// CHECK: call i32 @__kmpc_cancel_barrier(%ident_t*
// CHECK: br label
// CHECK: [[CONTINUE]]
// CHECK: br label
@@ -116,7 +112,6 @@ for (int i = 0; i < argc; ++i) {
// CHECK: [[CMP:%.+]] = icmp ne i32 [[RES]], 0
// CHECK: br i1 [[CMP]], label %[[EXIT:[^,]+]],
// CHECK: [[EXIT]]
-// CHECK: call i32 @__kmpc_cancel_barrier(%ident_t*
// CHECK: br label %[[RETURN:.+]]
// CHECK: [[RETURN]]
// CHECK: ret void
@@ -126,7 +121,6 @@ for (int i = 0; i < argc; ++i) {
// CHECK: [[CMP:%.+]] = icmp ne i32 [[RES]], 0
// CHECK: br i1 [[CMP]], label %[[EXIT:[^,]+]],
// CHECK: [[EXIT]]
-// CHECK: call i32 @__kmpc_cancel_barrier(%ident_t*
// CHECK: br label %[[RETURN:.+]]
// CHECK: [[RETURN]]
// CHECK: ret i32 0
@@ -137,7 +131,6 @@ for (int i = 0; i < argc; ++i) {
// CHECK: [[CMP:%.+]] = icmp ne i32 [[RES]], 0
// CHECK: br i1 [[CMP]], label %[[EXIT:[^,].+]], label %[[CONTINUE:.+]]
// CHECK: [[EXIT]]
-// CHECK: call i32 @__kmpc_cancel_barrier(%ident_t*
// CHECK: br label
// CHECK: [[CONTINUE]]
// CHECK: br label
@@ -150,7 +143,6 @@ for (int i = 0; i < argc; ++i) {
// CHECK: [[CMP:%.+]] = icmp ne i32 [[RES]], 0
// CHECK: br i1 [[CMP]], label %[[EXIT:[^,].+]], label %[[CONTINUE:.+]]
// CHECK: [[EXIT]]
-// CHECK: call i32 @__kmpc_cancel_barrier(%ident_t*
// CHECK: br label
// CHECK: [[CONTINUE]]
// CHECK: br label
@@ -158,7 +150,6 @@ for (int i = 0; i < argc; ++i) {
// CHECK: [[CMP:%.+]] = icmp ne i32 [[RES]], 0
// CHECK: br i1 [[CMP]], label %[[EXIT:[^,].+]], label %[[CONTINUE:.+]]
// CHECK: [[EXIT]]
-// CHECK: call i32 @__kmpc_cancel_barrier(%ident_t*
// CHECK: br label
// CHECK: [[CONTINUE]]
// CHECK: br label
@@ -171,7 +162,6 @@ for (int i = 0; i < argc; ++i) {
// CHECK: [[CMP:%.+]] = icmp ne i32 [[RES]], 0
// CHECK: br i1 [[CMP]], label %[[EXIT:[^,].+]], label %[[CONTINUE:.+]]
// CHECK: [[EXIT]]
-// CHECK: call i32 @__kmpc_cancel_barrier(%ident_t*
// CHECK: br label
// CHECK: [[CONTINUE]]
// CHECK: br label
More information about the cfe-commits
mailing list