mirror of
https://github.com/c64scene-ar/llvm-6502.git
synced 2026-04-24 13:18:17 +00:00
Lower X%C into X/C+stuff. This allows the 'division by a constant' logic to
apply to rems as well as divs. This fixes PR945 and speeds up ReedSolomon
from 14.57s to 10.90s (which is now faster than gcc).
It compiles CodeGen/X86/rem.ll into:
_test1:
subl $4, %esp
movl %esi, (%esp)
movl $2155905153, %ecx
movl 8(%esp), %esi
movl %esi, %eax
imull %ecx
addl %esi, %edx
movl %edx, %eax
shrl $31, %eax
sarl $7, %edx
addl %eax, %edx
imull $255, %edx, %eax
subl %eax, %esi
movl %esi, %eax
movl (%esp), %esi
addl $4, %esp
ret
_test2:
movl 4(%esp), %eax
movl %eax, %ecx
sarl $31, %ecx
shrl $24, %ecx
addl %eax, %ecx
andl $4294967040, %ecx
subl %ecx, %eax
ret
_test3:
subl $4, %esp
movl %esi, (%esp)
movl $2155905153, %ecx
movl 8(%esp), %esi
movl %esi, %eax
mull %ecx
shrl $7, %edx
imull $255, %edx, %eax
subl %eax, %esi
movl %esi, %eax
movl (%esp), %esi
addl $4, %esp
ret
instead of div/idiv instructions.
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@30920 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
@@ -885,6 +885,18 @@ SDOperand DAGCombiner::visitSREM(SDNode *N) {
|
||||
if (TLI.MaskedValueIsZero(N1, SignBit) &&
|
||||
TLI.MaskedValueIsZero(N0, SignBit))
|
||||
return DAG.getNode(ISD::UREM, VT, N0, N1);
|
||||
|
||||
// Unconditionally lower X%C -> X-X/C*C. This allows the X/C logic to hack on
|
||||
// the remainder operation.
|
||||
if (N1C && !N1C->isNullValue()) {
|
||||
SDOperand Div = DAG.getNode(ISD::SDIV, VT, N0, N1);
|
||||
SDOperand Mul = DAG.getNode(ISD::MUL, VT, Div, N1);
|
||||
SDOperand Sub = DAG.getNode(ISD::SUB, VT, N0, Mul);
|
||||
AddToWorkList(Div.Val);
|
||||
AddToWorkList(Mul.Val);
|
||||
return Sub;
|
||||
}
|
||||
|
||||
return SDOperand();
|
||||
}
|
||||
|
||||
@@ -911,6 +923,18 @@ SDOperand DAGCombiner::visitUREM(SDNode *N) {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Unconditionally lower X%C -> X-X/C*C. This allows the X/C logic to hack on
|
||||
// the remainder operation.
|
||||
if (N1C && !N1C->isNullValue()) {
|
||||
SDOperand Div = DAG.getNode(ISD::UDIV, VT, N0, N1);
|
||||
SDOperand Mul = DAG.getNode(ISD::MUL, VT, Div, N1);
|
||||
SDOperand Sub = DAG.getNode(ISD::SUB, VT, N0, Mul);
|
||||
AddToWorkList(Div.Val);
|
||||
AddToWorkList(Mul.Val);
|
||||
return Sub;
|
||||
}
|
||||
|
||||
return SDOperand();
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user