diff --git a/src/dsql/ExprNodes.cpp b/src/dsql/ExprNodes.cpp index 8066bf30be..23bc600f0d 100644 --- a/src/dsql/ExprNodes.cpp +++ b/src/dsql/ExprNodes.cpp @@ -4272,11 +4272,7 @@ dsc* CurrentTimeNode::execute(thread_db* tdbb, jrd_req* request) const request->req_flags &= ~req_null; // Use the request timestamp. - ISC_TIMESTAMP_TZ currentTimeStamp = request->getTimeStampTz(); - - impure->vlu_misc.vlu_sql_time_tz.time_zone = tdbb->getAttachment()->att_current_timezone; - impure->vlu_misc.vlu_sql_time_tz.utc_time = TimeZoneUtil::timeStampTzToTimeTz(currentTimeStamp).utc_time; - + impure->vlu_misc.vlu_sql_time_tz = request->getTimeTz(); TimeStamp::round_time(impure->vlu_misc.vlu_sql_time_tz.utc_time, precision); impure->vlu_desc.makeTimeTz(&impure->vlu_misc.vlu_sql_time_tz); diff --git a/src/jrd/req.h b/src/jrd/req.h index d5b478d91c..86c7511369 100644 --- a/src/jrd/req.h +++ b/src/jrd/req.h @@ -239,6 +239,8 @@ private: // These are valid only when !req_gmt_timestamp.isEmpty(), so no initialization is necessary. mutable ISC_TIMESTAMP req_local_timestamp; // Timestamp in req_timezone's timezone mutable ISC_USHORT req_timezone; // Timezone borrowed from the attachment + mutable ISC_TIME req_local_time; // req_gmt_timestamp converted to local time (WITH TZ) + mutable bool req_local_time_valid; // req_local_time calculation is expensive. So is it valid (calculated)? public: MemoryPool* req_pool; @@ -410,6 +412,35 @@ public: return timeStampTz; } + ISC_TIME_TZ getTimeTz() const + { + fb_assert(!req_gmt_timestamp.isEmpty()); + + ISC_TIME_TZ timeTz; + + if (req_timezone != req_attachment->att_current_timezone) + updateLocalTimeStamp(); + + if (req_local_time_valid) + { + timeTz.utc_time = req_local_time; + timeTz.time_zone = req_timezone; + } + else + { + ISC_TIMESTAMP_TZ timeStamp; + timeStamp.utc_timestamp = req_gmt_timestamp.value(); + timeStamp.time_zone = req_timezone; + + timeTz = Firebird::TimeZoneUtil::timeStampTzToTimeTz(timeStamp); + + req_local_time = timeTz.utc_time; + req_local_time_valid = true; + } + + return timeTz; + } + void validateTimeStamp() { if (req_gmt_timestamp.isEmpty()) @@ -425,6 +456,7 @@ private: req_local_timestamp = Firebird::TimeZoneUtil::timeStampTzToTimeStamp( getTimeStampTz(), req_attachment->att_current_timezone); req_timezone = req_attachment->att_current_timezone; + req_local_time_valid = false; } };