summaryrefslogtreecommitdiffstats
path: root/test/CodeGenObjC
diff options
context:
space:
mode:
Diffstat (limited to 'test/CodeGenObjC')
-rw-r--r--test/CodeGenObjC/2008-10-3-EhValue.m2
-rw-r--r--test/CodeGenObjC/arc-arm.m20
-rw-r--r--test/CodeGenObjC/arc-block-ivar-layout.m60
-rw-r--r--test/CodeGenObjC/arc-blocks.m133
-rw-r--r--test/CodeGenObjC/arc-captured-32bit-block-var-layout.m425
-rw-r--r--test/CodeGenObjC/arc-captured-block-var-inlined-layout.m112
-rw-r--r--test/CodeGenObjC/arc-captured-block-var-layout.m425
-rw-r--r--test/CodeGenObjC/arc-exceptions.m5
-rw-r--r--test/CodeGenObjC/arc-foreach.m8
-rw-r--r--test/CodeGenObjC/arc-ivar-layout.m1
-rw-r--r--test/CodeGenObjC/arc-no-runtime.m4
-rw-r--r--test/CodeGenObjC/arc-property.m76
-rw-r--r--test/CodeGenObjC/arc-related-result-type.m10
-rw-r--r--test/CodeGenObjC/arc.m9
-rw-r--r--test/CodeGenObjC/atomic-aggregate-property.m11
-rw-r--r--test/CodeGenObjC/attr-minsize.m12
-rw-r--r--test/CodeGenObjC/block-var-layout.m6
-rw-r--r--test/CodeGenObjC/builtin-memfns.m10
-rw-r--r--test/CodeGenObjC/category-super-class-meth.m32
-rw-r--r--test/CodeGenObjC/debug-info-crash-2.m2
-rw-r--r--test/CodeGenObjC/debug-info-fwddecl.m2
-rw-r--r--test/CodeGenObjC/debug-info-impl.m2
-rw-r--r--test/CodeGenObjC/debug-info-ivars.m24
-rw-r--r--test/CodeGenObjC/debug-info-pubtypes.m4
-rw-r--r--test/CodeGenObjC/debug-info-self.m8
-rw-r--r--test/CodeGenObjC/exceptions.m4
-rw-r--r--test/CodeGenObjC/gnu-exceptions.m2
-rw-r--r--test/CodeGenObjC/ivar-layout-64.m52
-rw-r--r--test/CodeGenObjC/mrr-captured-block-var-inlined-layout.m65
-rw-r--r--test/CodeGenObjC/newproperty-nested-synthesis-1.m1
-rw-r--r--test/CodeGenObjC/objc-arc-container-subscripting.m5
-rw-r--r--test/CodeGenObjC/objc2-ivar-assign.m3
-rw-r--r--test/CodeGenObjC/optimized-setter-ios-device.m33
-rw-r--r--test/CodeGenObjC/optimized-setter.m3
-rw-r--r--test/CodeGenObjC/prop-metadata-gnu.m15
-rw-r--r--test/CodeGenObjC/property.m5
-rw-r--r--test/CodeGenObjC/synchronized.m8
-rw-r--r--test/CodeGenObjC/synthesize_ivar-cont-class.m3
-rw-r--r--test/CodeGenObjC/synthesize_ivar.m3
-rw-r--r--test/CodeGenObjC/undefined-protocol.m3
-rw-r--r--test/CodeGenObjC/unoptimized-setter.m32
41 files changed, 1501 insertions, 139 deletions
diff --git a/test/CodeGenObjC/2008-10-3-EhValue.m b/test/CodeGenObjC/2008-10-3-EhValue.m
index 0ed0d89..bc4dfdb 100644
--- a/test/CodeGenObjC/2008-10-3-EhValue.m
+++ b/test/CodeGenObjC/2008-10-3-EhValue.m
@@ -1,4 +1,4 @@
-// RUN: %clang -fexceptions -S -emit-llvm %s -o /dev/null
+// RUN: %clang -fexceptions -fobjc-exceptions -S -emit-llvm %s -o /dev/null
@interface Object {
@public
diff --git a/test/CodeGenObjC/arc-arm.m b/test/CodeGenObjC/arc-arm.m
index 23da3be..2ab8cb6 100644
--- a/test/CodeGenObjC/arc-arm.m
+++ b/test/CodeGenObjC/arc-arm.m
@@ -13,8 +13,24 @@ void test1(void) {
// CHECK-NEXT: call void asm sideeffect "mov\09r7, r7
// CHECK-NEXT: [[T1:%.*]] = call i8* @objc_retainAutoreleasedReturnValue(i8* [[T0]])
// CHECK-NEXT: store i8* [[T1]],
- // CHECK-NEXT: load
- // CHECK-NEXT: call void @objc_release
+ // CHECK-NEXT: call void @objc_storeStrong(
// CHECK-NEXT: ret void
id x = test1_helper();
}
+
+// rdar://problem/12133032
+@class A;
+A *test2(void) {
+ extern A *test2_helper(void);
+ // CHECK: [[T0:%.*]] = call arm_aapcscc [[A:%.*]]* @test2_helper()
+ // CHECK-NEXT: ret [[A]]* [[T0]]
+ return test2_helper();
+}
+
+id test3(void) {
+ extern A *test3_helper(void);
+ // CHECK: [[T0:%.*]] = call arm_aapcscc [[A:%.*]]* @test3_helper()
+ // CHECK-NEXT: [[T1:%.*]] = bitcast [[A]]* [[T0]] to i8*
+ // CHECK-NEXT: ret i8* [[T1]]
+ return test3_helper();
+}
diff --git a/test/CodeGenObjC/arc-block-ivar-layout.m b/test/CodeGenObjC/arc-block-ivar-layout.m
deleted file mode 100644
index 6c82f29..0000000
--- a/test/CodeGenObjC/arc-block-ivar-layout.m
+++ /dev/null
@@ -1,60 +0,0 @@
-// RUN: %clang_cc1 -fblocks -fobjc-arc -fobjc-runtime-has-weak -triple x86_64-apple-darwin -O0 -emit-llvm %s -o %t-64.s
-// RUN: FileCheck -check-prefix LP64 --input-file=%t-64.s %s
-// rdar://8991729
-
-__weak id wid;
-void x(id y) {}
-void y(int a) {}
-
-extern id opaque_id();
-
-void f() {
- __block int byref_int = 0;
- char ch = 'a';
- char ch1 = 'b';
- char ch2 = 'c';
- short sh = 2;
- const id bar = (id) opaque_id();
- id baz = 0;
- __strong id strong_void_sta;
- __block id byref_bab = (id)0;
- __block id bl_var1;
- int i; double dob;
-
-// The patterns here are a sequence of bytes, each saying first how
-// many sizeof(void*) chunks to skip (high nibble) and then how many
-// to scan (low nibble). A zero byte says that we've reached the end
-// of the pattern.
-//
-// All of these patterns start with 01 3x because the block header on
-// LP64 consists of an isa pointer (which we're supposed to scan for
-// some reason) followed by three words (2 ints, a function pointer,
-// and a descriptor pointer).
-
-// Test 1
-// byref int, short, char, char, char, id, id, strong id, byref id
-// 01 35 10 00
-// CHECK-LP64: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [4 x i8] c"\015\10\00"
- void (^b)() = ^{
- byref_int = sh + ch+ch1+ch2 ;
- x(bar);
- x(baz);
- x((id)strong_void_sta);
- x(byref_bab);
- };
- b();
-
-// Test 2
-// byref int, short, char, char, char, id, id, strong id, byref void*, byref id
-// 01 36 10 00
-// CHECK-LP64: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [4 x i8] c"\016\10\00"
- void (^c)() = ^{
- byref_int = sh + ch+ch1+ch2 ;
- x(bar);
- x(baz);
- x((id)strong_void_sta);
- x(wid);
- bl_var1 = 0;
- x(byref_bab);
- };
-}
diff --git a/test/CodeGenObjC/arc-blocks.m b/test/CodeGenObjC/arc-blocks.m
index 2326bce..e776517 100644
--- a/test/CodeGenObjC/arc-blocks.m
+++ b/test/CodeGenObjC/arc-blocks.m
@@ -1,4 +1,5 @@
// RUN: %clang_cc1 -triple x86_64-apple-darwin10 -emit-llvm -fblocks -fobjc-arc -fobjc-runtime-has-weak -O2 -disable-llvm-optzns -o - %s | FileCheck %s
+// RUN: %clang_cc1 -triple x86_64-apple-darwin10 -emit-llvm -fblocks -fobjc-arc -fobjc-runtime-has-weak -o - %s | FileCheck -check-prefix=CHECK-UNOPT %s
// This shouldn't crash.
void test0(id (^maker)(void)) {
@@ -41,6 +42,24 @@ void test2(id x) {
// CHECK-NEXT: ret void
extern void test2_helper(id (^)(void));
test2_helper(^{ return x; });
+
+// CHECK: define internal void @__copy_helper_block_
+// CHECK: [[T0:%.*]] = load i8**
+// CHECK-NEXT: [[SRC:%.*]] = bitcast i8* [[T0]] to [[BLOCK_T]]*
+// CHECK-NEXT: [[T0:%.*]] = load i8**
+// CHECK-NEXT: [[DST:%.*]] = bitcast i8* [[T0]] to [[BLOCK_T]]*
+// CHECK-NEXT: [[T0:%.*]] = getelementptr inbounds [[BLOCK_T]]* [[SRC]], i32 0, i32 5
+// CHECK-NEXT: [[T1:%.*]] = load i8** [[T0]]
+// CHECK-NEXT: [[T2:%.*]] = call i8* @objc_retain(i8* [[T1]]) nounwind
+// CHECK-NEXT: ret void
+
+// CHECK: define internal void @__destroy_helper_block_
+// CHECK: [[T0:%.*]] = load i8**
+// CHECK-NEXT: [[T1:%.*]] = bitcast i8* [[T0]] to [[BLOCK_T]]*
+// CHECK-NEXT: [[T2:%.*]] = getelementptr inbounds [[BLOCK_T]]* [[T1]], i32 0, i32 5
+// CHECK-NEXT: [[T3:%.*]] = load i8** [[T2]]
+// CHECK-NEXT: call void @objc_release(i8* [[T3]])
+// CHECK-NEXT: ret void
}
void test3(void (^sink)(id*)) {
@@ -99,8 +118,8 @@ void test4(void) {
// CHECK-NEXT: [[T1:%.*]] = call i8* @objc_retainAutoreleasedReturnValue(i8* [[T0]])
// CHECK-NEXT: store i8* [[T1]], i8** [[SLOT]]
// CHECK-NEXT: [[SLOT:%.*]] = getelementptr inbounds [[BYREF_T]]* [[VAR]], i32 0, i32 6
- // 0x42000000 - has signature, copy/dispose helpers
- // CHECK: store i32 1107296256,
+ // 0x42800000 - has signature, copy/dispose helpers, as well as BLOCK_HAS_EXTENDED_LAYOUT
+ // CHECK: store i32 -1040187392,
// CHECK: [[T0:%.*]] = bitcast [[BYREF_T]]* [[VAR]] to i8*
// CHECK-NEXT: store i8* [[T0]], i8**
// CHECK: call void @test4_helper(
@@ -151,8 +170,8 @@ void test5(void) {
// CHECK-NEXT: [[T1:%.*]] = call i8* @objc_retainAutoreleasedReturnValue(i8* [[T0]])
// CHECK-NEXT: store i8* [[T1]], i8** [[VAR]],
// CHECK-NEXT: call void @objc_release(i8* [[T1]])
- // 0x40000000 - has signature but no copy/dispose
- // CHECK: store i32 1073741824, i32*
+ // 0x40800000 - has signature but no copy/dispose, as well as BLOCK_HAS_EXTENDED_LAYOUT
+ // CHECK: store i32 -1073741824, i32*
// CHECK: [[CAPTURE:%.*]] = getelementptr inbounds [[BLOCK_T]]* [[BLOCK]], i32 0, i32 5
// CHECK-NEXT: [[T0:%.*]] = load i8** [[VAR]]
// CHECK-NEXT: store i8* [[T0]], i8** [[CAPTURE]]
@@ -179,8 +198,8 @@ void test6(void) {
// CHECK-NEXT: call i8* @objc_initWeak(i8** [[SLOT]], i8* [[T1]])
// CHECK-NEXT: call void @objc_release(i8* [[T1]])
// CHECK-NEXT: [[SLOT:%.*]] = getelementptr inbounds [[BYREF_T]]* [[VAR]], i32 0, i32 6
- // 0x42000000 - has signature, copy/dispose helpers
- // CHECK: store i32 1107296256,
+ // 0x42800000 - has signature, copy/dispose helpers, as well as BLOCK_HAS_EXTENDED_LAYOUT
+ // CHECK: store i32 -1040187392,
// CHECK: [[T0:%.*]] = bitcast [[BYREF_T]]* [[VAR]] to i8*
// CHECK-NEXT: store i8* [[T0]], i8**
// CHECK: call void @test6_helper(
@@ -228,8 +247,8 @@ void test7(void) {
// CHECK-NEXT: [[T1:%.*]] = call i8* @objc_retainAutoreleasedReturnValue(i8* [[T0]])
// CHECK-NEXT: call i8* @objc_initWeak(i8** [[VAR]], i8* [[T1]])
// CHECK-NEXT: call void @objc_release(i8* [[T1]])
- // 0x42000000 - has signature, copy/dispose helpers
- // CHECK: store i32 1107296256,
+ // 0x42800000 - has signature, copy/dispose helpers, as well as BLOCK_HAS_EXTENDED_LAYOUT
+ // CHECK: store i32 -1040187392,
// CHECK: [[SLOT:%.*]] = getelementptr inbounds [[BLOCK_T]]* [[BLOCK]], i32 0, i32 5
// CHECK-NEXT: [[T0:%.*]] = call i8* @objc_loadWeak(i8** [[VAR]])
// CHECK-NEXT: call i8* @objc_initWeak(i8** [[SLOT]], i8* [[T0]])
@@ -359,7 +378,7 @@ void test10a(void) {
// CHECK: [[T0:%.*]] = load i8** {{%.*}}
// CHECK-NEXT: [[T1:%.*]] = bitcast i8* [[T0]] to [[BYREF_T]]*
// CHECK-NEXT: [[T2:%.*]] = getelementptr inbounds [[BYREF_T]]* [[T1]], i32 0, i32 6
-// CHECK-NEXT: [[T3:%.*]] = load void ()** [[T2]], align 8
+// CHECK-NEXT: [[T3:%.*]] = load void ()** [[T2]]
// CHECK-NEXT: [[T4:%.*]] = bitcast void ()* [[T3]] to i8*
// CHECK-NEXT: call void @objc_release(i8* [[T4]])
// CHECK-NEXT: ret void
@@ -532,3 +551,99 @@ void test16() {
// CHECK-NEXT: [[SLOTREL:%.*]] = getelementptr inbounds [[BLOCK_T]]* [[BLOCK]], i32 0, i32 5
// CHECK-NEXT: store void ()* null, void ()** [[BLKVAR]], align 8
}
+
+// rdar://12151005
+//
+// This is an intentional exception to our conservative jump-scope
+// checking for full-expressions containing block literals with
+// non-trivial cleanups: if the block literal appears in the operand
+// of a return statement, there's no need to extend its lifetime.
+id (^test17(id self, int which))(void) {
+ switch (which) {
+ case 1: return ^{ return self; };
+ case 0: return ^{ return self; };
+ }
+ return (void*) 0;
+}
+// CHECK: define i8* ()* @test17(
+// CHECK: [[RET:%.*]] = alloca i8* ()*, align
+// CHECK-NEXT: [[SELF:%.*]] = alloca i8*,
+// CHECK: [[B0:%.*]] = alloca [[BLOCK:<.*>]], align
+// CHECK: [[B1:%.*]] = alloca [[BLOCK]], align
+// CHECK: [[T0:%.*]] = call i8* @objc_retain(i8*
+// CHECK-NEXT: store i8* [[T0]], i8** [[SELF]], align
+// CHECK-NOT: objc_retain
+// CHECK-NOT: objc_release
+// CHECK: [[DESTROY:%.*]] = getelementptr inbounds [[BLOCK]]* [[B0]], i32 0, i32 5
+// CHECK-NOT: objc_retain
+// CHECK-NOT: objc_release
+// CHECK: [[T0:%.*]] = getelementptr inbounds [[BLOCK]]* [[B0]], i32 0, i32 5
+// CHECK-NEXT: [[T1:%.*]] = load i8** [[SELF]], align
+// CHECK-NEXT: [[T2:%.*]] = call i8* @objc_retain(i8* [[T1]])
+// CHECK-NEXT: store i8* [[T2]], i8** [[T0]],
+// CHECK-NEXT: [[T0:%.*]] = bitcast [[BLOCK]]* [[B0]] to i8* ()*
+// CHECK-NEXT: [[T1:%.*]] = bitcast i8* ()* [[T0]] to i8*
+// CHECK-NEXT: [[T2:%.*]] = call i8* @objc_retainBlock(i8* [[T1]])
+// CHECK-NEXT: [[T3:%.*]] = bitcast i8* [[T2]] to i8* ()*
+// CHECK-NEXT: store i8* ()* [[T3]], i8* ()** [[RET]]
+// CHECK-NEXT: [[T0:%.*]] = load i8** [[DESTROY]]
+// CHECK-NEXT: call void @objc_release(i8* [[T0]])
+// CHECK-NEXT: store i32
+// CHECK-NEXT: br label
+// CHECK-NOT: objc_retain
+// CHECK-NOT: objc_release
+// CHECK: [[DESTROY:%.*]] = getelementptr inbounds [[BLOCK]]* [[B1]], i32 0, i32 5
+// CHECK-NOT: objc_retain
+// CHECK-NOT: objc_release
+// CHECK: [[T0:%.*]] = getelementptr inbounds [[BLOCK]]* [[B1]], i32 0, i32 5
+// CHECK-NEXT: [[T1:%.*]] = load i8** [[SELF]], align
+// CHECK-NEXT: [[T2:%.*]] = call i8* @objc_retain(i8* [[T1]])
+// CHECK-NEXT: store i8* [[T2]], i8** [[T0]],
+// CHECK-NEXT: [[T0:%.*]] = bitcast [[BLOCK]]* [[B1]] to i8* ()*
+// CHECK-NEXT: [[T1:%.*]] = bitcast i8* ()* [[T0]] to i8*
+// CHECK-NEXT: [[T2:%.*]] = call i8* @objc_retainBlock(i8* [[T1]])
+// CHECK-NEXT: [[T3:%.*]] = bitcast i8* [[T2]] to i8* ()*
+// CHECK-NEXT: store i8* ()* [[T3]], i8* ()** [[RET]]
+// CHECK-NEXT: [[T0:%.*]] = load i8** [[DESTROY]]
+// CHECK-NEXT: call void @objc_release(i8* [[T0]])
+// CHECK-NEXT: store i32
+// CHECK-NEXT: br label
+
+void test18(id x) {
+// CHECK-UNOPT: define void @test18(
+// CHECK-UNOPT: [[X:%.*]] = alloca i8*,
+// CHECK-UNOPT-NEXT: [[BLOCK:%.*]] = alloca [[BLOCK_T:<{.*}>]],
+// CHECK-UNOPT-NEXT: [[PARM:%.*]] = call i8* @objc_retain(i8* {{%.*}})
+// CHECK-UNOPT-NEXT: store i8* [[PARM]], i8** [[X]]
+// CHECK-UNOPT-NEXT: [[SLOTREL:%.*]] = getelementptr inbounds [[BLOCK_T]]* [[BLOCK]], i32 0, i32 5
+// CHECK-UNOPT: [[SLOT:%.*]] = getelementptr inbounds [[BLOCK_T]]* [[BLOCK]], i32 0, i32 5
+// CHECK-UNOPT-NEXT: [[T0:%.*]] = load i8** [[X]],
+// CHECK-UNOPT-NEXT: [[T1:%.*]] = call i8* @objc_retain(i8* [[T0]])
+// CHECK-UNOPT-NEXT: store i8* [[T1]], i8** [[SLOT]],
+// CHECK-UNOPT-NEXT: bitcast
+// CHECK-UNOPT-NEXT: call void @test18_helper(
+// CHECK-UNOPT-NEXT: call void @objc_storeStrong(i8** [[SLOTREL]], i8* null) nounwind
+// CHECK-UNOPT-NEXT: call void @objc_storeStrong(i8** [[X]], i8* null) nounwind
+// CHECK-UNOPT-NEXT: ret void
+ extern void test18_helper(id (^)(void));
+ test18_helper(^{ return x; });
+
+// CHECK-UNOPT: define internal void @__copy_helper_block_
+// CHECK-UNOPT: [[T0:%.*]] = load i8**
+// CHECK-UNOPT-NEXT: [[SRC:%.*]] = bitcast i8* [[T0]] to [[BLOCK_T]]*
+// CHECK-UNOPT-NEXT: [[T0:%.*]] = load i8**
+// CHECK-UNOPT-NEXT: [[DST:%.*]] = bitcast i8* [[T0]] to [[BLOCK_T]]*
+// CHECK-UNOPT-NEXT: [[T0:%.*]] = getelementptr inbounds [[BLOCK_T]]* [[SRC]], i32 0, i32 5
+// CHECK-UNOPT-NEXT: [[T1:%.*]] = getelementptr inbounds [[BLOCK_T]]* [[DST]], i32 0, i32 5
+// CHECK-UNOPT-NEXT: [[T2:%.*]] = load i8** [[T0]]
+// CHECK-UNOPT-NEXT: store i8* null, i8** [[T1]]
+// CHECK-UNOPT-NEXT: call void @objc_storeStrong(i8** [[T1]], i8* [[T2]]) nounwind
+// CHECK-UNOPT-NEXT: ret void
+
+// CHECK-UNOPT: define internal void @__destroy_helper_block_
+// CHECK-UNOPT: [[T0:%.*]] = load i8**
+// CHECK-UNOPT-NEXT: [[T1:%.*]] = bitcast i8* [[T0]] to [[BLOCK_T]]*
+// CHECK-UNOPT-NEXT: [[T2:%.*]] = getelementptr inbounds [[BLOCK_T]]* [[T1]], i32 0, i32 5
+// CHECK-UNOPT-NEXT: call void @objc_storeStrong(i8** [[T2]], i8* null)
+// CHECK-UNOPT-NEXT: ret void
+}
diff --git a/test/CodeGenObjC/arc-captured-32bit-block-var-layout.m b/test/CodeGenObjC/arc-captured-32bit-block-var-layout.m
new file mode 100644
index 0000000..6c72138
--- /dev/null
+++ b/test/CodeGenObjC/arc-captured-32bit-block-var-layout.m
@@ -0,0 +1,425 @@
+// RUN: %clang_cc1 -fblocks -fobjc-arc -fobjc-runtime-has-weak -triple i386-apple-darwin -O0 -emit-llvm %s -o %t-64.s
+// RUN: FileCheck --input-file=%t-64.s %s
+// rdar://12184410
+
+void x(id y) {}
+void y(int a) {}
+
+extern id opaque_id();
+
+void f() {
+ __weak id wid;
+ __block int byref_int = 0;
+ char ch = 'a';
+ char ch1 = 'b';
+ char ch2 = 'c';
+ short sh = 2;
+ const id bar = (id) opaque_id();
+ id baz = 0;
+ __strong id strong_void_sta;
+ __block id byref_bab = (id)0;
+ __block id bl_var1;
+ int i; double dob;
+
+// The patterns here are a sequence of bytes, each saying first how
+// many sizeof(void*) chunks to skip (high nibble) and then how many
+// to scan (low nibble). A zero byte says that we've reached the end
+// of the pattern.
+//
+// All of these patterns start with 01 3x because the block header on
+// LP64 consists of an isa pointer (which we're supposed to scan for
+// some reason) followed by three words (2 ints, a function pointer,
+// and a descriptor pointer).
+
+// Test 1
+// block variable layout: BL_BYREF:1, BL_STRONG:3, BL_BYREF:1, BL_OPERATOR:0
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [4 x i8] c"@2@\00"
+ void (^b)() = ^{
+ byref_int = sh + ch+ch1+ch2 ;
+ x(bar);
+ x(baz);
+ x((id)strong_void_sta);
+ x(byref_bab);
+ };
+ b();
+
+// Test 2
+// block variable layout: BL_BYREF:1, BL_STRONG:3, BL_WEAK:1, BL_BYREF:2, BL_OPERATOR:0
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [5 x i8] c"@2PA\00"
+ void (^c)() = ^{
+ byref_int = sh + ch+ch1+ch2 ;
+ x(bar);
+ x(baz);
+ x((id)strong_void_sta);
+ x(wid);
+ bl_var1 = 0;
+ x(byref_bab);
+ };
+}
+
+@class NSString, NSNumber;
+void g() {
+ NSString *foo;
+ NSNumber *bar;
+ unsigned int bletch;
+ __weak id weak_delegate;
+ unsigned int i;
+ NSString *y;
+ NSString *z;
+// block variable layout: BL_STRONG:2, BL_WEAK:1, BL_STRONG:2, BL_OPERATOR:0
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [5 x i8] c"!1P1\00"
+ void (^c)() = ^{
+ int j = i + bletch;
+ x(foo);
+ x(bar);
+ x(weak_delegate);
+ x(y);
+ x(z);
+ };
+ c();
+}
+
+// Test 5 (unions/structs and their nesting):
+void h() {
+ struct S5 {
+ int i1;
+ __unsafe_unretained id o1;
+ struct V {
+ int i2;
+ __unsafe_unretained id o2;
+ } v1;
+ int i3;
+ union UI {
+ void * i1;
+ __unsafe_unretained id o1;
+ int i3;
+ __unsafe_unretained id o3;
+ }ui;
+ };
+
+ union U {
+ void * i1;
+ __unsafe_unretained id o1;
+ int i3;
+ __unsafe_unretained id o3;
+ }ui;
+
+ struct S5 s2;
+ union U u2;
+ __block id block_id;
+
+/**
+block variable layout: BL_NON_OBJECT_WORD:1, BL_UNRETAINE:1, BL_NON_OBJECT_WORD:1,
+ BL_UNRETAINE:1, BL_NON_OBJECT_WORD:3, BL_BYREF:1, BL_OPERATOR:0
+*/
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [7 x i8] c" ` `\22@\00"
+ void (^c)() = ^{
+ x(s2.ui.o1);
+ x(u2.o1);
+ block_id = 0;
+ };
+ c();
+}
+
+// Test for array of stuff.
+void arr1() {
+ struct S {
+ __unsafe_unretained id unsafe_unretained_var[4];
+ } imported_s;
+
+// block variable layout: BL_UNRETAINE:4, BL_OPERATOR:0
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [2 x i8] c"c\00"
+ void (^c)() = ^{
+ x(imported_s.unsafe_unretained_var[2]);
+ };
+
+ c();
+}
+
+// Test2 for array of stuff.
+void arr2() {
+ struct S {
+ int a;
+ __unsafe_unretained id unsafe_unretained_var[4];
+ } imported_s;
+
+// block variable layout: BL_NON_OBJECT_WORD:1, BL_UNRETAINE:4, BL_OPERATOR:0
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [3 x i8] c" c\00"
+ void (^c)() = ^{
+ x(imported_s.unsafe_unretained_var[2]);
+ };
+
+ c();
+}
+
+// Test3 for array of stuff.
+void arr3() {
+ struct S {
+ int a;
+ __unsafe_unretained id unsafe_unretained_var[0];
+ } imported_s;
+
+// block variable layout: BL_OPERATOR:0
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [1 x i8] zeroinitializer
+ void (^c)() = ^{
+ int i = imported_s.a;
+ };
+
+ c();
+}
+
+
+// Test4 for array of stuff.
+@class B;
+void arr4() {
+ struct S {
+ struct s0 {
+ __unsafe_unretained id s_f0;
+ __unsafe_unretained id s_f1;
+ } f0;
+
+ __unsafe_unretained id f1;
+
+ struct s1 {
+ int *f0;
+ __unsafe_unretained B *f1;
+ } f4[2][2];
+ } captured_s;
+
+/**
+block variable layout: BL_UNRETAINE:3,
+ BL_NON_OBJECT_WORD:1, BL_UNRETAINE:1,
+ BL_NON_OBJECT_WORD:1, BL_UNRETAINE:1,
+ BL_NON_OBJECT_WORD:1, BL_UNRETAINE:1,
+ BL_NON_OBJECT_WORD:1, BL_UNRETAINE:1,
+ BL_OPERATOR:0
+*/
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [10 x i8]
+ void (^c)() = ^{
+ id i = captured_s.f0.s_f1;
+ };
+
+ c();
+}
+
+// Test1 bitfield in cpatured aggregate.
+void bf1() {
+ struct S {
+ int flag : 25;
+ int flag1: 7;
+ int flag2 :1;
+ int flag3: 7;
+ int flag4: 24;
+ } s;
+
+// block variable layout: BL_OPERATOR:0
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [1 x i8] zeroinitializer
+ int (^c)() = ^{
+ return s.flag;
+ };
+ c();
+}
+
+// Test2 bitfield in cpatured aggregate.
+void bf2() {
+ struct S {
+ int flag : 1;
+ } s;
+
+// block variable layout: BL_OPERATOR:0
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [1 x i8] zeroinitializer
+ int (^c)() = ^{
+ return s.flag;
+ };
+ c();
+}
+
+// Test3 bitfield in cpatured aggregate.
+void bf3() {
+
+ struct {
+ unsigned short _reserved : 16;
+
+ unsigned char _draggedNodesAreDeletable: 1;
+ unsigned char _draggedOutsideOutlineView : 1;
+ unsigned char _adapterRespondsTo_addRootPaths : 1;
+ unsigned char _adapterRespondsTo_moveDataNodes : 1;
+ unsigned char _adapterRespondsTo_removeRootDataNode : 1;
+ unsigned char _adapterRespondsTo_doubleClickDataNode : 1;
+ unsigned char _adapterRespondsTo_selectDataNode : 1;
+ unsigned char _adapterRespondsTo_textDidEndEditing : 1;
+ unsigned char _adapterRespondsTo_updateAndSaveRoots : 1;
+ unsigned char _adapterRespondsTo_askToDeleteRootNodes : 1;
+ unsigned char _adapterRespondsTo_contextMenuForSelectedNodes : 1;
+ unsigned char _adapterRespondsTo_pasteboardFilenamesForNodes : 1;
+ unsigned char _adapterRespondsTo_writeItemsToPasteboard : 1;
+ unsigned char _adapterRespondsTo_writeItemsToPasteboardXXXX : 1;
+
+ unsigned int _filler : 32;
+ } _flags;
+
+// block variable layout: BL_OPERATOR:0
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [1 x i8] zeroinitializer
+ unsigned char (^c)() = ^{
+ return _flags._draggedNodesAreDeletable;
+ };
+
+ c();
+}
+
+// Test4 unnamed bitfield
+void bf4() {
+
+ struct {
+ unsigned short _reserved : 16;
+
+ unsigned char _draggedNodesAreDeletable: 1;
+ unsigned char _draggedOutsideOutlineView : 1;
+ unsigned char _adapterRespondsTo_addRootPaths : 1;
+ unsigned char _adapterRespondsTo_moveDataNodes : 1;
+ unsigned char _adapterRespondsTo_removeRootDataNode : 1;
+ unsigned char _adapterRespondsTo_doubleClickDataNode : 1;
+ unsigned char _adapterRespondsTo_selectDataNode : 1;
+ unsigned char _adapterRespondsTo_textDidEndEditing : 1;
+
+ unsigned long long : 64;
+
+ unsigned char _adapterRespondsTo_updateAndSaveRoots : 1;
+ unsigned char _adapterRespondsTo_askToDeleteRootNodes : 1;
+ unsigned char _adapterRespondsTo_contextMenuForSelectedNodes : 1;
+ unsigned char _adapterRespondsTo_pasteboardFilenamesForNodes : 1;
+ unsigned char _adapterRespondsTo_writeItemsToPasteboard : 1;
+ unsigned char _adapterRespondsTo_writeItemsToPasteboardXXXX : 1;
+
+ unsigned int _filler : 32;
+ } _flags;
+
+// block variable layout: BL_OPERATOR:0
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [1 x i8] zeroinitializer
+ unsigned char (^c)() = ^{
+ return _flags._draggedNodesAreDeletable;
+ };
+
+ c();
+}
+
+
+
+// Test5 unnamed bitfield.
+void bf5() {
+ struct {
+ unsigned char flag : 1;
+ unsigned int : 32;
+ unsigned char flag1 : 1;
+ } _flags;
+
+// block variable layout: BL_OPERATOR:0
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [1 x i8] zeroinitializer
+ unsigned char (^c)() = ^{
+ return _flags.flag;
+ };
+
+ c();
+}
+
+
+// Test6 0 length bitfield.
+void bf6() {
+ struct {
+ unsigned char flag : 1;
+ unsigned int : 0;
+ unsigned char flag1 : 1;
+ } _flags;
+
+// block variable layout: BL_OPERATOR:0
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [1 x i8] zeroinitializer
+ unsigned char (^c)() = ^{
+ return _flags.flag;
+ };
+
+ c();
+}
+
+// Test7 large number of captured variables.
+void Test7() {
+ __weak id wid;
+ __weak id wid1, wid2, wid3, wid4;
+ __weak id wid5, wid6, wid7, wid8;
+ __weak id wid9, wid10, wid11, wid12;
+ __weak id wid13, wid14, wid15, wid16;
+ const id bar = (id) opaque_id();
+//block variable layout: BL_STRONG:1, BL_WEAK:16, BL_OPERATOR:0
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [3 x i8] c"0_\00"
+ void (^b)() = ^{
+ x(bar);
+ x(wid1);
+ x(wid2);
+ x(wid3);
+ x(wid4);
+ x(wid5);
+ x(wid6);
+ x(wid7);
+ x(wid8);
+ x(wid9);
+ x(wid10);
+ x(wid11);
+ x(wid12);
+ x(wid13);
+ x(wid14);
+ x(wid15);
+ x(wid16);
+ };
+}
+
+
+// Test 8 very large number of captured variables.
+void Test8() {
+__weak id wid;
+ __weak id wid1, wid2, wid3, wid4;
+ __weak id wid5, wid6, wid7, wid8;
+ __weak id wid9, wid10, wid11, wid12;
+ __weak id wid13, wid14, wid15, wid16;
+ __weak id w1, w2, w3, w4;
+ __weak id w5, w6, w7, w8;
+ __weak id w9, w10, w11, w12;
+ __weak id w13, w14, w15, w16;
+ const id bar = (id) opaque_id();
+// block variable layout: BL_STRONG:1, BL_WEAK:16, BL_WEAK:16, BL_WEAK:1, BL_OPERATOR:0
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [5 x i8]
+ void (^b)() = ^{
+ x(bar);
+ x(wid1);
+ x(wid2);
+ x(wid3);
+ x(wid4);
+ x(wid5);
+ x(wid6);
+ x(wid7);
+ x(wid8);
+ x(wid9);
+ x(wid10);
+ x(wid11);
+ x(wid12);
+ x(wid13);
+ x(wid14);
+ x(wid15);
+ x(wid16);
+ x(w1);
+ x(w2);
+ x(w3);
+ x(w4);
+ x(w5);
+ x(w6);
+ x(w7);
+ x(w8);
+ x(w9);
+ x(w10);
+ x(w11);
+ x(w12);
+ x(w13);
+ x(w14);
+ x(w15);
+ x(w16);
+ x(wid);
+ };
+}
diff --git a/test/CodeGenObjC/arc-captured-block-var-inlined-layout.m b/test/CodeGenObjC/arc-captured-block-var-inlined-layout.m
new file mode 100644
index 0000000..b930737
--- /dev/null
+++ b/test/CodeGenObjC/arc-captured-block-var-inlined-layout.m
@@ -0,0 +1,112 @@
+// RUN: %clang_cc1 -fblocks -fobjc-arc -fobjc-runtime-has-weak -triple x86_64-apple-darwin -O0 -emit-llvm %s -o - | FileCheck %s
+// RUN: %clang_cc1 -fblocks -fobjc-arc -fobjc-runtime-has-weak -triple i386-apple-darwin -O0 -emit-llvm %s -o - | FileCheck -check-prefix=CHECK-i386 %s
+// rdar://12184410
+
+void x(id y) {}
+void y(int a) {}
+
+extern id opaque_id();
+
+void f() {
+ __block int byref_int = 0;
+ const id bar = (id) opaque_id();
+ id baz = 0;
+ __strong id strong_void_sta;
+ __block id byref_bab = (id)0;
+ __block id bl_var1;
+
+// Inline instruction for block variable layout: 0x0100
+// CHECK: i8* getelementptr inbounds ([6 x i8]* {{@.*}}, i32 0, i32 0), i64 256 }
+// CHECK-i386: i8* getelementptr inbounds ([6 x i8]* {{@.*}}, i32 0, i32 0), i32 256 }
+ void (^b)() = ^{
+ x(bar);
+ };
+
+// Inline instruction for block variable layout: 0x0210
+// CHECK: i8* getelementptr inbounds ([6 x i8]* {{@.*}}, i32 0, i32 0), i64 528 }
+// CHECK-i386: i8* getelementptr inbounds ([6 x i8]* {{@.*}}, i32 0, i32 0), i32 528 }
+ void (^c)() = ^{
+ x(bar);
+ x(baz);
+ byref_int = 1;
+ };
+
+// Inline instruction for block variable layout: 0x0230
+// CHECK: i8* getelementptr inbounds ([6 x i8]* {{@.*}}, i32 0, i32 0), i64 560 }
+// CHECK-i386: i8* getelementptr inbounds ([6 x i8]* {{@.*}}, i32 0, i32 0), i32 560 }
+ void (^d)() = ^{
+ x(bar);
+ x(baz);
+ byref_int = 1;
+ bl_var1 = 0;
+ byref_bab = 0;
+ };
+
+// Inline instruction for block variable layout: 0x0231
+// CHECK: i8* getelementptr inbounds ([6 x i8]* {{@.*}}, i32 0, i32 0), i64 561 }
+// CHECK-i386: i8* getelementptr inbounds ([6 x i8]* {{@.*}}, i32 0, i32 0), i32 561 }
+ __weak id wid;
+ id (^e)() = ^{
+ x(bar);
+ x(baz);
+ byref_int = 1;
+ bl_var1 = 0;
+ byref_bab = 0;
+ return wid;
+ };
+
+// Inline instruction for block variable layout: 0x0235
+// CHECK: i8* getelementptr inbounds ([6 x i8]* {{@.*}}, i32 0, i32 0), i64 565 }
+// CHECK-i386: i8* getelementptr inbounds ([6 x i8]* {{@.*}}, i32 0, i32 0), i32 565 }
+ __weak id wid1, wid2, wid3, wid4;
+ id (^f)() = ^{
+ x(bar);
+ x(baz);
+ byref_int = 1;
+ bl_var1 = 0;
+ byref_bab = 0;
+ x(wid1);
+ x(wid2);
+ x(wid3);
+ x(wid4);
+ return wid;
+ };
+
+// Inline instruction for block variable layout: 0x035
+// CHECK: i8* getelementptr inbounds ([6 x i8]* {{@.*}}, i32 0, i32 0), i64 53 }
+// CHECK-i386: i8* getelementptr inbounds ([6 x i8]* {{@.*}}, i32 0, i32 0), i32 53 }
+ id (^g)() = ^{
+ byref_int = 1;
+ bl_var1 = 0;
+ byref_bab = 0;
+ x(wid1);
+ x(wid2);
+ x(wid3);
+ x(wid4);
+ return wid;
+ };
+
+// Inline instruction for block variable layout: 0x01
+// CHECK: i8* getelementptr inbounds ([6 x i8]* {{@.*}}, i32 0, i32 0), i64 1 }
+// CHECK-i386: i8* getelementptr inbounds ([6 x i8]* {{@.*}}, i32 0, i32 0), i32 1 }
+ id (^h)() = ^{
+ return wid;
+ };
+
+// Inline instruction for block variable layout: 0x020
+// CHECK: i8* getelementptr inbounds ([6 x i8]* {{@.*}}, i32 0, i32 0), i64 32 }
+// CHECK-i386: i8* getelementptr inbounds ([6 x i8]* {{@.*}}, i32 0, i32 0), i32 32 }
+ void (^ii)() = ^{
+ byref_int = 1;
+ byref_bab = 0;
+ };
+
+// Inline instruction for block variable layout: 0x0102
+// CHECK: i8* getelementptr inbounds ([6 x i8]* {{@.*}}, i32 0, i32 0), i64 258 }
+// CHECK-i386: i8* getelementptr inbounds ([6 x i8]* {{@.*}}, i32 0, i32 0), i32 258 }
+ void (^jj)() = ^{
+ x(bar);
+ x(wid1);
+ x(wid2);
+ };
+}
diff --git a/test/CodeGenObjC/arc-captured-block-var-layout.m b/test/CodeGenObjC/arc-captured-block-var-layout.m
new file mode 100644
index 0000000..77f042e
--- /dev/null
+++ b/test/CodeGenObjC/arc-captured-block-var-layout.m
@@ -0,0 +1,425 @@
+// RUN: %clang_cc1 -fblocks -fobjc-arc -fobjc-runtime-has-weak -triple x86_64-apple-darwin -O0 -emit-llvm %s -o %t-64.s
+// RUN: FileCheck -check-prefix LP64 --input-file=%t-64.s %s
+// rdar://12184410
+
+void x(id y) {}
+void y(int a) {}
+
+extern id opaque_id();
+
+void f() {
+ __weak id wid;
+ __block int byref_int = 0;
+ char ch = 'a';
+ char ch1 = 'b';
+ char ch2 = 'c';
+ short sh = 2;
+ const id bar = (id) opaque_id();
+ id baz = 0;
+ __strong id strong_void_sta;
+ __block id byref_bab = (id)0;
+ __block id bl_var1;
+ int i; double dob;
+
+// The patterns here are a sequence of bytes, each saying first how
+// many sizeof(void*) chunks to skip (high nibble) and then how many
+// to scan (low nibble). A zero byte says that we've reached the end
+// of the pattern.
+//
+// All of these patterns start with 01 3x because the block header on
+// LP64 consists of an isa pointer (which we're supposed to scan for
+// some reason) followed by three words (2 ints, a function pointer,
+// and a descriptor pointer).
+
+// Test 1
+// block variable layout: BL_BYREF:1, BL_STRONG:3, BL_BYREF:1, BL_OPERATOR:0
+// CHECK-LP64: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [4 x i8] c"@2@\00"
+ void (^b)() = ^{
+ byref_int = sh + ch+ch1+ch2 ;
+ x(bar);
+ x(baz);
+ x((id)strong_void_sta);
+ x(byref_bab);
+ };
+ b();
+
+// Test 2
+// block variable layout: BL_BYREF:1, BL_STRONG:3, BL_WEAK:1, BL_BYREF:2, BL_OPERATOR:0
+// CHECK-LP64: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [5 x i8] c"@2PA\00"
+ void (^c)() = ^{
+ byref_int = sh + ch+ch1+ch2 ;
+ x(bar);
+ x(baz);
+ x((id)strong_void_sta);
+ x(wid);
+ bl_var1 = 0;
+ x(byref_bab);
+ };
+}
+
+@class NSString, NSNumber;
+void g() {
+ NSString *foo;
+ NSNumber *bar;
+ unsigned int bletch;
+ __weak id weak_delegate;
+ unsigned int i;
+ NSString *y;
+ NSString *z;
+// block variable layout: BL_STRONG:2, BL_WEAK:1, BL_STRONG:2, BL_OPERATOR:0
+// CHECK-LP64: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [4 x i8] c"1P1\00"
+ void (^c)() = ^{
+ int j = i + bletch;
+ x(foo);
+ x(bar);
+ x(weak_delegate);
+ x(y);
+ x(z);
+ };
+ c();
+}
+
+// Test 5 (unions/structs and their nesting):
+void h() {
+ struct S5 {
+ int i1;
+ __unsafe_unretained id o1;
+ struct V {
+ int i2;
+ __unsafe_unretained id o2;
+ } v1;
+ int i3;
+ union UI {
+ void * i1;
+ __unsafe_unretained id o1;
+ int i3;
+ __unsafe_unretained id o3;
+ }ui;
+ };
+
+ union U {
+ void * i1;
+ __unsafe_unretained id o1;
+ int i3;
+ __unsafe_unretained id o3;
+ }ui;
+
+ struct S5 s2;
+ union U u2;
+ __block id block_id;
+
+/**
+block variable layout: BL_NON_OBJECT_WORD:1, BL_UNRETAINE:1, BL_NON_OBJECT_WORD:1,
+ BL_UNRETAINE:1, BL_NON_OBJECT_WORD:3, BL_BYREF:1, BL_OPERATOR:0
+*/
+// CHECK-LP64: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [7 x i8] c" ` `\22@\00"
+ void (^c)() = ^{
+ x(s2.ui.o1);
+ x(u2.o1);
+ block_id = 0;
+ };
+ c();
+}
+
+// Test for array of stuff.
+void arr1() {
+ struct S {
+ __unsafe_unretained id unsafe_unretained_var[4];
+ } imported_s;
+
+// block variable layout: BL_UNRETAINE:4, BL_OPERATOR:0
+// CHECK-LP64: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [2 x i8] c"c\00"
+ void (^c)() = ^{
+ x(imported_s.unsafe_unretained_var[2]);
+ };
+
+ c();
+}
+
+// Test2 for array of stuff.
+void arr2() {
+ struct S {
+ int a;
+ __unsafe_unretained id unsafe_unretained_var[4];
+ } imported_s;
+
+// block variable layout: BL_NON_OBJECT_WORD:1, BL_UNRETAINE:4, BL_OPERATOR:0
+// CHECK-LP64: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [3 x i8] c" c\00"
+ void (^c)() = ^{
+ x(imported_s.unsafe_unretained_var[2]);
+ };
+
+ c();
+}
+
+// Test3 for array of stuff.
+void arr3() {
+ struct S {
+ int a;
+ __unsafe_unretained id unsafe_unretained_var[0];
+ } imported_s;
+
+// block variable layout: BL_OPERATOR:0
+// CHECK-LP64: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [1 x i8] zeroinitializer
+ void (^c)() = ^{
+ int i = imported_s.a;
+ };
+
+ c();
+}
+
+
+// Test4 for array of stuff.
+@class B;
+void arr4() {
+ struct S {
+ struct s0 {
+ __unsafe_unretained id s_f0;
+ __unsafe_unretained id s_f1;
+ } f0;
+
+ __unsafe_unretained id f1;
+
+ struct s1 {
+ int *f0;
+ __unsafe_unretained B *f1;
+ } f4[2][2];
+ } captured_s;
+
+/**
+block variable layout: BL_UNRETAINE:3,
+ BL_NON_OBJECT_WORD:1, BL_UNRETAINE:1,
+ BL_NON_OBJECT_WORD:1, BL_UNRETAINE:1,
+ BL_NON_OBJECT_WORD:1, BL_UNRETAINE:1,
+ BL_NON_OBJECT_WORD:1, BL_UNRETAINE:1,
+ BL_OPERATOR:0
+*/
+// CHECK-LP64: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [10 x i8]
+ void (^c)() = ^{
+ id i = captured_s.f0.s_f1;
+ };
+
+ c();
+}
+
+// Test1 bitfield in cpatured aggregate.
+void bf1() {
+ struct S {
+ int flag : 25;
+ int flag1: 7;
+ int flag2 :1;
+ int flag3: 7;
+ int flag4: 24;
+ } s;
+
+// block variable layout: BL_OPERATOR:0
+// CHECK-LP64: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [1 x i8] zeroinitializer
+ int (^c)() = ^{
+ return s.flag;
+ };
+ c();
+}
+
+// Test2 bitfield in cpatured aggregate.
+void bf2() {
+ struct S {
+ int flag : 1;
+ } s;
+
+// block variable layout: BL_OPERATOR:0
+// CHECK-LP64: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [1 x i8] zeroinitializer
+ int (^c)() = ^{
+ return s.flag;
+ };
+ c();
+}
+
+// Test3 bitfield in cpatured aggregate.
+void bf3() {
+
+ struct {
+ unsigned short _reserved : 16;
+
+ unsigned char _draggedNodesAreDeletable: 1;
+ unsigned char _draggedOutsideOutlineView : 1;
+ unsigned char _adapterRespondsTo_addRootPaths : 1;
+ unsigned char _adapterRespondsTo_moveDataNodes : 1;
+ unsigned char _adapterRespondsTo_removeRootDataNode : 1;
+ unsigned char _adapterRespondsTo_doubleClickDataNode : 1;
+ unsigned char _adapterRespondsTo_selectDataNode : 1;
+ unsigned char _adapterRespondsTo_textDidEndEditing : 1;
+ unsigned char _adapterRespondsTo_updateAndSaveRoots : 1;
+ unsigned char _adapterRespondsTo_askToDeleteRootNodes : 1;
+ unsigned char _adapterRespondsTo_contextMenuForSelectedNodes : 1;
+ unsigned char _adapterRespondsTo_pasteboardFilenamesForNodes : 1;
+ unsigned char _adapterRespondsTo_writeItemsToPasteboard : 1;
+ unsigned char _adapterRespondsTo_writeItemsToPasteboardXXXX : 1;
+
+ unsigned int _filler : 32;
+ } _flags;
+
+// block variable layout: BL_OPERATOR:0
+// CHECK-LP64: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [1 x i8] zeroinitializer
+ unsigned char (^c)() = ^{
+ return _flags._draggedNodesAreDeletable;
+ };
+
+ c();
+}
+
+// Test4 unnamed bitfield
+void bf4() {
+
+ struct {
+ unsigned short _reserved : 16;
+
+ unsigned char _draggedNodesAreDeletable: 1;
+ unsigned char _draggedOutsideOutlineView : 1;
+ unsigned char _adapterRespondsTo_addRootPaths : 1;
+ unsigned char _adapterRespondsTo_moveDataNodes : 1;
+ unsigned char _adapterRespondsTo_removeRootDataNode : 1;
+ unsigned char _adapterRespondsTo_doubleClickDataNode : 1;
+ unsigned char _adapterRespondsTo_selectDataNode : 1;
+ unsigned char _adapterRespondsTo_textDidEndEditing : 1;
+
+ unsigned long long : 64;
+
+ unsigned char _adapterRespondsTo_updateAndSaveRoots : 1;
+ unsigned char _adapterRespondsTo_askToDeleteRootNodes : 1;
+ unsigned char _adapterRespondsTo_contextMenuForSelectedNodes : 1;
+ unsigned char _adapterRespondsTo_pasteboardFilenamesForNodes : 1;
+ unsigned char _adapterRespondsTo_writeItemsToPasteboard : 1;
+ unsigned char _adapterRespondsTo_writeItemsToPasteboardXXXX : 1;
+
+ unsigned int _filler : 32;
+ } _flags;
+
+// block variable layout: BL_OPERATOR:0
+// CHECK-LP64: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [1 x i8] zeroinitializer
+ unsigned char (^c)() = ^{
+ return _flags._draggedNodesAreDeletable;
+ };
+
+ c();
+}
+
+
+
+// Test5 unnamed bitfield.
+void bf5() {
+ struct {
+ unsigned char flag : 1;
+ unsigned int : 32;
+ unsigned char flag1 : 1;
+ } _flags;
+
+// block variable layout: BL_OPERATOR:0
+// CHECK-LP64: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [1 x i8] zeroinitializer
+ unsigned char (^c)() = ^{
+ return _flags.flag;
+ };
+
+ c();
+}
+
+
+// Test6 0 length bitfield.
+void bf6() {
+ struct {
+ unsigned char flag : 1;
+ unsigned int : 0;
+ unsigned char flag1 : 1;
+ } _flags;
+
+// block variable layout: BL_OPERATOR:0
+// CHECK-LP64: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [1 x i8] zeroinitializer
+ unsigned char (^c)() = ^{
+ return _flags.flag;
+ };
+
+ c();
+}
+
+// Test7 large number of captured variables.
+void Test7() {
+ __weak id wid;
+ __weak id wid1, wid2, wid3, wid4;
+ __weak id wid5, wid6, wid7, wid8;
+ __weak id wid9, wid10, wid11, wid12;
+ __weak id wid13, wid14, wid15, wid16;
+ const id bar = (id) opaque_id();
+//block variable layout: BL_STRONG:1, BL_WEAK:16, BL_OPERATOR:0
+// CHECK-LP64: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [3 x i8] c"0_\00"
+ void (^b)() = ^{
+ x(bar);
+ x(wid1);
+ x(wid2);
+ x(wid3);
+ x(wid4);
+ x(wid5);
+ x(wid6);
+ x(wid7);
+ x(wid8);
+ x(wid9);
+ x(wid10);
+ x(wid11);
+ x(wid12);
+ x(wid13);
+ x(wid14);
+ x(wid15);
+ x(wid16);
+ };
+}
+
+
+// Test 8 very large number of captured variables.
+void Test8() {
+__weak id wid;
+ __weak id wid1, wid2, wid3, wid4;
+ __weak id wid5, wid6, wid7, wid8;
+ __weak id wid9, wid10, wid11, wid12;
+ __weak id wid13, wid14, wid15, wid16;
+ __weak id w1, w2, w3, w4;
+ __weak id w5, w6, w7, w8;
+ __weak id w9, w10, w11, w12;
+ __weak id w13, w14, w15, w16;
+ const id bar = (id) opaque_id();
+// block variable layout: BL_STRONG:1, BL_WEAK:16, BL_WEAK:16, BL_WEAK:1, BL_OPERATOR:0
+// CHECK-LP64: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [5 x i8]
+ void (^b)() = ^{
+ x(bar);
+ x(wid1);
+ x(wid2);
+ x(wid3);
+ x(wid4);
+ x(wid5);
+ x(wid6);
+ x(wid7);
+ x(wid8);
+ x(wid9);
+ x(wid10);
+ x(wid11);
+ x(wid12);
+ x(wid13);
+ x(wid14);
+ x(wid15);
+ x(wid16);
+ x(w1);
+ x(w2);
+ x(w3);
+ x(w4);
+ x(w5);
+ x(w6);
+ x(w7);
+ x(w8);
+ x(w9);
+ x(w10);
+ x(w11);
+ x(w12);
+ x(w13);
+ x(w14);
+ x(w15);
+ x(w16);
+ x(wid);
+ };
+}
diff --git a/test/CodeGenObjC/arc-exceptions.m b/test/CodeGenObjC/arc-exceptions.m
index 5ef5aba..63945e3 100644
--- a/test/CodeGenObjC/arc-exceptions.m
+++ b/test/CodeGenObjC/arc-exceptions.m
@@ -20,9 +20,8 @@ void test0(void) {
// CHECK-NEXT: [[T3:%.*]] = call i8* @objc_retain(i8* [[T2]]) nounwind
// CHECK-NEXT: [[T4:%.*]] = bitcast i8* [[T3]] to [[ETY]]*
// CHECK-NEXT: store [[ETY]]* [[T4]], [[ETY]]** [[E]]
-// CHECK-NEXT: [[T0:%.*]] = load [[ETY]]** [[E]]
-// CHECK-NEXT: [[T1:%.*]] = bitcast [[ETY]]* [[T0]] to i8*
-// CHECK-NEXT: call void @objc_release(i8* [[T1]]) nounwind
+// CHECK-NEXT: [[T0:%.*]] = bitcast [[ETY]]** [[E]] to i8**
+// CHECK-NEXT: call void @objc_storeStrong(i8** [[T0]], i8* null) nounwind
// CHECK-NEXT: call void @objc_end_catch() nounwind
void test1_helper(void);
diff --git a/test/CodeGenObjC/arc-foreach.m b/test/CodeGenObjC/arc-foreach.m
index 67fad4d..b8d2d30 100644
--- a/test/CodeGenObjC/arc-foreach.m
+++ b/test/CodeGenObjC/arc-foreach.m
@@ -67,8 +67,7 @@ void test0(NSArray *array) {
// CHECK-LP64-NEXT: store i8* [[T2]], i8** [[T0]]
// CHECK-LP64-NEXT: [[T1:%.*]] = bitcast [[BLOCK_T]]* [[BLOCK]]
// CHECK-LP64: call void @use_block(
-// CHECK-LP64-NEXT: [[T1:%.*]] = load i8** [[D0]]
-// CHECK-LP64-NEXT: call void @objc_release(i8* [[T1]])
+// CHECK-LP64-NEXT: call void @objc_storeStrong(i8** [[D0]], i8* null)
// CHECK-LP64: [[T0:%.*]] = load i8** @"\01L_OBJC_SELECTOR_REFERENCES_
// CHECK-LP64-NEXT: [[T1:%.*]] = bitcast [[ARRAY_T]]* [[SAVED_ARRAY]] to i8*
@@ -79,9 +78,8 @@ void test0(NSArray *array) {
// CHECK-LP64-NEXT: call void @objc_release(i8* [[T0]])
// Destroy 'array'.
-// CHECK-LP64: [[T0:%.*]] = load [[ARRAY_T]]** [[ARRAY]]
-// CHECK-LP64-NEXT: [[T1:%.*]] = bitcast [[ARRAY_T]]* [[T0]] to i8*
-// CHECK-LP64-NEXT: call void @objc_release(i8* [[T1]])
+// CHECK-LP64: [[T0:%.*]] = bitcast [[ARRAY_T]]** [[ARRAY]] to i8**
+// CHECK-LP64-NEXT: call void @objc_storeStrong(i8** [[T0]], i8* null)
// CHECK-LP64-NEXT: ret void
// CHECK-LP64: define internal void @__test0_block_invoke
diff --git a/test/CodeGenObjC/arc-ivar-layout.m b/test/CodeGenObjC/arc-ivar-layout.m
index 7f58a0c..9068314 100644
--- a/test/CodeGenObjC/arc-ivar-layout.m
+++ b/test/CodeGenObjC/arc-ivar-layout.m
@@ -1,5 +1,6 @@
// RUN: %clang_cc1 -fobjc-arc -fobjc-runtime-has-weak -triple x86_64-apple-darwin -O0 -S %s -o %t-64.s
// RUN: FileCheck -check-prefix LP64 --input-file=%t-64.s %s
+// REQUIRES: x86-64-registered-target
// rdar://8991729
@interface NSObject {
diff --git a/test/CodeGenObjC/arc-no-runtime.m b/test/CodeGenObjC/arc-no-runtime.m
index 3c85e87..f5f5b90 100644
--- a/test/CodeGenObjC/arc-no-runtime.m
+++ b/test/CodeGenObjC/arc-no-runtime.m
@@ -1,9 +1,13 @@
// RUN: %clang_cc1 -triple x86_64-apple-darwin10 -fobjc-arc -emit-llvm %s -o - | FileCheck %s
// rdar://problem/9224855
+id make(void) __attribute__((ns_returns_retained));
void test0() {
+ make();
id x = 0;
// CHECK: call void @objc_release(
+ // CHECK: call void @objc_storeStrong(
}
// CHECK: declare extern_weak void @objc_release(
+// CHECK: declare extern_weak void @objc_storeStrong(
diff --git a/test/CodeGenObjC/arc-property.m b/test/CodeGenObjC/arc-property.m
index 6c5180b..db00e36 100644
--- a/test/CodeGenObjC/arc-property.m
+++ b/test/CodeGenObjC/arc-property.m
@@ -11,5 +11,77 @@ void test0(Test0 *t0, id value) {
// CHECK: call i8* @objc_retain(
// CHECK: call i8* @objc_retain(
// CHECK: @objc_msgSend
-// CHECK: call void @objc_release(
-// CHECK: call void @objc_release(
+// CHECK: call void @objc_storeStrong(
+// CHECK: call void @objc_storeStrong(
+
+struct S1 { Class isa; };
+@interface Test1
+@property (nonatomic, strong) __attribute__((NSObject)) struct S1 *pointer;
+@end
+@implementation Test1
+@synthesize pointer;
+@end
+// The getter should be a simple load.
+// CHECK: define internal [[S1:%.*]]* @"\01-[Test1 pointer]"(
+// CHECK: [[OFFSET:%.*]] = load i64* @"OBJC_IVAR_$_Test1.pointer"
+// CHECK-NEXT: [[T0:%.*]] = bitcast [[TEST1:%.*]]* {{%.*}} to i8*
+// CHECK-NEXT: [[T1:%.*]] = getelementptr inbounds i8* [[T0]], i64 [[OFFSET]]
+// CHECK-NEXT: [[T2:%.*]] = bitcast i8* [[T1]] to [[S1]]**
+// CHECK-NEXT: [[T3:%.*]] = load [[S1]]** [[T2]], align 8
+// CHECK-NEXT: ret [[S1]]* [[T3]]
+
+// The setter should be using objc_setProperty.
+// CHECK: define internal void @"\01-[Test1 setPointer:]"(
+// CHECK: [[T0:%.*]] = bitcast [[TEST1]]* {{%.*}} to i8*
+// CHECK-NEXT: [[OFFSET:%.*]] = load i64* @"OBJC_IVAR_$_Test1.pointer"
+// CHECK-NEXT: [[T1:%.*]] = load [[S1]]** {{%.*}}
+// CHECK-NEXT: [[T2:%.*]] = bitcast [[S1]]* [[T1]] to i8*
+// CHECK-NEXT: call void @objc_setProperty(i8* [[T0]], i8* {{%.*}}, i64 [[OFFSET]], i8* [[T2]], i1 zeroext false, i1 zeroext false)
+// CHECK-NEXT: ret void
+
+
+// rdar://problem/12039404
+@interface Test2 {
+@private
+ Class _theClass;
+}
+@property (copy) Class theClass;
+@end
+
+static Class theGlobalClass;
+@implementation Test2
+@synthesize theClass = _theClass;
+- (void) test {
+ _theClass = theGlobalClass;
+}
+@end
+// CHECK: define internal void @"\01-[Test2 test]"(
+// CHECK: [[T0:%.*]] = load i8** @theGlobalClass, align 8
+// CHECK-NEXT: [[T1:%.*]] = load [[TEST2:%.*]]**
+// CHECK-NEXT: [[OFFSET:%.*]] = load i64* @"OBJC_IVAR_$_Test2._theClass"
+// CHECK-NEXT: [[T2:%.*]] = bitcast [[TEST2]]* [[T1]] to i8*
+// CHECK-NEXT: [[T3:%.*]] = getelementptr inbounds i8* [[T2]], i64 [[OFFSET]]
+// CHECK-NEXT: [[T4:%.*]] = bitcast i8* [[T3]] to i8**
+// CHECK-NEXT: call void @objc_storeStrong(i8** [[T4]], i8* [[T0]]) nounwind
+// CHECK-NEXT: ret void
+
+// CHECK: define internal i8* @"\01-[Test2 theClass]"(
+// CHECK: [[OFFSET:%.*]] = load i64* @"OBJC_IVAR_$_Test2._theClass"
+// CHECK-NEXT: [[T0:%.*]] = call i8* @objc_getProperty(i8* {{.*}}, i8* {{.*}}, i64 [[OFFSET]], i1 zeroext true)
+// CHECK-NEXT: ret i8* [[T0]]
+
+// CHECK: define internal void @"\01-[Test2 setTheClass:]"(
+// CHECK: [[T0:%.*]] = bitcast [[TEST2]]* {{%.*}} to i8*
+// CHECK-NEXT: [[OFFSET:%.*]] = load i64* @"OBJC_IVAR_$_Test2._theClass"
+// CHECK-NEXT: [[T1:%.*]] = load i8** {{%.*}}
+// CHECK-NEXT: call void @objc_setProperty(i8* [[T0]], i8* {{%.*}}, i64 [[OFFSET]], i8* [[T1]], i1 zeroext true, i1 zeroext true)
+// CHECK-NEXT: ret void
+
+// CHECK: define internal void @"\01-[Test2 .cxx_destruct]"(
+// CHECK: [[T0:%.*]] = load [[TEST2]]**
+// CHECK-NEXT: [[OFFSET:%.*]] = load i64* @"OBJC_IVAR_$_Test2._theClass"
+// CHECK-NEXT: [[T1:%.*]] = bitcast [[TEST2]]* [[T0]] to i8*
+// CHECK-NEXT: [[T2:%.*]] = getelementptr inbounds i8* [[T1]], i64 [[OFFSET]]
+// CHECK-NEXT: [[T3:%.*]] = bitcast i8* [[T2]] to i8**
+// CHECK-NEXT: call void @objc_storeStrong(i8** [[T3]], i8* null) nounwind
+// CHECK-NEXT: ret void
diff --git a/test/CodeGenObjC/arc-related-result-type.m b/test/CodeGenObjC/arc-related-result-type.m
index f73aa50..ee0a41d 100644
--- a/test/CodeGenObjC/arc-related-result-type.m
+++ b/test/CodeGenObjC/arc-related-result-type.m
@@ -20,11 +20,9 @@ void test0(Test0 *val) {
// CHECK-NEXT: [[T1:%.*]] = call i8* @objc_retainAutoreleasedReturnValue(i8* [[T0]])
// CHECK-NEXT: [[T2:%.*]] = bitcast i8* [[T1]] to [[TEST0]]*
// CHECK-NEXT: store [[TEST0]]* [[T2]], [[TEST0]]** [[X]]
-// CHECK-NEXT: [[T0:%.*]] = load [[TEST0]]** [[X]]
-// CHECK-NEXT: [[T1:%.*]] = bitcast [[TEST0]]* [[T0]] to i8*
-// CHECK-NEXT: call void @objc_release(i8* [[T1]])
-// CHECK-NEXT: [[T0:%.*]] = load [[TEST0]]** [[VAL]]
-// CHECK-NEXT: [[T1:%.*]] = bitcast [[TEST0]]* [[T0]] to i8*
-// CHECK-NEXT: call void @objc_release(i8* [[T1]])
+// CHECK-NEXT: [[T0:%.*]] = bitcast [[TEST0]]** [[X]] to i8**
+// CHECK-NEXT: call void @objc_storeStrong(i8** [[T0]], i8* null)
+// CHECK-NEXT: [[T0:%.*]] = bitcast [[TEST0]]** [[VAL]] to i8**
+// CHECK-NEXT: call void @objc_storeStrong(i8** [[T0]], i8* null)
// CHECK-NEXT: ret void
}
diff --git a/test/CodeGenObjC/arc.m b/test/CodeGenObjC/arc.m
index 66a6a2f..8e38019 100644
--- a/test/CodeGenObjC/arc.m
+++ b/test/CodeGenObjC/arc.m
@@ -602,7 +602,10 @@ void test22(_Bool cond) {
// rdar://problem/8922540
// Note that we no longer emit .release_ivars flags.
-// CHECK-GLOBALS: @"\01l_OBJC_CLASS_RO_$_Test23" = internal global [[RO_T:%.*]] { i32 134,
+// rdar://problem/12492434
+// Note that we set the flag saying that we need destruction *and*
+// the flag saying that we don't also need construction.
+// CHECK-GLOBALS: @"\01l_OBJC_CLASS_RO_$_Test23" = internal global [[RO_T:%.*]] { i32 390,
@interface Test23 { id x; } @end
@implementation Test23 @end
@@ -1358,9 +1361,9 @@ void test59(void) {
// CHECK: define void @test59()
// CHECK: [[T0:%.*]] = call i8* @test59_getlock()
// CHECK-NEXT: [[T1:%.*]] = call i8* @objc_retainAutoreleasedReturnValue(i8* [[T0]])
- // CHECK-NEXT: call void @objc_sync_enter(i8* [[T1]])
+ // CHECK-NEXT: call i32 @objc_sync_enter(i8* [[T1]])
// CHECK-NEXT: call void @test59_body()
- // CHECK-NEXT: call void @objc_sync_exit(i8* [[T1]])
+ // CHECK-NEXT: call i32 @objc_sync_exit(i8* [[T1]])
// CHECK-NEXT: call void @objc_release(i8* [[T1]])
// CHECK-NEXT: ret void
}
diff --git a/test/CodeGenObjC/atomic-aggregate-property.m b/test/CodeGenObjC/atomic-aggregate-property.m
index 978299b..878255b 100644
--- a/test/CodeGenObjC/atomic-aggregate-property.m
+++ b/test/CodeGenObjC/atomic-aggregate-property.m
@@ -1,6 +1,7 @@
// RUN: %clang_cc1 -triple x86_64-apple-darwin10 -fobjc-gc -emit-llvm -o - %s | FileCheck -check-prefix LP64 %s
// RUN: %clang_cc1 -x objective-c++ -triple x86_64-apple-darwin10 -fobjc-gc -emit-llvm -o - %s | FileCheck -check-prefix LP64 %s
// rdar: // 7849824
+// <rdar://problem/12547611>
struct s {
double a, b, c, d;
@@ -12,16 +13,20 @@ struct s1 {
id k;
};
+struct s2 {};
+
@interface A
@property (readwrite) double x;
@property (readwrite) struct s y;
@property (nonatomic, readwrite) struct s1 z;
+@property (readwrite) struct s2 a;
@end
@implementation A
@synthesize x;
@synthesize y;
@synthesize z;
+@synthesize a;
@end
// CHECK-LP64: define internal double @"\01-[A x]"(
// CHECK-LP64: load atomic i64* {{%.*}} unordered, align 8
@@ -40,3 +45,9 @@ struct s1 {
// CHECK-LP64: define internal void @"\01-[A setZ:]"(
// CHECK-LP64: call i8* @objc_memmove_collectable(
+
+// CHECK-LP64: define internal void @"\01-[A a]"(
+// (do nothing)
+
+// CHECK-LP64: define internal void @"\01-[A setA:]"(
+// (do nothing)
diff --git a/test/CodeGenObjC/attr-minsize.m b/test/CodeGenObjC/attr-minsize.m
new file mode 100644
index 0000000..f46107e
--- /dev/null
+++ b/test/CodeGenObjC/attr-minsize.m
@@ -0,0 +1,12 @@
+// RUN: %clang_cc1 -emit-llvm -o - %s | FileCheck %s
+
+@interface Test
+- (void)test;
+@end
+
+@implementation Test
+- (void)test __attribute__((minsize)) {
+ // CHECK: define{{.*}}Test test
+ // CHECK: minsize
+}
+@end
diff --git a/test/CodeGenObjC/block-var-layout.m b/test/CodeGenObjC/block-var-layout.m
index c8065be..71b14da 100644
--- a/test/CodeGenObjC/block-var-layout.m
+++ b/test/CodeGenObjC/block-var-layout.m
@@ -90,7 +90,7 @@ void f() {
// Test 4
// struct S (int, id, int, id, int, id)
-// 01 41 11 11
+// 01 41 11 11 00
// CHECK-LP64: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [5 x i8] c"\01A\11\11\00"
struct S s2;
void (^e)() = ^{
@@ -128,8 +128,8 @@ void Test5() {
union U u2;
// struct s2 (int, id, int, id, int, id?), union u2 (id?)
-// 01 41 11 12 70 00
-// CHECK-LP64: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [6 x i8] c"\01A\11\12p\00"
+// 01 41 11 12 00
+// CHECK-LP64: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [5 x i8] c"\01A\11\12\00"
void (^c)() = ^{
x(s2.ui.o1);
x(u2.o1);
diff --git a/test/CodeGenObjC/builtin-memfns.m b/test/CodeGenObjC/builtin-memfns.m
new file mode 100644
index 0000000..bb425c0
--- /dev/null
+++ b/test/CodeGenObjC/builtin-memfns.m
@@ -0,0 +1,10 @@
+// RUN: %clang_cc1 -triple x86_64-apple-macosx10.8.0 -emit-llvm -o - %s | FileCheck %s
+
+void *memcpy(void *restrict s1, const void *restrict s2, unsigned long n);
+
+// PR13697
+void test1(int *a, id b) {
+ // CHECK: @test1
+ // CHECK: call void @llvm.memcpy.p0i8.p0i8.i64(i8* {{.*}}, i8* {{.*}}, i64 8, i32 1, i1 false)
+ memcpy(a, b, 8);
+}
diff --git a/test/CodeGenObjC/category-super-class-meth.m b/test/CodeGenObjC/category-super-class-meth.m
index 6f02aff..5ba7adf 100644
--- a/test/CodeGenObjC/category-super-class-meth.m
+++ b/test/CodeGenObjC/category-super-class-meth.m
@@ -1,19 +1,29 @@
-// RUN: %clang_cc1 -emit-llvm -o %t %s
-
-@interface BASE
-+ (int) BaseMeth;
+// RUN: %clang_cc1 %s -emit-llvm -triple x86_64-apple-darwin -o - | FileCheck %s
+// rdar://12459358
+@interface NSObject
+-(id)copy;
++(id)copy;
@end
-@interface Child: BASE
-@end
+@interface Sub1 : NSObject @end
-@interface Child (Categ)
-+ (int) flushCache2;
+@implementation Sub1
+-(id)copy { return [super copy]; } // ok: instance method in class
++(id)copy { return [super copy]; } // ok: class method in class
@end
-@implementation Child @end
+@interface Sub2 : NSObject @end
+
+@interface Sub2 (Category) @end
-@implementation Child (Categ)
-+ (int) flushCache2 { [super BaseMeth]; }
+@implementation Sub2 (Category)
+-(id)copy { return [super copy]; } // ok: instance method in category
++(id)copy { return [super copy]; } // BAD: class method in category
@end
+// CHECK: define internal i8* @"\01+[Sub2(Category) copy]
+// CHECK: [[ONE:%.*]] = load %struct._class_t** @"\01L_OBJC_CLASSLIST_SUP_REFS_$_3"
+// CHECK: [[TWO:%.*]] = bitcast %struct._class_t* [[ONE]] to i8*
+// CHECK: [[THREE:%.*]] = getelementptr inbounds %struct._objc_super* [[OBJC_SUPER:%.*]], i32 0, i32 1
+// CHECK: store i8* [[TWO]], i8** [[THREE]]
+// CHECK: [[FOUR:%.*]] = load i8** @"\01L_OBJC_SELECTOR_REFERENCES_"
diff --git a/test/CodeGenObjC/debug-info-crash-2.m b/test/CodeGenObjC/debug-info-crash-2.m
index a2acd9d..7d05f53 100644
--- a/test/CodeGenObjC/debug-info-crash-2.m
+++ b/test/CodeGenObjC/debug-info-crash-2.m
@@ -1,4 +1,6 @@
// RUN: %clang_cc1 -triple x86_64-apple-darwin11 -g -S %s -o -
+// REQUIRES: x86-64-registered-target
+
@class Bar;
@interface Foo
@property (strong, nonatomic) Bar *window;
diff --git a/test/CodeGenObjC/debug-info-fwddecl.m b/test/CodeGenObjC/debug-info-fwddecl.m
index ebdc5f2..8f2860c 100644
--- a/test/CodeGenObjC/debug-info-fwddecl.m
+++ b/test/CodeGenObjC/debug-info-fwddecl.m
@@ -2,4 +2,4 @@
@class ForwardObjcClass;
ForwardObjcClass *ptr = 0;
-// CHECK: metadata !{i32 {{.*}}, null, metadata !"ForwardObjcClass", metadata !{{.*}}, i32 2, i32 0, i32 0, i32 0, i32 4, null, null, i32 16} ; [ DW_TAG_structure_type ]
+// CHECK: metadata !{i32 {{.*}}, null, metadata !"ForwardObjcClass", metadata !{{.*}}, i32 2, i64 0, i64 0, i32 0, i32 4, null, null, i32 16} ; [ DW_TAG_structure_type ]
diff --git a/test/CodeGenObjC/debug-info-impl.m b/test/CodeGenObjC/debug-info-impl.m
index 8ad5903..a8450dd 100644
--- a/test/CodeGenObjC/debug-info-impl.m
+++ b/test/CodeGenObjC/debug-info-impl.m
@@ -1,5 +1,5 @@
// RUN: %clang_cc1 -triple x86_64-apple-darwin10 -g -S -emit-llvm %s -o - | FileCheck %s
-// CHECK: metadata !{i32 {{.*}}, metadata {{.*}}, metadata !"Circle", metadata {{.*}}, i32 11, i64 64, i64 64, i32 0, i32 512, null, metadata {{.*}}, i32 16, i32 0} ; [ DW_TAG_structure_type ]
+// CHECK: metadata !{i32 {{.*}}, metadata {{.*}}, metadata !"Circle", metadata {{.*}}, i32 11, i64 64, i64 64, i32 0, i32 512, null, metadata {{.*}}, i32 16, i32 0, i32 0} ; [ DW_TAG_structure_type ]
@interface NSObject {
struct objc_object *isa;
}
diff --git a/test/CodeGenObjC/debug-info-ivars.m b/test/CodeGenObjC/debug-info-ivars.m
new file mode 100644
index 0000000..24705e1a
--- /dev/null
+++ b/test/CodeGenObjC/debug-info-ivars.m
@@ -0,0 +1,24 @@
+// RUN: %clang_cc1 -triple x86_64-apple-darwin10 -emit-llvm -g %s -o - | FileCheck %s
+
+__attribute((objc_root_class)) @interface NSObject {
+ id isa;
+}
+@end
+
+@interface BaseClass : NSObject
+{
+ int i;
+ unsigned flag_1 : 9;
+ unsigned flag_2 : 9;
+ unsigned : 1;
+ unsigned flag_3 : 9;
+}
+@end
+
+@implementation BaseClass
+@end
+
+// CHECK: metadata !{i32 786445, metadata !{{[0-9]*}}, metadata !"i", metadata !{{[0-9]*}}, i32 10, i64 32, i64 32, i64 0, i32 2, metadata !{{[0-9]*}}, null} ; [ DW_TAG_member ] [i] [line 10, size 32, align 32, offset 0] [protected] [from int]
+// CHECK: metadata !{i32 786445, metadata !{{[0-9]*}}, metadata !"flag_1", metadata !{{[0-9]*}}, i32 11, i64 9, i64 32, i64 0, i32 2, metadata !{{[0-9]*}}, null} ; [ DW_TAG_member ] [flag_1] [line 11, size 9, align 32, offset 0] [protected] [from unsigned int]
+// CHECK: metadata !{i32 786445, metadata !{{[0-9]*}}, metadata !"flag_2", metadata !{{[0-9]*}}, i32 12, i64 9, i64 32, i64 1, i32 2, metadata !{{[0-9]*}}, null} ; [ DW_TAG_member ] [flag_2] [line 12, size 9, align 32, offset 1] [protected] [from unsigned int]
+// CHECK: metadata !{i32 786445, metadata !{{[0-9]*}}, metadata !"flag_3", metadata !{{[0-9]*}}, i32 14, i64 9, i64 32, i64 3, i32 2, metadata !{{[0-9]*}}, null} ; [ DW_TAG_member ] [flag_3] [line 14, size 9, align 32, offset 3] [protected] [from unsigned int] \ No newline at end of file
diff --git a/test/CodeGenObjC/debug-info-pubtypes.m b/test/CodeGenObjC/debug-info-pubtypes.m
index 658430d..91d9cd1 100644
--- a/test/CodeGenObjC/debug-info-pubtypes.m
+++ b/test/CodeGenObjC/debug-info-pubtypes.m
@@ -1,7 +1,7 @@
// REQUIRES: x86-64-registered-target
-// RUN: %clang -cc1 -triple x86_64-apple-darwin10 -g -emit-llvm %s -o - | FileCheck %s
+// RUN: %clang_cc1 -triple x86_64-apple-darwin10 -g -emit-llvm %s -o - | FileCheck %s
-// CHECK: !5 = metadata !{i32 {{.*}}, metadata !6, metadata !"H", metadata !6, i32 6, i64 0, i64 8, i32 0, i32 512, null, metadata !2, i32 16, i32 0} ; [ DW_TAG_structure_type ]
+// CHECK: !5 = metadata !{i32 {{.*}}, metadata !6, metadata !"H", metadata !6, i32 6, i64 0, i64 8, i32 0, i32 512, null, metadata !2, i32 16, i32 0, i32 0} ; [ DW_TAG_structure_type ]
@interface H
-(void) foo;
diff --git a/test/CodeGenObjC/debug-info-self.m b/test/CodeGenObjC/debug-info-self.m
index 9146ab3..9f23435 100644
--- a/test/CodeGenObjC/debug-info-self.m
+++ b/test/CodeGenObjC/debug-info-self.m
@@ -1,8 +1,12 @@
-// RUN: %clang -fverbose-asm -g -S %s -o - | grep DW_AT_artificial | count 3
+// RUN: %clang_cc1 -emit-llvm -g %s -o - | FileCheck %s
// self and _cmd are marked as DW_AT_artificial.
-// abbrev code emits another DT_artificial comment.
// myarg is not marked as DW_AT_artificial.
+// CHECK: metadata !{i32 {{.*}}, metadata !9, metadata !"self", metadata !15, i32 16777232, metadata !30, i32 1088, i32 0} ; [ DW_TAG_arg_variable ] [self] [line 16]
+// CHECK: metadata !{i32 {{.*}}, metadata !9, metadata !"_cmd", metadata !15, i32 33554448, metadata !33, i32 64, i32 0} ; [ DW_TAG_arg_variable ] [_cmd] [line 16]
+// CHECK: metadata !{i32 {{.*}}, metadata !9, metadata !"myarg", metadata !6, i32 50331664, metadata !24, i32 0, i32 0} ; [ DW_TAG_arg_variable ] [myarg] [line 16]
+
+
@interface MyClass {
}
- (id)init:(int) myarg;
diff --git a/test/CodeGenObjC/exceptions.m b/test/CodeGenObjC/exceptions.m
index 25780fd..551e67c 100644
--- a/test/CodeGenObjC/exceptions.m
+++ b/test/CodeGenObjC/exceptions.m
@@ -149,8 +149,8 @@ void f4() {
// finally.call-exit: Predecessors are the @try and @catch fallthroughs
// as well as the no-match case in the catch mechanism. The i1 is whether
// to rethrow and should be true only in the last case.
- // CHECK: phi i1
- // CHECK-NEXT: phi i8*
+ // CHECK: phi i8*
+ // CHECK-NEXT: phi i1
// CHECK-NEXT: call void @objc_exception_try_exit([[EXNDATA_T]]* [[EXNDATA]])
// CHECK-NEXT: call void @f4_help(i32 2)
// CHECK-NEXT: br i1
diff --git a/test/CodeGenObjC/gnu-exceptions.m b/test/CodeGenObjC/gnu-exceptions.m
index 141747e..b7d0adb 100644
--- a/test/CodeGenObjC/gnu-exceptions.m
+++ b/test/CodeGenObjC/gnu-exceptions.m
@@ -20,7 +20,7 @@ void test0() {
// CHECK: call void @log(i32 0)
- // CHECK: call void @objc_exception_throw
+ // CHECK: resume
log(0);
}
diff --git a/test/CodeGenObjC/ivar-layout-64.m b/test/CodeGenObjC/ivar-layout-64.m
index ea4cdce..91a8375 100644
--- a/test/CodeGenObjC/ivar-layout-64.m
+++ b/test/CodeGenObjC/ivar-layout-64.m
@@ -1,15 +1,5 @@
-// RUNX: llvm-gcc -m64 -fobjc-gc -emit-llvm -S -o %t %s &&
-// RUN: %clang_cc1 -triple x86_64-apple-darwin10 -fobjc-gc -emit-llvm -o %t %s
-// RUN: grep '@"\\01L_OBJC_CLASS_NAME_.*" = internal global .* c"A\\00"' %t
-// RUN: grep '@"\\01L_OBJC_CLASS_NAME_.*" = internal global .* c"\\11q\\10\\00"' %t
-// RUN: grep '@"\\01L_OBJC_CLASS_NAME_.*" = internal global .* c"!q\\00"' %t
-// RUN: grep '@"\\01L_OBJC_CLASS_NAME_.*" = internal global .* c"\\01\\14\\00"' %t
-// RUNX: llvm-gcc -ObjC++ -m64 -fobjc-gc -emit-llvm -S -o %t %s &&
-// RUN: %clang_cc1 -x objective-c++ -triple x86_64-apple-darwin10 -fobjc-gc -emit-llvm -o %t %s
-// RUN: grep '@"\\01L_OBJC_CLASS_NAME_.*" = internal global .* c"A\\00"' %t
-// RUN: grep '@"\\01L_OBJC_CLASS_NAME_.*" = internal global .* c"\\11q\\10\\00"' %t
-// RUN: grep '@"\\01L_OBJC_CLASS_NAME_.*" = internal global .* c"!q\\00"' %t
-// RUN: grep '@"\\01L_OBJC_CLASS_NAME_.*" = internal global .* c"\\01\\14\\00"' %t
+// RUN: %clang_cc1 -triple x86_64-apple-darwin10 -fobjc-gc -emit-llvm -o - %s | FileCheck %s
+// RUN: %clang_cc1 -x objective-c++ -triple x86_64-apple-darwin10 -fobjc-gc -emit-llvm -o - %s | FileCheck %s
/*
@@ -43,6 +33,11 @@ __weak B *f2;
@property int p3;
@end
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global {{.*}} c"C\00"
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global {{.*}} c"\11p\00"
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global {{.*}} c"!`\00"
+
+
@implementation C
@synthesize p3 = _p3;
@end
@@ -53,8 +48,10 @@ __weak B *f2;
@property (assign) __weak id p2;
@end
-// FIXME: Check layout for this class, once it is clear what the right
-// answer is.
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global {{.*}} c"A\00"
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global {{.*}} c"\11q\10\00"
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global {{.*}} c"!q\00"
+
@implementation A
@synthesize p0 = _p0;
@synthesize p1 = _p1;
@@ -65,8 +62,10 @@ __weak B *f2;
@property int p3;
@end
-// FIXME: Check layout for this class, once it is clear what the right
-// answer is.
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global {{.*}} c"D\00"
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global {{.*}} c"\11p\00"
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global {{.*}} c"!`\00"
+
@implementation D
@synthesize p3 = _p3;
@end
@@ -90,5 +89,26 @@ typedef unsigned int FSCatalogInfoBitmap;
}
@end
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global {{.*}} c"NSFileLocationComponent\00"
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global {{.*}} c"\01\14\00"
+
@implementation NSFileLocationComponent @end
+@interface NSObject {
+ id isa;
+}
+@end
+
+@interface Foo : NSObject {
+ id ivar;
+
+ unsigned long bitfield :31;
+ unsigned long bitfield2 :1;
+ unsigned long bitfield3 :32;
+}
+@end
+
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global {{.*}} c"Foo\00"
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global {{.*}} c"\02\10\00"
+
+@implementation Foo @end
diff --git a/test/CodeGenObjC/mrr-captured-block-var-inlined-layout.m b/test/CodeGenObjC/mrr-captured-block-var-inlined-layout.m
new file mode 100644
index 0000000..f1e02dd
--- /dev/null
+++ b/test/CodeGenObjC/mrr-captured-block-var-inlined-layout.m
@@ -0,0 +1,65 @@
+// RUN: %clang_cc1 -fblocks -triple x86_64-apple-darwin -O0 -emit-llvm %s -o - | FileCheck %s
+// RUN: %clang_cc1 -fblocks -triple i386-apple-darwin -O0 -emit-llvm %s -o - | FileCheck -check-prefix=CHECK-i386 %s
+// rdar://12184410
+
+void x(id y) {}
+void y(int a) {}
+
+extern id opaque_id();
+__weak id wid;
+
+void f() {
+ __block int byref_int = 0;
+ const id bar = (id) opaque_id();
+ id baz = 0;
+ __strong id strong_void_sta;
+ __block id byref_bab = (id)0;
+ __block id bl_var1;
+
+// block variable layout: BL_UNRETAINED:1, BL_OPERATOR:0
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [2 x i8] c"`\00"
+// CHECK-i386: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [2 x i8] c"`\00"
+ void (^b)() = ^{
+ x(bar);
+ };
+
+// block variable layout: BL_UNRETAINED:2, BL_BYREF:1, BL_OPERATOR:0
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [3 x i8] c"a@\00"
+// CHECK-i386: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [3 x i8] c"a@\00"
+ void (^c)() = ^{
+ x(bar);
+ x(baz);
+ byref_int = 1;
+ };
+
+// block variable layout: BL_UNRETAINED:2, BL_BYREF:3, BL_OPERATOR:0
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [3 x i8] c"aB\00
+// CHECK-i386: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [3 x i8] c"aB\00
+ void (^d)() = ^{
+ x(bar);
+ x(baz);
+ byref_int = 1;
+ bl_var1 = 0;
+ byref_bab = 0;
+ };
+
+// block variable layout: BL_UNRETAINED:2, BL_BYREF:3, BL_OPERATOR:0
+// CHECK: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [3 x i8] c"aB\00"
+// CHECK-i386: @"\01L_OBJC_CLASS_NAME_{{.*}}" = internal global [3 x i8] c"aB\00"
+ id (^e)() = ^{
+ x(bar);
+ x(baz);
+ byref_int = 1;
+ bl_var1 = 0;
+ byref_bab = 0;
+ return wid;
+ };
+
+// Inline instruction for block variable layout: 0x020
+// CHECK: i8* getelementptr inbounds ([6 x i8]* {{@.*}}, i32 0, i32 0), i64 32 }
+// CHECK-i386: i8* getelementptr inbounds ([6 x i8]* {{@.*}}, i32 0, i32 0), i32 32 }
+ void (^ii)() = ^{
+ byref_int = 1;
+ byref_bab = 0;
+ };
+}
diff --git a/test/CodeGenObjC/newproperty-nested-synthesis-1.m b/test/CodeGenObjC/newproperty-nested-synthesis-1.m
index 4831c22..aa0c8c9 100644
--- a/test/CodeGenObjC/newproperty-nested-synthesis-1.m
+++ b/test/CodeGenObjC/newproperty-nested-synthesis-1.m
@@ -1,4 +1,5 @@
// RUN: %clang_cc1 -emit-llvm -o %t %s
+// REQUIRES: LP64
@interface Object
- (id) new;
diff --git a/test/CodeGenObjC/objc-arc-container-subscripting.m b/test/CodeGenObjC/objc-arc-container-subscripting.m
index 8924916..71339c7 100644
--- a/test/CodeGenObjC/objc-arc-container-subscripting.m
+++ b/test/CodeGenObjC/objc-arc-container-subscripting.m
@@ -13,9 +13,8 @@ id func() {
// CHECK: [[call:%.*]] = call i8* bitcast (i8* (i8*, i8*, ...)* @objc_msgSend
// CHECK: [[SIX:%.*]] = call i8* @objc_retainAutoreleasedReturnValue(i8* [[call]]) nounwind
-// CHECK: [[ARRAY:%.*]] = load %0**
-// CHECK: [[ARRAY_CASTED:%.*]] = bitcast{{.*}}[[ARRAY]] to i8*
-// CHECK: call void @objc_release(i8* [[ARRAY_CASTED]])
+// CHECK: [[ARRAY_CASTED:%.*]] = bitcast %0** {{%.*}} to i8**
+// CHECK: call void @objc_storeStrong(i8** [[ARRAY_CASTED]], i8* null)
// CHECK: [[EIGHT:%.*]] = call i8* @objc_autoreleaseReturnValue(i8* [[SIX]]) nounwind
// CHECK: ret i8* [[EIGHT]]
diff --git a/test/CodeGenObjC/objc2-ivar-assign.m b/test/CodeGenObjC/objc2-ivar-assign.m
index af76800..05a7b35 100644
--- a/test/CodeGenObjC/objc2-ivar-assign.m
+++ b/test/CodeGenObjC/objc2-ivar-assign.m
@@ -1,6 +1,9 @@
// RUN: %clang_cc1 -fobjc-gc -emit-llvm -o %t %s
// RUN: grep objc_assign_ivar %t | count 6
+// PR13820
+// REQUIRES: LP64
+
@interface I @end
typedef I TI;
diff --git a/test/CodeGenObjC/optimized-setter-ios-device.m b/test/CodeGenObjC/optimized-setter-ios-device.m
new file mode 100644
index 0000000..6fa322a
--- /dev/null
+++ b/test/CodeGenObjC/optimized-setter-ios-device.m
@@ -0,0 +1,33 @@
+// RUN: %clang_cc1 %s -emit-llvm -fobjc-runtime=ios-6.0.0 -triple thumbv7-apple-ios6.0.0 -o - | FileCheck %s
+// rdar://11915017
+
+@interface I
+// void objc_setProperty_nonatomic(id self, SEL _cmd, id newValue, ptrdiff_t offset);
+// objc_setProperty(..., NO, NO)
+@property (nonatomic, retain) id nonatomicProperty;
+
+// void objc_setProperty_nonatomic_copy(id self, SEL _cmd, id newValue, ptrdiff_t offset);
+// objc_setProperty(..., NO, YES)
+@property (nonatomic, copy) id nonatomicPropertyCopy;
+
+// void objc_setProperty_atomic(id self, SEL _cmd, id newValue, ptrdiff_t offset);
+// objc_setProperty(..., YES, NO)
+@property (retain) id atomicProperty;
+
+// void objc_setProperty_atomic_copy(id self, SEL _cmd, id newValue, ptrdiff_t offset);
+// objc_setProperty(..., YES, YES)
+@property (copy) id atomicPropertyCopy;
+@end
+
+@implementation I
+@synthesize nonatomicProperty;
+@synthesize nonatomicPropertyCopy;
+@synthesize atomicProperty;
+@synthesize atomicPropertyCopy;
+@end
+
+// CHECK: call arm_aapcscc void @objc_setProperty_nonatomic
+// CHECK: call arm_aapcscc void @objc_setProperty_nonatomic_copy
+// CHECK: call arm_aapcscc void @objc_setProperty_atomic
+// CHECK: call arm_aapcscc void @objc_setProperty_atomic_copy
+
diff --git a/test/CodeGenObjC/optimized-setter.m b/test/CodeGenObjC/optimized-setter.m
index 0e1b388..6f5cfb1 100644
--- a/test/CodeGenObjC/optimized-setter.m
+++ b/test/CodeGenObjC/optimized-setter.m
@@ -1,4 +1,5 @@
-// RUN: %clang_cc1 %s -emit-llvm -triple x86_64-apple-macosx10.8.0 -o - | FileCheck %s
+// RUN: %clang_cc1 %s -emit-llvm -fobjc-runtime=macosx-10.8 -triple x86_64-apple-macosx10.8.0 -o - | FileCheck %s
+// RUN: %clang_cc1 %s -emit-llvm -fobjc-runtime=ios-6.0.0 -triple x86_64-apple-ios6.0.0 -o - | FileCheck %s
// rdar://10179974
@interface I
diff --git a/test/CodeGenObjC/prop-metadata-gnu.m b/test/CodeGenObjC/prop-metadata-gnu.m
new file mode 100644
index 0000000..c15d978
--- /dev/null
+++ b/test/CodeGenObjC/prop-metadata-gnu.m
@@ -0,0 +1,15 @@
+// RUN: %clang -S -emit-llvm %s -o - -x objective-c -fobjc-runtime=gcc | FileCheck --check-prefix=GCC %s
+// RUN: %clang -S -emit-llvm %s -o - -x objective-c -fobjc-runtime=gnustep-1.5 | FileCheck --check-prefix=GCC %s
+// RUN: %clang -S -emit-llvm %s -o - -x objective-c -fobjc-runtime=gnustep-1.6 | FileCheck --check-prefix=GNUSTEP %s
+//
+@interface helloclass {
+@private int varName;
+}
+@property (readwrite,assign) int propName;
+@end
+
+@implementation helloclass
+@synthesize propName = varName;
+@end
+// GCC-NOT: Ti,VvarName
+// GNUSTEP: Ti,VvarName
diff --git a/test/CodeGenObjC/property.m b/test/CodeGenObjC/property.m
index 16881d6..aab7c73 100644
--- a/test/CodeGenObjC/property.m
+++ b/test/CodeGenObjC/property.m
@@ -1,4 +1,7 @@
-// RUN: %clang_cc1 -emit-llvm -o - %s | FileCheck %s
+// RUN: %clang_cc1 -triple i386-unknown-unknown -emit-llvm -o - %s | FileCheck %s
+
+// PR13820
+// REQUIRES: LP64
// TODO: actually test most of this instead of just emitting it
diff --git a/test/CodeGenObjC/synchronized.m b/test/CodeGenObjC/synchronized.m
index 1f01282..e927882 100644
--- a/test/CodeGenObjC/synchronized.m
+++ b/test/CodeGenObjC/synchronized.m
@@ -11,7 +11,7 @@
// CHECK: define internal void @"\01-[MyClass method]"
- (void)method
{
- // CHECK: call void @objc_sync_enter
+ // CHECK: call i32 @objc_sync_enter
// CHECK: call void @objc_exception_try_enter
// CHECK: call i32 @_setjmp
@synchronized(self) {
@@ -26,21 +26,21 @@ void foo(id a) {
// CHECK: [[SYNC:%.*]] = alloca i8*
// CHECK: store i8* [[AVAL:%.*]], i8** [[A]]
- // CHECK-NEXT: call void @objc_sync_enter(i8* [[AVAL]])
+ // CHECK-NEXT: call i32 @objc_sync_enter(i8* [[AVAL]])
// CHECK-NEXT: store i8* [[AVAL]], i8** [[SYNC]]
// CHECK-NEXT: call void @objc_exception_try_enter
// CHECK: call i32 @_setjmp
@synchronized(a) {
// This is unreachable, but the optimizers can't know that.
// CHECK: call void asm sideeffect "", "=*m,=*m,=*m"(i8** [[A]], i8** [[SYNC]]
- // CHECK: call void @objc_sync_exit
+ // CHECK: call i32 @objc_sync_exit
// CHECK: call i8* @objc_exception_extract
// CHECK: call void @objc_exception_throw
// CHECK: unreachable
// CHECK: call void @objc_exception_try_exit
// CHECK: [[T:%.*]] = load i8** [[SYNC]]
- // CHECK-NEXT: call void @objc_sync_exit
+ // CHECK-NEXT: call i32 @objc_sync_exit
// CHECK: ret void
return;
}
diff --git a/test/CodeGenObjC/synthesize_ivar-cont-class.m b/test/CodeGenObjC/synthesize_ivar-cont-class.m
index 6bc7ac8..9822702 100644
--- a/test/CodeGenObjC/synthesize_ivar-cont-class.m
+++ b/test/CodeGenObjC/synthesize_ivar-cont-class.m
@@ -1,6 +1,9 @@
// RUN: %clang_cc1 -emit-llvm -o %t %s
// RUN: grep '@"OBJC_IVAR_$_XCOrganizerDeviceNodeInfo.viewController"' %t
+// PR13820
+// REQUIRES: LP64
+
@interface XCOrganizerNodeInfo
@property (readonly, retain) id viewController;
@end
diff --git a/test/CodeGenObjC/synthesize_ivar.m b/test/CodeGenObjC/synthesize_ivar.m
index e4fbe10..92f6096 100644
--- a/test/CodeGenObjC/synthesize_ivar.m
+++ b/test/CodeGenObjC/synthesize_ivar.m
@@ -1,5 +1,8 @@
// RUN: %clang_cc1 -emit-llvm -o %t %s
+// PR13820
+// REQUIRES: LP64
+
@interface I
@property int IP;
@end
diff --git a/test/CodeGenObjC/undefined-protocol.m b/test/CodeGenObjC/undefined-protocol.m
index e5a72ab..78cf8da 100644
--- a/test/CodeGenObjC/undefined-protocol.m
+++ b/test/CodeGenObjC/undefined-protocol.m
@@ -1,5 +1,8 @@
// RUN: %clang_cc1 -emit-llvm-only -fobjc-runtime=gcc %s
+// PR13820
+// REQUIRES: LP64
+
@protocol MadeUpProtocol;
@interface Object <MadeUpProtocol> @end
diff --git a/test/CodeGenObjC/unoptimized-setter.m b/test/CodeGenObjC/unoptimized-setter.m
new file mode 100644
index 0000000..adcf087
--- /dev/null
+++ b/test/CodeGenObjC/unoptimized-setter.m
@@ -0,0 +1,32 @@
+// RUN: %clang_cc1 %s -emit-llvm -fobjc-runtime=macosx-10.6.0 -triple x86_64-apple-macosx10.6.0 -o - | FileCheck %s
+// rdar://11858187
+
+@interface I
+// void objc_setProperty_nonatomic(id self, SEL _cmd, id newValue, ptrdiff_t offset);
+// objc_setProperty(..., NO, NO)
+@property (nonatomic, retain) id nonatomicProperty;
+
+// void objc_setProperty_nonatomic_copy(id self, SEL _cmd, id newValue, ptrdiff_t offset);
+// objc_setProperty(..., NO, YES)
+@property (nonatomic, copy) id nonatomicPropertyCopy;
+
+// void objc_setProperty_atomic(id self, SEL _cmd, id newValue, ptrdiff_t offset);
+// objc_setProperty(..., YES, NO)
+@property (retain) id atomicProperty;
+
+// void objc_setProperty_atomic_copy(id self, SEL _cmd, id newValue, ptrdiff_t offset);
+// objc_setProperty(..., YES, YES)
+@property (copy) id atomicPropertyCopy;
+@end
+
+@implementation I
+@synthesize nonatomicProperty;
+@synthesize nonatomicPropertyCopy;
+@synthesize atomicProperty;
+@synthesize atomicPropertyCopy;
+@end
+
+// CHECK-NOT: call void @objc_setProperty_nonatomic
+// CHECK-NOT: call void @objc_setProperty_nonatomic_copy
+// CHECK-NOT: call void @objc_setProperty_atomic
+// CHECK-NOT: call void @objc_setProperty_atomic_copy
OpenPOWER on IntegriCloud