forked from OSchip/llvm-project
-Wuninitialized should not warn about variables captured by blocks as byref.
Note this can potentially be enhanced to detect if the __block variable is actually written by the block, or only when the block "escapes" or is actually used, but that requires more analysis than it is probably worth for this simple check. llvm-svn: 128681
This commit is contained in:
parent
0888bcf542
commit
77361761fb
|
@ -440,13 +440,18 @@ void TransferFunctions::BlockStmt_VisitObjCForCollectionStmt(
|
|||
void TransferFunctions::VisitBlockExpr(BlockExpr *be) {
|
||||
if (!flagBlockUses || !handler)
|
||||
return;
|
||||
AnalysisContext::referenced_decls_iterator i, e;
|
||||
llvm::tie(i, e) = ac.getReferencedBlockVars(be->getBlockDecl());
|
||||
for ( ; i != e; ++i) {
|
||||
const VarDecl *vd = *i;
|
||||
if (vd->getAttr<BlocksAttr>() || !vd->hasLocalStorage() ||
|
||||
!isTrackedVar(vd))
|
||||
const BlockDecl *bd = be->getBlockDecl();
|
||||
for (BlockDecl::capture_const_iterator i = bd->capture_begin(),
|
||||
e = bd->capture_end() ; i != e; ++i) {
|
||||
const VarDecl *vd = i->getVariable();
|
||||
if (!vd->hasLocalStorage())
|
||||
continue;
|
||||
if (!isTrackedVar(vd))
|
||||
continue;
|
||||
if (i->isByRef()) {
|
||||
vals[vd] = Initialized;
|
||||
continue;
|
||||
}
|
||||
Value v = vals[vd];
|
||||
if (isUninitialized(v))
|
||||
handler->handleUseOfUninitVariable(be, vd, isAlwaysUninit(v));
|
||||
|
|
|
@ -328,3 +328,12 @@ void test50()
|
|||
char c[1 ? : 2]; // no-warning
|
||||
}
|
||||
|
||||
int test51(void)
|
||||
{
|
||||
__block int a;
|
||||
^(void) {
|
||||
a = 42;
|
||||
}();
|
||||
return a; // no-warning
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in New Issue