mirror of
https://github.com/llvm/llvm-project.git
synced 2025-04-25 07:16:05 +00:00
[CUDA] Add appropriate host/device attribute to builtins.
Differential Revision: http://reviews.llvm.org/D12122 llvm-svn: 245496
This commit is contained in:
parent
61ede1519c
commit
39259ffc65
@ -81,6 +81,11 @@ public:
|
|||||||
return getRecord(ID).Type;
|
return getRecord(ID).Type;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// \brief Return true if this function is a target-specific builtin
|
||||||
|
bool isTSBuiltin(unsigned ID) const {
|
||||||
|
return ID >= Builtin::FirstTSBuiltin;
|
||||||
|
}
|
||||||
|
|
||||||
/// \brief Return true if this function has no side effects and doesn't
|
/// \brief Return true if this function has no side effects and doesn't
|
||||||
/// read memory.
|
/// read memory.
|
||||||
bool isConst(unsigned ID) const {
|
bool isConst(unsigned ID) const {
|
||||||
|
@ -525,7 +525,7 @@ Sema::CheckBuiltinFunctionCall(FunctionDecl *FDecl, unsigned BuiltinID,
|
|||||||
|
|
||||||
// Since the target specific builtins for each arch overlap, only check those
|
// Since the target specific builtins for each arch overlap, only check those
|
||||||
// of the arch we are compiling for.
|
// of the arch we are compiling for.
|
||||||
if (BuiltinID >= Builtin::FirstTSBuiltin) {
|
if (Context.BuiltinInfo.isTSBuiltin(BuiltinID)) {
|
||||||
switch (Context.getTargetInfo().getTriple().getArch()) {
|
switch (Context.getTargetInfo().getTriple().getArch()) {
|
||||||
case llvm::Triple::arm:
|
case llvm::Triple::arm:
|
||||||
case llvm::Triple::armeb:
|
case llvm::Triple::armeb:
|
||||||
|
@ -11187,6 +11187,17 @@ void Sema::AddKnownFunctionAttributes(FunctionDecl *FD) {
|
|||||||
FD->addAttr(NoThrowAttr::CreateImplicit(Context, FD->getLocation()));
|
FD->addAttr(NoThrowAttr::CreateImplicit(Context, FD->getLocation()));
|
||||||
if (Context.BuiltinInfo.isConst(BuiltinID) && !FD->hasAttr<ConstAttr>())
|
if (Context.BuiltinInfo.isConst(BuiltinID) && !FD->hasAttr<ConstAttr>())
|
||||||
FD->addAttr(ConstAttr::CreateImplicit(Context, FD->getLocation()));
|
FD->addAttr(ConstAttr::CreateImplicit(Context, FD->getLocation()));
|
||||||
|
if (getLangOpts().CUDA && Context.BuiltinInfo.isTSBuiltin(BuiltinID) &&
|
||||||
|
!FD->hasAttr<CUDADeviceAttr>() && !FD->hasAttr<CUDAHostAttr>()) {
|
||||||
|
// Target-specific builtins are assumed to be intended for use
|
||||||
|
// in this particular CUDA compilation mode and should have
|
||||||
|
// appropriate attribute set so we can enforce CUDA function
|
||||||
|
// call restrictions.
|
||||||
|
if (getLangOpts().CUDAIsDevice)
|
||||||
|
FD->addAttr(CUDADeviceAttr::CreateImplicit(Context, FD->getLocation()));
|
||||||
|
else
|
||||||
|
FD->addAttr(CUDAHostAttr::CreateImplicit(Context, FD->getLocation()));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
IdentifierInfo *Name = FD->getIdentifier();
|
IdentifierInfo *Name = FD->getIdentifier();
|
||||||
|
35
clang/test/SemaCUDA/builtins.cu
Normal file
35
clang/test/SemaCUDA/builtins.cu
Normal file
@ -0,0 +1,35 @@
|
|||||||
|
// Tests that target-specific builtins have appropriate host/device
|
||||||
|
// attributes and that CUDA call restrictions are enforced. Also
|
||||||
|
// verify that non-target builtins can be used from both host and
|
||||||
|
// device functions.
|
||||||
|
//
|
||||||
|
// REQUIRES: x86-registered-target
|
||||||
|
// REQUIRES: nvptx-registered-target
|
||||||
|
// RUN: %clang_cc1 -triple x86_64-unknown-unknown -fsyntax-only -verify %s
|
||||||
|
// RUN: %clang_cc1 -triple nvptx64-unknown-cuda -fcuda-is-device \
|
||||||
|
// RUN: -fsyntax-only -verify %s
|
||||||
|
|
||||||
|
|
||||||
|
#ifdef __CUDA_ARCH__
|
||||||
|
// Device-side builtins are not allowed to be called from host functions.
|
||||||
|
void hf() {
|
||||||
|
int x = __builtin_ptx_read_tid_x(); // expected-note {{'__builtin_ptx_read_tid_x' declared here}}
|
||||||
|
// expected-error@-1 {{reference to __device__ function '__builtin_ptx_read_tid_x' in __host__ function}}
|
||||||
|
x = __builtin_abs(1);
|
||||||
|
}
|
||||||
|
__attribute__((device)) void df() {
|
||||||
|
int x = __builtin_ptx_read_tid_x();
|
||||||
|
x = __builtin_abs(1);
|
||||||
|
}
|
||||||
|
#else
|
||||||
|
// Host-side builtins are not allowed to be called from device functions.
|
||||||
|
__attribute__((device)) void df() {
|
||||||
|
int x = __builtin_ia32_rdtsc(); // expected-note {{'__builtin_ia32_rdtsc' declared here}}
|
||||||
|
// expected-error@-1 {{reference to __host__ function '__builtin_ia32_rdtsc' in __device__ function}}
|
||||||
|
x = __builtin_abs(1);
|
||||||
|
}
|
||||||
|
void hf() {
|
||||||
|
int x = __builtin_ia32_rdtsc();
|
||||||
|
x = __builtin_abs(1);
|
||||||
|
}
|
||||||
|
#endif
|
@ -1,10 +1,10 @@
|
|||||||
// RUN: %clang_cc1 -std=gnu++11 -triple nvptx64-unknown-unknown -fsyntax-only -verify %s
|
// RUN: %clang_cc1 -triple nvptx64-unknown-unknown -fcuda-is-device -fsyntax-only -verify %s
|
||||||
|
|
||||||
#include "Inputs/cuda.h"
|
#include "Inputs/cuda.h"
|
||||||
|
|
||||||
// expected-no-diagnostics
|
// expected-no-diagnostics
|
||||||
__device__ void __threadfence_system() {
|
__device__ void __threadfence_system() {
|
||||||
// This shouldn't produce an error, since __nvvm_membar_sys is inferred to
|
// This shouldn't produce an error, since __nvvm_membar_sys should be
|
||||||
// be __host__ __device__ and thus callable from device code.
|
// __device__ and thus callable from device code.
|
||||||
__nvvm_membar_sys();
|
__nvvm_membar_sys();
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user