1 ; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py 2 ; RUN: llc < %s -mtriple=x86_64-pc-linux -mattr=+sse2 | FileCheck %s --check-prefix=SSE --check-prefix=SSE2 3 ; RUN: llc < %s -mtriple=x86_64-pc-linux -mattr=+sse4.1 | FileCheck %s --check-prefix=SSE --check-prefix=SSE41 4 ; RUN: llc < %s -mtriple=x86_64-pc-linux -mattr=+avx | FileCheck %s --check-prefix=AVX --check-prefix=AVX1 5 ; RUN: llc < %s -mtriple=x86_64-pc-linux -mattr=+avx2 | FileCheck %s --check-prefix=AVX --check-prefix=AVX2 6 7 ; 8 ; ExtractElement - Constant Index 9 ; 10 11 define i8 @extractelement_v16i8_1(<16 x i8> %a) nounwind { 12 ; SSE2-LABEL: extractelement_v16i8_1: 13 ; SSE2: # %bb.0: 14 ; SSE2-NEXT: movd %xmm0, %eax 15 ; SSE2-NEXT: shrl $8, %eax 16 ; SSE2-NEXT: # kill: def $al killed $al killed $eax 17 ; SSE2-NEXT: retq 18 ; 19 ; SSE41-LABEL: extractelement_v16i8_1: 20 ; SSE41: # %bb.0: 21 ; SSE41-NEXT: pextrb $1, %xmm0, %eax 22 ; SSE41-NEXT: # kill: def $al killed $al killed $eax 23 ; SSE41-NEXT: retq 24 ; 25 ; AVX-LABEL: extractelement_v16i8_1: 26 ; AVX: # %bb.0: 27 ; AVX-NEXT: vpextrb $1, %xmm0, %eax 28 ; AVX-NEXT: # kill: def $al killed $al killed $eax 29 ; AVX-NEXT: retq 30 %b = extractelement <16 x i8> %a, i256 1 31 ret i8 %b 32 } 33 34 define i8 @extractelement_v16i8_11(<16 x i8> %a) nounwind { 35 ; SSE2-LABEL: extractelement_v16i8_11: 36 ; SSE2: # %bb.0: 37 ; SSE2-NEXT: pextrw $5, %xmm0, %eax 38 ; SSE2-NEXT: shrl $8, %eax 39 ; SSE2-NEXT: # kill: def $al killed $al killed $eax 40 ; SSE2-NEXT: retq 41 ; 42 ; SSE41-LABEL: extractelement_v16i8_11: 43 ; SSE41: # %bb.0: 44 ; SSE41-NEXT: pextrb $11, %xmm0, %eax 45 ; SSE41-NEXT: # kill: def $al killed $al killed $eax 46 ; SSE41-NEXT: retq 47 ; 48 ; AVX-LABEL: extractelement_v16i8_11: 49 ; AVX: # %bb.0: 50 ; AVX-NEXT: vpextrb $11, %xmm0, %eax 51 ; AVX-NEXT: # kill: def $al killed $al killed $eax 52 ; AVX-NEXT: retq 53 %b = extractelement <16 x i8> %a, i256 11 54 ret i8 %b 55 } 56 57 define i8 @extractelement_v16i8_14(<16 x i8> %a) nounwind { 58 ; SSE2-LABEL: extractelement_v16i8_14: 59 ; SSE2: # %bb.0: 60 ; SSE2-NEXT: pextrw $7, %xmm0, %eax 61 ; SSE2-NEXT: # kill: def $al killed $al killed $eax 62 ; SSE2-NEXT: retq 63 ; 64 ; SSE41-LABEL: extractelement_v16i8_14: 65 ; SSE41: # %bb.0: 66 ; SSE41-NEXT: pextrb $14, %xmm0, %eax 67 ; SSE41-NEXT: # kill: def $al killed $al killed $eax 68 ; SSE41-NEXT: retq 69 ; 70 ; AVX-LABEL: extractelement_v16i8_14: 71 ; AVX: # %bb.0: 72 ; AVX-NEXT: vpextrb $14, %xmm0, %eax 73 ; AVX-NEXT: # kill: def $al killed $al killed $eax 74 ; AVX-NEXT: retq 75 %b = extractelement <16 x i8> %a, i256 14 76 ret i8 %b 77 } 78 79 define i8 @extractelement_v32i8_1(<32 x i8> %a) nounwind { 80 ; SSE2-LABEL: extractelement_v32i8_1: 81 ; SSE2: # %bb.0: 82 ; SSE2-NEXT: movd %xmm0, %eax 83 ; SSE2-NEXT: shrl $8, %eax 84 ; SSE2-NEXT: # kill: def $al killed $al killed $eax 85 ; SSE2-NEXT: retq 86 ; 87 ; SSE41-LABEL: extractelement_v32i8_1: 88 ; SSE41: # %bb.0: 89 ; SSE41-NEXT: pextrb $1, %xmm0, %eax 90 ; SSE41-NEXT: # kill: def $al killed $al killed $eax 91 ; SSE41-NEXT: retq 92 ; 93 ; AVX-LABEL: extractelement_v32i8_1: 94 ; AVX: # %bb.0: 95 ; AVX-NEXT: vpextrb $1, %xmm0, %eax 96 ; AVX-NEXT: # kill: def $al killed $al killed $eax 97 ; AVX-NEXT: vzeroupper 98 ; AVX-NEXT: retq 99 %b = extractelement <32 x i8> %a, i256 1 100 ret i8 %b 101 } 102 103 define i8 @extractelement_v32i8_17(<32 x i8> %a) nounwind { 104 ; SSE2-LABEL: extractelement_v32i8_17: 105 ; SSE2: # %bb.0: 106 ; SSE2-NEXT: movd %xmm1, %eax 107 ; SSE2-NEXT: shrl $8, %eax 108 ; SSE2-NEXT: # kill: def $al killed $al killed $eax 109 ; SSE2-NEXT: retq 110 ; 111 ; SSE41-LABEL: extractelement_v32i8_17: 112 ; SSE41: # %bb.0: 113 ; SSE41-NEXT: pextrb $1, %xmm1, %eax 114 ; SSE41-NEXT: # kill: def $al killed $al killed $eax 115 ; SSE41-NEXT: retq 116 ; 117 ; AVX1-LABEL: extractelement_v32i8_17: 118 ; AVX1: # %bb.0: 119 ; AVX1-NEXT: vextractf128 $1, %ymm0, %xmm0 120 ; AVX1-NEXT: vpextrb $1, %xmm0, %eax 121 ; AVX1-NEXT: # kill: def $al killed $al killed $eax 122 ; AVX1-NEXT: vzeroupper 123 ; AVX1-NEXT: retq 124 ; 125 ; AVX2-LABEL: extractelement_v32i8_17: 126 ; AVX2: # %bb.0: 127 ; AVX2-NEXT: vextracti128 $1, %ymm0, %xmm0 128 ; AVX2-NEXT: vpextrb $1, %xmm0, %eax 129 ; AVX2-NEXT: # kill: def $al killed $al killed $eax 130 ; AVX2-NEXT: vzeroupper 131 ; AVX2-NEXT: retq 132 %b = extractelement <32 x i8> %a, i256 17 133 ret i8 %b 134 } 135 136 define i16 @extractelement_v8i16_0(<8 x i16> %a, i256 %i) nounwind { 137 ; SSE-LABEL: extractelement_v8i16_0: 138 ; SSE: # %bb.0: 139 ; SSE-NEXT: movd %xmm0, %eax 140 ; SSE-NEXT: # kill: def $ax killed $ax killed $eax 141 ; SSE-NEXT: retq 142 ; 143 ; AVX-LABEL: extractelement_v8i16_0: 144 ; AVX: # %bb.0: 145 ; AVX-NEXT: vmovd %xmm0, %eax 146 ; AVX-NEXT: # kill: def $ax killed $ax killed $eax 147 ; AVX-NEXT: retq 148 %b = extractelement <8 x i16> %a, i256 0 149 ret i16 %b 150 } 151 152 define i16 @extractelement_v8i16_3(<8 x i16> %a, i256 %i) nounwind { 153 ; SSE-LABEL: extractelement_v8i16_3: 154 ; SSE: # %bb.0: 155 ; SSE-NEXT: pextrw $3, %xmm0, %eax 156 ; SSE-NEXT: # kill: def $ax killed $ax killed $eax 157 ; SSE-NEXT: retq 158 ; 159 ; AVX-LABEL: extractelement_v8i16_3: 160 ; AVX: # %bb.0: 161 ; AVX-NEXT: vpextrw $3, %xmm0, %eax 162 ; AVX-NEXT: # kill: def $ax killed $ax killed $eax 163 ; AVX-NEXT: retq 164 %b = extractelement <8 x i16> %a, i256 3 165 ret i16 %b 166 } 167 168 define i16 @extractelement_v16i16_0(<16 x i16> %a, i256 %i) nounwind { 169 ; SSE-LABEL: extractelement_v16i16_0: 170 ; SSE: # %bb.0: 171 ; SSE-NEXT: movd %xmm0, %eax 172 ; SSE-NEXT: # kill: def $ax killed $ax killed $eax 173 ; SSE-NEXT: retq 174 ; 175 ; AVX-LABEL: extractelement_v16i16_0: 176 ; AVX: # %bb.0: 177 ; AVX-NEXT: vmovd %xmm0, %eax 178 ; AVX-NEXT: # kill: def $ax killed $ax killed $eax 179 ; AVX-NEXT: vzeroupper 180 ; AVX-NEXT: retq 181 %b = extractelement <16 x i16> %a, i256 0 182 ret i16 %b 183 } 184 185 define i16 @extractelement_v16i16_13(<16 x i16> %a, i256 %i) nounwind { 186 ; SSE-LABEL: extractelement_v16i16_13: 187 ; SSE: # %bb.0: 188 ; SSE-NEXT: pextrw $5, %xmm1, %eax 189 ; SSE-NEXT: # kill: def $ax killed $ax killed $eax 190 ; SSE-NEXT: retq 191 ; 192 ; AVX1-LABEL: extractelement_v16i16_13: 193 ; AVX1: # %bb.0: 194 ; AVX1-NEXT: vextractf128 $1, %ymm0, %xmm0 195 ; AVX1-NEXT: vpextrw $5, %xmm0, %eax 196 ; AVX1-NEXT: # kill: def $ax killed $ax killed $eax 197 ; AVX1-NEXT: vzeroupper 198 ; AVX1-NEXT: retq 199 ; 200 ; AVX2-LABEL: extractelement_v16i16_13: 201 ; AVX2: # %bb.0: 202 ; AVX2-NEXT: vextracti128 $1, %ymm0, %xmm0 203 ; AVX2-NEXT: vpextrw $5, %xmm0, %eax 204 ; AVX2-NEXT: # kill: def $ax killed $ax killed $eax 205 ; AVX2-NEXT: vzeroupper 206 ; AVX2-NEXT: retq 207 %b = extractelement <16 x i16> %a, i256 13 208 ret i16 %b 209 } 210 211 define i32 @extractelement_v4i32_0(<4 x i32> %a) nounwind { 212 ; SSE-LABEL: extractelement_v4i32_0: 213 ; SSE: # %bb.0: 214 ; SSE-NEXT: movd %xmm0, %eax 215 ; SSE-NEXT: retq 216 ; 217 ; AVX-LABEL: extractelement_v4i32_0: 218 ; AVX: # %bb.0: 219 ; AVX-NEXT: vmovd %xmm0, %eax 220 ; AVX-NEXT: retq 221 %b = extractelement <4 x i32> %a, i256 0 222 ret i32 %b 223 } 224 225 define i32 @extractelement_v4i32_3(<4 x i32> %a) nounwind { 226 ; SSE2-LABEL: extractelement_v4i32_3: 227 ; SSE2: # %bb.0: 228 ; SSE2-NEXT: pshufd {{.*#+}} xmm0 = xmm0[3,1,2,3] 229 ; SSE2-NEXT: movd %xmm0, %eax 230 ; SSE2-NEXT: retq 231 ; 232 ; SSE41-LABEL: extractelement_v4i32_3: 233 ; SSE41: # %bb.0: 234 ; SSE41-NEXT: extractps $3, %xmm0, %eax 235 ; SSE41-NEXT: retq 236 ; 237 ; AVX-LABEL: extractelement_v4i32_3: 238 ; AVX: # %bb.0: 239 ; AVX-NEXT: vextractps $3, %xmm0, %eax 240 ; AVX-NEXT: retq 241 %b = extractelement <4 x i32> %a, i256 3 242 ret i32 %b 243 } 244 245 define i32 @extractelement_v8i32_0(<8 x i32> %a) nounwind { 246 ; SSE-LABEL: extractelement_v8i32_0: 247 ; SSE: # %bb.0: 248 ; SSE-NEXT: movd %xmm1, %eax 249 ; SSE-NEXT: retq 250 ; 251 ; AVX1-LABEL: extractelement_v8i32_0: 252 ; AVX1: # %bb.0: 253 ; AVX1-NEXT: vextractf128 $1, %ymm0, %xmm0 254 ; AVX1-NEXT: vmovd %xmm0, %eax 255 ; AVX1-NEXT: vzeroupper 256 ; AVX1-NEXT: retq 257 ; 258 ; AVX2-LABEL: extractelement_v8i32_0: 259 ; AVX2: # %bb.0: 260 ; AVX2-NEXT: vextracti128 $1, %ymm0, %xmm0 261 ; AVX2-NEXT: vmovd %xmm0, %eax 262 ; AVX2-NEXT: vzeroupper 263 ; AVX2-NEXT: retq 264 %b = extractelement <8 x i32> %a, i256 4 265 ret i32 %b 266 } 267 268 define i32 @extractelement_v8i32_4(<8 x i32> %a) nounwind { 269 ; SSE-LABEL: extractelement_v8i32_4: 270 ; SSE: # %bb.0: 271 ; SSE-NEXT: movd %xmm1, %eax 272 ; SSE-NEXT: retq 273 ; 274 ; AVX1-LABEL: extractelement_v8i32_4: 275 ; AVX1: # %bb.0: 276 ; AVX1-NEXT: vextractf128 $1, %ymm0, %xmm0 277 ; AVX1-NEXT: vmovd %xmm0, %eax 278 ; AVX1-NEXT: vzeroupper 279 ; AVX1-NEXT: retq 280 ; 281 ; AVX2-LABEL: extractelement_v8i32_4: 282 ; AVX2: # %bb.0: 283 ; AVX2-NEXT: vextracti128 $1, %ymm0, %xmm0 284 ; AVX2-NEXT: vmovd %xmm0, %eax 285 ; AVX2-NEXT: vzeroupper 286 ; AVX2-NEXT: retq 287 %b = extractelement <8 x i32> %a, i256 4 288 ret i32 %b 289 } 290 291 define i32 @extractelement_v8i32_7(<8 x i32> %a) nounwind { 292 ; SSE2-LABEL: extractelement_v8i32_7: 293 ; SSE2: # %bb.0: 294 ; SSE2-NEXT: pshufd {{.*#+}} xmm0 = xmm1[3,1,2,3] 295 ; SSE2-NEXT: movd %xmm0, %eax 296 ; SSE2-NEXT: retq 297 ; 298 ; SSE41-LABEL: extractelement_v8i32_7: 299 ; SSE41: # %bb.0: 300 ; SSE41-NEXT: extractps $3, %xmm1, %eax 301 ; SSE41-NEXT: retq 302 ; 303 ; AVX-LABEL: extractelement_v8i32_7: 304 ; AVX: # %bb.0: 305 ; AVX-NEXT: vextractf128 $1, %ymm0, %xmm0 306 ; AVX-NEXT: vextractps $3, %xmm0, %eax 307 ; AVX-NEXT: vzeroupper 308 ; AVX-NEXT: retq 309 %b = extractelement <8 x i32> %a, i64 7 310 ret i32 %b 311 } 312 313 define i64 @extractelement_v2i64_0(<2 x i64> %a, i256 %i) nounwind { 314 ; SSE-LABEL: extractelement_v2i64_0: 315 ; SSE: # %bb.0: 316 ; SSE-NEXT: movq %xmm0, %rax 317 ; SSE-NEXT: retq 318 ; 319 ; AVX-LABEL: extractelement_v2i64_0: 320 ; AVX: # %bb.0: 321 ; AVX-NEXT: vmovq %xmm0, %rax 322 ; AVX-NEXT: retq 323 %b = extractelement <2 x i64> %a, i256 0 324 ret i64 %b 325 } 326 327 define i64 @extractelement_v2i64_1(<2 x i64> %a, i256 %i) nounwind { 328 ; SSE2-LABEL: extractelement_v2i64_1: 329 ; SSE2: # %bb.0: 330 ; SSE2-NEXT: pshufd {{.*#+}} xmm0 = xmm0[2,3,0,1] 331 ; SSE2-NEXT: movq %xmm0, %rax 332 ; SSE2-NEXT: retq 333 ; 334 ; SSE41-LABEL: extractelement_v2i64_1: 335 ; SSE41: # %bb.0: 336 ; SSE41-NEXT: pextrq $1, %xmm0, %rax 337 ; SSE41-NEXT: retq 338 ; 339 ; AVX-LABEL: extractelement_v2i64_1: 340 ; AVX: # %bb.0: 341 ; AVX-NEXT: vpextrq $1, %xmm0, %rax 342 ; AVX-NEXT: retq 343 %b = extractelement <2 x i64> %a, i256 1 344 ret i64 %b 345 } 346 347 define i64 @extractelement_v4i64_1(<4 x i64> %a, i256 %i) nounwind { 348 ; SSE2-LABEL: extractelement_v4i64_1: 349 ; SSE2: # %bb.0: 350 ; SSE2-NEXT: pshufd {{.*#+}} xmm0 = xmm0[2,3,0,1] 351 ; SSE2-NEXT: movq %xmm0, %rax 352 ; SSE2-NEXT: retq 353 ; 354 ; SSE41-LABEL: extractelement_v4i64_1: 355 ; SSE41: # %bb.0: 356 ; SSE41-NEXT: pextrq $1, %xmm0, %rax 357 ; SSE41-NEXT: retq 358 ; 359 ; AVX-LABEL: extractelement_v4i64_1: 360 ; AVX: # %bb.0: 361 ; AVX-NEXT: vpextrq $1, %xmm0, %rax 362 ; AVX-NEXT: vzeroupper 363 ; AVX-NEXT: retq 364 %b = extractelement <4 x i64> %a, i256 1 365 ret i64 %b 366 } 367 368 define i64 @extractelement_v4i64_3(<4 x i64> %a, i256 %i) nounwind { 369 ; SSE2-LABEL: extractelement_v4i64_3: 370 ; SSE2: # %bb.0: 371 ; SSE2-NEXT: pshufd {{.*#+}} xmm0 = xmm1[2,3,0,1] 372 ; SSE2-NEXT: movq %xmm0, %rax 373 ; SSE2-NEXT: retq 374 ; 375 ; SSE41-LABEL: extractelement_v4i64_3: 376 ; SSE41: # %bb.0: 377 ; SSE41-NEXT: pextrq $1, %xmm1, %rax 378 ; SSE41-NEXT: retq 379 ; 380 ; AVX1-LABEL: extractelement_v4i64_3: 381 ; AVX1: # %bb.0: 382 ; AVX1-NEXT: vextractf128 $1, %ymm0, %xmm0 383 ; AVX1-NEXT: vpextrq $1, %xmm0, %rax 384 ; AVX1-NEXT: vzeroupper 385 ; AVX1-NEXT: retq 386 ; 387 ; AVX2-LABEL: extractelement_v4i64_3: 388 ; AVX2: # %bb.0: 389 ; AVX2-NEXT: vextracti128 $1, %ymm0, %xmm0 390 ; AVX2-NEXT: vpextrq $1, %xmm0, %rax 391 ; AVX2-NEXT: vzeroupper 392 ; AVX2-NEXT: retq 393 %b = extractelement <4 x i64> %a, i256 3 394 ret i64 %b 395 } 396 397 ; 398 ; ExtractElement - Variable Index 399 ; 400 401 define i8 @extractelement_v16i8_var(<16 x i8> %a, i256 %i) nounwind { 402 ; SSE-LABEL: extractelement_v16i8_var: 403 ; SSE: # %bb.0: 404 ; SSE-NEXT: andl $15, %edi 405 ; SSE-NEXT: movaps %xmm0, -{{[0-9]+}}(%rsp) 406 ; SSE-NEXT: movb -24(%rsp,%rdi), %al 407 ; SSE-NEXT: retq 408 ; 409 ; AVX-LABEL: extractelement_v16i8_var: 410 ; AVX: # %bb.0: 411 ; AVX-NEXT: andl $15, %edi 412 ; AVX-NEXT: vmovaps %xmm0, -{{[0-9]+}}(%rsp) 413 ; AVX-NEXT: movb -24(%rsp,%rdi), %al 414 ; AVX-NEXT: retq 415 %b = extractelement <16 x i8> %a, i256 %i 416 ret i8 %b 417 } 418 419 define i8 @extractelement_v32i8_var(<32 x i8> %a, i256 %i) nounwind { 420 ; SSE-LABEL: extractelement_v32i8_var: 421 ; SSE: # %bb.0: 422 ; SSE-NEXT: pushq %rbp 423 ; SSE-NEXT: movq %rsp, %rbp 424 ; SSE-NEXT: andq $-32, %rsp 425 ; SSE-NEXT: subq $64, %rsp 426 ; SSE-NEXT: andl $31, %edi 427 ; SSE-NEXT: movaps %xmm1, {{[0-9]+}}(%rsp) 428 ; SSE-NEXT: movaps %xmm0, (%rsp) 429 ; SSE-NEXT: movb (%rsp,%rdi), %al 430 ; SSE-NEXT: movq %rbp, %rsp 431 ; SSE-NEXT: popq %rbp 432 ; SSE-NEXT: retq 433 ; 434 ; AVX-LABEL: extractelement_v32i8_var: 435 ; AVX: # %bb.0: 436 ; AVX-NEXT: pushq %rbp 437 ; AVX-NEXT: movq %rsp, %rbp 438 ; AVX-NEXT: andq $-32, %rsp 439 ; AVX-NEXT: subq $64, %rsp 440 ; AVX-NEXT: andl $31, %edi 441 ; AVX-NEXT: vmovaps %ymm0, (%rsp) 442 ; AVX-NEXT: movb (%rsp,%rdi), %al 443 ; AVX-NEXT: movq %rbp, %rsp 444 ; AVX-NEXT: popq %rbp 445 ; AVX-NEXT: vzeroupper 446 ; AVX-NEXT: retq 447 %b = extractelement <32 x i8> %a, i256 %i 448 ret i8 %b 449 } 450 451 define i16 @extractelement_v8i16_var(<8 x i16> %a, i256 %i) nounwind { 452 ; SSE-LABEL: extractelement_v8i16_var: 453 ; SSE: # %bb.0: 454 ; SSE-NEXT: andl $7, %edi 455 ; SSE-NEXT: movaps %xmm0, -{{[0-9]+}}(%rsp) 456 ; SSE-NEXT: movzwl -24(%rsp,%rdi,2), %eax 457 ; SSE-NEXT: retq 458 ; 459 ; AVX-LABEL: extractelement_v8i16_var: 460 ; AVX: # %bb.0: 461 ; AVX-NEXT: andl $7, %edi 462 ; AVX-NEXT: vmovaps %xmm0, -{{[0-9]+}}(%rsp) 463 ; AVX-NEXT: movzwl -24(%rsp,%rdi,2), %eax 464 ; AVX-NEXT: retq 465 %b = extractelement <8 x i16> %a, i256 %i 466 ret i16 %b 467 } 468 469 define i16 @extractelement_v16i16_var(<16 x i16> %a, i256 %i) nounwind { 470 ; SSE-LABEL: extractelement_v16i16_var: 471 ; SSE: # %bb.0: 472 ; SSE-NEXT: pushq %rbp 473 ; SSE-NEXT: movq %rsp, %rbp 474 ; SSE-NEXT: andq $-32, %rsp 475 ; SSE-NEXT: subq $64, %rsp 476 ; SSE-NEXT: andl $15, %edi 477 ; SSE-NEXT: movaps %xmm1, {{[0-9]+}}(%rsp) 478 ; SSE-NEXT: movaps %xmm0, (%rsp) 479 ; SSE-NEXT: movzwl (%rsp,%rdi,2), %eax 480 ; SSE-NEXT: movq %rbp, %rsp 481 ; SSE-NEXT: popq %rbp 482 ; SSE-NEXT: retq 483 ; 484 ; AVX-LABEL: extractelement_v16i16_var: 485 ; AVX: # %bb.0: 486 ; AVX-NEXT: pushq %rbp 487 ; AVX-NEXT: movq %rsp, %rbp 488 ; AVX-NEXT: andq $-32, %rsp 489 ; AVX-NEXT: subq $64, %rsp 490 ; AVX-NEXT: andl $15, %edi 491 ; AVX-NEXT: vmovaps %ymm0, (%rsp) 492 ; AVX-NEXT: movzwl (%rsp,%rdi,2), %eax 493 ; AVX-NEXT: movq %rbp, %rsp 494 ; AVX-NEXT: popq %rbp 495 ; AVX-NEXT: vzeroupper 496 ; AVX-NEXT: retq 497 %b = extractelement <16 x i16> %a, i256 %i 498 ret i16 %b 499 } 500 501 define i32 @extractelement_v4i32_var(<4 x i32> %a, i256 %i) nounwind { 502 ; SSE-LABEL: extractelement_v4i32_var: 503 ; SSE: # %bb.0: 504 ; SSE-NEXT: andl $3, %edi 505 ; SSE-NEXT: movaps %xmm0, -{{[0-9]+}}(%rsp) 506 ; SSE-NEXT: movl -24(%rsp,%rdi,4), %eax 507 ; SSE-NEXT: retq 508 ; 509 ; AVX-LABEL: extractelement_v4i32_var: 510 ; AVX: # %bb.0: 511 ; AVX-NEXT: andl $3, %edi 512 ; AVX-NEXT: vmovaps %xmm0, -{{[0-9]+}}(%rsp) 513 ; AVX-NEXT: movl -24(%rsp,%rdi,4), %eax 514 ; AVX-NEXT: retq 515 %b = extractelement <4 x i32> %a, i256 %i 516 ret i32 %b 517 } 518 519 define i32 @extractelement_v8i32_var(<8 x i32> %a, i256 %i) nounwind { 520 ; SSE-LABEL: extractelement_v8i32_var: 521 ; SSE: # %bb.0: 522 ; SSE-NEXT: pushq %rbp 523 ; SSE-NEXT: movq %rsp, %rbp 524 ; SSE-NEXT: andq $-32, %rsp 525 ; SSE-NEXT: subq $64, %rsp 526 ; SSE-NEXT: andl $7, %edi 527 ; SSE-NEXT: movaps %xmm1, {{[0-9]+}}(%rsp) 528 ; SSE-NEXT: movaps %xmm0, (%rsp) 529 ; SSE-NEXT: movl (%rsp,%rdi,4), %eax 530 ; SSE-NEXT: movq %rbp, %rsp 531 ; SSE-NEXT: popq %rbp 532 ; SSE-NEXT: retq 533 ; 534 ; AVX-LABEL: extractelement_v8i32_var: 535 ; AVX: # %bb.0: 536 ; AVX-NEXT: pushq %rbp 537 ; AVX-NEXT: movq %rsp, %rbp 538 ; AVX-NEXT: andq $-32, %rsp 539 ; AVX-NEXT: subq $64, %rsp 540 ; AVX-NEXT: andl $7, %edi 541 ; AVX-NEXT: vmovaps %ymm0, (%rsp) 542 ; AVX-NEXT: movl (%rsp,%rdi,4), %eax 543 ; AVX-NEXT: movq %rbp, %rsp 544 ; AVX-NEXT: popq %rbp 545 ; AVX-NEXT: vzeroupper 546 ; AVX-NEXT: retq 547 %b = extractelement <8 x i32> %a, i256 %i 548 ret i32 %b 549 } 550 551 define i64 @extractelement_v2i64_var(<2 x i64> %a, i256 %i) nounwind { 552 ; SSE-LABEL: extractelement_v2i64_var: 553 ; SSE: # %bb.0: 554 ; SSE-NEXT: andl $1, %edi 555 ; SSE-NEXT: movaps %xmm0, -{{[0-9]+}}(%rsp) 556 ; SSE-NEXT: movq -24(%rsp,%rdi,8), %rax 557 ; SSE-NEXT: retq 558 ; 559 ; AVX-LABEL: extractelement_v2i64_var: 560 ; AVX: # %bb.0: 561 ; AVX-NEXT: andl $1, %edi 562 ; AVX-NEXT: vmovaps %xmm0, -{{[0-9]+}}(%rsp) 563 ; AVX-NEXT: movq -24(%rsp,%rdi,8), %rax 564 ; AVX-NEXT: retq 565 %b = extractelement <2 x i64> %a, i256 %i 566 ret i64 %b 567 } 568 569 define i64 @extractelement_v4i64_var(<4 x i64> %a, i256 %i) nounwind { 570 ; SSE-LABEL: extractelement_v4i64_var: 571 ; SSE: # %bb.0: 572 ; SSE-NEXT: pushq %rbp 573 ; SSE-NEXT: movq %rsp, %rbp 574 ; SSE-NEXT: andq $-32, %rsp 575 ; SSE-NEXT: subq $64, %rsp 576 ; SSE-NEXT: andl $3, %edi 577 ; SSE-NEXT: movaps %xmm1, {{[0-9]+}}(%rsp) 578 ; SSE-NEXT: movaps %xmm0, (%rsp) 579 ; SSE-NEXT: movq (%rsp,%rdi,8), %rax 580 ; SSE-NEXT: movq %rbp, %rsp 581 ; SSE-NEXT: popq %rbp 582 ; SSE-NEXT: retq 583 ; 584 ; AVX-LABEL: extractelement_v4i64_var: 585 ; AVX: # %bb.0: 586 ; AVX-NEXT: pushq %rbp 587 ; AVX-NEXT: movq %rsp, %rbp 588 ; AVX-NEXT: andq $-32, %rsp 589 ; AVX-NEXT: subq $64, %rsp 590 ; AVX-NEXT: andl $3, %edi 591 ; AVX-NEXT: vmovaps %ymm0, (%rsp) 592 ; AVX-NEXT: movq (%rsp,%rdi,8), %rax 593 ; AVX-NEXT: movq %rbp, %rsp 594 ; AVX-NEXT: popq %rbp 595 ; AVX-NEXT: vzeroupper 596 ; AVX-NEXT: retq 597 %b = extractelement <4 x i64> %a, i256 %i 598 ret i64 %b 599 } 600 601 ; 602 ; ExtractElement - Constant (Out Of Range) Index 603 ; 604 605 define i8 @extractelement_32i8_m1(<32 x i8> %a) nounwind { 606 ; SSE-LABEL: extractelement_32i8_m1: 607 ; SSE: # %bb.0: 608 ; SSE-NEXT: retq 609 ; 610 ; AVX-LABEL: extractelement_32i8_m1: 611 ; AVX: # %bb.0: 612 ; AVX-NEXT: retq 613 %b = extractelement <32 x i8> %a, i256 -1 614 ret i8 %b 615 } 616 617 define i16 @extractelement_v16i16_m4(<16 x i16> %a, i256 %i) nounwind { 618 ; SSE-LABEL: extractelement_v16i16_m4: 619 ; SSE: # %bb.0: 620 ; SSE-NEXT: retq 621 ; 622 ; AVX-LABEL: extractelement_v16i16_m4: 623 ; AVX: # %bb.0: 624 ; AVX-NEXT: retq 625 %b = extractelement <16 x i16> %a, i256 -4 626 ret i16 %b 627 } 628 629 define i32 @extractelement_v8i32_15(<8 x i32> %a) nounwind { 630 ; SSE-LABEL: extractelement_v8i32_15: 631 ; SSE: # %bb.0: 632 ; SSE-NEXT: retq 633 ; 634 ; AVX-LABEL: extractelement_v8i32_15: 635 ; AVX: # %bb.0: 636 ; AVX-NEXT: retq 637 %b = extractelement <8 x i32> %a, i64 15 638 ret i32 %b 639 } 640 641 define i64 @extractelement_v4i64_4(<4 x i64> %a, i256 %i) nounwind { 642 ; SSE-LABEL: extractelement_v4i64_4: 643 ; SSE: # %bb.0: 644 ; SSE-NEXT: retq 645 ; 646 ; AVX-LABEL: extractelement_v4i64_4: 647 ; AVX: # %bb.0: 648 ; AVX-NEXT: retq 649 %b = extractelement <4 x i64> %a, i256 4 650 ret i64 %b 651 } 652