зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1648820 - Part 2: Optimize Math.hypot in CacheIR. r=iain
Differential Revision: https://phabricator.services.mozilla.com/D83022
This commit is contained in:
Родитель
45fed54608
Коммит
1335a54165
|
@ -5996,6 +5996,64 @@ AttachDecision CallIRGenerator::tryAttachMathPow(HandleFunction callee) {
|
|||
return AttachDecision::Attach;
|
||||
}
|
||||
|
||||
AttachDecision CallIRGenerator::tryAttachMathHypot(HandleFunction callee) {
|
||||
// Only optimize if there are 2-4 arguments.
|
||||
if (argc_ < 2 || argc_ > 4) {
|
||||
return AttachDecision::NoAction;
|
||||
}
|
||||
|
||||
for (size_t i = 0; i < argc_; i++) {
|
||||
if (!args_[i].isNumber()) {
|
||||
return AttachDecision::NoAction;
|
||||
}
|
||||
}
|
||||
|
||||
// Initialize the input operand.
|
||||
Int32OperandId argcId(writer.setInputOperandId(0));
|
||||
|
||||
// Guard callee is the 'hypot' native function.
|
||||
emitNativeCalleeGuard(callee);
|
||||
|
||||
ValOperandId firstId = writer.loadStandardCallArgument(0, argc_);
|
||||
ValOperandId secondId = writer.loadStandardCallArgument(1, argc_);
|
||||
|
||||
NumberOperandId firstNumId = writer.guardIsNumber(firstId);
|
||||
NumberOperandId secondNumId = writer.guardIsNumber(secondId);
|
||||
|
||||
ValOperandId thirdId;
|
||||
ValOperandId fourthId;
|
||||
NumberOperandId thirdNumId;
|
||||
NumberOperandId fourthNumId;
|
||||
|
||||
switch (argc_) {
|
||||
case 2:
|
||||
writer.mathHypot2NumberResult(firstNumId, secondNumId);
|
||||
break;
|
||||
case 3:
|
||||
thirdId = writer.loadStandardCallArgument(2, argc_);
|
||||
thirdNumId = writer.guardIsNumber(thirdId);
|
||||
writer.mathHypot3NumberResult(firstNumId, secondNumId, thirdNumId);
|
||||
break;
|
||||
case 4:
|
||||
thirdId = writer.loadStandardCallArgument(2, argc_);
|
||||
fourthId = writer.loadStandardCallArgument(3, argc_);
|
||||
thirdNumId = writer.guardIsNumber(thirdId);
|
||||
fourthNumId = writer.guardIsNumber(fourthId);
|
||||
writer.mathHypot4NumberResult(firstNumId, secondNumId, thirdNumId,
|
||||
fourthNumId);
|
||||
break;
|
||||
default:
|
||||
MOZ_CRASH("Unexpected number of arguments to hypot function.");
|
||||
}
|
||||
|
||||
// Math.hypot always returns a double so we don't need type monitoring.
|
||||
writer.returnFromIC();
|
||||
cacheIRStubKind_ = BaselineCacheIRStubKind::Regular;
|
||||
|
||||
trackAttached("MathHypot");
|
||||
return AttachDecision::Attach;
|
||||
}
|
||||
|
||||
AttachDecision CallIRGenerator::tryAttachMathATan2(HandleFunction callee) {
|
||||
// Requires two numbers as arguments.
|
||||
if (argc_ != 2 || !args_[0].isNumber() || !args_[1].isNumber()) {
|
||||
|
@ -6363,6 +6421,8 @@ AttachDecision CallIRGenerator::tryAttachInlinableNative(
|
|||
return tryAttachMathSqrt(callee);
|
||||
case InlinableNative::MathFRound:
|
||||
return tryAttachMathFRound(callee);
|
||||
case InlinableNative::MathHypot:
|
||||
return tryAttachMathHypot(callee);
|
||||
case InlinableNative::MathATan2:
|
||||
return tryAttachMathATan2(callee);
|
||||
case InlinableNative::MathSin:
|
||||
|
|
|
@ -1602,6 +1602,7 @@ class MOZ_RAII CallIRGenerator : public IRGenerator {
|
|||
AttachDecision tryAttachMathRound(HandleFunction callee);
|
||||
AttachDecision tryAttachMathSqrt(HandleFunction callee);
|
||||
AttachDecision tryAttachMathFRound(HandleFunction callee);
|
||||
AttachDecision tryAttachMathHypot(HandleFunction callee);
|
||||
AttachDecision tryAttachMathATan2(HandleFunction callee);
|
||||
AttachDecision tryAttachMathFunction(HandleFunction callee,
|
||||
UnaryMathFunction fun);
|
||||
|
|
|
@ -3884,6 +3884,108 @@ bool CacheIRCompiler::emitMathFRoundNumberResult(NumberOperandId inputId) {
|
|||
return true;
|
||||
}
|
||||
|
||||
bool CacheIRCompiler::emitMathHypot2NumberResult(NumberOperandId first,
|
||||
NumberOperandId second) {
|
||||
JitSpew(JitSpew_Codegen, "%s", __FUNCTION__);
|
||||
AutoOutputRegister output(*this);
|
||||
AutoScratchRegisterMaybeOutput scratch(allocator, masm, output);
|
||||
|
||||
AutoAvailableFloatRegister floatScratch0(*this, FloatReg0);
|
||||
AutoAvailableFloatRegister floatScratch1(*this, FloatReg1);
|
||||
|
||||
allocator.ensureDoubleRegister(masm, first, floatScratch0);
|
||||
allocator.ensureDoubleRegister(masm, second, floatScratch1);
|
||||
|
||||
LiveRegisterSet save(GeneralRegisterSet::Volatile(), liveVolatileFloatRegs());
|
||||
masm.PushRegsInMask(save);
|
||||
|
||||
masm.setupUnalignedABICall(scratch);
|
||||
masm.passABIArg(floatScratch0, MoveOp::DOUBLE);
|
||||
masm.passABIArg(floatScratch1, MoveOp::DOUBLE);
|
||||
|
||||
masm.callWithABI(JS_FUNC_TO_DATA_PTR(void*, ecmaHypot), MoveOp::DOUBLE);
|
||||
masm.storeCallFloatResult(floatScratch0);
|
||||
|
||||
LiveRegisterSet ignore;
|
||||
ignore.add(floatScratch0);
|
||||
masm.PopRegsInMaskIgnore(save, ignore);
|
||||
|
||||
masm.boxDouble(floatScratch0, output.valueReg(), floatScratch0);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool CacheIRCompiler::emitMathHypot3NumberResult(NumberOperandId first,
|
||||
NumberOperandId second,
|
||||
NumberOperandId third) {
|
||||
JitSpew(JitSpew_Codegen, "%s", __FUNCTION__);
|
||||
AutoOutputRegister output(*this);
|
||||
AutoScratchRegisterMaybeOutput scratch(allocator, masm, output);
|
||||
|
||||
AutoAvailableFloatRegister floatScratch0(*this, FloatReg0);
|
||||
AutoAvailableFloatRegister floatScratch1(*this, FloatReg1);
|
||||
AutoAvailableFloatRegister floatScratch2(*this, FloatReg2);
|
||||
|
||||
allocator.ensureDoubleRegister(masm, first, floatScratch0);
|
||||
allocator.ensureDoubleRegister(masm, second, floatScratch1);
|
||||
allocator.ensureDoubleRegister(masm, third, floatScratch2);
|
||||
|
||||
LiveRegisterSet save(GeneralRegisterSet::Volatile(), liveVolatileFloatRegs());
|
||||
masm.PushRegsInMask(save);
|
||||
|
||||
masm.setupUnalignedABICall(scratch);
|
||||
masm.passABIArg(floatScratch0, MoveOp::DOUBLE);
|
||||
masm.passABIArg(floatScratch1, MoveOp::DOUBLE);
|
||||
masm.passABIArg(floatScratch2, MoveOp::DOUBLE);
|
||||
|
||||
masm.callWithABI(JS_FUNC_TO_DATA_PTR(void*, hypot3), MoveOp::DOUBLE);
|
||||
masm.storeCallFloatResult(floatScratch0);
|
||||
|
||||
LiveRegisterSet ignore;
|
||||
ignore.add(floatScratch0);
|
||||
masm.PopRegsInMaskIgnore(save, ignore);
|
||||
|
||||
masm.boxDouble(floatScratch0, output.valueReg(), floatScratch0);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool CacheIRCompiler::emitMathHypot4NumberResult(NumberOperandId first,
|
||||
NumberOperandId second,
|
||||
NumberOperandId third,
|
||||
NumberOperandId fourth) {
|
||||
JitSpew(JitSpew_Codegen, "%s", __FUNCTION__);
|
||||
AutoOutputRegister output(*this);
|
||||
AutoScratchRegisterMaybeOutput scratch(allocator, masm, output);
|
||||
|
||||
AutoAvailableFloatRegister floatScratch0(*this, FloatReg0);
|
||||
AutoAvailableFloatRegister floatScratch1(*this, FloatReg1);
|
||||
AutoAvailableFloatRegister floatScratch2(*this, FloatReg2);
|
||||
AutoAvailableFloatRegister floatScratch3(*this, FloatReg3);
|
||||
|
||||
allocator.ensureDoubleRegister(masm, first, floatScratch0);
|
||||
allocator.ensureDoubleRegister(masm, second, floatScratch1);
|
||||
allocator.ensureDoubleRegister(masm, third, floatScratch2);
|
||||
allocator.ensureDoubleRegister(masm, fourth, floatScratch3);
|
||||
|
||||
LiveRegisterSet save(GeneralRegisterSet::Volatile(), liveVolatileFloatRegs());
|
||||
masm.PushRegsInMask(save);
|
||||
|
||||
masm.setupUnalignedABICall(scratch);
|
||||
masm.passABIArg(floatScratch0, MoveOp::DOUBLE);
|
||||
masm.passABIArg(floatScratch1, MoveOp::DOUBLE);
|
||||
masm.passABIArg(floatScratch2, MoveOp::DOUBLE);
|
||||
masm.passABIArg(floatScratch3, MoveOp::DOUBLE);
|
||||
|
||||
masm.callWithABI(JS_FUNC_TO_DATA_PTR(void*, hypot4), MoveOp::DOUBLE);
|
||||
masm.storeCallFloatResult(floatScratch0);
|
||||
|
||||
LiveRegisterSet ignore;
|
||||
ignore.add(floatScratch0);
|
||||
masm.PopRegsInMaskIgnore(save, ignore);
|
||||
|
||||
masm.boxDouble(floatScratch0, output.valueReg(), floatScratch0);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool CacheIRCompiler::emitMathAtan2NumberResult(NumberOperandId yId,
|
||||
NumberOperandId xId) {
|
||||
JitSpew(JitSpew_Codegen, "%s", __FUNCTION__);
|
||||
|
|
|
@ -920,6 +920,33 @@
|
|||
args:
|
||||
rng: RawPointerField
|
||||
|
||||
- name: MathHypot2NumberResult
|
||||
shared: true
|
||||
transpile: false
|
||||
cost_estimate: 4
|
||||
args:
|
||||
first: NumberId
|
||||
second: NumberId
|
||||
|
||||
- name: MathHypot3NumberResult
|
||||
shared: true
|
||||
transpile: false
|
||||
cost_estimate: 4
|
||||
args:
|
||||
first: NumberId
|
||||
second: NumberId
|
||||
third: NumberId
|
||||
|
||||
- name: MathHypot4NumberResult
|
||||
shared: true
|
||||
transpile: false
|
||||
cost_estimate: 4
|
||||
args:
|
||||
first: NumberId
|
||||
second: NumberId
|
||||
third: NumberId
|
||||
fourth: NumberId
|
||||
|
||||
- name: MathAtan2NumberResult
|
||||
shared: true
|
||||
transpile: true
|
||||
|
|
Загрузка…
Ссылка в новой задаче