@@ -104,6 +104,81 @@ T_ROM_PATCH(0x0038CE70, kROMPatchVoid, kROMPatchVoid, kROMPatchVoid, "Debugger"
104104 return 0L ;
105105}
106106
107+ /*
108+ * Set the time to the host time
109+ */
110+
111+ static const KUInt32 delta1904to1970 = 2082844800 ;
112+
113+ T_ROM_PATCH (0x00255578 , kROMPatchVoid , kROMPatchVoid , kROMPatchVoid , " RealClockSeconds" )
114+ {
115+ (void ) ioUnit;
116+ time_t t = time (NULL );
117+ struct tm gm;
118+ struct tm local;
119+ #if TARGET_OS_WIN32
120+ gmtime_s (&gm, &t);
121+ localtime_s (&local, &t);
122+ #else
123+ gmtime_r (&t, &gm);
124+ localtime_r (&t, &local);
125+ #endif
126+ double tzoffset = difftime (mktime (&local), mktime (&gm));
127+ ioCPU->SetRegister (0 , t + tzoffset + delta1904to1970);
128+ ioCPU->SetRegister (15 , ioCPU->GetRegister (14 ) + 4 );
129+ return 0L ;
130+ }
131+
132+ /* Patches for the 2010 problem:
133+ *
134+ * The low level NewtonOS clock will continue to run with seconds since
135+ * 1904-01-01T00:00:00. The NewtonScript functions which have been using a time
136+ * base of 1993-01-01T00:00:00 will however be patched so that they will use a
137+ * new time base of 2008-01-01T00:00:00. The patches will add or substract the
138+ * delta between the time bases.
139+ *
140+ * The base year will need to be updated in 2026.
141+ */
142+
143+ /* Delta from 2008-01-01T00:00:00 to 1993-01-01T00:00:00 */
144+
145+ static const KUInt32 safeIntervalDeltaSeconds = 473299200 ;
146+
147+ /*
148+ * Adjust seconds values returned to NS layer into safe interval
149+ */
150+
151+ T_ROM_PATCH (0x00089B80 , kROMPatchVoid , kROMPatchVoid , kROMPatchVoid , " FTimeInSeconds" )
152+ {
153+ ioCPU->SetRegister (0 , (ioCPU->GetRegister (0 ) - safeIntervalDeltaSeconds) << 2 );
154+ return ioUnit;
155+ }
156+
157+ /*
158+ * Fix date from seconds returned to NS layer
159+ */
160+
161+ T_ROM_PATCH (0x0008A8A8 , kROMPatchVoid , kROMPatchVoid , kROMPatchVoid , " FDateFromSeconds" )
162+ {
163+ ioCPU->SetRegister (1 , ioCPU->GetRegister (1 ) + safeIntervalDeltaSeconds);
164+ ioCPU->SetRegister (0 , ioCPU->GetRegister (13 ));
165+ return ioUnit;
166+ }
167+
168+ static const KUInt32 newTimeBaseMinutes = 218799360 ; /* 2008/1/1 in minutes from 1904/1/1 as NS integer */
169+ static const KUInt32 newTimeBaseSeconds = 3281990400 ; /* 2008/1/1 in seconds from 1904/1/1 as NS integer */
170+
171+ TJITGenericPatch timeBase1 (0x420750 , kROMPatchVoid , kROMPatchVoid , kROMPatchVoid ,
172+ newTimeBaseMinutes, " Time base (1/4)" );
173+ TJITGenericPatch timeBase2 (0x420798 , kROMPatchVoid , kROMPatchVoid , kROMPatchVoid ,
174+ newTimeBaseMinutes, " Time base (2/4)" );
175+ TJITGenericPatch timeBase3 (0x4dca14 , kROMPatchVoid , kROMPatchVoid , kROMPatchVoid ,
176+ newTimeBaseMinutes, " Time base (3/4)" );
177+ TJITGenericPatch timeBase4 (0x30F088 , kROMPatchVoid , kROMPatchVoid , kROMPatchVoid ,
178+ newTimeBaseSeconds, " Time base (4/4)" );
179+ TJITGenericPatch ignoreSettingTime (0x0008A20C , kROMPatchVoid , kROMPatchVoid , kROMPatchVoid ,
180+ 0xe1a0f00e , " Ignore setting time" ); // mov pc, lr
181+
107182// ========================================================================== //
108183// MARK: -
109184// TJITGenericPatchManager
0 commit comments