forked from OSchip/llvm-project
[CUDA] Add implicit conversion of __launch_bounds__ arguments to rvalue.
Fixes clang crash reported in PR27778. Differential Revision: http://reviews.llvm.org/D20985 llvm-svn: 271951
This commit is contained in:
parent
acad605df9
commit
bcec9dac14
|
@ -28,6 +28,7 @@
|
|||
#include "clang/Lex/Preprocessor.h"
|
||||
#include "clang/Sema/DeclSpec.h"
|
||||
#include "clang/Sema/DelayedDiagnostic.h"
|
||||
#include "clang/Sema/Initialization.h"
|
||||
#include "clang/Sema/Lookup.h"
|
||||
#include "clang/Sema/Scope.h"
|
||||
#include "llvm/ADT/StringExtras.h"
|
||||
|
@ -4039,48 +4040,60 @@ bool Sema::CheckRegparmAttr(const AttributeList &Attr, unsigned &numParams) {
|
|||
return false;
|
||||
}
|
||||
|
||||
// Checks whether an argument of launch_bounds attribute is acceptable
|
||||
// May output an error.
|
||||
static bool checkLaunchBoundsArgument(Sema &S, Expr *E,
|
||||
const CUDALaunchBoundsAttr &Attr,
|
||||
const unsigned Idx) {
|
||||
// Checks whether an argument of launch_bounds attribute is
|
||||
// acceptable, performs implicit conversion to Rvalue, and returns
|
||||
// non-nullptr Expr result on success. Otherwise, it returns nullptr
|
||||
// and may output an error.
|
||||
static Expr *makeLaunchBoundsArgExpr(Sema &S, Expr *E,
|
||||
const CUDALaunchBoundsAttr &Attr,
|
||||
const unsigned Idx) {
|
||||
if (S.DiagnoseUnexpandedParameterPack(E))
|
||||
return false;
|
||||
return nullptr;
|
||||
|
||||
// Accept template arguments for now as they depend on something else.
|
||||
// We'll get to check them when they eventually get instantiated.
|
||||
if (E->isValueDependent())
|
||||
return true;
|
||||
return E;
|
||||
|
||||
llvm::APSInt I(64);
|
||||
if (!E->isIntegerConstantExpr(I, S.Context)) {
|
||||
S.Diag(E->getExprLoc(), diag::err_attribute_argument_n_type)
|
||||
<< &Attr << Idx << AANT_ArgumentIntegerConstant << E->getSourceRange();
|
||||
return false;
|
||||
return nullptr;
|
||||
}
|
||||
// Make sure we can fit it in 32 bits.
|
||||
if (!I.isIntN(32)) {
|
||||
S.Diag(E->getExprLoc(), diag::err_ice_too_large) << I.toString(10, false)
|
||||
<< 32 << /* Unsigned */ 1;
|
||||
return false;
|
||||
return nullptr;
|
||||
}
|
||||
if (I < 0)
|
||||
S.Diag(E->getExprLoc(), diag::warn_attribute_argument_n_negative)
|
||||
<< &Attr << Idx << E->getSourceRange();
|
||||
|
||||
return true;
|
||||
// We may need to perform implicit conversion of the argument.
|
||||
InitializedEntity Entity = InitializedEntity::InitializeParameter(
|
||||
S.Context, S.Context.getConstType(S.Context.IntTy), /*consume*/ false);
|
||||
ExprResult ValArg = S.PerformCopyInitialization(Entity, SourceLocation(), E);
|
||||
assert(!ValArg.isInvalid() &&
|
||||
"Unexpected PerformCopyInitialization() failure.");
|
||||
|
||||
return ValArg.getAs<Expr>();
|
||||
}
|
||||
|
||||
void Sema::AddLaunchBoundsAttr(SourceRange AttrRange, Decl *D, Expr *MaxThreads,
|
||||
Expr *MinBlocks, unsigned SpellingListIndex) {
|
||||
CUDALaunchBoundsAttr TmpAttr(AttrRange, Context, MaxThreads, MinBlocks,
|
||||
SpellingListIndex);
|
||||
|
||||
if (!checkLaunchBoundsArgument(*this, MaxThreads, TmpAttr, 0))
|
||||
MaxThreads = makeLaunchBoundsArgExpr(*this, MaxThreads, TmpAttr, 0);
|
||||
if (MaxThreads == nullptr)
|
||||
return;
|
||||
|
||||
if (MinBlocks && !checkLaunchBoundsArgument(*this, MinBlocks, TmpAttr, 1))
|
||||
return;
|
||||
if (MinBlocks) {
|
||||
MinBlocks = makeLaunchBoundsArgExpr(*this, MinBlocks, TmpAttr, 1);
|
||||
if (MinBlocks == nullptr)
|
||||
return;
|
||||
}
|
||||
|
||||
D->addAttr(::new (Context) CUDALaunchBoundsAttr(
|
||||
AttrRange, Context, MaxThreads, MinBlocks, SpellingListIndex));
|
||||
|
|
|
@ -79,3 +79,8 @@ Kernel7()
|
|||
}
|
||||
// CHECK: !{{[0-9]+}} = !{void ()* @{{.*}}Kernel7{{.*}}, !"maxntidx",
|
||||
// CHECK-NOT: !{{[0-9]+}} = !{void ()* @{{.*}}Kernel7{{.*}}, !"minctasm",
|
||||
|
||||
const char constchar = 12;
|
||||
__global__ void __launch_bounds__(constint, constchar) Kernel8() {}
|
||||
// CHECK: !{{[0-9]+}} = !{void ()* @{{.*}}Kernel8{{.*}}, !"maxntidx", i32 100
|
||||
// CHECK: !{{[0-9]+}} = !{void ()* @{{.*}}Kernel8{{.*}}, !"minctasm", i32 12
|
||||
|
|
|
@ -0,0 +1,6 @@
|
|||
// RUN: %clang_cc1 -fsyntax-only %s
|
||||
|
||||
#include "Inputs/cuda.h"
|
||||
|
||||
const int constint = 512;
|
||||
__launch_bounds__(constint) void TestConstInt(void) {}
|
Loading…
Reference in New Issue