blocks.cpp revision 461c9c1bc39ed8cbe8311f396f7ee3839e9fda53
1// RUN: %clang_cc1 %s -fblocks -triple x86_64-apple-darwin -emit-llvm -o - | FileCheck %s 2 3namespace test0 { 4 // CHECK: define void @_ZN5test04testEi( 5 // CHECK: define internal void @__test_block_invoke_{{.*}}( 6 // CHECK: define internal void @__block_global_{{.*}}( 7 void test(int x) { 8 ^{ ^{ (void) x; }; }; 9 } 10} 11 12extern void (^out)(); 13 14namespace test1 { 15 // Capturing const objects doesn't require a local block. 16 // CHECK: define void @_ZN5test15test1Ev() 17 // CHECK: store void ()* bitcast ({{.*}} @__block_literal_global{{.*}} to void ()*), void ()** @out 18 void test1() { 19 const int NumHorsemen = 4; 20 out = ^{ (void) NumHorsemen; }; 21 } 22 23 // That applies to structs too... 24 // CHECK: define void @_ZN5test15test2Ev() 25 // CHECK: store void ()* bitcast ({{.*}} @__block_literal_global{{.*}} to void ()*), void ()** @out 26 struct loc { double x, y; }; 27 void test2() { 28 const loc target = { 5, 6 }; 29 out = ^{ (void) target; }; 30 } 31 32 // ...unless they have mutable fields... 33 // CHECK: define void @_ZN5test15test3Ev() 34 // CHECK: [[BLOCK:%.*]] = alloca [[BLOCK_T:%.*]], 35 // CHECK: [[T0:%.*]] = bitcast [[BLOCK_T]]* [[BLOCK]] to void ()* 36 // CHECK: store void ()* [[T0]], void ()** @out 37 struct mut { mutable int x; }; 38 void test3() { 39 const mut obj = { 5 }; 40 out = ^{ (void) obj; }; 41 } 42 43 // ...or non-trivial destructors... 44 // CHECK: define void @_ZN5test15test4Ev() 45 // CHECK: [[OBJ:%.*]] = alloca 46 // CHECK: [[BLOCK:%.*]] = alloca [[BLOCK_T:%.*]], 47 // CHECK: [[T0:%.*]] = bitcast [[BLOCK_T]]* [[BLOCK]] to void ()* 48 // CHECK: store void ()* [[T0]], void ()** @out 49 struct scope { int x; ~scope(); }; 50 void test4() { 51 const scope obj = { 5 }; 52 out = ^{ (void) obj; }; 53 } 54 55 // ...or non-trivial copy constructors, but it's not clear how to do 56 // that and still have a constant initializer in '03. 57} 58