summaryrefslogtreecommitdiffstats
path: root/clang/lib/CodeGen/CGBlocks.cpp
diff options
context:
space:
mode:
authorMike Stump <mrs@apple.com>2009-10-21 22:01:24 +0000
committerMike Stump <mrs@apple.com>2009-10-21 22:01:24 +0000
commit066b61668455c8e3558b2667d4cee4eb3dd17219 (patch)
treeef0f9fdd3fcfe9b074e5be69d07ec5d4089f85f4 /clang/lib/CodeGen/CGBlocks.cpp
parent2505c1e17af59fc395eaceaf21fd5a2152cc7a05 (diff)
downloadbcm5719-llvm-066b61668455c8e3558b2667d4cee4eb3dd17219.tar.gz
bcm5719-llvm-066b61668455c8e3558b2667d4cee4eb3dd17219.zip
Refine collection of BlockDeclRefExprs. WIP.
llvm-svn: 84787
Diffstat (limited to 'clang/lib/CodeGen/CGBlocks.cpp')
-rw-r--r--clang/lib/CodeGen/CGBlocks.cpp25
1 files changed, 16 insertions, 9 deletions
diff --git a/clang/lib/CodeGen/CGBlocks.cpp b/clang/lib/CodeGen/CGBlocks.cpp
index af64fd5546d..08c45874a39 100644
--- a/clang/lib/CodeGen/CGBlocks.cpp
+++ b/clang/lib/CodeGen/CGBlocks.cpp
@@ -73,24 +73,29 @@ llvm::Constant *BlockModule::getNSConcreteStackBlock() {
return NSConcreteStackBlock;
}
-static void CollectBlockDeclRefInfo(const Stmt *S,
- CodeGenFunction::BlockInfo &Info) {
+static void CollectBlockDeclRefInfo(
+ const Stmt *S, CodeGenFunction::BlockInfo &Info,
+ llvm::SmallSet<const DeclContext *, 16> &InnerContexts) {
for (Stmt::const_child_iterator I = S->child_begin(), E = S->child_end();
I != E; ++I)
if (*I)
- CollectBlockDeclRefInfo(*I, Info);
+ CollectBlockDeclRefInfo(*I, Info, InnerContexts);
// We want to ensure we walk down into block literals so we can find
// all nested BlockDeclRefExprs.
- if (const BlockExpr *BE = dyn_cast<BlockExpr>(S))
- CollectBlockDeclRefInfo(BE->getBody(), Info);
+ if (const BlockExpr *BE = dyn_cast<BlockExpr>(S)) {
+ InnerContexts.insert(cast<DeclContext>(BE->getBlockDecl()));
+ CollectBlockDeclRefInfo(BE->getBody(), Info, InnerContexts);
+ }
- if (const BlockDeclRefExpr *DE = dyn_cast<BlockDeclRefExpr>(S)) {
+ if (const BlockDeclRefExpr *BDRE = dyn_cast<BlockDeclRefExpr>(S)) {
// FIXME: Handle enums.
- if (isa<FunctionDecl>(DE->getDecl()))
+ if (isa<FunctionDecl>(BDRE->getDecl()))
return;
- Info.DeclRefs.push_back(DE);
+ // Only Decls that escape are added.
+ if (!InnerContexts.count(BDRE->getDecl()->getDeclContext()))
+ Info.DeclRefs.push_back(BDRE);
}
}
@@ -130,7 +135,9 @@ llvm::Value *CodeGenFunction::BuildBlockLiteralTmp(const BlockExpr *BE) {
std::string Name = CurFn->getName();
CodeGenFunction::BlockInfo Info(0, Name.c_str());
- CollectBlockDeclRefInfo(BE->getBody(), Info);
+ llvm::SmallSet<const DeclContext *, 16> InnerContexts;
+ InnerContexts.insert(BE->getBlockDecl());
+ CollectBlockDeclRefInfo(BE->getBody(), Info, InnerContexts);
// Check if the block can be global.
// FIXME: This test doesn't work for nested blocks yet. Longer term, I'd like
OpenPOWER on IntegriCloud