[OpenBIOS] r606 - trunk/openbios-devel/drivers
svn at openbios.org
svn at openbios.org
Tue Nov 10 22:57:01 CET 2009
Author: laurent
Date: 2009-11-10 21:57:00 +0000 (Tue, 10 Nov 2009)
New Revision: 606
Modified:
trunk/openbios-devel/drivers/cuda.c
Log:
Define methods get-time and set-time of /pci/mac-io/via-cuda/rtc.
We can now have date&time from our openbios command line interface...
Signed-off-by: Laurent Vivier <Laurent at vivier.eu>
Modified: trunk/openbios-devel/drivers/cuda.c
===================================================================
--- trunk/openbios-devel/drivers/cuda.c 2009-11-10 21:52:40 UTC (rev 605)
+++ trunk/openbios-devel/drivers/cuda.c 2009-11-10 21:57:00 UTC (rev 606)
@@ -58,7 +58,9 @@
#define CUDA_PACKET 1
/* CUDA commands (2nd byte) */
-#define CUDA_POWERDOWN 0xa
+#define CUDA_GET_TIME 0x03
+#define CUDA_SET_TIME 0x09
+#define CUDA_POWERDOWN 0x0a
#define CUDA_RESET_SYSTEM 0x11
static uint8_t cuda_readb (cuda_t *dev, int reg)
@@ -233,8 +235,115 @@
RET(-1);
}
+/*
+ * get-time ( -- second minute hour day month year )
+ *
+ */
+
+static const int days_month[12] =
+ { 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 };
+static const int days_month_leap[12] =
+ { 31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 };
+
+static inline int is_leap(int year)
+{
+ return ((year % 4 == 0) && (year % 100 != 0)) || (year % 400 == 0);
+}
+
+static void
+rtc_get_time(int *idx)
+{
+ uint8_t cmdbuf[2], obuf[64];
+ ucell second, minute, hour, day, month, year;
+ uint32_t now;
+ int current;
+ const int *days;
+
+ cmdbuf[0] = CUDA_GET_TIME;
+ cuda_request(main_cuda, CUDA_PACKET, cmdbuf, sizeof(cmdbuf), obuf);
+
+ /* seconds since 01/01/1904 */
+
+ now = (obuf[3] << 24) + (obuf[4] << 16) + (obuf[5] << 8) + obuf[6];
+
+ second = now % 60;
+ now /= 60;
+
+ minute = now % 60;
+ now /= 60;
+
+ hour = now % 24;
+ now /= 24;
+
+ year = now * 100 / 36525;
+ now -= year * 36525 / 100;
+ year += 1904;
+
+ days = is_leap(year) ? days_month_leap : days_month;
+
+ current = 0;
+ month = 0;
+ while (month < 12) {
+ if (now <= current + days[month]) {
+ break;
+ }
+ current += days[month];
+ month++;
+ }
+ month++;
+
+ day = now - current;
+
+ PUSH(second);
+ PUSH(minute);
+ PUSH(hour);
+ PUSH(day);
+ PUSH(month);
+ PUSH(year);
+}
+
+/*
+ * set-time ( second minute hour day month year -- )
+ *
+ */
+
+static void
+rtc_set_time(int *idx)
+{
+ uint8_t cmdbuf[5], obuf[3];
+ ucell second, minute, hour, day, month, year;
+ const int *days;
+ uint32_t now;
+ unsigned int nb_days;
+ int i;
+
+ year = POP();
+ month = POP();
+ day = POP();
+ hour = POP();
+ minute = POP();
+ second = POP();
+
+ days = is_leap(year) ? days_month_leap : days_month;
+ nb_days = (year - 1904) * 36525 / 100 + day;
+ for (i = 0; i < month - 1; i++)
+ nb_days += days[i];
+
+ now = (((nb_days * 24) + hour) * 60 + minute) * 60 + second;
+
+ cmdbuf[0] = CUDA_SET_TIME;
+ cmdbuf[1] = now >> 24;
+ cmdbuf[2] = now >> 16;
+ cmdbuf[3] = now >> 8;
+ cmdbuf[4] = now;
+
+ cuda_request(main_cuda, CUDA_PACKET, cmdbuf, sizeof(cmdbuf), obuf);
+}
+
NODE_METHODS(rtc) = {
{ "open", rtc_open },
+ { "get-time", rtc_get_time },
+ { "set-time", rtc_set_time },
};
static void
More information about the OpenBIOS
mailing list