diff options
Diffstat (limited to 'test/CodeGenObjC/synchronized.m')
-rw-r--r-- | test/CodeGenObjC/synchronized.m | 56 |
1 files changed, 47 insertions, 9 deletions
diff --git a/test/CodeGenObjC/synchronized.m b/test/CodeGenObjC/synchronized.m index 1af8234..2a80906 100644 --- a/test/CodeGenObjC/synchronized.m +++ b/test/CodeGenObjC/synchronized.m @@ -1,6 +1,4 @@ -// RUN: %clang_cc1 -emit-llvm -triple=i686-apple-darwin9 -o %t %s -O2 -// RUN: grep 'ret i32' %t | count 1 -// RUN: grep 'ret i32 1' %t | count 1 +// RUN: %clang_cc1 -emit-llvm -triple=i686-apple-darwin9 -o - %s -O2 | FileCheck %s @interface MyClass { @@ -10,31 +8,71 @@ @implementation MyClass +// CHECK: define internal void @"\01-[MyClass method]" - (void)method { - @synchronized(self) - { - } + // CHECK: call void @objc_sync_enter + // CHECK: call void @objc_exception_try_enter + // CHECK: call i32 @_setjmp + @synchronized(self) { + } } @end +// CHECK: define void @foo( void foo(id a) { + // CHECK: [[A:%.*]] = alloca i8* + // CHECK: [[SYNC:%.*]] = alloca i8* + + // CHECK: store i8* [[AVAL:%.*]], i8** [[A]] + // CHECK-NEXT: call void @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 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: ret void return; } + } +// CHECK: define i32 @f0( int f0(id a) { + // TODO: we can optimize the ret to a constant if we can figure out + // either that x isn't stored to within the synchronized block or + // that the synchronized block can't longjmp. + + // CHECK: [[X:%.*]] = alloca i32 + // CHECK: store i32 1, i32* [[X]] int x = 0; @synchronized((x++, a)) { } - return x; // ret i32 1 + + // CHECK: [[T:%.*]] = load i32* [[X]] + // CHECK: ret i32 [[T]] + return x; } +// CHECK: define void @f1( void f1(id a) { - // The trick here is that the return shouldn't go through clean up, - // but there isn't a simple way to check this property. + // Check that the return doesn't go through the cleanup. + extern void opaque(void); + opaque(); + + // CHECK: call void @opaque() + // CHECK-NEXT: ret void + @synchronized(({ return; }), a) { return; } |