mirror of
https://github.com/mozilla/gecko-dev.git
synced 2024-10-19 16:25:38 +00:00
Bug 1550751 - Skip rounding the dividend of non-truncated integer division, as already handled by a bailout. r=mgaudet
Differential Revision: https://phabricator.services.mozilla.com/D30672 --HG-- extra : moz-landing-system : lando
This commit is contained in:
parent
132d447ea6
commit
d9f43206ff
@ -1208,13 +1208,22 @@ void CodeGenerator::visitDivPowTwoI(LDivPowTwoI* ins) {
|
||||
// rounded result when the numerator is negative. See 10-1
|
||||
// "Signed Division by a Known Power of 2" in Henry
|
||||
// S. Warren, Jr.'s Hacker's Delight.
|
||||
if (mir->canBeNegativeDividend()) {
|
||||
if (mir->canBeNegativeDividend() && mir->isTruncated()) {
|
||||
// Note: There is no need to execute this code, which handles how to
|
||||
// round the signed integer division towards 0, if we previously bailed
|
||||
// due to a non-zero remainder.
|
||||
Register lhsCopy = ToRegister(ins->numeratorCopy());
|
||||
MOZ_ASSERT(lhsCopy != lhs);
|
||||
if (shift > 1) {
|
||||
// Copy the sign bit of the numerator. (= (2^32 - 1) or 0)
|
||||
masm.sarl(Imm32(31), lhs);
|
||||
}
|
||||
// Divide by 2^(32 - shift)
|
||||
// i.e. (= (2^32 - 1) / 2^(32 - shift) or 0)
|
||||
// i.e. (= (2^shift - 1) or 0)
|
||||
masm.shrl(Imm32(32 - shift), lhs);
|
||||
// If signed, make any 1 bit below the shifted bits to bubble up, such
|
||||
// that once shifted the value would be rounded towards 0.
|
||||
masm.addl(lhsCopy, lhs);
|
||||
}
|
||||
masm.sarl(Imm32(shift), lhs);
|
||||
|
@ -173,12 +173,16 @@ void LIRGeneratorX86Shared::lowerDivI(MDiv* div) {
|
||||
if (rhs != 0 && uint32_t(1) << shift == Abs(rhs)) {
|
||||
LAllocation lhs = useRegisterAtStart(div->lhs());
|
||||
LDivPowTwoI* lir;
|
||||
if (!div->canBeNegativeDividend()) {
|
||||
// When truncated with maybe a non-zero remainder, we have to round the
|
||||
// result toward 0. This requires an extra register to round up/down
|
||||
// whether the left-hand-side is signed.
|
||||
bool needRoundNeg = div->canBeNegativeDividend() && div->isTruncated();
|
||||
if (!needRoundNeg) {
|
||||
// Numerator is unsigned, so does not need adjusting.
|
||||
lir = new (alloc()) LDivPowTwoI(lhs, lhs, shift, rhs < 0);
|
||||
} else {
|
||||
// Numerator is signed, and needs adjusting, and an extra
|
||||
// lhs copy register is needed.
|
||||
// Numerator might be signed, and needs adjusting, and an extra lhs copy
|
||||
// is needed to round the result of the integer division towards zero.
|
||||
lir = new (alloc())
|
||||
LDivPowTwoI(lhs, useRegister(div->lhs()), shift, rhs < 0);
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user