1
0
forked from 0ad/0ad

Revert 64bit number conversions added in c0ca70efd2, don't add the previous long and unsigned long conversions back and use double in the Replay menu.

64bit conversions (including the long ones) are not safe, because not
every number can be converted to the 2^53 JS numbers and pretending to
do so is asking for bugs.
Explicitly use the double type in the Replay menu, because std::time_t
is unspecified and some platforms like Ubuntu yakkety:i386 fail to
build, looking for long.
Double should work for the next 285 million years, becomes consistent
with SavedGame.cpp, is tested by test_ScriptConversions.cpp and doesn't
pretend to cover all 64bit numbers.

Patch By: echotangoecho
Differential Revision: https://code.wildfiregames.com/D205
Refs #3848 D84 D112

This was SVN commit r19367.
This commit is contained in:
elexis 2017-04-01 21:06:55 +00:00
parent c664fb7b6d
commit 1e07787e76
3 changed files with 1 additions and 114 deletions

View File

@ -54,7 +54,7 @@ CReplayLogger::~CReplayLogger()
void CReplayLogger::StartGame(JS::MutableHandleValue attribs)
{
// Add timestamp, since the file-modification-date can change
m_ScriptInterface.SetProperty(attribs, "timestamp", std::time(nullptr));
m_ScriptInterface.SetProperty(attribs, "timestamp", (double)std::time(nullptr));
// Add engine version and currently loaded mods for sanity checks when replaying
m_ScriptInterface.SetProperty(attribs, "engine_version", CStr(engine_version));

View File

@ -116,53 +116,6 @@ template<> bool ScriptInterface::FromJSVal<u8>(JSContext* cx, JS::HandleValue v,
return true;
}
template<> bool ScriptInterface::FromJSVal<i64>(JSContext* cx, JS::HandleValue v, i64& out)
{
JSAutoRequest rq(cx);
i64 tmp;
bool ok = JS::ToInt64(cx, v, &tmp);
out = (i64)tmp;
return ok;
}
template<> bool ScriptInterface::FromJSVal<u64>(JSContext* cx, JS::HandleValue v, u64& out)
{
JSAutoRequest rq(cx);
u64 tmp;
bool ok = JS::ToUint64(cx, v, &tmp);
out = (u64)tmp;
return ok;
}
// see comment below (where the same preprocessor condition is used)
#if MSC_VERSION && ARCH_AMD64
template<> bool ScriptInterface::FromJSVal<size_t>(JSContext* cx, JS::HandleValue v, size_t& out)
{
JSAutoRequest rq(cx);
int tmp;
if(!FromJSVal<int>(cx, v, tmp))
return false;
if(temp < 0)
return false;
out = (size_t)tmp;
return true;
}
template<> bool ScriptInterface::FromJSVal<ssize_t>(JSContext* cx, JS::HandleValue v, ssize_t& out)
{
JSAutoRequest rq(cx);
int tmp;
if(!FromJSVal<int>(cx, v, tmp))
return false;
if(tmp < 0)
return false;
out = (ssize_t)tmp;
return true;
}
#endif
template<> bool ScriptInterface::FromJSVal<std::wstring>(JSContext* cx, JS::HandleValue v, std::wstring& out)
{
JSAutoRequest rq(cx);
@ -294,35 +247,6 @@ template<> void ScriptInterface::ToJSVal<u32>(JSContext* UNUSED(cx), JS::Mutable
ret.set(JS::NumberValue(val));
}
template<> void ScriptInterface::ToJSVal<i64>(JSContext* UNUSED(cx), JS::MutableHandleValue ret, const i64& val)
{
ret.set(JS::NumberValue((int)val));
}
template<> void ScriptInterface::ToJSVal<u64>(JSContext* UNUSED(cx), JS::MutableHandleValue ret, const u64& val)
{
ret.set(JS::NumberValue((int)val));
}
// (s)size_t are considered to be identical to (unsigned) int by GCC and
// their specializations would cause conflicts there. On x86_64 GCC, s/size_t
// is equivalent to (unsigned) long, but the same solution applies; use the
// long and unsigned long specializations instead of s/size_t.
// for some reason, x64 MSC treats size_t as distinct from unsigned long:
#if MSC_VERSION && ARCH_AMD64
template<> void ScriptInterface::ToJSVal<size_t>(JSContext* UNUSED(cx), JS::MutableHandleValue ret, const size_t& val)
{
ret.set(JS::NumberValue((int)val));
}
template<> void ScriptInterface::ToJSVal<ssize_t>(JSContext* UNUSED(cx), JS::MutableHandleValue ret, const ssize_t& val)
{
ret.set(JS::NumberValue((int)val));
}
#endif
template<> void ScriptInterface::ToJSVal<std::wstring>(JSContext* cx, JS::MutableHandleValue ret, const std::wstring& val)
{
JSAutoRequest rq(cx);

View File

@ -141,22 +141,6 @@ public:
roundtrip<u32>(1073741824, "1073741824"); // JSVAL_INT_MAX+1
}
roundtrip<i64>(0, "0");
roundtrip<i64>(123, "123");
roundtrip<i64>(-123, "-123");
roundtrip<i64>(1073741822, "1073741822"); // JSVAL_INT_MAX-1
roundtrip<i64>(1073741823, "1073741823"); // JSVAL_INT_MAX
roundtrip<i64>(-1073741823, "-1073741823"); // JSVAL_INT_MIN+1
roundtrip<i64>(-1073741824, "-1073741824"); // JSVAL_INT_MIN
roundtrip<i64>(1073741824, "1073741824"); // JSVAL_INT_MAX+1
roundtrip<i64>(-1073741825, "-1073741825"); // JSVAL_INT_MIN-1
roundtrip<u64>(0, "0");
roundtrip<u64>(123, "123");
roundtrip<u64>(1073741822, "1073741822"); // JSVAL_INT_MAX-1
roundtrip<u64>(1073741823, "1073741823"); // JSVAL_INT_MAX
roundtrip<u64>(1073741824, "1073741824"); // JSVAL_INT_MAX+1
std::string s1 = "test";
s1[1] = '\0';
std::string s2 = "тест";
@ -218,27 +202,6 @@ public:
TS_ASSERT(val6.isInt32());
TS_ASSERT(val7.isInt32());
TS_ASSERT(val8.isDouble());
JS::RootedValue val9(cx), val10(cx), val11(cx), val12(cx), val13(cx), val14(cx), val15(cx), val16(cx), val17(cx);
ScriptInterface::ToJSVal<i64>(cx, &val9, 0);
ScriptInterface::ToJSVal<i64>(cx, &val10, 2147483646); // JSVAL_INT_MAX-1
ScriptInterface::ToJSVal<i64>(cx, &val11, 2147483647); // JSVAL_INT_MAX
ScriptInterface::ToJSVal<i64>(cx, &val12, -2147483647); // JSVAL_INT_MIN+1
ScriptInterface::ToJSVal<i64>(cx, &val13, -(i64)2147483648u); // JSVAL_INT_MIN
TS_ASSERT(val9.isInt32());
TS_ASSERT(val10.isInt32());
TS_ASSERT(val11.isInt32());
TS_ASSERT(val12.isInt32());
TS_ASSERT(val13.isInt32());
ScriptInterface::ToJSVal<u64>(cx, &val14, 0);
ScriptInterface::ToJSVal<u64>(cx, &val15, 2147483646u); // JSVAL_INT_MAX-1
ScriptInterface::ToJSVal<u64>(cx, &val16, 2147483647u); // JSVAL_INT_MAX
ScriptInterface::ToJSVal<u64>(cx, &val17, 2147483648u); // JSVAL_INT_MAX+1
TS_ASSERT(val14.isInt32());
TS_ASSERT(val15.isInt32());
TS_ASSERT(val16.isInt32());
TS_ASSERT(val17.isInt32());
}
void test_nonfinite()