diff options
| author | Ted Kremenek <kremenek@apple.com> | 2011-03-31 22:32:41 +0000 |
|---|---|---|
| committer | Ted Kremenek <kremenek@apple.com> | 2011-03-31 22:32:41 +0000 |
| commit | 77361761fbcf92fa5138a54b8425e76e76a852a1 (patch) | |
| tree | f9db5205256a80c56347caa7e5a89ec660f0a94d | |
| parent | 0888bcf542411eb84d198ac549cfe14cc1a64a79 (diff) | |
| download | llvm-77361761fbcf92fa5138a54b8425e76e76a852a1.zip llvm-77361761fbcf92fa5138a54b8425e76e76a852a1.tar.gz llvm-77361761fbcf92fa5138a54b8425e76e76a852a1.tar.bz2 | |
-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
| -rw-r--r-- | clang/lib/Analysis/UninitializedValues.cpp | 17 | ||||
| -rw-r--r-- | clang/test/Sema/uninit-variables.c | 9 |
2 files changed, 20 insertions, 6 deletions
diff --git a/clang/lib/Analysis/UninitializedValues.cpp b/clang/lib/Analysis/UninitializedValues.cpp index f3cf905..58191ec 100644 --- a/clang/lib/Analysis/UninitializedValues.cpp +++ b/clang/lib/Analysis/UninitializedValues.cpp @@ -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)); diff --git a/clang/test/Sema/uninit-variables.c b/clang/test/Sema/uninit-variables.c index 85e6394..17bd07f 100644 --- a/clang/test/Sema/uninit-variables.c +++ b/clang/test/Sema/uninit-variables.c @@ -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 +} + |
