diff --git a/llvm/lib/Transforms/IPO/OpenMPOpt.cpp b/llvm/lib/Transforms/IPO/OpenMPOpt.cpp --- a/llvm/lib/Transforms/IPO/OpenMPOpt.cpp +++ b/llvm/lib/Transforms/IPO/OpenMPOpt.cpp @@ -1480,6 +1480,9 @@ auto &SetterRFI = OMPInfoCache.RFIs[OMPInfoCache.ICVs[ICV].Setter]; Function *CalledFunction = CB->getCalledFunction(); + // Indirect call, assume ICV changes. + if (CalledFunction == nullptr) + return nullptr; if (CalledFunction == GetterRFI.Declaration) return None; if (CalledFunction == SetterRFI.Declaration) { diff --git a/llvm/test/Transforms/OpenMP/icv_tracking.ll b/llvm/test/Transforms/OpenMP/icv_tracking.ll --- a/llvm/test/Transforms/OpenMP/icv_tracking.ll +++ b/llvm/test/Transforms/OpenMP/icv_tracking.ll @@ -30,6 +30,21 @@ ret i32 %2 } +define void @indirect_call(void ()* %0) { +; CHECK-LABEL: define {{[^@]+}}@indirect_call +; CHECK-SAME: (void ()* [[TMP0:%.*]]) +; CHECK-NEXT: call void @omp_set_num_threads(i32 4) +; CHECK-NEXT: tail call void [[TMP0]]() +; CHECK-NEXT: [[TMP2:%.*]] = tail call i32 @omp_get_max_threads() +; CHECK-NEXT: tail call void @use(i32 [[TMP2]]) +; CHECK-NEXT: ret void + call void @omp_set_num_threads(i32 4) + tail call void %0() + %2 = tail call i32 @omp_get_max_threads() + tail call void @use(i32 %2) + ret void +} + define dso_local i32 @foo(i32 %0, i32 %1) { ; CHECK-LABEL: define {{[^@]+}}@foo ; CHECK-SAME: (i32 [[TMP0:%.*]], i32 [[TMP1:%.*]])