Home | History | Annotate | Download | only in X86
      1 ; RUN: llc -verify-machineinstrs -mtriple=i686-pc-windows-msvc < %s | FileCheck --check-prefix=X86 %s
      2 ; RUN: llc -verify-machineinstrs -mtriple=x86_64-pc-windows-msvc < %s | FileCheck --check-prefix=X64 %s
      3 
      4 %struct.Dtor = type { i8 }
      5 
      6 define void @simple_cleanup() #0 personality i8* bitcast (i32 (...)* @__CxxFrameHandler3 to i8*) {
      7 entry:
      8   %o = alloca %struct.Dtor, align 1
      9   invoke void @f(i32 1)
     10           to label %invoke.cont unwind label %ehcleanup
     11 
     12 invoke.cont:                                      ; preds = %entry
     13   call x86_thiscallcc void @"\01??1Dtor@@QAE@XZ"(%struct.Dtor* %o) #2
     14   ret void
     15 
     16 ehcleanup:                                        ; preds = %entry
     17   %0 = cleanuppad within none []
     18   call x86_thiscallcc void @"\01??1Dtor@@QAE@XZ"(%struct.Dtor* %o) #2 [ "funclet"(token %0) ]
     19   cleanupret from %0 unwind to caller
     20 }
     21 
     22 ; CHECK: simple_cleanup:                         # @simple_cleanup
     23 ; CHECK:         pushq   %rbp
     24 ; CHECK:         subq    $48, %rsp
     25 ; CHECK:         leaq    48(%rsp), %rbp
     26 ; CHECK:         movq    $-2, -8(%rbp)
     27 ; CHECK:         movl    $1, %ecx
     28 ; CHECK:         callq   f
     29 ; CHECK:         callq   "??1Dtor@@QAE@XZ"
     30 ; CHECK:         nop
     31 ; CHECK:         addq    $48, %rsp
     32 ; CHECK:         popq    %rbp
     33 ; CHECK:         retq
     34 
     35 ; CHECK: "?dtor$2@?0?simple_cleanup@4HA":
     36 ; CHECK:         callq   "??1Dtor@@QAE@XZ"
     37 ; CHECK:         retq
     38 
     39 ; CHECK: $cppxdata$simple_cleanup:
     40 ; CHECK-NEXT:         .long   429065506
     41 ; CHECK-NEXT:         .long   1
     42 ; CHECK-NEXT:         .long   ($stateUnwindMap$simple_cleanup)@IMGREL
     43 ; CHECK-NEXT:         .long   0
     44 ; CHECK-NEXT:         .long   0
     45 ; CHECK-NEXT:         .long   3
     46 ; CHECK-NEXT:         .long   ($ip2state$simple_cleanup)@IMGREL
     47 ; UnwindHelp offset should match the -2 store above
     48 ; CHECK-NEXT:         .long   40
     49 ; CHECK-NEXT:         .long   0
     50 ; CHECK-NEXT:         .long   1
     51 
     52 declare void @f(i32) #0
     53 
     54 declare i32 @__CxxFrameHandler3(...)
     55 
     56 ; Function Attrs: nounwind
     57 declare x86_thiscallcc void @"\01??1Dtor@@QAE@XZ"(%struct.Dtor*) #1
     58 
     59 define void @nested_cleanup() #0 personality i8* bitcast (i32 (...)* @__CxxFrameHandler3 to i8*) {
     60 entry:
     61   %o1 = alloca %struct.Dtor, align 1
     62   %o2 = alloca %struct.Dtor, align 1
     63   invoke void @f(i32 1)
     64           to label %invoke.cont unwind label %cleanup.outer
     65 
     66 invoke.cont:                                      ; preds = %entry
     67   invoke void @f(i32 2)
     68           to label %invoke.cont.1 unwind label %cleanup.inner
     69 
     70 invoke.cont.1:                                    ; preds = %invoke.cont
     71   call x86_thiscallcc void @"\01??1Dtor@@QAE@XZ"(%struct.Dtor* %o2) #2
     72   invoke void @f(i32 3)
     73           to label %invoke.cont.2 unwind label %cleanup.outer
     74 
     75 invoke.cont.2:                                    ; preds = %invoke.cont.1
     76   call x86_thiscallcc void @"\01??1Dtor@@QAE@XZ"(%struct.Dtor* %o1) #2
     77   ret void
     78 
     79 cleanup.inner:                                        ; preds = %invoke.cont
     80   %0 = cleanuppad within none []
     81   call x86_thiscallcc void @"\01??1Dtor@@QAE@XZ"(%struct.Dtor* %o2) #2 [ "funclet"(token %0) ]
     82   cleanupret from %0 unwind label %cleanup.outer
     83 
     84 cleanup.outer:                                      ; preds = %invoke.cont.1, %cleanup.inner, %entry
     85   %1 = cleanuppad within none []
     86   call x86_thiscallcc void @"\01??1Dtor@@QAE@XZ"(%struct.Dtor* %o1) #2 [ "funclet"(token %1) ]
     87   cleanupret from %1 unwind to caller
     88 }
     89 
     90 ; X86-LABEL: _nested_cleanup:
     91 ; X86: pushl   $1
     92 ; X86: calll   _f
     93 ; X86: pushl   $2
     94 ; X86: calll   _f
     95 ; X86: pushl   $3
     96 ; X86: calll   _f
     97 
     98 ; X86: "?dtor$[[cleanup_inner:[0-9]+]]@?0?nested_cleanup@4HA":
     99 ; X86: LBB1_[[cleanup_inner]]: # %cleanup.inner{{$}}
    100 ; X86: pushl %ebp
    101 ; X86: leal    {{.*}}(%ebp), %ecx
    102 ; X86: calll   "??1Dtor@@QAE@XZ"
    103 ; X86: popl %ebp
    104 ; X86: retl
    105 
    106 ; X86: "?dtor$[[cleanup_outer:[0-9]+]]@?0?nested_cleanup@4HA":
    107 ; X86: LBB1_[[cleanup_outer]]: # %cleanup.outer{{$}}
    108 ; X86: pushl %ebp
    109 ; X86: leal    {{.*}}(%ebp), %ecx
    110 ; X86: calll   "??1Dtor@@QAE@XZ"
    111 ; X86: popl %ebp
    112 ; X86: retl
    113 
    114 ; X86: L__ehtable$nested_cleanup:
    115 ; X86:         .long   429065506
    116 ; X86:         .long   2
    117 ; X86:         .long   ($stateUnwindMap$nested_cleanup)
    118 ; X86:         .long   0
    119 ; X86:         .long   0
    120 ; X86:         .long   0
    121 ; X86:         .long   0
    122 ; X86:         .long   0
    123 ; X86:         .long   1
    124 ; X86: $stateUnwindMap$nested_cleanup:
    125 ; X86:         .long   -1
    126 ; X86:         .long   "?dtor$[[cleanup_outer]]@?0?nested_cleanup@4HA"
    127 ; X86:         .long   0
    128 ; X86:         .long   "?dtor$[[cleanup_inner]]@?0?nested_cleanup@4HA"
    129 
    130 ; X64-LABEL: nested_cleanup:
    131 ; X64: .Lfunc_begin1:
    132 ; X64: .Ltmp13:
    133 ; X64: movl    $1, %ecx
    134 ; X64: callq   f
    135 ; X64: .Ltmp15:
    136 ; X64: movl    $2, %ecx
    137 ; X64: callq   f
    138 ; X64: .Ltmp16:
    139 ; X64: callq   "??1Dtor@@QAE@XZ"
    140 ; X64: .Ltmp17:
    141 ; X64: movl    $3, %ecx
    142 ; X64: callq   f
    143 ; X64: .Ltmp18:
    144 
    145 ; X64: "?dtor$[[cleanup_inner:[0-9]+]]@?0?nested_cleanup@4HA":
    146 ; X64: LBB1_[[cleanup_inner]]: # %cleanup.inner{{$}}
    147 ; X64: pushq %rbp
    148 ; X64: leaq    {{.*}}(%rbp), %rcx
    149 ; X64: callq   "??1Dtor@@QAE@XZ"
    150 ; X64: popq %rbp
    151 ; X64: retq
    152 
    153 ; X64:        .seh_handlerdata
    154 ; X64:        .text
    155 ; X64:        .seh_endproc
    156 
    157 ; X64: "?dtor$[[cleanup_outer:[0-9]+]]@?0?nested_cleanup@4HA":
    158 ; X64: LBB1_[[cleanup_outer]]: # %cleanup.outer{{$}}
    159 ; X64: pushq %rbp
    160 ; X64: leaq    {{.*}}(%rbp), %rcx
    161 ; X64: callq   "??1Dtor@@QAE@XZ"
    162 ; X64: popq %rbp
    163 ; X64: retq
    164 
    165 ; X64:        .section .xdata,"dr"
    166 ; X64-NEXT: .p2align  2
    167 ; X64: $cppxdata$nested_cleanup:
    168 ; X64-NEXT: .long   429065506
    169 ; X64-NEXT: .long   2
    170 ; X64-NEXT: .long   ($stateUnwindMap$nested_cleanup)@IMGREL
    171 ; X64-NEXT: .long   0
    172 ; X64-NEXT: .long   0
    173 ; X64-NEXT: .long   5
    174 ; X64-NEXT: .long   ($ip2state$nested_cleanup)@IMGREL
    175 ; X64-NEXT: .long   56
    176 ; X64-NEXT: .long   0
    177 ; X64-NEXT: .long   1
    178 
    179 ; X64: $stateUnwindMap$nested_cleanup:
    180 ; X64-NEXT: .long   -1
    181 ; X64-NEXT: .long   "?dtor$[[cleanup_outer]]@?0?nested_cleanup@4HA"@IMGREL
    182 ; X64-NEXT: .long   0
    183 ; X64-NEXT: .long   "?dtor$[[cleanup_inner]]@?0?nested_cleanup@4HA"@IMGREL
    184 
    185 ; X64: $ip2state$nested_cleanup:
    186 ; X64-NEXT: .long   .Lfunc_begin1@IMGREL
    187 ; X64-NEXT: .long   -1
    188 ; X64-NEXT: .long   .Ltmp13@IMGREL
    189 ; X64-NEXT: .long   0
    190 ; X64-NEXT: .long   .Ltmp15@IMGREL
    191 ; X64-NEXT: .long   1
    192 ; X64-NEXT: .long   .Ltmp17@IMGREL
    193 ; X64-NEXT: .long   0
    194 ; X64-NEXT: .long   .Ltmp18@IMGREL+1
    195 ; X64-NEXT: .long   -1
    196 
    197 attributes #0 = { "disable-tail-calls"="false" "less-precise-fpmad"="false" "no-frame-pointer-elim"="false" "no-infs-fp-math"="false" "no-nans-fp-math"="false" "no-realign-stack" "stack-protector-buffer-size"="8" "unsafe-fp-math"="false" "use-soft-float"="false" }
    198 attributes #1 = { nounwind "disable-tail-calls"="false" "less-precise-fpmad"="false" "no-frame-pointer-elim"="false" "no-infs-fp-math"="false" "no-nans-fp-math"="false" "no-realign-stack" "stack-protector-buffer-size"="8" "unsafe-fp-math"="false" "use-soft-float"="false" }
    199 attributes #2 = { nounwind }
    200