Home | History | Annotate | Download | only in X86
      1 # RUN: llc -mtriple=i686-- -run-pass machine-cp -verify-machineinstrs -o - %s | FileCheck %s
      2 
      3 --- |
      4   declare void @foo()
      5   define void @copyprop_remove_kill0() { ret void }
      6   define void @copyprop_remove_kill1() { ret void }
      7   define void @copyprop_remove_kill2() { ret void }
      8   define void @copyprop0() { ret void }
      9   define void @copyprop1() { ret void }
     10   define void @copyprop2() { ret void }
     11   define void @nocopyprop0() { ret void }
     12   define void @nocopyprop1() { ret void }
     13   define void @nocopyprop2() { ret void }
     14   define void @nocopyprop3() { ret void }
     15   define void @nocopyprop4() { ret void }
     16   define void @nocopyprop5() { ret void }
     17 ...
     18 ---
     19 # The second copy is redundant and will be removed, check that we also remove
     20 # the kill flag of intermediate instructions.
     21 # CHECK-LABEL: name: copyprop_remove_kill0
     22 # CHECK: bb.0:
     23 # CHECK-NEXT: $rax = COPY $rdi
     24 # CHECK-NEXT: NOOP implicit $rdi
     25 # CHECK-NOT: COPY
     26 # CHECK-NEXT: NOOP implicit $rax, implicit $rdi
     27 name: copyprop_remove_kill0
     28 body: |
     29   bb.0:
     30     $rax = COPY $rdi
     31     NOOP implicit killed $rdi
     32     $rdi = COPY $rax
     33     NOOP implicit $rax, implicit $rdi
     34 ...
     35 ---
     36 # The second copy is redundant and will be removed, check that we also remove
     37 # the kill flag of intermediate instructions.
     38 # CHECK-LABEL: name: copyprop_remove_kill1
     39 # CHECK: bb.0:
     40 # CHECK-NEXT: $rax = COPY $rdi
     41 # CHECK-NEXT: NOOP implicit $edi
     42 # CHECK-NOT: COPY
     43 # CHECK-NEXT: NOOP implicit $rax, implicit $rdi
     44 name: copyprop_remove_kill1
     45 body: |
     46   bb.0:
     47     $rax = COPY $rdi
     48     NOOP implicit killed $edi
     49     $rdi = COPY $rax
     50     NOOP implicit $rax, implicit $rdi
     51 ...
     52 ---
     53 # The second copy is redundant and will be removed, check that we also remove
     54 # the kill flag of intermediate instructions.
     55 # CHECK-LABEL: name: copyprop_remove_kill2
     56 # CHECK: bb.0:
     57 # CHECK-NEXT: $ax = COPY $di
     58 # CHECK-NEXT: NOOP implicit $rdi
     59 # CHECK-NOT: COPY
     60 # CHECK-NEXT: NOOP implicit $rax, implicit $rdi
     61 name: copyprop_remove_kill2
     62 body: |
     63   bb.0:
     64     $ax = COPY $di
     65     NOOP implicit killed $rdi
     66     $di = COPY $ax
     67     NOOP implicit $rax, implicit $rdi
     68 ...
     69 ---
     70 # The second copy is redundant; the call preserves the source and dest register.
     71 # CHECK-LABEL: name: copyprop0
     72 # CHECK: bb.0:
     73 # CHECK-NEXT: $rax = COPY $rdi
     74 # CHECK-NEXT: CALL64pcrel32 @foo, csr_64_rt_mostregs
     75 # CHECK-NEXT: NOOP implicit $edi
     76 # CHECK-NOT: COPY
     77 # CHECK-NEXT: NOOP implicit $rax, implicit $rdi
     78 name: copyprop0
     79 body: |
     80   bb.0:
     81     $rax = COPY $rdi
     82     CALL64pcrel32 @foo, csr_64_rt_mostregs
     83     NOOP implicit killed $edi
     84     $rdi = COPY $rax
     85     NOOP implicit $rax, implicit $rdi
     86 ...
     87 ---
     88 # The 2nd copy is redundant; The call preserves the source and dest register.
     89 # CHECK-LABEL: name: copyprop1
     90 # CHECK: bb.0:
     91 # CHECK-NEXT: $rax = COPY $rdi
     92 # CHECK-NEXT: NOOP implicit $rax
     93 # CHECK-NEXT: NOOP implicit $rax, implicit $rdi
     94 name: copyprop1
     95 body: |
     96   bb.0:
     97     $rax = COPY $rdi
     98     NOOP implicit killed $rax
     99     $rax = COPY $rdi
    100     NOOP implicit $rax, implicit $rdi
    101 ...
    102 ---
    103 # CHECK-LABEL: name: copyprop2
    104 # CHECK: bb.0:
    105 # CHECK-NEXT: $rax = COPY $rdi
    106 # CHECK-NEXT: NOOP implicit $ax
    107 # CHECK-NEXT: CALL64pcrel32 @foo, csr_64_rt_mostregs
    108 # CHECK-NOT: $rax = COPY $rdi
    109 # CHECK-NEXT: NOOP implicit $rax, implicit $rdi
    110 name: copyprop2
    111 body: |
    112   bb.0:
    113     $rax = COPY $rdi
    114     NOOP implicit killed $ax
    115     CALL64pcrel32 @foo, csr_64_rt_mostregs
    116     $rax = COPY $rdi
    117     NOOP implicit $rax, implicit $rdi
    118 ...
    119 ---
    120 # The second copy is not redundant if the source register ($rax) is clobbered
    121 # even if the dest ($rbp) is not.
    122 # CHECK-LABEL: name: nocopyprop0
    123 # CHECK: bb.0:
    124 # CHECK-NEXT: $rax = COPY $rbp
    125 # CHECK-NEXT: CALL64pcrel32 @foo, csr_64, implicit $rax, implicit $rbp
    126 # CHECK-NEXT: $rbp = COPY $rax
    127 # CHECK-NEXT: NOOP implicit $rax, implicit $rbp
    128 name: nocopyprop0
    129 body: |
    130   bb.0:
    131     $rax = COPY $rbp
    132     CALL64pcrel32 @foo, csr_64, implicit $rax, implicit $rbp
    133     $rbp = COPY $rax
    134     NOOP implicit $rax, implicit $rbp
    135 ...
    136 ---
    137 # The second copy is not redundant if the dest register ($rax) is clobbered
    138 # even if the source ($rbp) is not.
    139 # CHECK-LABEL: name: nocopyprop1
    140 # CHECK: bb.0:
    141 # CHECK-NEXT: $rbp = COPY $rax
    142 # CHECK-NEXT: CALL64pcrel32 @foo, csr_64, implicit $rax, implicit $rbp
    143 # CHECK-NEXT: $rax = COPY $rbp
    144 # CHECK-NEXT: NOOP implicit $rax, implicit $rbp
    145 name: nocopyprop1
    146 body: |
    147   bb.0:
    148     $rbp = COPY $rax
    149     CALL64pcrel32 @foo, csr_64, implicit $rax, implicit $rbp
    150     $rax = COPY $rbp
    151     NOOP implicit $rax, implicit $rbp
    152 ...
    153 ---
    154 # The second copy is not redundant if the source register ($rax) is clobbered
    155 # even if the dest ($rbp) is not.
    156 # CHECK-LABEL: name: nocopyprop2
    157 # CHECK: bb.0:
    158 # CHECK-NEXT: $rax = COPY $rbp
    159 # CHECK-NEXT: CALL64pcrel32 @foo, csr_64, implicit $rax, implicit $rbp
    160 # CHECK-NEXT: $rax = COPY $rbp
    161 # CHECK-NEXT: NOOP implicit $rax, implicit $rbp
    162 name: nocopyprop2
    163 body: |
    164   bb.0:
    165     $rax = COPY $rbp
    166     CALL64pcrel32 @foo, csr_64, implicit $rax, implicit $rbp
    167     $rax = COPY $rbp
    168     NOOP implicit $rax, implicit $rbp
    169 ...
    170 ---
    171 # The second copy is not redundant if the dest register ($rax) is clobbered
    172 # even if the source ($rbp) is not.
    173 # CHECK-LABEL: name: nocopyprop3
    174 # CHECK: bb.0:
    175 # CHECK-NEXT: $rbp = COPY $rax
    176 # CHECK-NEXT: CALL64pcrel32 @foo, csr_64, implicit $rax, implicit $rbp
    177 # CHECK-NEXT: $rbp = COPY $rax
    178 # CHECK-NEXT: NOOP implicit $rax, implicit $rbp
    179 name: nocopyprop3
    180 body: |
    181   bb.0:
    182     $rbp = COPY $rax
    183     CALL64pcrel32 @foo, csr_64, implicit $rax, implicit $rbp
    184     $rbp = COPY $rax
    185     NOOP implicit $rax, implicit $rbp
    186 ...
    187 ---
    188 # A reserved register may change its value so the 2nd copy is not redundant.
    189 # CHECK-LABEL: name: nocopyprop4
    190 # CHECK: bb.0:
    191 # CHECK-NEXT: $rax = COPY $rip
    192 # CHECK-NEXT: NOOP implicit $rax
    193 # CHECK-NEXT: $rax = COPY $rip
    194 # CHECK-NEXT: NOOP implicit $rax
    195 name: nocopyprop4
    196 body: |
    197   bb.0:
    198     $rax = COPY $rip
    199     NOOP implicit $rax
    200     $rax = COPY $rip
    201     NOOP implicit $rax
    202 ...
    203 ---
    204 # Writing to a reserved register may have additional effects (slightly illegal
    205 # testcase because writing to $rip like this should make the instruction a jump)
    206 # CHECK-LABEL: name: nocopyprop5
    207 # CHECK: bb.0:
    208 # CHECK-NEXT: $rip = COPY $rax
    209 # CHECK-NEXT: $rip = COPY $rax
    210 name: nocopyprop5
    211 body: |
    212   bb.0:
    213     $rip = COPY $rax
    214     $rip = COPY $rax
    215 ...
    216