зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1123777: Have SIMD shifts + splat + with functions apply ToInt32 to their scalar arguments; r=till
--HG-- extra : rebase_source : 9d7aa748738c8ec1a13ac53d15946a5c8665c956
This commit is contained in:
Родитель
b06e99dd64
Коммит
d8781fab29
|
@ -722,27 +722,18 @@ FuncWith(JSContext *cx, unsigned argc, Value *vp)
|
||||||
typedef typename V::Elem Elem;
|
typedef typename V::Elem Elem;
|
||||||
|
|
||||||
CallArgs args = CallArgsFromVp(argc, vp);
|
CallArgs args = CallArgsFromVp(argc, vp);
|
||||||
if (args.length() != 2 || !IsVectorObject<V>(args[0]) ||
|
if (args.length() != 2 || !IsVectorObject<V>(args[0]))
|
||||||
(!args[1].isNumber() && !args[1].isBoolean()))
|
|
||||||
{
|
|
||||||
return ErrorBadArgs(cx);
|
return ErrorBadArgs(cx);
|
||||||
}
|
|
||||||
|
|
||||||
Elem *val = TypedObjectMemory<Elem *>(args[0]);
|
Elem *vec = TypedObjectMemory<Elem *>(args[0]);
|
||||||
Elem result[V::lanes];
|
Elem result[V::lanes];
|
||||||
|
|
||||||
if (args[1].isNumber()) {
|
Elem value;
|
||||||
Elem withAsNumber;
|
if (!V::toType(cx, args[1], &value))
|
||||||
if (!V::toType(cx, args[1], &withAsNumber))
|
return false;
|
||||||
return false;
|
|
||||||
for (unsigned i = 0; i < V::lanes; i++)
|
for (unsigned i = 0; i < V::lanes; i++)
|
||||||
result[i] = OpWith<Elem>::apply(i, withAsNumber, val[i]);
|
result[i] = OpWith<Elem>::apply(i, value, vec[i]);
|
||||||
} else {
|
|
||||||
MOZ_ASSERT(args[1].isBoolean());
|
|
||||||
bool withAsBool = args[1].toBoolean();
|
|
||||||
for (unsigned i = 0; i < V::lanes; i++)
|
|
||||||
result[i] = OpWith<Elem>::apply(i, withAsBool, val[i]);
|
|
||||||
}
|
|
||||||
return StoreResult<V>(cx, args, result);
|
return StoreResult<V>(cx, args, result);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -816,7 +807,7 @@ Int32x4BinaryScalar(JSContext *cx, unsigned argc, Value *vp)
|
||||||
return ErrorBadArgs(cx);
|
return ErrorBadArgs(cx);
|
||||||
|
|
||||||
int32_t result[4];
|
int32_t result[4];
|
||||||
if (!IsVectorObject<Int32x4>(args[0]) || !args[1].isNumber())
|
if (!IsVectorObject<Int32x4>(args[0]))
|
||||||
return ErrorBadArgs(cx);
|
return ErrorBadArgs(cx);
|
||||||
|
|
||||||
int32_t *val = TypedObjectMemory<int32_t *>(args[0]);
|
int32_t *val = TypedObjectMemory<int32_t *>(args[0]);
|
||||||
|
@ -911,7 +902,7 @@ FuncSplat(JSContext *cx, unsigned argc, Value *vp)
|
||||||
typedef typename Vret::Elem RetElem;
|
typedef typename Vret::Elem RetElem;
|
||||||
|
|
||||||
CallArgs args = CallArgsFromVp(argc, vp);
|
CallArgs args = CallArgsFromVp(argc, vp);
|
||||||
if (args.length() != 1 || !args[0].isNumber())
|
if (args.length() != 1)
|
||||||
return ErrorBadArgs(cx);
|
return ErrorBadArgs(cx);
|
||||||
|
|
||||||
RetElem arg;
|
RetElem arg;
|
||||||
|
|
|
@ -273,7 +273,10 @@ struct Float32x4 {
|
||||||
return a;
|
return a;
|
||||||
}
|
}
|
||||||
static bool toType(JSContext *cx, JS::HandleValue v, Elem *out) {
|
static bool toType(JSContext *cx, JS::HandleValue v, Elem *out) {
|
||||||
*out = v.toNumber();
|
double d;
|
||||||
|
if (!ToNumber(cx, v, &d))
|
||||||
|
return false;
|
||||||
|
*out = float(d);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
static void setReturn(CallArgs &args, Elem value) {
|
static void setReturn(CallArgs &args, Elem value) {
|
||||||
|
@ -293,8 +296,7 @@ struct Float64x2 {
|
||||||
return a;
|
return a;
|
||||||
}
|
}
|
||||||
static bool toType(JSContext *cx, JS::HandleValue v, Elem *out) {
|
static bool toType(JSContext *cx, JS::HandleValue v, Elem *out) {
|
||||||
*out = v.toNumber();
|
return ToNumber(cx, v, out);
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
static void setReturn(CallArgs &args, Elem value) {
|
static void setReturn(CallArgs &args, Elem value) {
|
||||||
args.rval().setDouble(JS::CanonicalizeNaN(value));
|
args.rval().setDouble(JS::CanonicalizeNaN(value));
|
||||||
|
|
|
@ -1,91 +0,0 @@
|
||||||
// |reftest| skip-if(!this.hasOwnProperty("SIMD"))
|
|
||||||
var BUGNUMBER = 946042;
|
|
||||||
var float32x4 = SIMD.float32x4;
|
|
||||||
var int32x4 = SIMD.int32x4;
|
|
||||||
|
|
||||||
var summary = 'float32x4 with';
|
|
||||||
|
|
||||||
function test() {
|
|
||||||
print(BUGNUMBER + ": " + summary);
|
|
||||||
|
|
||||||
var a = float32x4(1, 2, 3, 4);
|
|
||||||
var x = SIMD.float32x4.withX(a, 5);
|
|
||||||
var y = SIMD.float32x4.withY(a, 5);
|
|
||||||
var z = SIMD.float32x4.withZ(a, 5);
|
|
||||||
var w = SIMD.float32x4.withW(a, 5);
|
|
||||||
assertEq(x.x, 5);
|
|
||||||
assertEq(x.y, 2);
|
|
||||||
assertEq(x.z, 3);
|
|
||||||
assertEq(x.w, 4);
|
|
||||||
|
|
||||||
assertEq(y.x, 1);
|
|
||||||
assertEq(y.y, 5);
|
|
||||||
assertEq(y.z, 3);
|
|
||||||
assertEq(y.w, 4);
|
|
||||||
|
|
||||||
assertEq(z.x, 1);
|
|
||||||
assertEq(z.y, 2);
|
|
||||||
assertEq(z.z, 5);
|
|
||||||
assertEq(z.w, 4);
|
|
||||||
|
|
||||||
assertEq(w.x, 1);
|
|
||||||
assertEq(w.y, 2);
|
|
||||||
assertEq(w.z, 3);
|
|
||||||
assertEq(w.w, 5);
|
|
||||||
|
|
||||||
var b = float32x4(1.87, 2.08, 3.84, 4.17);
|
|
||||||
var x1 = SIMD.float32x4.withX(b, 5.38);
|
|
||||||
var y1 = SIMD.float32x4.withY(b, 5.19);
|
|
||||||
var z1 = SIMD.float32x4.withZ(b, 5.11);
|
|
||||||
var w1 = SIMD.float32x4.withW(b, 5.07);
|
|
||||||
assertEq(x1.x, Math.fround(5.38));
|
|
||||||
assertEq(x1.y, Math.fround(2.08));
|
|
||||||
assertEq(x1.z, Math.fround(3.84));
|
|
||||||
assertEq(x1.w, Math.fround(4.17));
|
|
||||||
|
|
||||||
assertEq(y1.x, Math.fround(1.87));
|
|
||||||
assertEq(y1.y, Math.fround(5.19));
|
|
||||||
assertEq(y1.z, Math.fround(3.84));
|
|
||||||
assertEq(y1.w, Math.fround(4.17));
|
|
||||||
|
|
||||||
assertEq(z1.x, Math.fround(1.87));
|
|
||||||
assertEq(z1.y, Math.fround(2.08));
|
|
||||||
assertEq(z1.z, Math.fround(5.11));
|
|
||||||
assertEq(z1.w, Math.fround(4.17));
|
|
||||||
|
|
||||||
assertEq(w1.x, Math.fround(1.87));
|
|
||||||
assertEq(w1.y, Math.fround(2.08));
|
|
||||||
assertEq(w1.z, Math.fround(3.84));
|
|
||||||
assertEq(w1.w, Math.fround(5.07));
|
|
||||||
|
|
||||||
var c = float32x4(NaN, -0, Infinity, -Infinity);
|
|
||||||
var x2 = SIMD.float32x4.withX(c, 0);
|
|
||||||
var y2 = SIMD.float32x4.withY(c, 0);
|
|
||||||
var z2 = SIMD.float32x4.withZ(c, 0);
|
|
||||||
var w2 = SIMD.float32x4.withW(c, 0);
|
|
||||||
assertEq(x2.x, 0);
|
|
||||||
assertEq(x2.y, -0);
|
|
||||||
assertEq(x2.z, Infinity);
|
|
||||||
assertEq(x2.w, -Infinity);
|
|
||||||
|
|
||||||
assertEq(y2.x, NaN);
|
|
||||||
assertEq(y2.y, 0);
|
|
||||||
assertEq(y2.z, Infinity);
|
|
||||||
assertEq(y2.w, -Infinity);
|
|
||||||
|
|
||||||
assertEq(z2.x, NaN);
|
|
||||||
assertEq(z2.y, -0);
|
|
||||||
assertEq(z2.z, 0);
|
|
||||||
assertEq(z2.w, -Infinity);
|
|
||||||
|
|
||||||
assertEq(w2.x, NaN);
|
|
||||||
assertEq(w2.y, -0);
|
|
||||||
assertEq(w2.z, Infinity);
|
|
||||||
assertEq(w2.w, 0);
|
|
||||||
|
|
||||||
if (typeof reportCompare === "function")
|
|
||||||
reportCompare(true, true);
|
|
||||||
}
|
|
||||||
|
|
||||||
test();
|
|
||||||
|
|
|
@ -1,36 +0,0 @@
|
||||||
// |reftest| skip-if(!this.hasOwnProperty("SIMD"))
|
|
||||||
var BUGNUMBER = 1031203;
|
|
||||||
var float64x2 = SIMD.float64x2;
|
|
||||||
|
|
||||||
var summary = 'float64x2 with';
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Any copyright is dedicated to the Public Domain.
|
|
||||||
* https://creativecommons.org/publicdomain/zero/1.0/
|
|
||||||
*/
|
|
||||||
|
|
||||||
function test() {
|
|
||||||
print(BUGNUMBER + ": " + summary);
|
|
||||||
|
|
||||||
var a = float64x2(1, 2);
|
|
||||||
var x = float64x2.withX(a, 5);
|
|
||||||
var y = float64x2.withY(a, 5);
|
|
||||||
assertEq(x.x, 5);
|
|
||||||
assertEq(x.y, 2);
|
|
||||||
assertEq(y.x, 1);
|
|
||||||
assertEq(y.y, 5);
|
|
||||||
|
|
||||||
var b = float64x2(NaN, -0);
|
|
||||||
var x1 = float64x2.withX(b, Infinity);
|
|
||||||
var y1 = float64x2.withY(b, -Infinity);
|
|
||||||
assertEq(x1.x, Infinity);
|
|
||||||
assertEq(x1.y, -0);
|
|
||||||
assertEq(y1.x, NaN);
|
|
||||||
assertEq(y1.y, -Infinity);
|
|
||||||
|
|
||||||
if (typeof reportCompare === "function")
|
|
||||||
reportCompare(true, true);
|
|
||||||
}
|
|
||||||
|
|
||||||
test();
|
|
||||||
|
|
|
@ -1,28 +0,0 @@
|
||||||
// |reftest| skip-if(!this.hasOwnProperty("SIMD"))
|
|
||||||
var BUGNUMBER = 946042;
|
|
||||||
var float32x4 = SIMD.float32x4;
|
|
||||||
var int32x4 = SIMD.int32x4;
|
|
||||||
|
|
||||||
var summary = 'int32x4 with';
|
|
||||||
|
|
||||||
function test() {
|
|
||||||
print(BUGNUMBER + ": " + summary);
|
|
||||||
|
|
||||||
var INT32_MAX = Math.pow(2, 31) - 1;
|
|
||||||
|
|
||||||
var a = int32x4(1, 2, 3, 4);
|
|
||||||
var x = SIMD.int32x4.withX(a, 5);
|
|
||||||
var y = SIMD.int32x4.withY(a, 5);
|
|
||||||
var z = SIMD.int32x4.withZ(a, 5);
|
|
||||||
var w = SIMD.int32x4.withW(a, INT32_MAX + 1);
|
|
||||||
assertEq(x.x, 5);
|
|
||||||
assertEq(y.y, 5);
|
|
||||||
assertEq(z.z, 5);
|
|
||||||
assertEq(w.w, (INT32_MAX + 1) | 0);
|
|
||||||
|
|
||||||
if (typeof reportCompare === "function")
|
|
||||||
reportCompare(true, true);
|
|
||||||
}
|
|
||||||
|
|
||||||
test();
|
|
||||||
|
|
|
@ -18,6 +18,11 @@ function ursh(a, b) {
|
||||||
}
|
}
|
||||||
|
|
||||||
function test() {
|
function test() {
|
||||||
|
function TestError() {};
|
||||||
|
|
||||||
|
var good = {valueOf: () => 21};
|
||||||
|
var bad = {valueOf: () => {throw new TestError(); }};
|
||||||
|
|
||||||
for (var v of [
|
for (var v of [
|
||||||
int32x4(-1, 2, -3, 4),
|
int32x4(-1, 2, -3, 4),
|
||||||
int32x4(INT32_MAX, INT32_MIN, INT32_MAX - 1, INT32_MIN + 1)
|
int32x4(INT32_MAX, INT32_MIN, INT32_MAX - 1, INT32_MIN + 1)
|
||||||
|
@ -28,8 +33,17 @@ function test() {
|
||||||
testBinaryScalarFunc(v, bits, int32x4.shiftRightArithmeticByScalar, rsh);
|
testBinaryScalarFunc(v, bits, int32x4.shiftRightArithmeticByScalar, rsh);
|
||||||
testBinaryScalarFunc(v, bits, int32x4.shiftRightLogicalByScalar, ursh);
|
testBinaryScalarFunc(v, bits, int32x4.shiftRightLogicalByScalar, ursh);
|
||||||
}
|
}
|
||||||
|
// Test that the shift count is coerced to an int32.
|
||||||
|
testBinaryScalarFunc(v, undefined, int32x4.shiftLeftByScalar, lsh);
|
||||||
|
testBinaryScalarFunc(v, 3.5, int32x4.shiftLeftByScalar, lsh);
|
||||||
|
testBinaryScalarFunc(v, good, int32x4.shiftLeftByScalar, lsh);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
var v = SIMD.int32x4(1,2,3,4);
|
||||||
|
assertThrowsInstanceOf(() => SIMD.int32x4.shiftLeftByScalar(v, bad), TestError);
|
||||||
|
assertThrowsInstanceOf(() => SIMD.int32x4.shiftRightArithmeticByScalar(v, bad), TestError);
|
||||||
|
assertThrowsInstanceOf(() => SIMD.int32x4.shiftRightLogicalByScalar(v, bad), TestError);
|
||||||
|
|
||||||
if (typeof reportCompare === "function")
|
if (typeof reportCompare === "function")
|
||||||
reportCompare(true, true);
|
reportCompare(true, true);
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,38 @@
|
||||||
|
// |reftest| skip-if(!this.hasOwnProperty("SIMD"))
|
||||||
|
|
||||||
|
var float64x2 = SIMD.float64x2;
|
||||||
|
var float32x4 = SIMD.float32x4;
|
||||||
|
var int32x4 = SIMD.int32x4;
|
||||||
|
|
||||||
|
function TestSplatX4(type, inputs, coerceFunc) {
|
||||||
|
for (var x of inputs) {
|
||||||
|
assertEqX4(SIMD[type].splat(x), [x, x, x, x].map(coerceFunc));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function TestSplatX2(type, inputs, coerceFunc) {
|
||||||
|
for (var x of inputs) {
|
||||||
|
assertEqX2(SIMD[type].splat(x), [x, x].map(coerceFunc));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function test() {
|
||||||
|
function TestError(){};
|
||||||
|
|
||||||
|
var good = {valueOf: () => 19.89};
|
||||||
|
var bad = {valueOf: () => { throw new TestError(); }};
|
||||||
|
|
||||||
|
TestSplatX4('int32x4', [0, undefined, 3.5, 42, -1337, INT32_MAX, INT32_MAX + 1, good], (x) => x | 0);
|
||||||
|
assertThrowsInstanceOf(() => SIMD.int32x4.splat(bad), TestError);
|
||||||
|
|
||||||
|
TestSplatX4('float32x4', [0, undefined, 3.5, 42, -13.37, Infinity, NaN, -0, good], (x) => Math.fround(x));
|
||||||
|
assertThrowsInstanceOf(() => SIMD.float32x4.splat(bad), TestError);
|
||||||
|
|
||||||
|
TestSplatX2('float64x2', [0, undefined, 3.5, 42, -13.37, Infinity, NaN, -0, good], (x) => +x);
|
||||||
|
assertThrowsInstanceOf(() => SIMD.float64x2.splat(bad), TestError);
|
||||||
|
|
||||||
|
if (typeof reportCompare === "function")
|
||||||
|
reportCompare(true, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
test();
|
|
@ -0,0 +1,90 @@
|
||||||
|
// |reftest| skip-if(!this.hasOwnProperty("SIMD"))
|
||||||
|
var BUGNUMBER = 946042;
|
||||||
|
var float32x4 = SIMD.float32x4;
|
||||||
|
var int32x4 = SIMD.int32x4;
|
||||||
|
var float64x2 = SIMD.float64x2;
|
||||||
|
|
||||||
|
var summary = 'with{X,Y,Z,W}';
|
||||||
|
|
||||||
|
function withX(arr, x) {
|
||||||
|
if (arr.length == 2)
|
||||||
|
return [x, arr[1]];
|
||||||
|
return [x, arr[1], arr[2], arr[3]];
|
||||||
|
}
|
||||||
|
function withY(arr, x) {
|
||||||
|
if (arr.length == 2)
|
||||||
|
return [arr[0], x];
|
||||||
|
return [arr[0], x, arr[2], arr[3]];
|
||||||
|
}
|
||||||
|
function withZ(arr, x) {
|
||||||
|
return [arr[0], arr[1], x, arr[3]];
|
||||||
|
}
|
||||||
|
function withW(arr, x) {
|
||||||
|
return [arr[0], arr[1], arr[2], x];
|
||||||
|
}
|
||||||
|
|
||||||
|
function testWith(vec, scalar, simdFunc, func) {
|
||||||
|
var varr = simdToArray(vec);
|
||||||
|
var observed = simdToArray(simdFunc(vec, scalar));
|
||||||
|
var expected = func(varr, scalar);
|
||||||
|
for (var i = 0; i < observed.length; i++)
|
||||||
|
assertEq(observed[i], expected[i]);
|
||||||
|
}
|
||||||
|
|
||||||
|
function test() {
|
||||||
|
print(BUGNUMBER + ": " + summary);
|
||||||
|
|
||||||
|
function testType(type, inputs) {
|
||||||
|
var length = simdToArray(inputs[0][0]).length;
|
||||||
|
for (var [vec, s] of inputs) {
|
||||||
|
testWith(vec, s, SIMD[type].withX, withX);
|
||||||
|
testWith(vec, s, SIMD[type].withY, withY);
|
||||||
|
if (length <= 2)
|
||||||
|
continue;
|
||||||
|
testWith(vec, s, SIMD[type].withZ, withZ);
|
||||||
|
testWith(vec, s, SIMD[type].withW, withW);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function TestError(){};
|
||||||
|
var good = {valueOf: () => 42};
|
||||||
|
var bad = {valueOf: () => {throw new TestError(); }};
|
||||||
|
|
||||||
|
var float32x4inputs = [
|
||||||
|
[float32x4(1, 2, 3, 4), 5],
|
||||||
|
[float32x4(1.87, 2.08, 3.84, 4.17), Math.fround(13.37)],
|
||||||
|
[float32x4(NaN, -0, Infinity, -Infinity), 0]
|
||||||
|
];
|
||||||
|
testType('float32x4', float32x4inputs);
|
||||||
|
|
||||||
|
var v = float32x4inputs[1][0];
|
||||||
|
assertEqX4(float32x4.withX(v, good), withX(simdToArray(v), good | 0));
|
||||||
|
assertThrowsInstanceOf(() => float32x4.withX(v, bad), TestError);
|
||||||
|
|
||||||
|
var float64x2inputs = [
|
||||||
|
[float64x2(1, 2), 5],
|
||||||
|
[float64x2(1.87, 2.08), Math.fround(13.37)],
|
||||||
|
[float64x2(NaN, -0), 0]
|
||||||
|
];
|
||||||
|
testType('float64x2', float64x2inputs);
|
||||||
|
|
||||||
|
var v = float64x2inputs[1][0];
|
||||||
|
assertEqX4(float64x2.withX(v, good), withX(simdToArray(v), good | 0));
|
||||||
|
assertThrowsInstanceOf(() => float64x2.withX(v, bad), TestError);
|
||||||
|
|
||||||
|
var int32x4inputs = [
|
||||||
|
[int32x4(1, 2, 3, 4), 5],
|
||||||
|
[int32x4(INT32_MIN, INT32_MAX, 3, 4), INT32_MIN],
|
||||||
|
];
|
||||||
|
testType('int32x4', int32x4inputs);
|
||||||
|
|
||||||
|
var v = int32x4inputs[1][0];
|
||||||
|
assertEqX4(int32x4.withX(v, good), withX(simdToArray(v), good | 0));
|
||||||
|
assertThrowsInstanceOf(() => int32x4.withX(v, bad), TestError);
|
||||||
|
|
||||||
|
if (typeof reportCompare === "function")
|
||||||
|
reportCompare(true, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
test();
|
||||||
|
|
Загрузка…
Ссылка в новой задаче