Kaya Kupferschmidt avatar Kaya Kupferschmidt committed 9333633

Fixed date conversions

Comments (0)

Files changed (10)

source/libs/magnum_core/source/magnum/datetime/Date.h

     inline void setJulianDay(int32 day)
         { m_JulianDay = day; }
     inline int64 getTotalSecondsSince1970() const
-        { return getTotalSecondsSince1601() - 2440587LL * SecondsPerDay; }
+        { return getTotalSeconds() - 2440588LL * SecondsPerDay; }
     inline int64 getTotalSecondsSince1601() const
-        { return (int64)m_JulianDay * SecondsPerDay; }
+        { return getTotalSeconds() - 2305814LL * SecondsPerDay; }
+    inline int64 getTotalSeconds() const
+        { return (int64)(m_JulianDay) * SecondsPerDay; }
 
     int getDayOfYear() const;
     int getDayOfMonth() const;

source/libs/magnum_core/source/magnum/datetime/DateTime.cpp

 }
 
 
+/*--------------------------------------------------------------------------*/
+/**
+ */
 void DateTime::setTotalSecondsSince1970(int64 secs)
 {
-    setTotalSecondsSince1601(secs + 2440587LL * SecondsPerDay);
+    setTotalSecondsSince1601(secs + 2440588LL * SecondsPerDay);
 }
 
 
  */
 void DateTime::setTotalSecondsSince1601(int64 seconds)
 {
+    setTotalSeconds(seconds + 2305814LL * SecondsPerDay);
+}
+
+
+/*--------------------------------------------------------------------------*/
+/**
+ */
+void DateTime::setTotalSeconds(int64 seconds)
+{
     bool sign = seconds < 0;
     int julianDay = sign ? -int(-seconds / SecondsPerDay) : int(seconds / SecondsPerDay);
     seconds -= julianDay * SecondsPerDay;
 
 /*--------------------------------------------------------------------------*/
 /** Convert standard unix time (number of seconds since 1.1.1970) to
- * ticks since 1.1.1601
+ * ticks since 1.1.4713 BC
  */
 int64 DateTime::posixTimeToTicks(int64 ptime)
 {
 
 
 /*--------------------------------------------------------------------------*/
-/** Convert ticks since 1.1.1601 to unix time.
+/** Convert ticks since 1.1.4713 BC to unix time.
  */
 int64 DateTime::ticksToPosixTime(int64 ticks)
 {
     return (ticks - UnixEpoch) / TicksPerSecond;
 }
 
+
+/*--------------------------------------------------------------------------*/
+/** Convert standard ansi time (number of seconds since 1.1.1601) to
+ * ticks since 1.1.4713 BC
+ */
+int64 DateTime::ansiTimeToTicks(int64 ptime)
+{
+    return ptime * TicksPerSecond + AnsiEpoch;
+}
+
+
+/*--------------------------------------------------------------------------*/
+/** Convert ticks since 1.1.4713 BC to ansi time.
+ */
+int64 DateTime::ticksToAnsiTime(int64 ticks)
+{
+    return (ticks - AnsiEpoch) / TicksPerSecond;
+}
+
 } }

source/libs/magnum_core/source/magnum/datetime/DateTime.h

 /*--------------------------------------------------------------------------*/
 /**
  * This class provides a timestamp that counts the the number of 
- * 100-nanosecond intervals since January 1, 1601. 
+ * 100-nanosecond intervals since January 1, 4713 BC.
  */
 class MAGNUM_CORE_API DateTime {
 STRUCT_METAINFO(DateTime);
     static const int64 TicksPerMinute = Time::TicksPerMinute;
     static const int64 TicksPerHour = Time::TicksPerHour;
     static const int64 TicksPerDay = Time::TicksPerDay;
-    static const int64 UnixEpoch = 2440587LL * TicksPerDay;
+    static const int64 UnixEpoch = 2440588LL * TicksPerDay;
+    static const int64 AnsiEpoch = 2305814LL * TicksPerDay;
 
     static const DateTime Invalid;
 
         { return m_Date.getJulianDay(); }
     //! Returns the total number of hours since the epoch
     inline int getTotalHours() const
-        { return m_Date.getJulianDay() * HoursPerDay + m_Time.getTotalHours(); }
+        { return getTotalDays() * HoursPerDay + m_Time.getTotalHours(); }
     //! Returns the total number of minutes since the epoch possibly including any leap seconds
     inline int64 getTotalMinutes() const
-        { return int64(m_Date.getJulianDay()) * MinutesPerDay + (m_Time.getTotalSeconds() + getTotalLeapSeconds())/60; }
+        { return int64(getTotalDays()) * MinutesPerDay + (m_Time.getTotalSeconds() + getTotalLeapSeconds())/60; }
     //! Returns the total number of seconds since the epoch including any leap seconds
     inline int64 getTotalSeconds() const
-        { return int64(m_Date.getJulianDay()) * SecondsPerDay + m_Time.getTotalSeconds() + getTotalLeapSeconds(); }
+        { return int64(getTotalDays()) * SecondsPerDay + m_Time.getTotalSeconds() + getTotalLeapSeconds(); }
     //! Returns the total number of milliseconds since the epoch including any leap seconds
     inline int64 getTotalMilliseconds() const
-        { return int64(m_Date.getJulianDay()) * MillisecondsPerDay + m_Time.getTotalMilliseconds() + getTotalLeapSeconds()*1000; }
+        { return int64(getTotalDays()) * MillisecondsPerDay + m_Time.getTotalMilliseconds() + getTotalLeapSeconds()*1000; }
 
     //! Returns the total amount of leap seconds since the epoch
     int getTotalLeapSeconds() const;
 
     void setTotalSecondsSince1970(int64 secs);
     void setTotalSecondsSince1601(int64 secs);
+    void setTotalSeconds(int64 secs);
 
     inline int64 getTotalSecondsSince1970() const
-        { return getTotalSeconds() - 2440587LL * SecondsPerDay; }
+        { return getTotalSeconds() - 2440588LL * SecondsPerDay; }
     inline int64 getTotalSecondsSince1601() const
-        { return getTotalSeconds(); }
+        { return getTotalSeconds() - 2305814LL * SecondsPerDay; }
 
     inline int getDayOfYear() const
         { return m_Date.getDayOfYear(); }
 
     static int64 posixTimeToTicks(int64 ptime);
     static int64 ticksToPosixTime(int64 );
+    static int64 ansiTimeToTicks(int64 ptime);
+    static int64 ticksToAnsiTime(int64 );
 
 private:
     void setAbsolute(int julianDay, int64 ticks);

source/libs/magnum_core/source/magnum/datetime/spi/TimeZoneImpl.cpp

     ZoneDefinition zd;
     zd.name = name;
     zd.offset = offset;
-    zd.tickOffset = DateTime::TicksPerSecond * offset;
     zd.isDst = isDst;
     m_ZoneDefinitions.insert(zd);
 }
     ZoneEntry entry;
     entry.idx = idx;
     entry.secondsSince1970 = secsSince1970;
-    entry.ticksSince1601 = DateTime::posixTimeToTicks(secsSince1970);
     m_ZoneEntries.insert(entry);
 }
 
 {
     LeapSecondEntry entry;
     entry.secondsSince1970 = secsSince1970;
-    entry.ticksSince1601 = DateTime::posixTimeToTicks(secsSince1970);
     entry.adjustment = adjustment;
     entry.offset = adjustment;
     m_LeapSeconds.insert(entry);

source/libs/magnum_core/source/magnum/datetime/spi/TimeZoneImpl.h

         String name;
         //! Offset from GMT in seconds
         int offset;
-        //! Offset from GMT in ticks
-        int tickOffset;
         //! True if daylight savings time
         bool isDst;
     };
     struct LeapSecondEntry {
         int64 secondsSince1970;
-        int64 ticksSince1601;
         //! Number of seconds to add at the given date
         int adjustment;
-        //! Total number of seconds to add since 1601
+        //! Total number of seconds to add
         int offset;
     };
     struct ZoneEntry {
         int64 secondsSince1970;
-        int64 ticksSince1601;
         //! ZoneDefinition index
         int idx;
     };

source/libs/magnum_core/source/magnum/datetime/spi/TimeZoneProviderImpl.cpp

 
     // Create transitions
     int timecnt = (int)zone.transitions.getSize();
-    for (int i = 0; i < timecnt; ++i) {
-        tz->insertZoneEntry(zone.transitions[i].time, zone.transitions[i].type);
+    if (timecnt > 0) {
+        tz->insertZoneEntry(zone.transitions[0].time, zone.transitions[0].type);
+        for (int i = 1; i < timecnt; ++i) {
+            tz->insertZoneEntry(zone.transitions[i].time, zone.transitions[i-1].type);
+        }
     }
 
     // load leap seconds table

source/unittest/datetime/Test_Date.h

     TEST_ASSERT( date.getMonth() == 12 );
     TEST_ASSERT( date.getDayOfMonth() == 31 );
     TEST_ASSERT( date.getJulianDay() == 2450083 );
+
+    Date epoch1970(1970,1,1);
+    TEST_ASSERT( epoch1970.getTotalSecondsSince1970() == 0 );
+    TEST_ASSERT( epoch1970.getJulianDay() == 2440588 );
+
+    Date epoch1601(1601,1,1);
+    TEST_ASSERT( epoch1601.getTotalSecondsSince1601() == 0 );
+    TEST_ASSERT( epoch1601.getJulianDay() == 2305814 );
+
+    Date epoch4713(-4713,1,2);
+    TEST_ASSERT( epoch4713.getTotalSeconds() == 24*60*60 );
+    TEST_ASSERT( epoch4713.getJulianDay() == 1 );
 }
 
 

source/unittest/datetime/Test_DateTime.h

 }
 
 
+void test_epoch()
+{
+    DateTime epoch1970(Date(1970,1,1), Time(0));
+    TEST_ASSERT( epoch1970.getTotalSecondsSince1970() == epoch1970.getTotalLeapSeconds() );
+
+    DateTime epoch1601(Date(1601,1,1), Time(0));
+    TEST_ASSERT( epoch1601.getTotalSecondsSince1601() == epoch1601.getTotalLeapSeconds() );
+}
+
+
 void test_arithmetic()
 {
     DateTime datetime;
 }
 
 
-Test_DateTime() {
+Test_DateTime()
+{
     TEST_ADD(Test_DateTime::test_basics);
+    TEST_ADD(Test_DateTime::test_epoch);
     TEST_ADD(Test_DateTime::test_arithmetic);
     TEST_ADD(Test_DateTime::test_timeoverflow);
     TEST_ADD(Test_DateTime::test_leapseconds);

source/unittest/datetime/Test_SimpleTimeZone.h

     TEST_ASSERT( tz->getDaylightSavings() == 3600 );
     TEST_ASSERT( tz->getOffsetFromUtc(Date::AD, 2012, 10, 27, Date::Saturday, 0) == 7200 );
     TEST_ASSERT( tz->getOffsetFromUtc(Date::AD, 2012, 10, 28, Date::Sunday, 0) == 7200 );
+    TEST_ASSERT( tz->getOffsetFromUtc(Date::AD, 2012, 10, 28, Date::Sunday, 3599) == 7200 );
     TEST_ASSERT( tz->getOffsetFromUtc(Date::AD, 2012, 10, 28, Date::Sunday, 3600) == 3600 );
     TEST_ASSERT( tz->getOffsetFromUtc(Date::AD, 2012, 10, 29, Date::Monday, 0) == 3600 );
 }

source/unittest/datetime/Test_TimeZone.h

     TEST_ASSERT( tz->hasDaylightSaving() );
     TEST_ASSERT( tz->getDaylightSavings() == 3600 );
     TEST_ASSERT( tz->getOffsetFromUtc(Date::AD, 2012, 10, 27, Date::Saturday, 0) == 7200 );
+    TEST_ASSERT( tz->getOffsetFromUtc(Date::AD, 2012, 10, 27, Date::Saturday, 24*60*60-1) == 7200 );
     TEST_ASSERT( tz->getOffsetFromUtc(Date::AD, 2012, 10, 28, Date::Sunday, 0) == 7200 );
+    TEST_ASSERT( tz->getOffsetFromUtc(Date::AD, 2012, 10, 28, Date::Sunday, 3599) == 7200 );
     TEST_ASSERT( tz->getOffsetFromUtc(Date::AD, 2012, 10, 28, Date::Sunday, 3600) == 3600 );
     TEST_ASSERT( tz->getOffsetFromUtc(Date::AD, 2012, 10, 29, Date::Monday, 0) == 3600 );
     //TEST_ASSERT( tz->getLeapSecondEntryCount() == 0 );
Tip: Filter by directory path e.g. /media app.js to search for public/media/app.js.
Tip: Use camelCasing e.g. ProjME to search for ProjectModifiedEvent.java.
Tip: Filter by extension type e.g. /repo .js to search for all .js files in the /repo directory.
Tip: Separate your search with spaces e.g. /ssh pom.xml to search for src/ssh/pom.xml.
Tip: Use ↑ and ↓ arrow keys to navigate and return to view the file.
Tip: You can also navigate files with Ctrl+j (next) and Ctrl+k (previous) and view the file with Ctrl+o.
Tip: You can also navigate files with Alt+j (next) and Alt+k (previous) and view the file with Alt+o.