Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[OpenMP] Prevent AMDGPU from overriding visibility on DT_nohost variables #68264

Merged
merged 1 commit into from
Oct 5, 2023

Conversation

jhuber6
Copy link
Contributor

@jhuber6 jhuber6 commented Oct 4, 2023

Summary:
There's some logic in the AMDGPU target that manually resets the
requested visibility of certain variables. This was triggering when we
set a constant variable in OpenMP. However, we shouldn't do this for
OpenMP when the variable has the nohost type. That implies that the
variable is not visible to the host and therefore does not need to be
visible, so we should respect the original value of it.

@llvmbot llvmbot added clang Clang issues not falling into any other category backend:AMDGPU clang:codegen labels Oct 4, 2023
@llvmbot
Copy link
Member

llvmbot commented Oct 4, 2023

@llvm/pr-subscribers-clang-codegen
@llvm/pr-subscribers-backend-amdgpu

@llvm/pr-subscribers-clang

Changes

Summary:
There's some logic in the AMDGPU target that manually resets the
requested visibility of certain variables. This was triggering when we
set a constant variable in OpenMP. However, we shouldn't do this for
OpenMP when the variable has the nohost type. That implies that the
variable is not visible to the host and therefore does not need to be
visible, so we should respect the original value of it.


Full diff: https://github.com/llvm/llvm-project/pull/68264.diff

2 Files Affected:

  • (modified) clang/lib/CodeGen/Targets/AMDGPU.cpp (+4)
  • (modified) clang/test/OpenMP/target_visibility.cpp (+5-1)
diff --git a/clang/lib/CodeGen/Targets/AMDGPU.cpp b/clang/lib/CodeGen/Targets/AMDGPU.cpp
index dc628b7345f59fd..70f906a42e6d9c4 100644
--- a/clang/lib/CodeGen/Targets/AMDGPU.cpp
+++ b/clang/lib/CodeGen/Targets/AMDGPU.cpp
@@ -308,6 +308,10 @@ static bool requiresAMDGPUProtectedVisibility(const Decl *D,
   if (GV->getVisibility() != llvm::GlobalValue::HiddenVisibility)
     return false;
 
+  if (auto *Attr = D->getAttr<OMPDeclareTargetDeclAttr>())
+    if (OMPDeclareTargetDeclAttr::DT_NoHost == Attr->getDevType())
+      return false;
+
   return D->hasAttr<OpenCLKernelAttr>() ||
          (isa<FunctionDecl>(D) && D->hasAttr<CUDAGlobalAttr>()) ||
          (isa<VarDecl>(D) &&
diff --git a/clang/test/OpenMP/target_visibility.cpp b/clang/test/OpenMP/target_visibility.cpp
index 938d164df89bffb..2ed90d4b8ba9a77 100644
--- a/clang/test/OpenMP/target_visibility.cpp
+++ b/clang/test/OpenMP/target_visibility.cpp
@@ -1,5 +1,5 @@
 // RUN: %clang_cc1 -debug-info-kind=limited -verify -fopenmp -x c++ -triple nvptx64-unknown-unknown -fopenmp-targets=nvptx64-nvidia-cuda -emit-llvm %s -fopenmp-is-target-device -o - | FileCheck %s
-// RUN: %clang_cc1 -debug-info-kind=limited -verify -fopenmp -x c++ -triple nvptx-unknown-unknown -fopenmp-targets=nvptx-nvidia-cuda -emit-llvm %s -fopenmp-is-target-device -o - | FileCheck %s
+// RUN: %clang_cc1 -debug-info-kind=limited -verify -fopenmp -x c++ -triple amdgcn-amd-amdhsa -fopenmp-targets=amdgcn-amd-amdhsa -emit-llvm %s -fopenmp-is-target-device -o - | FileCheck %s
 // expected-no-diagnostics
 
 
@@ -21,6 +21,10 @@ void B::bar() { A a; a.foo(); }
 void B::sbar() { A::sfoo(); }
 #pragma omp declare target to(B::bar, B::sbar)
 
+[[gnu::visibility("hidden")]] extern const int x = 0;
+#pragma omp declare target to(x) device_type(nohost)
+
+// CHECK-DAG: @x = hidden{{.*}} constant i32 0
 // CHECK-DAG: define hidden void @_ZN1B4sbarEv()
 // CHECK-DAG: define linkonce_odr hidden void @_ZN1A4sfooEv()
 // CHECK-DAG: define hidden void @_ZN1B3barEv(

@@ -1,5 +1,5 @@
// RUN: %clang_cc1 -debug-info-kind=limited -verify -fopenmp -x c++ -triple nvptx64-unknown-unknown -fopenmp-targets=nvptx64-nvidia-cuda -emit-llvm %s -fopenmp-is-target-device -o - | FileCheck %s
// RUN: %clang_cc1 -debug-info-kind=limited -verify -fopenmp -x c++ -triple nvptx-unknown-unknown -fopenmp-targets=nvptx-nvidia-cuda -emit-llvm %s -fopenmp-is-target-device -o - | FileCheck %s
// RUN: %clang_cc1 -debug-info-kind=limited -verify -fopenmp -x c++ -triple amdgcn-amd-amdhsa -fopenmp-targets=amdgcn-amd-amdhsa -emit-llvm %s -fopenmp-is-target-device -o - | FileCheck %s
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

maybe it is safer to have tests for both amdgcn and nvptx since they behave differently

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I just added --check-prefixes=CHECK,AMDGPU for the differences. Figured it's not worth making a new test just for this.

Copy link
Collaborator

@JonChesterfield JonChesterfield left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This stuff looks very cuda/opencl specific. It's definitely surprising for C++ code. Do we need it for openmp? If not it seems better to guard the hack with visibility behind if (hip)

@jhuber6
Copy link
Contributor Author

jhuber6 commented Oct 5, 2023

This stuff looks very cuda/opencl specific. It's definitely surprising for C++ code. Do we need it for openmp? If not it seems better to guard the hack with visibility behind if (hip)

You reminded me that I need to refine this logic as well. What it's doing here is basically the same as what we want to happen. If someone uses #pragma omp declare target on a variable without device_type(nohost) that means the host runtime will need to register it. If it's hidden then that will be a lookup error. I refined the logic to do the same handling for OpenMP, but ignore it if it's DT_nohost because then there's no registration code required.

@github-actions
Copy link

github-actions bot commented Oct 5, 2023

✅ With the latest revision this PR passed the C/C++ code formatter.

@jhuber6 jhuber6 force-pushed the AMDGPUVisibility branch 2 times, most recently from d770f8a to ddccf41 Compare October 5, 2023 14:27
(D->hasAttr<CUDADeviceAttr>() || D->hasAttr<CUDAConstantAttr>() ||
cast<VarDecl>(D)->getType()->isCUDADeviceBuiltinSurfaceType() ||
cast<VarDecl>(D)->getType()->isCUDADeviceBuiltinTextureType()));
return !D->hasAttr<OMPDeclareTargetDeclAttr>() &&
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

is this a spurious whitespace change?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not here, above there's an extra line. I'll fix that before I land, not worth force pushing.

@jdoerfert
Copy link
Member

Seems reasonable to me.

Copy link
Member

@jdoerfert jdoerfert left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LG if others don't object

…bles

Summary:
There's some logic in the AMDGPU target that manually resets the
requested visibility of certain variables. This was triggering when we
set a constant variable in OpenMP. However, we shouldn't do this for
OpenMP when the variable has the `nohost` type. That implies that the
variable is not visible to the host and therefore does not need to be
visible, so we should respect the original value of it.
@jhuber6 jhuber6 merged commit 1d959f9 into llvm:main Oct 5, 2023
2 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
backend:AMDGPU clang:codegen clang Clang issues not falling into any other category
Projects
None yet
Development

Successfully merging this pull request may close these issues.

5 participants