Home | History | Annotate | Download | only in ObjCARC
      1 ; RUN: opt -S -objc-arc < %s | FileCheck %s
      2 
      3 declare i8* @objc_retain(i8*)
      4 declare void @objc_release(i8*)
      5 declare i8* @objc_msgSend(i8*, i8*, ...)
      6 declare void @use_pointer(i8*)
      7 declare void @callee()
      8 
      9 ; ARCOpt shouldn't try to move the releases to the block containing the invoke.
     10 
     11 ; CHECK: define void @test0(
     12 ; CHECK: invoke.cont:
     13 ; CHECK:   call void @objc_release(i8* %zipFile) nounwind, !clang.imprecise_release !0
     14 ; CHECK:   ret void
     15 ; CHECK: lpad:
     16 ; CHECK:   call void @objc_release(i8* %zipFile) nounwind, !clang.imprecise_release !0
     17 ; CHECK:   ret void
     18 define void @test0(i8* %zipFile) {
     19 entry:
     20   call i8* @objc_retain(i8* %zipFile) nounwind
     21   call void @use_pointer(i8* %zipFile)
     22   invoke void bitcast (i8* (i8*, i8*, ...)* @objc_msgSend to void (i8*)*)(i8* %zipFile) 
     23           to label %invoke.cont unwind label %lpad
     24 
     25 invoke.cont:                                      ; preds = %entry
     26   call void @objc_release(i8* %zipFile) nounwind, !clang.imprecise_release !0
     27   ret void
     28 
     29 lpad:                                             ; preds = %entry
     30   call void @objc_release(i8* %zipFile) nounwind, !clang.imprecise_release !0
     31   ret void
     32 }
     33 
     34 ; ARCOpt should move the release before the callee calls.
     35 
     36 ; CHECK: define void @test1(
     37 ; CHECK: invoke.cont:
     38 ; CHECK:   call void @objc_release(i8* %zipFile) nounwind, !clang.imprecise_release !0
     39 ; CHECK:   call void @callee()
     40 ; CHECK:   br label %done
     41 ; CHECK: lpad:
     42 ; CHECK:   call void @objc_release(i8* %zipFile) nounwind, !clang.imprecise_release !0
     43 ; CHECK:   call void @callee()
     44 ; CHECK:   br label %done
     45 ; CHECK: done:
     46 ; CHECK-NEXT: ret void
     47 define void @test1(i8* %zipFile) {
     48 entry:
     49   call i8* @objc_retain(i8* %zipFile) nounwind
     50   call void @use_pointer(i8* %zipFile)
     51   invoke void bitcast (i8* (i8*, i8*, ...)* @objc_msgSend to void (i8*)*)(i8* %zipFile)
     52           to label %invoke.cont unwind label %lpad
     53 
     54 invoke.cont:                                      ; preds = %entry
     55   call void @callee()
     56   br label %done
     57 
     58 lpad:                                             ; preds = %entry
     59   call void @callee()
     60   br label %done
     61 
     62 done:
     63   call void @objc_release(i8* %zipFile) nounwind, !clang.imprecise_release !0
     64   ret void
     65 }
     66 
     67 !0 = metadata !{}
     68