1 ; RUN: llc < %s -march=x86-64 > %t 2 ; RUN: grep and %t | count 6 3 ; RUN: grep movzb %t | count 6 4 ; RUN: grep sar %t | count 12 5 6 ; Don't optimize away zext-inreg and sext-inreg on the loop induction 7 ; variable, because it isn't safe to do so in these cases. 8 9 define void @count_up(double* %d, i64 %n) nounwind { 10 entry: 11 br label %loop 12 13 loop: 14 %indvar = phi i64 [ 10, %entry ], [ %indvar.next, %loop ] 15 %indvar.i8 = and i64 %indvar, 255 16 %t0 = getelementptr double, double* %d, i64 %indvar.i8 17 %t1 = load double, double* %t0 18 %t2 = fmul double %t1, 0.1 19 store double %t2, double* %t0 20 %indvar.i24 = and i64 %indvar, 16777215 21 %t3 = getelementptr double, double* %d, i64 %indvar.i24 22 %t4 = load double, double* %t3 23 %t5 = fmul double %t4, 2.3 24 store double %t5, double* %t3 25 %t6 = getelementptr double, double* %d, i64 %indvar 26 %t7 = load double, double* %t6 27 %t8 = fmul double %t7, 4.5 28 store double %t8, double* %t6 29 %indvar.next = add i64 %indvar, 1 30 %exitcond = icmp eq i64 %indvar.next, 0 31 br i1 %exitcond, label %return, label %loop 32 33 return: 34 ret void 35 } 36 37 define void @count_down(double* %d, i64 %n) nounwind { 38 entry: 39 br label %loop 40 41 loop: 42 %indvar = phi i64 [ 10, %entry ], [ %indvar.next, %loop ] 43 %indvar.i8 = and i64 %indvar, 255 44 %t0 = getelementptr double, double* %d, i64 %indvar.i8 45 %t1 = load double, double* %t0 46 %t2 = fmul double %t1, 0.1 47 store double %t2, double* %t0 48 %indvar.i24 = and i64 %indvar, 16777215 49 %t3 = getelementptr double, double* %d, i64 %indvar.i24 50 %t4 = load double, double* %t3 51 %t5 = fmul double %t4, 2.3 52 store double %t5, double* %t3 53 %t6 = getelementptr double, double* %d, i64 %indvar 54 %t7 = load double, double* %t6 55 %t8 = fmul double %t7, 4.5 56 store double %t8, double* %t6 57 %indvar.next = sub i64 %indvar, 1 58 %exitcond = icmp eq i64 %indvar.next, 20 59 br i1 %exitcond, label %return, label %loop 60 61 return: 62 ret void 63 } 64 65 define void @count_up_signed(double* %d, i64 %n) nounwind { 66 entry: 67 br label %loop 68 69 loop: 70 %indvar = phi i64 [ 10, %entry ], [ %indvar.next, %loop ] 71 %s0 = shl i64 %indvar, 8 72 %indvar.i8 = ashr i64 %s0, 8 73 %t0 = getelementptr double, double* %d, i64 %indvar.i8 74 %t1 = load double, double* %t0 75 %t2 = fmul double %t1, 0.1 76 store double %t2, double* %t0 77 %s1 = shl i64 %indvar, 24 78 %indvar.i24 = ashr i64 %s1, 24 79 %t3 = getelementptr double, double* %d, i64 %indvar.i24 80 %t4 = load double, double* %t3 81 %t5 = fmul double %t4, 2.3 82 store double %t5, double* %t3 83 %t6 = getelementptr double, double* %d, i64 %indvar 84 %t7 = load double, double* %t6 85 %t8 = fmul double %t7, 4.5 86 store double %t8, double* %t6 87 %indvar.next = add i64 %indvar, 1 88 %exitcond = icmp eq i64 %indvar.next, 0 89 br i1 %exitcond, label %return, label %loop 90 91 return: 92 ret void 93 } 94 95 define void @count_down_signed(double* %d, i64 %n) nounwind { 96 entry: 97 br label %loop 98 99 loop: 100 %indvar = phi i64 [ 10, %entry ], [ %indvar.next, %loop ] 101 %s0 = shl i64 %indvar, 8 102 %indvar.i8 = ashr i64 %s0, 8 103 %t0 = getelementptr double, double* %d, i64 %indvar.i8 104 %t1 = load double, double* %t0 105 %t2 = fmul double %t1, 0.1 106 store double %t2, double* %t0 107 %s1 = shl i64 %indvar, 24 108 %indvar.i24 = ashr i64 %s1, 24 109 %t3 = getelementptr double, double* %d, i64 %indvar.i24 110 %t4 = load double, double* %t3 111 %t5 = fmul double %t4, 2.3 112 store double %t5, double* %t3 113 %t6 = getelementptr double, double* %d, i64 %indvar 114 %t7 = load double, double* %t6 115 %t8 = fmul double %t7, 4.5 116 store double %t8, double* %t6 117 %indvar.next = sub i64 %indvar, 1 118 %exitcond = icmp eq i64 %indvar.next, 20 119 br i1 %exitcond, label %return, label %loop 120 121 return: 122 ret void 123 } 124 125 define void @another_count_up(double* %d, i64 %n) nounwind { 126 entry: 127 br label %loop 128 129 loop: 130 %indvar = phi i64 [ 0, %entry ], [ %indvar.next, %loop ] 131 %indvar.i8 = and i64 %indvar, 255 132 %t0 = getelementptr double, double* %d, i64 %indvar.i8 133 %t1 = load double, double* %t0 134 %t2 = fmul double %t1, 0.1 135 store double %t2, double* %t0 136 %indvar.i24 = and i64 %indvar, 16777215 137 %t3 = getelementptr double, double* %d, i64 %indvar.i24 138 %t4 = load double, double* %t3 139 %t5 = fmul double %t4, 2.3 140 store double %t5, double* %t3 141 %t6 = getelementptr double, double* %d, i64 %indvar 142 %t7 = load double, double* %t6 143 %t8 = fmul double %t7, 4.5 144 store double %t8, double* %t6 145 %indvar.next = add i64 %indvar, 1 146 %exitcond = icmp eq i64 %indvar.next, %n 147 br i1 %exitcond, label %return, label %loop 148 149 return: 150 ret void 151 } 152 153 define void @another_count_down(double* %d, i64 %n) nounwind { 154 entry: 155 br label %loop 156 157 loop: 158 %indvar = phi i64 [ %n, %entry ], [ %indvar.next, %loop ] 159 %indvar.i8 = and i64 %indvar, 255 160 %t0 = getelementptr double, double* %d, i64 %indvar.i8 161 %t1 = load double, double* %t0 162 %t2 = fmul double %t1, 0.1 163 store double %t2, double* %t0 164 %indvar.i24 = and i64 %indvar, 16777215 165 %t3 = getelementptr double, double* %d, i64 %indvar.i24 166 %t4 = load double, double* %t3 167 %t5 = fmul double %t4, 2.3 168 store double %t5, double* %t3 169 %t6 = getelementptr double, double* %d, i64 %indvar 170 %t7 = load double, double* %t6 171 %t8 = fmul double %t7, 4.5 172 store double %t8, double* %t6 173 %indvar.next = sub i64 %indvar, 1 174 %exitcond = icmp eq i64 %indvar.next, 10 175 br i1 %exitcond, label %return, label %loop 176 177 return: 178 ret void 179 } 180 181 define void @another_count_up_signed(double* %d, i64 %n) nounwind { 182 entry: 183 br label %loop 184 185 loop: 186 %indvar = phi i64 [ 0, %entry ], [ %indvar.next, %loop ] 187 %s0 = shl i64 %indvar, 8 188 %indvar.i8 = ashr i64 %s0, 8 189 %t0 = getelementptr double, double* %d, i64 %indvar.i8 190 %t1 = load double, double* %t0 191 %t2 = fmul double %t1, 0.1 192 store double %t2, double* %t0 193 %s1 = shl i64 %indvar, 24 194 %indvar.i24 = ashr i64 %s1, 24 195 %t3 = getelementptr double, double* %d, i64 %indvar.i24 196 %t4 = load double, double* %t3 197 %t5 = fmul double %t4, 2.3 198 store double %t5, double* %t3 199 %t6 = getelementptr double, double* %d, i64 %indvar 200 %t7 = load double, double* %t6 201 %t8 = fmul double %t7, 4.5 202 store double %t8, double* %t6 203 %indvar.next = add i64 %indvar, 1 204 %exitcond = icmp eq i64 %indvar.next, %n 205 br i1 %exitcond, label %return, label %loop 206 207 return: 208 ret void 209 } 210 211 define void @another_count_down_signed(double* %d, i64 %n) nounwind { 212 entry: 213 br label %loop 214 215 loop: 216 %indvar = phi i64 [ %n, %entry ], [ %indvar.next, %loop ] 217 %s0 = shl i64 %indvar, 8 218 %indvar.i8 = ashr i64 %s0, 8 219 %t0 = getelementptr double, double* %d, i64 %indvar.i8 220 %t1 = load double, double* %t0 221 %t2 = fmul double %t1, 0.1 222 store double %t2, double* %t0 223 %s1 = shl i64 %indvar, 24 224 %indvar.i24 = ashr i64 %s1, 24 225 %t3 = getelementptr double, double* %d, i64 %indvar.i24 226 %t4 = load double, double* %t3 227 %t5 = fmul double %t4, 2.3 228 store double %t5, double* %t3 229 %t6 = getelementptr double, double* %d, i64 %indvar 230 %t7 = load double, double* %t6 231 %t8 = fmul double %t7, 4.5 232 store double %t8, double* %t6 233 %indvar.next = sub i64 %indvar, 1 234 %exitcond = icmp eq i64 %indvar.next, 10 235 br i1 %exitcond, label %return, label %loop 236 237 return: 238 ret void 239 } 240 241 define void @yet_another_count_down(double* %d, i64 %n) nounwind { 242 entry: 243 br label %loop 244 245 loop: 246 %indvar = phi i64 [ 0, %entry ], [ %indvar.next, %loop ] 247 %indvar.i8 = and i64 %indvar, 255 248 %t0 = getelementptr double, double* %d, i64 %indvar.i8 249 %t1 = load double, double* %t0 250 %t2 = fmul double %t1, 0.1 251 store double %t2, double* %t0 252 %indvar.i24 = and i64 %indvar, 16777215 253 %t3 = getelementptr double, double* %d, i64 %indvar.i24 254 %t4 = load double, double* %t3 255 %t5 = fmul double %t4, 2.3 256 store double %t5, double* %t3 257 %t6 = getelementptr double, double* %d, i64 %indvar 258 %t7 = load double, double* %t6 259 %t8 = fmul double %t7, 4.5 260 store double %t8, double* %t6 261 %indvar.next = sub i64 %indvar, 1 262 %exitcond = icmp eq i64 %indvar.next, 18446744073709551615 263 br i1 %exitcond, label %return, label %loop 264 265 return: 266 ret void 267 } 268 269 define void @yet_another_count_up(double* %d, i64 %n) nounwind { 270 entry: 271 br label %loop 272 273 loop: 274 %indvar = phi i64 [ 0, %entry ], [ %indvar.next, %loop ] 275 %indvar.i8 = and i64 %indvar, 255 276 %t0 = getelementptr double, double* %d, i64 %indvar.i8 277 %t1 = load double, double* %t0 278 %t2 = fmul double %t1, 0.1 279 store double %t2, double* %t0 280 %indvar.i24 = and i64 %indvar, 16777215 281 %t3 = getelementptr double, double* %d, i64 %indvar.i24 282 %t4 = load double, double* %t3 283 %t5 = fmul double %t4, 2.3 284 store double %t5, double* %t3 285 %t6 = getelementptr double, double* %d, i64 %indvar 286 %t7 = load double, double* %t6 287 %t8 = fmul double %t7, 4.5 288 store double %t8, double* %t6 289 %indvar.next = add i64 %indvar, 3 290 %exitcond = icmp eq i64 %indvar.next, 10 291 br i1 %exitcond, label %return, label %loop 292 293 return: 294 ret void 295 } 296 297 define void @still_another_count_down(double* %d, i64 %n) nounwind { 298 entry: 299 br label %loop 300 301 loop: 302 %indvar = phi i64 [ 10, %entry ], [ %indvar.next, %loop ] 303 %indvar.i8 = and i64 %indvar, 255 304 %t0 = getelementptr double, double* %d, i64 %indvar.i8 305 %t1 = load double, double* %t0 306 %t2 = fmul double %t1, 0.1 307 store double %t2, double* %t0 308 %indvar.i24 = and i64 %indvar, 16777215 309 %t3 = getelementptr double, double* %d, i64 %indvar.i24 310 %t4 = load double, double* %t3 311 %t5 = fmul double %t4, 2.3 312 store double %t5, double* %t3 313 %t6 = getelementptr double, double* %d, i64 %indvar 314 %t7 = load double, double* %t6 315 %t8 = fmul double %t7, 4.5 316 store double %t8, double* %t6 317 %indvar.next = sub i64 %indvar, 3 318 %exitcond = icmp eq i64 %indvar.next, 0 319 br i1 %exitcond, label %return, label %loop 320 321 return: 322 ret void 323 } 324 325 define void @yet_another_count_up_signed(double* %d, i64 %n) nounwind { 326 entry: 327 br label %loop 328 329 loop: 330 %indvar = phi i64 [ 0, %entry ], [ %indvar.next, %loop ] 331 %s0 = shl i64 %indvar, 8 332 %indvar.i8 = ashr i64 %s0, 8 333 %t0 = getelementptr double, double* %d, i64 %indvar.i8 334 %t1 = load double, double* %t0 335 %t2 = fmul double %t1, 0.1 336 store double %t2, double* %t0 337 %s1 = shl i64 %indvar, 24 338 %indvar.i24 = ashr i64 %s1, 24 339 %t3 = getelementptr double, double* %d, i64 %indvar.i24 340 %t4 = load double, double* %t3 341 %t5 = fmul double %t4, 2.3 342 store double %t5, double* %t3 343 %t6 = getelementptr double, double* %d, i64 %indvar 344 %t7 = load double, double* %t6 345 %t8 = fmul double %t7, 4.5 346 store double %t8, double* %t6 347 %indvar.next = add i64 %indvar, 3 348 %exitcond = icmp eq i64 %indvar.next, 10 349 br i1 %exitcond, label %return, label %loop 350 351 return: 352 ret void 353 } 354 355 define void @yet_another_count_down_signed(double* %d, i64 %n) nounwind { 356 entry: 357 br label %loop 358 359 loop: 360 %indvar = phi i64 [ 10, %entry ], [ %indvar.next, %loop ] 361 %s0 = shl i64 %indvar, 8 362 %indvar.i8 = ashr i64 %s0, 8 363 %t0 = getelementptr double, double* %d, i64 %indvar.i8 364 %t1 = load double, double* %t0 365 %t2 = fmul double %t1, 0.1 366 store double %t2, double* %t0 367 %s1 = shl i64 %indvar, 24 368 %indvar.i24 = ashr i64 %s1, 24 369 %t3 = getelementptr double, double* %d, i64 %indvar.i24 370 %t4 = load double, double* %t3 371 %t5 = fmul double %t4, 2.3 372 store double %t5, double* %t3 373 %t6 = getelementptr double, double* %d, i64 %indvar 374 %t7 = load double, double* %t6 375 %t8 = fmul double %t7, 4.5 376 store double %t8, double* %t6 377 %indvar.next = sub i64 %indvar, 3 378 %exitcond = icmp eq i64 %indvar.next, 0 379 br i1 %exitcond, label %return, label %loop 380 381 return: 382 ret void 383 } 384 385 386 387