aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMike Stump <mrs@apple.com>2009-04-21 00:51:43 +0000
committerMike Stump <mrs@apple.com>2009-04-21 00:51:43 +0000
commit75b163f4c832696edf4d66d8ac1ec0ed5ea59e17 (patch)
tree6ab6d3227f4d09aa85e8733a0fcc2bf3cb86439b
parent6bf2ae05c777052e5ec05649710380dea263e7e0 (diff)
Fixup codegen for write barriers for block variables. Radar 6786715
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@69642 91177308-0d34-0410-b5e6-96231b3b80d8
-rw-r--r--include/clang/AST/Type.h2
-rw-r--r--include/clang/Parse/DeclSpec.h12
-rw-r--r--lib/Parse/ParseDecl.cpp2
-rw-r--r--test/CodeGenObjC/blocks-1.m17
4 files changed, 22 insertions, 11 deletions
diff --git a/include/clang/AST/Type.h b/include/clang/AST/Type.h
index 62750087c0..d5d607fde9 100644
--- a/include/clang/AST/Type.h
+++ b/include/clang/AST/Type.h
@@ -2009,7 +2009,7 @@ inline bool Type::isPointerType() const {
return isa<PointerType>(CanonicalType.getUnqualifiedType());
}
inline bool Type::isBlockPointerType() const {
- return isa<BlockPointerType>(CanonicalType);
+ return isa<BlockPointerType>(CanonicalType.getUnqualifiedType());
}
inline bool Type::isReferenceType() const {
return isa<ReferenceType>(CanonicalType.getUnqualifiedType());
diff --git a/include/clang/Parse/DeclSpec.h b/include/clang/Parse/DeclSpec.h
index c3c07b7f4a..1be687be8e 100644
--- a/include/clang/Parse/DeclSpec.h
+++ b/include/clang/Parse/DeclSpec.h
@@ -561,7 +561,10 @@ struct DeclaratorChunk {
/// For now, sema will catch these as invalid.
/// The type qualifiers: const/volatile/restrict.
unsigned TypeQuals : 3;
- void destroy() {}
+ AttributeList *AttrList;
+ void destroy() {
+ delete AttrList;
+ }
};
struct MemberPointerTypeInfo {
@@ -617,7 +620,7 @@ struct DeclaratorChunk {
case MemberPointer: return Mem.AttrList;
case Array: return 0;
case Function: return 0;
- case BlockPointer: return 0; // FIXME: Do blocks have attr list?
+ case BlockPointer: return Cls.AttrList;
}
}
@@ -672,12 +675,13 @@ struct DeclaratorChunk {
/// getBlockPointer - Return a DeclaratorChunk for a block.
///
- static DeclaratorChunk getBlockPointer(unsigned TypeQuals,
- SourceLocation Loc) {
+ static DeclaratorChunk getBlockPointer(unsigned TypeQuals, SourceLocation Loc,
+ AttributeList *AL) {
DeclaratorChunk I;
I.Kind = BlockPointer;
I.Loc = Loc;
I.Cls.TypeQuals = TypeQuals;
+ I.Cls.AttrList = AL;
return I;
}
diff --git a/lib/Parse/ParseDecl.cpp b/lib/Parse/ParseDecl.cpp
index 55355880b1..938e965556 100644
--- a/lib/Parse/ParseDecl.cpp
+++ b/lib/Parse/ParseDecl.cpp
@@ -1876,7 +1876,7 @@ void Parser::ParseDeclaratorInternal(Declarator &D,
else
// Remember that we parsed a Block type, and remember the type-quals.
D.AddTypeInfo(DeclaratorChunk::getBlockPointer(DS.getTypeQualifiers(),
- Loc),
+ Loc, DS.TakeAttributes()),
SourceLocation());
} else {
// Is a reference
diff --git a/test/CodeGenObjC/blocks-1.m b/test/CodeGenObjC/blocks-1.m
index e343a58ee5..2b4f8faeb8 100644
--- a/test/CodeGenObjC/blocks-1.m
+++ b/test/CodeGenObjC/blocks-1.m
@@ -1,13 +1,13 @@
// RUN: clang-cc %s -emit-llvm -o %t -fobjc-gc -fblocks -triple i386-apple-darwin10 &&
-// RUN: grep "_Block_object_dispose" %t | count 4 &&
-// RUN: grep "__copy_helper_block_" %t | count 2 &&
-// RUN: grep "__destroy_helper_block_" %t | count 2 &&
+// RUN: grep "_Block_object_dispose" %t | count 6 &&
+// RUN: grep "__copy_helper_block_" %t | count 4 &&
+// RUN: grep "__destroy_helper_block_" %t | count 4 &&
// RUN: grep "__Block_byref_id_object_copy_" %t | count 2 &&
// RUN: grep "__Block_byref_id_object_dispose_" %t | count 2 &&
// RUN: grep "i32 135)" %t | count 0 &&
-// RUN: grep "_Block_object_assign" %t | count 3 &&
+// RUN: grep "_Block_object_assign" %t | count 4 &&
// RUN: grep "objc_read_weak" %t | count 2 &&
-// RUN: grep "objc_assign_weak" %t | count 2
+// RUN: grep "objc_assign_weak" %t | count 3
@interface NSDictionary @end
@@ -24,3 +24,10 @@ void foo() {
l = weakSelf;
weakSelf = l;
}
+
+void (^__weak b)(void);
+
+void test2() {
+ __block int i = 0;
+ b = ^ { ++i; };
+}