diff --git a/llvm/lib/CodeGen/SelectionDAG/DAGCombiner.cpp b/llvm/lib/CodeGen/SelectionDAG/DAGCombiner.cpp index d1c7e668a2604..5f5f89a11bcb3 100644 --- a/llvm/lib/CodeGen/SelectionDAG/DAGCombiner.cpp +++ b/llvm/lib/CodeGen/SelectionDAG/DAGCombiner.cpp @@ -12101,9 +12101,8 @@ SDValue DAGCombiner::visitBSWAP(SDNode *N) { auto *ShAmt = dyn_cast(N0.getOperand(1)); EVT HalfVT = EVT::getIntegerVT(*DAG.getContext(), BW / 2); if (ShAmt && ShAmt->getAPIntValue().ult(BW) && - ShAmt->getZExtValue() >= (BW / 2) && - (ShAmt->getZExtValue() % 16) == 0 && TLI.isTypeLegal(HalfVT) && - TLI.isTruncateFree(VT, HalfVT) && + ShAmt->getZExtValue() >= (BW / 2) && (ShAmt->getZExtValue() % 8) == 0 && + TLI.isTypeLegal(HalfVT) && TLI.isTruncateFree(VT, HalfVT) && (!LegalOperations || hasOperation(ISD::BSWAP, HalfVT))) { SDValue Res = N0.getOperand(0); if (uint64_t NewShAmt = (ShAmt->getZExtValue() - (BW / 2))) diff --git a/llvm/test/CodeGen/X86/combine-bswap.ll b/llvm/test/CodeGen/X86/combine-bswap.ll index 1f074c877f3ae..0a40c61c79719 100644 --- a/llvm/test/CodeGen/X86/combine-bswap.ll +++ b/llvm/test/CodeGen/X86/combine-bswap.ll @@ -236,6 +236,26 @@ define i64 @test_bswap64_shift48(i64 %a0) { ret i64 %b } +define i64 @test_bswap64_shift40(i64 %a0) { +; X86-LABEL: test_bswap64_shift40: +; X86: # %bb.0: +; X86-NEXT: movl {{[0-9]+}}(%esp), %eax +; X86-NEXT: bswapl %eax +; X86-NEXT: shrl $8, %eax +; X86-NEXT: xorl %edx, %edx +; X86-NEXT: retl +; +; X64-LABEL: test_bswap64_shift40: +; X64: # %bb.0: +; X64-NEXT: movq %rdi, %rax +; X64-NEXT: bswapl %eax +; X64-NEXT: shrl $8, %eax +; X64-NEXT: retq + %s = shl i64 %a0, 40 + %b = call i64 @llvm.bswap.i64(i64 %s) + ret i64 %b +} + define i32 @test_bswap32_shift17(i32 %a0) { ; X86-LABEL: test_bswap32_shift17: ; X86: # %bb.0: