Download raw body.
Y2K40 fixes for macppc
Several macppc systems (the oldest ones with ADB, and the laptops) store
the time as the unsigned number of seconds since 1904.
Instead of wrapping around in january 2038, they do so in february 2040.
I might not be around to see this, but the following diff tries to cope
with this by acknowledging that this hardware was built in the late
1990s, if not later, and that timestamps in the 1904-1970 range should
be handled as in the 2040-2106 range instead.
With this diff, a PowerMac1,1 (courtesy of otto@ 21 years ago) allows
the system date to be set in 2041, and picks it correctly upon reboot.
Index: dev/adb.c
===================================================================
RCS file: /OpenBSD/src/sys/arch/macppc/dev/adb.c,v
diff -u -p -r1.52 adb.c
--- dev/adb.c 14 Apr 2024 03:26:25 -0000 1.52
+++ dev/adb.c 9 Oct 2026 19:00:27 -0000
@@ -1417,6 +1417,9 @@ set_adb_info(ADBSetInfoBlock * info, int
}
+/* Number of seconds between 19040101 and 19700101 */
+#define DIFF19041970 2082844800
+
/* caller should really use machine-independent version: getPramTime */
/* this version does pseudo-adb access only */
int
@@ -1430,7 +1433,7 @@ adb_read_date_time(time_t *time)
switch (adbHardware) {
case ADB_HW_PMU:
- pm_read_date_time(time);
+ pm_read_date_time(&t);
retcode = 0;
break;
@@ -1450,7 +1453,6 @@ adb_read_date_time(time_t *time)
delay(20); /* completion occurs too soon? */
memcpy(&t, output + 1, sizeof(t));
- *time = (time_t)t;
retcode = 0;
break;
@@ -1460,9 +1462,16 @@ adb_read_date_time(time_t *time)
break;
}
if (retcode == 0) {
-#define DIFF19041970 2082844800
+ /*
+ * The value we've obtained is a 32-bit value of the number
+ * of seconds since 1904. It will wrap on 20400206.
+ * Since this hardware did not exist until the late 1990s,
+ * assume negative values are beyond 2040.
+ */
+ *time = (time_t)t;
+ if (t < DIFF19041970)
+ *time += 1ULL << 32;
*time -= DIFF19041970;
-
} else {
*time = 0;
}
@@ -1483,7 +1492,7 @@ adb_set_date_time(time_t time)
switch (adbHardware) {
case ADB_HW_CUDA:
- t = time; /* XXX eventually truncates */
+ t = time; /* truncates */
output[0] = 0x06; /* 6 byte message */
output[1] = 0x01; /* to pram/rtc device */
Index: dev/pm_direct.c
===================================================================
RCS file: /OpenBSD/src/sys/arch/macppc/dev/pm_direct.c,v
diff -u -p -r1.35 pm_direct.c
--- dev/pm_direct.c 22 Nov 2023 18:14:35 -0000 1.35
+++ dev/pm_direct.c 9 Oct 2026 19:00:27 -0000
@@ -738,10 +738,9 @@ pm_adb_poweroff(void)
}
void
-pm_read_date_time(time_t *time)
+pm_read_date_time(uint32_t *time)
{
PMData p;
- u_int32_t t;
p.command = PMU_READ_RTC;
p.num_data = 0;
@@ -749,20 +748,18 @@ pm_read_date_time(time_t *time)
p.r_buf = p.data;
pmgrop(&p);
- bcopy(p.data, &t, sizeof(t));
- *time = (time_t)t;
+ bcopy(p.data, time, sizeof(*time));
}
void
-pm_set_date_time(time_t time)
+pm_set_date_time(uint32_t time)
{
PMData p;
- u_int32_t t = time; /* XXX eventually truncates */
p.command = PMU_SET_RTC;
- p.num_data = sizeof(t);
+ p.num_data = sizeof(time);
p.s_buf = p.r_buf = p.data;
- bcopy(&t, p.data, sizeof(t));
+ bcopy(&time, p.data, sizeof(time));
pmgrop(&p);
}
Index: dev/pm_direct.h
===================================================================
RCS file: /OpenBSD/src/sys/arch/macppc/dev/pm_direct.h,v
diff -u -p -r1.17 pm_direct.h
--- dev/pm_direct.h 22 Oct 2024 21:50:02 -0000 1.17
+++ dev/pm_direct.h 9 Oct 2026 19:00:27 -0000
@@ -54,8 +54,8 @@ int pm_adb_op(u_char *, void *, void *,
void pm_adb_restart(void);
void pm_adb_poweroff(void);
void pm_intr(void);
-void pm_read_date_time(time_t *);
-void pm_set_date_time(time_t);
+void pm_read_date_time(uint32_t *);
+void pm_set_date_time(uint32_t);
struct pmu_battery_info {
unsigned int flags;
Y2K40 fixes for macppc