mirror of
https://gitee.com/openharmony/arkcompiler_ets_runtime
synced 2024-11-26 19:50:55 +00:00
Reason: fix Date cache bug
Issue: https://gitee.com/openharmony/arkcompiler_ets_runtime/issues/IB1MTB?from=project-issue Test: Build & Boot devices Signed-off-by: wupengyong <wupengyong@huawei.com> Change-Id: I2a4b21bae79ff8d97b624acce4410d48ac954259
This commit is contained in:
parent
915632ea3d
commit
2ac7a1eb83
@ -39,7 +39,7 @@ JSTaggedValue BuiltinsDate::DateConstructor(EcmaRuntimeCallInfo *argv)
|
||||
JSHandle<JSTaggedValue> newTarget = GetNewTarget(argv);
|
||||
if (newTarget->IsUndefined()) {
|
||||
double now = JSDate::Now().GetDouble();
|
||||
CString str = JSDate::ToDateString(now);
|
||||
CString str = JSDate::ToDateString(thread, now);
|
||||
return GetTaggedString(thread, str.c_str());
|
||||
}
|
||||
|
||||
|
@ -342,19 +342,19 @@
|
||||
}
|
||||
|
||||
// NOLINTNEXTLINE(cppcoreguidelines-macro-usage)
|
||||
#define GET_DATE_VALUE(name, code, isLocal) \
|
||||
static JSTaggedValue name(EcmaRuntimeCallInfo *argv) \
|
||||
{ \
|
||||
ASSERT(argv); \
|
||||
JSThread *thread = argv->GetThread(); \
|
||||
[[maybe_unused]] EcmaHandleScope handleScope(thread); \
|
||||
JSHandle<JSTaggedValue> msg = GetThis(argv); \
|
||||
if (!msg->IsDate()) { \
|
||||
THROW_TYPE_ERROR_AND_RETURN(thread, "Not a Date Object", JSTaggedValue::Exception()); \
|
||||
} \
|
||||
JSHandle<JSDate> jsDate(msg); \
|
||||
double result = jsDate->GetDateValue(jsDate->GetTimeValue().GetDouble(), code, isLocal); \
|
||||
return GetTaggedDouble(result); \
|
||||
#define GET_DATE_VALUE(name, code, isLocal) \
|
||||
static JSTaggedValue name(EcmaRuntimeCallInfo *argv) \
|
||||
{ \
|
||||
ASSERT(argv); \
|
||||
JSThread *thread = argv->GetThread(); \
|
||||
[[maybe_unused]] EcmaHandleScope handleScope(thread); \
|
||||
JSHandle<JSTaggedValue> msg = GetThis(argv); \
|
||||
if (!msg->IsDate()) { \
|
||||
THROW_TYPE_ERROR_AND_RETURN(thread, "Not a Date Object", JSTaggedValue::Exception()); \
|
||||
} \
|
||||
JSHandle<JSDate> jsDate(msg); \
|
||||
double result = jsDate->GetDateValue(thread, jsDate->GetTimeValue().GetDouble(), code, isLocal); \
|
||||
return GetTaggedDouble(result); \
|
||||
}
|
||||
|
||||
// NOLINTNEXTLINE(cppcoreguidelines-macro-usage)
|
||||
|
@ -25,11 +25,6 @@
|
||||
|
||||
namespace panda::ecmascript {
|
||||
using NumberHelper = base::NumberHelper;
|
||||
bool DateUtils::isCached_ = false;
|
||||
int DateUtils::preSumDays_ = 0;
|
||||
int DateUtils::preDays_ = 0;
|
||||
int DateUtils::preMonth_ = 0;
|
||||
int DateUtils::preYear_ = 0;
|
||||
static const std::array<CString, WEEKDAY> WEEK_DAY_NAME = {"Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"};
|
||||
static const std::array<CString, MOUTH_PER_YEAR> MONTH_NAME = {
|
||||
"Jan", "Feb", "Mar", "Apr", "May", "Jun",
|
||||
@ -652,13 +647,13 @@ void JSDate::AppendStrToTargetLength(const CString &str, int length, CString &ta
|
||||
}
|
||||
}
|
||||
|
||||
bool JSDate::GetThisDateValues(std::array<int64_t, DATE_LENGTH> *date, bool isLocal) const
|
||||
bool JSDate::GetThisDateValues(JSThread *thread, std::array<int64_t, DATE_LENGTH> *date, bool isLocal) const
|
||||
{
|
||||
double timeMs = this->GetTimeValue().GetDouble();
|
||||
if (std::isnan(timeMs)) {
|
||||
return false;
|
||||
}
|
||||
GetDateValues(timeMs, date, isLocal);
|
||||
GetDateValues(thread, timeMs, date, isLocal);
|
||||
return true;
|
||||
}
|
||||
|
||||
@ -666,7 +661,7 @@ bool JSDate::GetThisDateValues(std::array<int64_t, DATE_LENGTH> *date, bool isLo
|
||||
JSTaggedValue JSDate::ToDateString(JSThread *thread) const
|
||||
{
|
||||
std::array<int64_t, DATE_LENGTH> fields = {0};
|
||||
if (!GetThisDateValues(&fields, true)) {
|
||||
if (!GetThisDateValues(thread, &fields, true)) {
|
||||
return JSTaggedValue(base::NAN_VALUE);
|
||||
}
|
||||
CString str;
|
||||
@ -683,13 +678,13 @@ JSTaggedValue JSDate::ToDateString(JSThread *thread) const
|
||||
}
|
||||
|
||||
// static
|
||||
CString JSDate::ToDateString(double timeMs)
|
||||
CString JSDate::ToDateString(JSThread *thread, double timeMs)
|
||||
{
|
||||
if (std::isnan(timeMs)) {
|
||||
return "Invalid Date";
|
||||
}
|
||||
std::array<int64_t, DATE_LENGTH> fields = {0};
|
||||
GetDateValues(timeMs, &fields, true);
|
||||
GetDateValues(thread, timeMs, &fields, true);
|
||||
CString localTime;
|
||||
int localMin = 0;
|
||||
localMin = GetLocalOffsetFromOS(timeMs, true);
|
||||
@ -725,7 +720,7 @@ CString JSDate::ToDateString(double timeMs)
|
||||
JSTaggedValue JSDate::ToISOString(JSThread *thread) const
|
||||
{
|
||||
std::array<int64_t, DATE_LENGTH> fields = {0};
|
||||
if (!GetThisDateValues(&fields, false)) {
|
||||
if (!GetThisDateValues(thread, &fields, false)) {
|
||||
return JSTaggedValue(base::NAN_VALUE);
|
||||
}
|
||||
CString year = ToCString(fields[YEAR]);
|
||||
@ -760,7 +755,7 @@ JSTaggedValue JSDate::ToString(JSThread *thread) const
|
||||
{
|
||||
int localMin = 0;
|
||||
std::array<int64_t, DATE_LENGTH> fields = {0};
|
||||
if (!GetThisDateValues(&fields, true)) {
|
||||
if (!GetThisDateValues(thread, &fields, true)) {
|
||||
return JSTaggedValue(base::NAN_VALUE);
|
||||
}
|
||||
CString localTime;
|
||||
@ -799,7 +794,7 @@ JSTaggedValue JSDate::ToTimeString(JSThread *thread) const
|
||||
{
|
||||
int localMin = 0;
|
||||
std::array<int64_t, DATE_LENGTH> fields = {0};
|
||||
if (!GetThisDateValues(&fields, true)) {
|
||||
if (!GetThisDateValues(thread, &fields, true)) {
|
||||
return JSTaggedValue(base::NAN_VALUE);
|
||||
}
|
||||
CString localTime;
|
||||
@ -829,7 +824,7 @@ JSTaggedValue JSDate::ToTimeString(JSThread *thread) const
|
||||
JSTaggedValue JSDate::ToUTCString(JSThread *thread) const
|
||||
{
|
||||
std::array<int64_t, DATE_LENGTH> fields = {0};
|
||||
if (!GetThisDateValues(&fields, false)) {
|
||||
if (!GetThisDateValues(thread, &fields, false)) {
|
||||
return JSTaggedValue(base::NAN_VALUE);
|
||||
}
|
||||
CString str;
|
||||
@ -860,7 +855,7 @@ JSTaggedValue JSDate::ValueOf() const
|
||||
}
|
||||
|
||||
// static
|
||||
void JSDate::GetDateValues(double timeMs, std::array<int64_t, DATE_LENGTH> *date, bool isLocal)
|
||||
void JSDate::GetDateValues(JSThread *thread, double timeMs, std::array<int64_t, DATE_LENGTH> *date, bool isLocal)
|
||||
{
|
||||
int64_t tz = 0;
|
||||
int64_t timeMsInt = static_cast<int64_t>(timeMs);
|
||||
@ -869,17 +864,17 @@ void JSDate::GetDateValues(double timeMs, std::array<int64_t, DATE_LENGTH> *date
|
||||
timeMsInt += tz * MS_PER_SECOND * SEC_PER_MINUTE;
|
||||
}
|
||||
|
||||
DateUtils::TransferTimeToDate(timeMsInt, date);
|
||||
thread->GetDateUtils()->TransferTimeToDate(timeMsInt, date);
|
||||
(*date)[TIMEZONE] = -tz;
|
||||
}
|
||||
|
||||
double JSDate::GetDateValue(double timeMs, uint8_t code, bool isLocal) const
|
||||
double JSDate::GetDateValue(JSThread *thread, double timeMs, uint8_t code, bool isLocal) const
|
||||
{
|
||||
if (std::isnan(timeMs)) {
|
||||
return base::NAN_VALUE;
|
||||
}
|
||||
std::array<int64_t, DATE_LENGTH> date = {0};
|
||||
GetDateValues(timeMs, &date, isLocal);
|
||||
GetDateValues(thread, timeMs, &date, isLocal);
|
||||
return static_cast<double>(date[code]);
|
||||
}
|
||||
|
||||
@ -907,13 +902,13 @@ JSTaggedValue JSDate::SetDateValue(EcmaRuntimeCallInfo *argv, uint32_t code, boo
|
||||
timeMs = 0.0;
|
||||
isSelectLocal = false;
|
||||
}
|
||||
JSThread *thread = argv->GetThread();
|
||||
if (!std::isnan(timeMs)) {
|
||||
GetDateValues(timeMs, &date, isSelectLocal);
|
||||
GetDateValues(thread, timeMs, &date, isSelectLocal);
|
||||
}
|
||||
// When timeMs is NaN, the corresponding parameters still need to be obtained
|
||||
for (uint32_t i = 0; i < count; i++) {
|
||||
JSHandle<JSTaggedValue> value = base::BuiltinsBase::GetCallArg(argv, i);
|
||||
JSThread *thread = argv->GetThread();
|
||||
JSTaggedNumber res = JSTaggedValue::ToNumber(thread, value);
|
||||
RETURN_EXCEPTION_IF_ABRUPT_COMPLETION(thread);
|
||||
double temp = res.GetNumber();
|
||||
|
@ -71,21 +71,24 @@ static constexpr char DEL = 127;
|
||||
|
||||
class DateUtils {
|
||||
public:
|
||||
static void TransferTimeToDate(int64_t timeMs, std::array<int64_t, DATE_LENGTH> *date);
|
||||
explicit DateUtils() = default;
|
||||
virtual ~DateUtils() = default;
|
||||
|
||||
void TransferTimeToDate(int64_t timeMs, std::array<int64_t, DATE_LENGTH> *date);
|
||||
// return the year, update days.
|
||||
void GetYearFromDays(std::array<int64_t, DATE_LENGTH> *date);
|
||||
static int64_t Mod(int64_t a, int b);
|
||||
static bool IsLeap(int64_t year);
|
||||
static int64_t GetDaysInYear(int64_t year);
|
||||
static int64_t GetDaysFromYear(int64_t year);
|
||||
// return the year, update days.
|
||||
static void GetYearFromDays(std::array<int64_t, DATE_LENGTH> *date);
|
||||
static int64_t FloorDiv(int64_t a, int64_t b);
|
||||
|
||||
private:
|
||||
static bool isCached_;
|
||||
static int preSumDays_;
|
||||
static int preDays_;
|
||||
static int preMonth_;
|
||||
static int preYear_;
|
||||
bool isCached_ {false};
|
||||
int preSumDays_ {0};
|
||||
int preDays_ {0};
|
||||
int preMonth_ {0};
|
||||
int preYear_ {0};
|
||||
};
|
||||
class JSDate : public JSObject {
|
||||
public:
|
||||
@ -133,7 +136,7 @@ public:
|
||||
|
||||
// 20.4.4.35
|
||||
JSTaggedValue ToDateString(JSThread *thread) const;
|
||||
static CString ToDateString(double timeMs);
|
||||
static CString ToDateString(JSThread *thread, double timeMs);
|
||||
|
||||
// 20.4.4.36
|
||||
JSTaggedValue ToISOString(JSThread *thread) const;
|
||||
@ -151,7 +154,7 @@ public:
|
||||
JSTaggedValue ValueOf() const;
|
||||
|
||||
JSTaggedValue SetDateValue(EcmaRuntimeCallInfo *argv, uint32_t code, bool isLocal) const;
|
||||
double GetDateValue(double timeMs, uint8_t code, bool isLocal) const;
|
||||
double GetDateValue(JSThread *thread, double timeMs, uint8_t code, bool isLocal) const;
|
||||
static JSTaggedValue GetTimeFromString(const char *str, int len);
|
||||
|
||||
static constexpr double MAX_DOUBLE = std::numeric_limits<double>::max();
|
||||
@ -165,13 +168,13 @@ public:
|
||||
static constexpr int MAX_DAYS_MONTH = 31;
|
||||
static double SetDateValues(const std::array<int64_t, DATE_LENGTH> *date, bool isLocal);
|
||||
static double SetDateValues(int64_t year, int64_t month, int64_t day);
|
||||
static void GetDateValues(double timeMs, std::array<int64_t, DATE_LENGTH> *date, bool isLocal);
|
||||
static void GetDateValues(JSThread *thread, double timeMs, std::array<int64_t, DATE_LENGTH> *date, bool isLocal);
|
||||
static CString StrToTargetLength(const CString &str, int length);
|
||||
static void AppendStrToTargetLength(const CString &str, int length, CString &target);
|
||||
DECL_DUMP()
|
||||
|
||||
private:
|
||||
bool GetThisDateValues(std::array<int64_t, DATE_LENGTH> *date, bool isLocal) const;
|
||||
bool GetThisDateValues(JSThread *thread, std::array<int64_t, DATE_LENGTH> *date, bool isLocal) const;
|
||||
CString GetLocaleTimeStr(const std::array<int64_t, DATE_LENGTH> &fields) const;
|
||||
CString GetLocaleDateStr(const std::array<int64_t, DATE_LENGTH> &fields) const;
|
||||
static int64_t MathMod(int64_t a, int b);
|
||||
|
@ -17,6 +17,7 @@
|
||||
|
||||
#include "ecmascript/runtime.h"
|
||||
#include "ecmascript/debugger/js_debugger_manager.h"
|
||||
#include "ecmascript/js_date.h"
|
||||
#include "ecmascript/js_object-inl.h"
|
||||
#include "ecmascript/js_tagged_value.h"
|
||||
#include "ecmascript/runtime_call_id.h"
|
||||
@ -130,6 +131,7 @@ JSThread::JSThread(EcmaVM *vm) : id_(os::thread::GetCurrentThreadId()), vm_(vm)
|
||||
}
|
||||
vmThreadControl_ = new VmThreadControl(this);
|
||||
SetBCStubStatus(BCStubStatus::NORMAL_BC_STUB);
|
||||
dateUtils_ = new DateUtils();
|
||||
}
|
||||
|
||||
JSThread::JSThread(EcmaVM *vm, ThreadType threadType) : id_(os::thread::GetCurrentThreadId()),
|
||||
@ -181,6 +183,10 @@ JSThread::~JSThread()
|
||||
if (!IsDaemonThread()) {
|
||||
UnregisterThread(this);
|
||||
}
|
||||
if (dateUtils_ != nullptr) {
|
||||
delete dateUtils_;
|
||||
dateUtils_ = nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
ThreadId JSThread::GetCurrentThreadId()
|
||||
|
@ -40,6 +40,7 @@
|
||||
#endif
|
||||
|
||||
namespace panda::ecmascript {
|
||||
class DateUtils;
|
||||
class EcmaContext;
|
||||
class EcmaVM;
|
||||
class EcmaHandleScope;
|
||||
@ -1474,7 +1475,10 @@ public:
|
||||
RegisterRTInterface(kungfu::RuntimeStubCSigns::ID_ASMFastWriteBarrier, asmCheckStub);
|
||||
}
|
||||
|
||||
|
||||
DateUtils *GetDateUtils() const
|
||||
{
|
||||
return dateUtils_;
|
||||
}
|
||||
|
||||
#ifndef NDEBUG
|
||||
inline void LaunchSuspendAll()
|
||||
@ -1620,6 +1624,7 @@ private:
|
||||
RecursiveMutex jitMutex_;
|
||||
bool machineCodeLowMemory_ {false};
|
||||
RecursiveMutex profileTypeAccessorLockMutex_;
|
||||
DateUtils *dateUtils_ {nullptr};
|
||||
|
||||
#ifndef NDEBUG
|
||||
MutatorLock::MutatorLockState mutatorLockState_ = MutatorLock::MutatorLockState::UNLOCKED;
|
||||
|
Loading…
Reference in New Issue
Block a user