Bug 1200809 part 7 - Convert SIMD natives to new InlinableNatives system. r=nbp

This commit is contained in:
Jan de Mooij 2015-09-11 18:52:32 -07:00
parent 3a3a37d452
commit 34f74c8efb
4 changed files with 191 additions and 148 deletions

View File

@ -21,6 +21,7 @@
#include "jsprf.h"
#include "builtin/TypedObject.h"
#include "jit/InlinableNatives.h"
#include "js/Value.h"
#include "jsobjinlines.h"
@ -244,7 +245,7 @@ const JSFunctionSpec Float32x4Defn::TypedObjectMethods[] = {
const JSFunctionSpec Float32x4Defn::Methods[] = {
#define SIMD_FLOAT32X4_FUNCTION_ITEM(Name, Func, Operands) \
JS_FN(#Name, js::simd_float32x4_##Name, Operands, 0),
JS_INLINABLE_FN(#Name, js::simd_float32x4_##Name, Operands, 0, SimdFloat32x4),
FLOAT32X4_FUNCTION_LIST(SIMD_FLOAT32X4_FUNCTION_ITEM)
#undef SIMD_FLOAT32x4_FUNCTION_ITEM
JS_FS_END
@ -344,7 +345,7 @@ const JSFunctionSpec Int32x4Defn::TypedObjectMethods[] = {
const JSFunctionSpec Int32x4Defn::Methods[] = {
#define SIMD_INT32X4_FUNCTION_ITEM(Name, Func, Operands) \
JS_FN(#Name, js::simd_int32x4_##Name, Operands, 0),
JS_INLINABLE_FN(#Name, js::simd_int32x4_##Name, Operands, 0, SimdInt32x4),
INT32X4_FUNCTION_LIST(SIMD_INT32X4_FUNCTION_ITEM)
#undef SIMD_INT32X4_FUNCTION_ITEM
JS_FS_END

View File

@ -79,6 +79,9 @@
\
_(CallBoundFunction) \
\
_(SimdInt32x4) \
_(SimdFloat32x4) \
\
_(TestBailout) \
_(TestAssertFloat32) \
_(TestAssertRecoveredOnBailout) \

View File

@ -842,6 +842,9 @@ class IonBuilder
IonBuilder::InliningStatus boxSimd(CallInfo& callInfo, MInstruction* ins,
InlineTypedObject* templateObj);
InliningStatus inlineSimdInt32x4(CallInfo& callInfo, JSNative native);
InliningStatus inlineSimdFloat32x4(CallInfo& callInfo, JSNative native);
template <typename T>
InliningStatus inlineBinarySimd(CallInfo& callInfo, JSNative native,
typename T::Operation op, SimdTypeDescr::Type type);

View File

@ -39,7 +39,6 @@ IonBuilder::InliningStatus
IonBuilder::inlineNativeCall(CallInfo& callInfo, JSFunction* target)
{
MOZ_ASSERT(target->isNative());
JSNative native = target->native();
if (!optimizationInfo().inlineNative()) {
trackOptimizationOutcome(TrackedOutcome::CantInlineDisabledIon);
@ -56,151 +55,6 @@ IonBuilder::inlineNativeCall(CallInfo& callInfo, JSFunction* target)
return InliningStatus_NotInlined;
}
// Simd functions
#define INLINE_FLOAT32X4_SIMD_ARITH_(OP) \
if (native == js::simd_float32x4_##OP) \
return inlineBinarySimd<MSimdBinaryArith>(callInfo, native, MSimdBinaryArith::Op_##OP, \
SimdTypeDescr::Float32x4);
#define INLINE_INT32X4_SIMD_ARITH_(OP) \
if (native == js::simd_int32x4_##OP) \
return inlineBinarySimd<MSimdBinaryArith>(callInfo, native, MSimdBinaryArith::Op_##OP, \
SimdTypeDescr::Int32x4);
ARITH_COMMONX4_SIMD_OP(INLINE_INT32X4_SIMD_ARITH_)
ARITH_COMMONX4_SIMD_OP(INLINE_FLOAT32X4_SIMD_ARITH_)
BINARY_ARITH_FLOAT32X4_SIMD_OP(INLINE_FLOAT32X4_SIMD_ARITH_)
#undef INLINE_SIMD_ARITH_
#undef INLINE_FLOAT32X4_SIMD_ARITH_
#define INLINE_SIMD_BITWISE_(OP) \
if (native == js::simd_int32x4_##OP) \
return inlineBinarySimd<MSimdBinaryBitwise>(callInfo, native, MSimdBinaryBitwise::OP##_, \
SimdTypeDescr::Int32x4); \
if (native == js::simd_float32x4_##OP) \
return inlineBinarySimd<MSimdBinaryBitwise>(callInfo, native, MSimdBinaryBitwise::OP##_, \
SimdTypeDescr::Float32x4);
BITWISE_COMMONX4_SIMD_OP(INLINE_SIMD_BITWISE_)
#undef INLINE_SIMD_BITWISE_
if (native == js::simd_int32x4_shiftLeftByScalar)
return inlineBinarySimd<MSimdShift>(callInfo, native, MSimdShift::lsh, SimdTypeDescr::Int32x4);
if (native == js::simd_int32x4_shiftRightArithmeticByScalar)
return inlineBinarySimd<MSimdShift>(callInfo, native, MSimdShift::rsh, SimdTypeDescr::Int32x4);
if (native == js::simd_int32x4_shiftRightLogicalByScalar)
return inlineBinarySimd<MSimdShift>(callInfo, native, MSimdShift::ursh, SimdTypeDescr::Int32x4);
#define INLINE_SIMD_COMPARISON_(OP) \
if (native == js::simd_int32x4_##OP) \
return inlineCompSimd(callInfo, native, MSimdBinaryComp::OP, SimdTypeDescr::Int32x4); \
if (native == js::simd_float32x4_##OP) \
return inlineCompSimd(callInfo, native, MSimdBinaryComp::OP, SimdTypeDescr::Float32x4);
COMP_COMMONX4_TO_INT32X4_SIMD_OP(INLINE_SIMD_COMPARISON_)
#undef INLINE_SIMD_COMPARISON_
if (native == js::simd_int32x4_extractLane)
return inlineSimdExtractLane(callInfo, native, SimdTypeDescr::Int32x4);
if (native == js::simd_float32x4_extractLane)
return inlineSimdExtractLane(callInfo, native, SimdTypeDescr::Float32x4);
if (native == js::simd_int32x4_replaceLane)
return inlineSimdReplaceLane(callInfo, native, SimdTypeDescr::Int32x4);
if (native == js::simd_float32x4_replaceLane)
return inlineSimdReplaceLane(callInfo, native, SimdTypeDescr::Float32x4);
if (native == js::simd_int32x4_not)
return inlineUnarySimd(callInfo, native, MSimdUnaryArith::not_, SimdTypeDescr::Int32x4);
if (native == js::simd_int32x4_neg)
return inlineUnarySimd(callInfo, native, MSimdUnaryArith::neg, SimdTypeDescr::Int32x4);
#define INLINE_SIMD_FLOAT32X4_UNARY_(OP) \
if (native == js::simd_float32x4_##OP) \
return inlineUnarySimd(callInfo, native, MSimdUnaryArith::OP, SimdTypeDescr::Float32x4);
UNARY_ARITH_FLOAT32X4_SIMD_OP(INLINE_SIMD_FLOAT32X4_UNARY_)
INLINE_SIMD_FLOAT32X4_UNARY_(neg)
#undef INLINE_SIMD_FLOAT32X4_UNARY_
if (native == js::simd_float32x4_not)
return inlineUnarySimd(callInfo, native, MSimdUnaryArith::not_, SimdTypeDescr::Float32x4);
typedef bool IsCast;
if (native == js::simd_float32x4_fromInt32x4)
return inlineSimdConvert(callInfo, native, IsCast(false), SimdTypeDescr::Int32x4, SimdTypeDescr::Float32x4);
if (native == js::simd_int32x4_fromFloat32x4)
return inlineSimdConvert(callInfo, native, IsCast(false), SimdTypeDescr::Float32x4, SimdTypeDescr::Int32x4);
if (native == js::simd_float32x4_fromInt32x4Bits)
return inlineSimdConvert(callInfo, native, IsCast(true), SimdTypeDescr::Int32x4, SimdTypeDescr::Float32x4);
if (native == js::simd_int32x4_fromFloat32x4Bits)
return inlineSimdConvert(callInfo, native, IsCast(true), SimdTypeDescr::Float32x4, SimdTypeDescr::Int32x4);
if (native == js::simd_int32x4_splat)
return inlineSimdSplat(callInfo, native, SimdTypeDescr::Int32x4);
if (native == js::simd_float32x4_splat)
return inlineSimdSplat(callInfo, native, SimdTypeDescr::Float32x4);
if (native == js::simd_int32x4_check)
return inlineSimdCheck(callInfo, native, SimdTypeDescr::Int32x4);
if (native == js::simd_float32x4_check)
return inlineSimdCheck(callInfo, native, SimdTypeDescr::Float32x4);
typedef bool IsElementWise;
if (native == js::simd_int32x4_select)
return inlineSimdSelect(callInfo, native, IsElementWise(true), SimdTypeDescr::Int32x4);
if (native == js::simd_int32x4_selectBits)
return inlineSimdSelect(callInfo, native, IsElementWise(false), SimdTypeDescr::Int32x4);
if (native == js::simd_float32x4_select)
return inlineSimdSelect(callInfo, native, IsElementWise(true), SimdTypeDescr::Float32x4);
if (native == js::simd_int32x4_swizzle)
return inlineSimdShuffle(callInfo, native, SimdTypeDescr::Int32x4, 1, 4);
if (native == js::simd_float32x4_swizzle)
return inlineSimdShuffle(callInfo, native, SimdTypeDescr::Float32x4, 1, 4);
if (native == js::simd_int32x4_shuffle)
return inlineSimdShuffle(callInfo, native, SimdTypeDescr::Int32x4, 2, 4);
if (native == js::simd_float32x4_shuffle)
return inlineSimdShuffle(callInfo, native, SimdTypeDescr::Float32x4, 2, 4);
if (native == js::simd_int32x4_load)
return inlineSimdLoad(callInfo, native, SimdTypeDescr::Int32x4, 4);
if (native == js::simd_int32x4_load1)
return inlineSimdLoad(callInfo, native, SimdTypeDescr::Int32x4, 1);
if (native == js::simd_int32x4_load2)
return inlineSimdLoad(callInfo, native, SimdTypeDescr::Int32x4, 2);
if (native == js::simd_int32x4_load3)
return inlineSimdLoad(callInfo, native, SimdTypeDescr::Int32x4, 3);
if (native == js::simd_float32x4_load)
return inlineSimdLoad(callInfo, native, SimdTypeDescr::Float32x4, 4);
if (native == js::simd_float32x4_load1)
return inlineSimdLoad(callInfo, native, SimdTypeDescr::Float32x4, 1);
if (native == js::simd_float32x4_load2)
return inlineSimdLoad(callInfo, native, SimdTypeDescr::Float32x4, 2);
if (native == js::simd_float32x4_load3)
return inlineSimdLoad(callInfo, native, SimdTypeDescr::Float32x4, 3);
if (native == js::simd_int32x4_store)
return inlineSimdStore(callInfo, native, SimdTypeDescr::Int32x4, 4);
if (native == js::simd_int32x4_store1)
return inlineSimdStore(callInfo, native, SimdTypeDescr::Int32x4, 1);
if (native == js::simd_int32x4_store2)
return inlineSimdStore(callInfo, native, SimdTypeDescr::Int32x4, 2);
if (native == js::simd_int32x4_store3)
return inlineSimdStore(callInfo, native, SimdTypeDescr::Int32x4, 3);
if (native == js::simd_float32x4_store)
return inlineSimdStore(callInfo, native, SimdTypeDescr::Float32x4, 4);
if (native == js::simd_float32x4_store1)
return inlineSimdStore(callInfo, native, SimdTypeDescr::Float32x4, 1);
if (native == js::simd_float32x4_store2)
return inlineSimdStore(callInfo, native, SimdTypeDescr::Float32x4, 2);
if (native == js::simd_float32x4_store3)
return inlineSimdStore(callInfo, native, SimdTypeDescr::Float32x4, 3);
if (native == js::simd_int32x4_bool)
return inlineSimdBool(callInfo, native, SimdTypeDescr::Int32x4);
if (!target->jitInfo() || target->jitInfo()->type() != JSJitInfo::InlinableNative) {
// Reaching here means we tried to inline a native for which there is no
// Ion specialization.
@ -347,6 +201,12 @@ IonBuilder::inlineNativeCall(CallInfo& callInfo, JSFunction* target)
case InlinableNative::CallBoundFunction:
return inlineBoundFunction(callInfo, target);
// SIMD natives.
case InlinableNative::SimdInt32x4:
return inlineSimdInt32x4(callInfo, target->native());
case InlinableNative::SimdFloat32x4:
return inlineSimdFloat32x4(callInfo, target->native());
// Testing functions.
case InlinableNative::TestBailout:
return inlineBailout(callInfo);
@ -3163,6 +3023,182 @@ IonBuilder::inlineConstructTypedObject(CallInfo& callInfo, TypeDescr* descr)
return InliningStatus_Inlined;
}
IonBuilder::InliningStatus
IonBuilder::inlineSimdInt32x4(CallInfo& callInfo, JSNative native)
{
#define INLINE_INT32X4_SIMD_ARITH_(OP) \
if (native == js::simd_int32x4_##OP) \
return inlineBinarySimd<MSimdBinaryArith>(callInfo, native, MSimdBinaryArith::Op_##OP, \
SimdTypeDescr::Int32x4);
ARITH_COMMONX4_SIMD_OP(INLINE_INT32X4_SIMD_ARITH_)
#undef INLINE_INT32X4_SIMD_ARITH_
#define INLINE_SIMD_BITWISE_(OP) \
if (native == js::simd_int32x4_##OP) \
return inlineBinarySimd<MSimdBinaryBitwise>(callInfo, native, MSimdBinaryBitwise::OP##_, \
SimdTypeDescr::Int32x4);
BITWISE_COMMONX4_SIMD_OP(INLINE_SIMD_BITWISE_)
#undef INLINE_SIMD_BITWISE_
if (native == js::simd_int32x4_shiftLeftByScalar)
return inlineBinarySimd<MSimdShift>(callInfo, native, MSimdShift::lsh, SimdTypeDescr::Int32x4);
if (native == js::simd_int32x4_shiftRightArithmeticByScalar)
return inlineBinarySimd<MSimdShift>(callInfo, native, MSimdShift::rsh, SimdTypeDescr::Int32x4);
if (native == js::simd_int32x4_shiftRightLogicalByScalar)
return inlineBinarySimd<MSimdShift>(callInfo, native, MSimdShift::ursh, SimdTypeDescr::Int32x4);
#define INLINE_SIMD_COMPARISON_(OP) \
if (native == js::simd_int32x4_##OP) \
return inlineCompSimd(callInfo, native, MSimdBinaryComp::OP, SimdTypeDescr::Int32x4);
COMP_COMMONX4_TO_INT32X4_SIMD_OP(INLINE_SIMD_COMPARISON_)
#undef INLINE_SIMD_COMPARISON_
if (native == js::simd_int32x4_extractLane)
return inlineSimdExtractLane(callInfo, native, SimdTypeDescr::Int32x4);
if (native == js::simd_int32x4_replaceLane)
return inlineSimdReplaceLane(callInfo, native, SimdTypeDescr::Int32x4);
if (native == js::simd_int32x4_not)
return inlineUnarySimd(callInfo, native, MSimdUnaryArith::not_, SimdTypeDescr::Int32x4);
if (native == js::simd_int32x4_neg)
return inlineUnarySimd(callInfo, native, MSimdUnaryArith::neg, SimdTypeDescr::Int32x4);
typedef bool IsCast;
if (native == js::simd_int32x4_fromFloat32x4)
return inlineSimdConvert(callInfo, native, IsCast(false), SimdTypeDescr::Float32x4, SimdTypeDescr::Int32x4);
if (native == js::simd_int32x4_fromFloat32x4Bits)
return inlineSimdConvert(callInfo, native, IsCast(true), SimdTypeDescr::Float32x4, SimdTypeDescr::Int32x4);
if (native == js::simd_int32x4_splat)
return inlineSimdSplat(callInfo, native, SimdTypeDescr::Int32x4);
if (native == js::simd_int32x4_check)
return inlineSimdCheck(callInfo, native, SimdTypeDescr::Int32x4);
typedef bool IsElementWise;
if (native == js::simd_int32x4_select)
return inlineSimdSelect(callInfo, native, IsElementWise(true), SimdTypeDescr::Int32x4);
if (native == js::simd_int32x4_selectBits)
return inlineSimdSelect(callInfo, native, IsElementWise(false), SimdTypeDescr::Int32x4);
if (native == js::simd_int32x4_swizzle)
return inlineSimdShuffle(callInfo, native, SimdTypeDescr::Int32x4, 1, 4);
if (native == js::simd_int32x4_shuffle)
return inlineSimdShuffle(callInfo, native, SimdTypeDescr::Int32x4, 2, 4);
if (native == js::simd_int32x4_load)
return inlineSimdLoad(callInfo, native, SimdTypeDescr::Int32x4, 4);
if (native == js::simd_int32x4_load1)
return inlineSimdLoad(callInfo, native, SimdTypeDescr::Int32x4, 1);
if (native == js::simd_int32x4_load2)
return inlineSimdLoad(callInfo, native, SimdTypeDescr::Int32x4, 2);
if (native == js::simd_int32x4_load3)
return inlineSimdLoad(callInfo, native, SimdTypeDescr::Int32x4, 3);
if (native == js::simd_int32x4_store)
return inlineSimdStore(callInfo, native, SimdTypeDescr::Int32x4, 4);
if (native == js::simd_int32x4_store1)
return inlineSimdStore(callInfo, native, SimdTypeDescr::Int32x4, 1);
if (native == js::simd_int32x4_store2)
return inlineSimdStore(callInfo, native, SimdTypeDescr::Int32x4, 2);
if (native == js::simd_int32x4_store3)
return inlineSimdStore(callInfo, native, SimdTypeDescr::Int32x4, 3);
if (native == js::simd_int32x4_bool)
return inlineSimdBool(callInfo, native, SimdTypeDescr::Int32x4);
return InliningStatus_NotInlined;
}
IonBuilder::InliningStatus
IonBuilder::inlineSimdFloat32x4(CallInfo& callInfo, JSNative native)
{
// Simd functions
#define INLINE_FLOAT32X4_SIMD_ARITH_(OP) \
if (native == js::simd_float32x4_##OP) \
return inlineBinarySimd<MSimdBinaryArith>(callInfo, native, MSimdBinaryArith::Op_##OP, \
SimdTypeDescr::Float32x4);
ARITH_COMMONX4_SIMD_OP(INLINE_FLOAT32X4_SIMD_ARITH_)
BINARY_ARITH_FLOAT32X4_SIMD_OP(INLINE_FLOAT32X4_SIMD_ARITH_)
#undef INLINE_FLOAT32X4_SIMD_ARITH_
#define INLINE_SIMD_BITWISE_(OP) \
if (native == js::simd_float32x4_##OP) \
return inlineBinarySimd<MSimdBinaryBitwise>(callInfo, native, MSimdBinaryBitwise::OP##_, \
SimdTypeDescr::Float32x4);
BITWISE_COMMONX4_SIMD_OP(INLINE_SIMD_BITWISE_)
#undef INLINE_SIMD_BITWISE_
#define INLINE_SIMD_COMPARISON_(OP) \
if (native == js::simd_float32x4_##OP) \
return inlineCompSimd(callInfo, native, MSimdBinaryComp::OP, SimdTypeDescr::Float32x4);
COMP_COMMONX4_TO_INT32X4_SIMD_OP(INLINE_SIMD_COMPARISON_)
#undef INLINE_SIMD_COMPARISON_
if (native == js::simd_float32x4_extractLane)
return inlineSimdExtractLane(callInfo, native, SimdTypeDescr::Float32x4);
if (native == js::simd_float32x4_replaceLane)
return inlineSimdReplaceLane(callInfo, native, SimdTypeDescr::Float32x4);
#define INLINE_SIMD_FLOAT32X4_UNARY_(OP) \
if (native == js::simd_float32x4_##OP) \
return inlineUnarySimd(callInfo, native, MSimdUnaryArith::OP, SimdTypeDescr::Float32x4);
UNARY_ARITH_FLOAT32X4_SIMD_OP(INLINE_SIMD_FLOAT32X4_UNARY_)
INLINE_SIMD_FLOAT32X4_UNARY_(neg)
#undef INLINE_SIMD_FLOAT32X4_UNARY_
if (native == js::simd_float32x4_not)
return inlineUnarySimd(callInfo, native, MSimdUnaryArith::not_, SimdTypeDescr::Float32x4);
typedef bool IsCast;
if (native == js::simd_float32x4_fromInt32x4)
return inlineSimdConvert(callInfo, native, IsCast(false), SimdTypeDescr::Int32x4, SimdTypeDescr::Float32x4);
if (native == js::simd_float32x4_fromInt32x4Bits)
return inlineSimdConvert(callInfo, native, IsCast(true), SimdTypeDescr::Int32x4, SimdTypeDescr::Float32x4);
if (native == js::simd_float32x4_splat)
return inlineSimdSplat(callInfo, native, SimdTypeDescr::Float32x4);
if (native == js::simd_float32x4_check)
return inlineSimdCheck(callInfo, native, SimdTypeDescr::Float32x4);
typedef bool IsElementWise;
if (native == js::simd_float32x4_select)
return inlineSimdSelect(callInfo, native, IsElementWise(true), SimdTypeDescr::Float32x4);
if (native == js::simd_float32x4_swizzle)
return inlineSimdShuffle(callInfo, native, SimdTypeDescr::Float32x4, 1, 4);
if (native == js::simd_float32x4_shuffle)
return inlineSimdShuffle(callInfo, native, SimdTypeDescr::Float32x4, 2, 4);
if (native == js::simd_float32x4_load)
return inlineSimdLoad(callInfo, native, SimdTypeDescr::Float32x4, 4);
if (native == js::simd_float32x4_load1)
return inlineSimdLoad(callInfo, native, SimdTypeDescr::Float32x4, 1);
if (native == js::simd_float32x4_load2)
return inlineSimdLoad(callInfo, native, SimdTypeDescr::Float32x4, 2);
if (native == js::simd_float32x4_load3)
return inlineSimdLoad(callInfo, native, SimdTypeDescr::Float32x4, 3);
if (native == js::simd_float32x4_store)
return inlineSimdStore(callInfo, native, SimdTypeDescr::Float32x4, 4);
if (native == js::simd_float32x4_store1)
return inlineSimdStore(callInfo, native, SimdTypeDescr::Float32x4, 1);
if (native == js::simd_float32x4_store2)
return inlineSimdStore(callInfo, native, SimdTypeDescr::Float32x4, 2);
if (native == js::simd_float32x4_store3)
return inlineSimdStore(callInfo, native, SimdTypeDescr::Float32x4, 3);
return InliningStatus_NotInlined;
}
IonBuilder::InliningStatus
IonBuilder::inlineConstructSimdObject(CallInfo& callInfo, SimdTypeDescr* descr)
{