Bug 1639153 - Part 6.4: Add tls dependency for WasmTruncateToInt64 and Int64ToFloatingPoint for arm. r=lth

In this patch we add a tls dependency for the remaining nodes which use
BuiltinThunk to call c++ runtime. By ABI requirements WasmTlsReg should
be set.

Differential Revision: https://phabricator.services.mozilla.com/D89239
This commit is contained in:
Dmitry Bezhetskov 2020-09-11 12:02:42 +00:00
Родитель d836e296cd
Коммит 9edeed7b15
19 изменённых файлов: 254 добавлений и 17 удалений

Просмотреть файл

@ -1861,6 +1861,16 @@ void LIRGenerator::visitWasmBuiltinModD(MWasmBuiltinModD* ins) {
defineReturn(lir, ins);
}
void LIRGenerator::visitBuiltinInt64ToFloatingPoint(
MBuiltinInt64ToFloatingPoint* ins) {
lowerBuiltinInt64ToFloatingPoint(ins);
}
void LIRGenerator::visitWasmBuiltinTruncateToInt64(
MWasmBuiltinTruncateToInt64* ins) {
lowerWasmBuiltinTruncateToInt64(ins);
}
void LIRGenerator::visitMod(MMod* ins) {
MOZ_ASSERT(ins->lhs()->type() == ins->rhs()->type());
MOZ_ASSERT(IsNumberType(ins->type()));

Просмотреть файл

@ -3995,6 +3995,45 @@ class MExtendInt32ToInt64 : public MUnaryInstruction,
AliasSet getAliasSet() const override { return AliasSet::None(); }
};
// The same as MWasmTruncateToInt64 but with the TLS dependency.
// It used only for arm now because on arm we need to call builtin to truncate
// to i64.
class MWasmBuiltinTruncateToInt64 : public MAryInstruction<2>,
public NoTypePolicy::Data {
TruncFlags flags_;
wasm::BytecodeOffset bytecodeOffset_;
MWasmBuiltinTruncateToInt64(MDefinition* def, MDefinition* tls,
TruncFlags flags,
wasm::BytecodeOffset bytecodeOffset)
: MAryInstruction(classOpcode),
flags_(flags),
bytecodeOffset_(bytecodeOffset) {
initOperand(0, def);
initOperand(1, tls);
setResultType(MIRType::Int64);
setGuard(); // neither removable nor movable because of possible
// side-effects.
}
public:
INSTRUCTION_HEADER(WasmBuiltinTruncateToInt64)
NAMED_OPERANDS((0, input), (1, tls));
TRIVIAL_NEW_WRAPPERS
bool isUnsigned() const { return flags_ & TRUNC_UNSIGNED; }
bool isSaturating() const { return flags_ & TRUNC_SATURATING; }
TruncFlags flags() const { return flags_; }
wasm::BytecodeOffset bytecodeOffset() const { return bytecodeOffset_; }
bool congruentTo(const MDefinition* ins) const override {
return congruentIfOperandsEqual(ins) &&
ins->toWasmBuiltinTruncateToInt64()->flags() == flags_;
}
AliasSet getAliasSet() const override { return AliasSet::None(); }
};
class MWasmTruncateToInt64 : public MUnaryInstruction,
public NoTypePolicy::Data {
TruncFlags flags_;
@ -4133,6 +4172,46 @@ class MInt64ToFloatingPoint : public MUnaryInstruction,
AliasSet getAliasSet() const override { return AliasSet::None(); }
};
// It used only for arm now because on arm we need to call builtin to convert
// i64 to float.
class MBuiltinInt64ToFloatingPoint : public MAryInstruction<2>,
public NoTypePolicy::Data {
bool isUnsigned_;
wasm::BytecodeOffset bytecodeOffset_;
MBuiltinInt64ToFloatingPoint(MDefinition* def, MDefinition* tls, MIRType type,
wasm::BytecodeOffset bytecodeOffset,
bool isUnsigned)
: MAryInstruction(classOpcode),
isUnsigned_(isUnsigned),
bytecodeOffset_(bytecodeOffset) {
MOZ_ASSERT(IsFloatingPointType(type));
initOperand(0, def);
initOperand(1, tls);
setResultType(type);
setMovable();
}
public:
INSTRUCTION_HEADER(BuiltinInt64ToFloatingPoint)
NAMED_OPERANDS((0, input), (1, tls));
TRIVIAL_NEW_WRAPPERS
bool isUnsigned() const { return isUnsigned_; }
wasm::BytecodeOffset bytecodeOffset() const { return bytecodeOffset_; }
bool congruentTo(const MDefinition* ins) const override {
if (!ins->isBuiltinInt64ToFloatingPoint()) {
return false;
}
if (ins->toBuiltinInt64ToFloatingPoint()->isUnsigned_ != isUnsigned_) {
return false;
}
return congruentIfOperandsEqual(ins);
}
AliasSet getAliasSet() const override { return AliasSet::None(); }
};
// Applies ECMA's ToNumber on a primitive (either typed or untyped) and expects
// the result to be precisely representable as an Int32, otherwise bails.
//

Просмотреть файл

@ -2339,11 +2339,16 @@ void CodeGenerator::visitWasmTruncateToInt32(LWasmTruncateToInt32* lir) {
}
void CodeGenerator::visitWasmTruncateToInt64(LWasmTruncateToInt64* lir) {
MOZ_ASSERT(gen->compilingWasm());
MOZ_ASSERT(ToRegister(lir->tls()) == WasmTlsReg);
masm.Push(WasmTlsReg);
int32_t framePushedAfterTls = masm.framePushed();
FloatRegister input = ToFloatRegister(lir->input());
FloatRegister inputDouble = input;
Register64 output = ToOutRegister64(lir);
MWasmTruncateToInt64* mir = lir->mir();
MWasmBuiltinTruncateToInt64* mir = lir->mir();
MIRType fromType = mir->input()->type();
OutOfLineWasmTruncateCheck* ool = nullptr;
@ -2364,29 +2369,31 @@ void CodeGenerator::visitWasmTruncateToInt64(LWasmTruncateToInt64* lir) {
masm.setupWasmABICall();
masm.passABIArg(inputDouble, MoveOp::DOUBLE);
int32_t tlsOffset = masm.framePushed() - framePushedAfterTls;
if (lir->mir()->isSaturating()) {
if (lir->mir()->isUnsigned()) {
masm.callWithABI(mir->bytecodeOffset(),
wasm::SymbolicAddress::SaturatingTruncateDoubleToUint64,
mozilla::Nothing());
mozilla::Some(tlsOffset));
} else {
masm.callWithABI(mir->bytecodeOffset(),
wasm::SymbolicAddress::SaturatingTruncateDoubleToInt64,
mozilla::Nothing());
mozilla::Some(tlsOffset));
}
} else {
if (lir->mir()->isUnsigned()) {
masm.callWithABI(mir->bytecodeOffset(),
wasm::SymbolicAddress::TruncateDoubleToUint64,
mozilla::Nothing());
mozilla::Some(tlsOffset));
} else {
masm.callWithABI(mir->bytecodeOffset(),
wasm::SymbolicAddress::TruncateDoubleToInt64,
mozilla::Nothing());
mozilla::Some(tlsOffset));
}
}
masm.Pop(input);
masm.Pop(WasmTlsReg);
// TruncateDoubleTo{UI,I}nt64 returns 0x8000000000000000 to indicate
// exceptional results, so check for that and produce the appropriate
@ -2419,9 +2426,15 @@ void CodeGeneratorARM::visitOutOfLineWasmTruncateCheck(
void CodeGenerator::visitInt64ToFloatingPointCall(
LInt64ToFloatingPointCall* lir) {
MOZ_ASSERT(gen->compilingWasm());
MOZ_ASSERT(ToRegister(lir->getOperand(LInt64ToFloatingPointCall::Tls)) ==
WasmTlsReg);
masm.Push(WasmTlsReg);
int32_t framePushedAfterTls = masm.framePushed();
Register64 input = ToRegister64(lir->getInt64Operand(0));
MInt64ToFloatingPoint* mir = lir->mir();
MBuiltinInt64ToFloatingPoint* mir = lir->mir();
MIRType toType = mir->type();
masm.setupWasmABICall();
@ -2436,13 +2449,17 @@ void CodeGenerator::visitInt64ToFloatingPointCall(
: (isUnsigned ? wasm::SymbolicAddress::Uint64ToDouble
: wasm::SymbolicAddress::Int64ToDouble);
int32_t tlsOffset = masm.framePushed() - framePushedAfterTls;
MoveOp::Type result =
toType == MIRType::Float32 ? MoveOp::FLOAT32 : MoveOp::DOUBLE;
masm.callWithABI(mir->bytecodeOffset(), callee, mozilla::Nothing(), result);
masm.callWithABI(mir->bytecodeOffset(), callee, mozilla::Some(tlsOffset),
result);
DebugOnly<FloatRegister> output(ToFloatRegister(lir->output()));
MOZ_ASSERT_IF(toType == MIRType::Double, output.value == ReturnDoubleReg);
MOZ_ASSERT_IF(toType == MIRType::Float32, output.value == ReturnFloat32Reg);
masm.Pop(WasmTlsReg);
}
void CodeGenerator::visitCopySignF(LCopySignF* ins) {

Просмотреть файл

@ -357,26 +357,47 @@ class LSoftUDivOrMod : public LBinaryCallInstructionHelper<1, 0> {
MInstruction* mir() { return mir_->toInstruction(); }
};
class LWasmTruncateToInt64 : public LCallInstructionHelper<INT64_PIECES, 1, 0> {
class LWasmTruncateToInt64 : public LCallInstructionHelper<INT64_PIECES, 2, 0> {
static const size_t Input = 0;
static const size_t Tls = 1;
public:
LIR_HEADER(WasmTruncateToInt64);
explicit LWasmTruncateToInt64(const LAllocation& in)
LWasmTruncateToInt64(const LAllocation& in, const LAllocation& tls)
: LCallInstructionHelper(classOpcode) {
setOperand(0, in);
setOperand(Input, in);
setOperand(Tls, tls);
}
MWasmTruncateToInt64* mir() const { return mir_->toWasmTruncateToInt64(); }
LAllocation* input() { return getOperand(Input); }
LAllocation* tls() { return getOperand(Tls); }
MWasmBuiltinTruncateToInt64* mir() const {
return mir_->toWasmBuiltinTruncateToInt64();
}
};
class LInt64ToFloatingPointCall
: public LCallInstructionHelper<1, INT64_PIECES, 0> {
: public LCallInstructionHelper<1, INT64_PIECES + 1, 0> {
public:
LIR_HEADER(Int64ToFloatingPointCall);
LInt64ToFloatingPointCall() : LCallInstructionHelper(classOpcode) {}
static const size_t Input = 0;
static const size_t Tls = INT64_PIECES;
MInt64ToFloatingPoint* mir() const { return mir_->toInt64ToFloatingPoint(); }
LInt64ToFloatingPointCall(const LInt64Allocation& in, const LAllocation& tls)
: LCallInstructionHelper(classOpcode) {
setInt64Operand(Input, in);
setOperand(Tls, tls);
}
LAllocation* input() { return getOperand(Input); }
LAllocation* tls() { return getOperand(Tls); }
MBuiltinInt64ToFloatingPoint* mir() const {
return mir_->toBuiltinInt64ToFloatingPoint();
}
};
namespace details {

Просмотреть файл

@ -953,18 +953,31 @@ void LIRGenerator::visitSubstr(MSubstr* ins) {
}
void LIRGenerator::visitWasmTruncateToInt64(MWasmTruncateToInt64* ins) {
MOZ_CRASH("We don't use MWasmTruncateToInt64 for arm");
}
void LIRGeneratorARM::lowerWasmBuiltinTruncateToInt64(
MWasmBuiltinTruncateToInt64* ins) {
MDefinition* opd = ins->input();
MDefinition* tls = ins->tls();
MOZ_ASSERT(opd->type() == MIRType::Double || opd->type() == MIRType::Float32);
defineReturn(new (alloc()) LWasmTruncateToInt64(useRegisterAtStart(opd)),
defineReturn(new (alloc()) LWasmTruncateToInt64(
useRegisterAtStart(opd), useFixedAtStart(tls, WasmTlsReg)),
ins);
}
void LIRGenerator::visitInt64ToFloatingPoint(MInt64ToFloatingPoint* ins) {
MOZ_CRASH("We use BuiltinInt64ToFloatingPoint instead.");
}
void LIRGeneratorARM::lowerBuiltinInt64ToFloatingPoint(
MBuiltinInt64ToFloatingPoint* ins) {
MOZ_ASSERT(ins->type() == MIRType::Double || ins->type() == MIRType::Float32);
auto* lir = new (alloc()) LInt64ToFloatingPointCall();
lir->setInt64Operand(0, useInt64RegisterAtStart(ins->input()));
auto* lir = new (alloc())
LInt64ToFloatingPointCall(useInt64RegisterAtStart(ins->input()),
useFixedAtStart(ins->tls(), WasmTlsReg));
defineReturn(lir, ins);
}

Просмотреть файл

@ -65,6 +65,8 @@ class LIRGeneratorARM : public LIRGeneratorShared {
void lowerForFPU(LInstructionHelper<1, 2, Temps>* ins, MDefinition* mir,
MDefinition* lhs, MDefinition* rhs);
void lowerBuiltinInt64ToFloatingPoint(MBuiltinInt64ToFloatingPoint* ins);
void lowerWasmBuiltinTruncateToInt64(MWasmBuiltinTruncateToInt64* ins);
void lowerForBitAndAndBranch(LBitAndAndBranch* baab, MInstruction* mir,
MDefinition* lhs, MDefinition* rhs);
void lowerTruncateDToInt32(MTruncateToInt32* ins);

Просмотреть файл

@ -526,6 +526,16 @@ void LIRGenerator::visitWasmTruncateToInt64(MWasmTruncateToInt64* ins) {
MOZ_CRASH("NYI");
}
void LIRGeneratorARM64::lowerWasmBuiltinTruncateToInt64(
MWasmBuiltinTruncateToInt64* ins) {
MOZ_CRASH("We don't use WasmBuiltinTruncateToInt64 for arm64");
}
void LIRGeneratorARM64::lowerBuiltinInt64ToFloatingPoint(
MBuiltinInt64ToFloatingPoint* ins) {
MOZ_CRASH("We don't use it for this architecture");
}
void LIRGenerator::visitWasmHeapBase(MWasmHeapBase* ins) { MOZ_CRASH("NYI"); }
void LIRGenerator::visitWasmLoad(MWasmLoad* ins) { MOZ_CRASH("NYI"); }

Просмотреть файл

@ -68,6 +68,8 @@ class LIRGeneratorARM64 : public LIRGeneratorShared {
void lowerForFPU(LInstructionHelper<1, 2, Temps>* ins, MDefinition* mir,
MDefinition* lhs, MDefinition* rhs);
void lowerBuiltinInt64ToFloatingPoint(MBuiltinInt64ToFloatingPoint* ins);
void lowerWasmBuiltinTruncateToInt64(MWasmBuiltinTruncateToInt64* ins);
void lowerForBitAndAndBranch(LBitAndAndBranch* baab, MInstruction* mir,
MDefinition* lhs, MDefinition* rhs);
void lowerTruncateDToInt32(MTruncateToInt32* ins);

Просмотреть файл

@ -234,6 +234,11 @@ void LIRGenerator::visitWasmTruncateToInt64(MWasmTruncateToInt64* ins) {
ins);
}
void LIRGeneratorMIPS::lowerWasmBuiltinTruncateToInt64(
MWasmBuiltinTruncateToInt64* ins) {
MOZ_CRASH("We don't use it for this architecture");
}
void LIRGenerator::visitInt64ToFloatingPoint(MInt64ToFloatingPoint* ins) {
MDefinition* opd = ins->input();
MOZ_ASSERT(opd->type() == MIRType::Int64);
@ -242,3 +247,8 @@ void LIRGenerator::visitInt64ToFloatingPoint(MInt64ToFloatingPoint* ins) {
defineReturn(
new (alloc()) LInt64ToFloatingPoint(useInt64RegisterAtStart(opd)), ins);
}
void LIRGeneratorMIPS::lowerBuiltinInt64ToFloatingPoint(
MBuiltinInt64ToFloatingPoint* ins) {
MOZ_CRASH("We don't use it for this architecture");
}

Просмотреть файл

@ -30,6 +30,8 @@ class LIRGeneratorMIPS : public LIRGeneratorMIPSShared {
size_t lirIndex);
void defineInt64Phi(MPhi* phi, size_t lirIndex);
void lowerBuiltinInt64ToFloatingPoint(MBuiltinInt64ToFloatingPoint* ins);
void lowerWasmBuiltinTruncateToInt64(MWasmBuiltinTruncateToInt64* ins);
void lowerTruncateDToInt32(MTruncateToInt32* ins);
void lowerTruncateFToInt32(MTruncateToInt32* ins);

Просмотреть файл

@ -161,6 +161,11 @@ void LIRGenerator::visitWasmTruncateToInt64(MWasmTruncateToInt64* ins) {
defineInt64(new (alloc()) LWasmTruncateToInt64(useRegister(opd)), ins);
}
void LIRGeneratorMIPS64::lowerWasmBuiltinTruncateToInt64(
MWasmBuiltinTruncateToInt64* ins) {
MOZ_CRASH("We don't use it for this architecture");
}
void LIRGenerator::visitInt64ToFloatingPoint(MInt64ToFloatingPoint* ins) {
MDefinition* opd = ins->input();
MOZ_ASSERT(opd->type() == MIRType::Int64);
@ -168,3 +173,8 @@ void LIRGenerator::visitInt64ToFloatingPoint(MInt64ToFloatingPoint* ins) {
define(new (alloc()) LInt64ToFloatingPoint(useInt64Register(opd)), ins);
}
void LIRGeneratorMIPS64::lowerBuiltinInt64ToFloatingPoint(
MBuiltinInt64ToFloatingPoint* ins) {
MOZ_CRASH("We don't use it for this architecture");
}

Просмотреть файл

@ -29,6 +29,8 @@ class LIRGeneratorMIPS64 : public LIRGeneratorMIPSShared {
void lowerUntypedPhiInput(MPhi* phi, uint32_t inputPosition, LBlock* block,
size_t lirIndex);
void lowerBuiltinInt64ToFloatingPoint(MBuiltinInt64ToFloatingPoint* ins);
void lowerWasmBuiltinTruncateToInt64(MWasmBuiltinTruncateToInt64* ins);
void lowerTruncateDToInt32(MTruncateToInt32* ins);
void lowerTruncateFToInt32(MTruncateToInt32* ins);

Просмотреть файл

@ -72,6 +72,12 @@ class LIRGeneratorNone : public LIRGeneratorShared {
void lowerConstantFloat32(float, MInstruction*) { MOZ_CRASH(); }
void lowerTruncateDToInt32(MTruncateToInt32*) { MOZ_CRASH(); }
void lowerTruncateFToInt32(MTruncateToInt32*) { MOZ_CRASH(); }
void lowerBuiltinInt64ToFloatingPoint(MBuiltinInt64ToFloatingPoint* ins) {
MOZ_CRASH();
}
void lowerWasmBuiltinTruncateToInt64(MWasmBuiltinTruncateToInt64* ins) {
MOZ_CRASH();
}
void lowerDivI(MDiv*) { MOZ_CRASH(); }
void lowerModI(MMod*) { MOZ_CRASH(); }
void lowerDivI64(MDiv*) { MOZ_CRASH(); }

Просмотреть файл

@ -551,6 +551,16 @@ class OutOfLineWasmTruncateCheckBase : public OutOfLineCodeBase<CodeGen> {
flags_(mir->flags()),
bytecodeOffset_(mir->bytecodeOffset()) {}
OutOfLineWasmTruncateCheckBase(MWasmBuiltinTruncateToInt64* mir,
FloatRegister input, Register64 output)
: fromType_(mir->input()->type()),
toType_(MIRType::Int64),
input_(input),
output_(Register::Invalid()),
output64_(output),
flags_(mir->flags()),
bytecodeOffset_(mir->bytecodeOffset()) {}
OutOfLineWasmTruncateCheckBase(MWasmTruncateToInt64* mir, FloatRegister input,
Register64 output)
: fromType_(mir->input()->type()),

Просмотреть файл

@ -393,6 +393,11 @@ void LIRGenerator::visitWasmTruncateToInt64(MWasmTruncateToInt64* ins) {
ins);
}
void LIRGeneratorX64::lowerWasmBuiltinTruncateToInt64(
MWasmBuiltinTruncateToInt64* ins) {
MOZ_CRASH("We don't use it for this architecture");
}
void LIRGenerator::visitInt64ToFloatingPoint(MInt64ToFloatingPoint* ins) {
MDefinition* opd = ins->input();
MOZ_ASSERT(opd->type() == MIRType::Int64);
@ -403,6 +408,11 @@ void LIRGenerator::visitInt64ToFloatingPoint(MInt64ToFloatingPoint* ins) {
ins);
}
void LIRGeneratorX64::lowerBuiltinInt64ToFloatingPoint(
MBuiltinInt64ToFloatingPoint* ins) {
MOZ_CRASH("We don't use it for this architecture");
}
void LIRGenerator::visitExtendInt32ToInt64(MExtendInt32ToInt64* ins) {
defineInt64(new (alloc()) LExtendInt32ToInt64(useAtStart(ins->input())), ins);
}

Просмотреть файл

@ -44,6 +44,8 @@ class LIRGeneratorX64 : public LIRGeneratorX86Shared {
bool needTempForPostBarrier() { return true; }
void lowerBuiltinInt64ToFloatingPoint(MBuiltinInt64ToFloatingPoint* ins);
void lowerWasmBuiltinTruncateToInt64(MWasmBuiltinTruncateToInt64* ins);
void lowerDivI64(MDiv* div);
void lowerWasmBuiltinDivI64(MWasmBuiltinDivI64* div);
void lowerModI64(MMod* mod);

Просмотреть файл

@ -668,6 +668,11 @@ void LIRGenerator::visitWasmTruncateToInt64(MWasmTruncateToInt64* ins) {
defineInt64(new (alloc()) LWasmTruncateToInt64(useRegister(opd), temp), ins);
}
void LIRGeneratorX86::lowerWasmBuiltinTruncateToInt64(
MWasmBuiltinTruncateToInt64* ins) {
MOZ_CRASH("We don't use it for this architecture");
}
void LIRGenerator::visitInt64ToFloatingPoint(MInt64ToFloatingPoint* ins) {
MDefinition* opd = ins->input();
MOZ_ASSERT(opd->type() == MIRType::Int64);
@ -684,6 +689,11 @@ void LIRGenerator::visitInt64ToFloatingPoint(MInt64ToFloatingPoint* ins) {
ins);
}
void LIRGeneratorX86::lowerBuiltinInt64ToFloatingPoint(
MBuiltinInt64ToFloatingPoint* ins) {
MOZ_CRASH("We don't use it for this architecture");
}
void LIRGenerator::visitExtendInt32ToInt64(MExtendInt32ToInt64* ins) {
if (ins->isUnsigned()) {
defineInt64(new (alloc())

Просмотреть файл

@ -48,6 +48,8 @@ class LIRGeneratorX86 : public LIRGeneratorX86Shared {
void lowerForMulInt64(LMulI64* ins, MMul* mir, MDefinition* lhs,
MDefinition* rhs);
void lowerBuiltinInt64ToFloatingPoint(MBuiltinInt64ToFloatingPoint* ins);
void lowerWasmBuiltinTruncateToInt64(MWasmBuiltinTruncateToInt64* ins);
void lowerDivI64(MDiv* div);
void lowerWasmBuiltinDivI64(MWasmBuiltinDivI64* div);
void lowerModI64(MMod* mod);

Просмотреть файл

@ -603,8 +603,13 @@ class FunctionCompiler {
if (inDeadCode()) {
return nullptr;
}
#if defined(JS_CODEGEN_ARM)
auto* ins = MBuiltinInt64ToFloatingPoint::New(
alloc(), op, tlsPointer_, type, bytecodeOffset(), isUnsigned);
#else
auto* ins = MInt64ToFloatingPoint::New(alloc(), op, type, bytecodeOffset(),
isUnsigned);
#endif
curBlock_->add(ins);
return ins;
}
@ -629,6 +634,16 @@ class FunctionCompiler {
return ins;
}
MDefinition* truncateWithTls(MDefinition* op, TruncFlags flags) {
if (inDeadCode()) {
return nullptr;
}
auto* ins = MWasmBuiltinTruncateToInt64::New(alloc(), op, tlsPointer_,
flags, bytecodeOffset());
curBlock_->add(ins);
return ins;
}
MDefinition* compare(MDefinition* lhs, MDefinition* rhs, JSOp op,
MCompare::CompareType type) {
if (inDeadCode()) {
@ -2770,7 +2785,11 @@ static bool EmitTruncate(FunctionCompiler& f, ValType operandType,
} else {
MOZ_ASSERT(resultType == ValType::I64);
MOZ_ASSERT(!f.env().isAsmJS());
#if defined(JS_CODEGEN_ARM)
f.iter().setResult(f.truncateWithTls(input, flags));
#else
f.iter().setResult(f.truncate<MWasmTruncateToInt64>(input, flags));
#endif
}
return true;
}