[OPENMP] Additional checking for local vars in initial values for threadprivate vars

llvm-svn: 209716
This commit is contained in:
Alexey Bataev 2014-05-28 07:40:25 +00:00
parent 7c747fc7c6
commit 18b92eeacb
3 changed files with 41 additions and 1 deletions

View File

@ -6956,6 +6956,8 @@ def err_omp_linear_expected_int_or_ptr : Error<
def warn_omp_linear_step_zero : Warning<
"zero linear step (%0 %select{|and other variables in clause }1should probably be const)">,
InGroup<OpenMPClauses>;
def err_omp_local_var_in_threadprivate_init : Error<
"variable with local storage in initial value of threadprivate variable">;
} // end of OpenMP category
let CategoryName = "Related Result Type Issue" in {

View File

@ -553,6 +553,35 @@ Sema::ActOnOpenMPThreadprivateDirective(SourceLocation Loc,
return DeclGroupPtrTy();
}
namespace {
class LocalVarRefChecker : public ConstStmtVisitor<LocalVarRefChecker, bool> {
Sema &SemaRef;
public:
bool VisitDeclRefExpr(const DeclRefExpr *E) {
if (auto VD = dyn_cast<VarDecl>(E->getDecl())) {
if (VD->hasLocalStorage()) {
SemaRef.Diag(E->getLocStart(),
diag::err_omp_local_var_in_threadprivate_init)
<< E->getSourceRange();
SemaRef.Diag(VD->getLocation(), diag::note_defined_here)
<< VD << VD->getSourceRange();
return true;
}
}
return false;
}
bool VisitStmt(const Stmt *S) {
for (auto Child : S->children()) {
if (Child && Visit(Child))
return true;
}
return false;
}
LocalVarRefChecker(Sema &SemaRef) : SemaRef(SemaRef) {}
};
} // namespace
OMPThreadPrivateDecl *
Sema::CheckOMPThreadPrivateDecl(SourceLocation Loc, ArrayRef<Expr *> VarList) {
SmallVector<Expr *, 8> Vars;
@ -592,6 +621,13 @@ Sema::CheckOMPThreadPrivateDecl(SourceLocation Loc, ArrayRef<Expr *> VarList) {
continue;
}
// Check if initial value of threadprivate variable reference variable with
// local storage (it is not supported by runtime).
if (auto Init = VD->getAnyInitializer()) {
LocalVarRefChecker Checker(*this);
if (Checker.Visit(Init)) continue;
}
Vars.push_back(RefExpr);
DSAStack->addDSA(VD, DE, OMPC_threadprivate);
}

View File

@ -108,10 +108,12 @@ int o; // expected-note {{candidate found by name lookup is '(anonymous namespac
int main(int argc, char **argv) { // expected-note {{'argc' defined here}}
int x, y = argc; // expected-note {{'y' defined here}}
int x, y = argc; // expected-note 2 {{'y' defined here}}
static double d1;
static double d2;
static double d3; // expected-note {{'d3' defined here}}
static Class LocalClass(y); // expected-error {{variable with local storage in initial value of threadprivate variable}}
#pragma omp threadprivate(LocalClass)
d.a = a;
d2++;