Update of /cvsroot/linux-mips/linux/drivers/char
In directory usw-pr-cvs1:/tmp/cvs-serv21086
Modified Files:
Makefile
Added Files:
rtc_dallas.c
Log Message:
Moved the new RTC Dallas standard using the new time code here. This will allow any mips device using a RTC PC style chip still using the old time standard to migrate with almost no change in code :-)
--- NEW FILE: rtc_dallas.c ---
/*
* Copyright 2001 James Simmons. jsi...@tr...
*
* arch/mips/kernel/rtc_dallas.c
* low-level RTC hookups for Dallas PC style chip.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by the
* Free Software Foundation; either version 2 of the License, or (at your
* option) any later version.
*/
/*
* This file exports a function, rtc_dallas_init(), which expects an
* uncached base address as the argument. It will set the two function
* pointers expected by the MIPS generic timer code.
*/
#include <linux/types.h>
#include <linux/time.h>
#include <asm/time.h>
#include <asm/addrspace.h>
#include <asm/debug.h>
#include <linux/mc146818rtc.h>
#define EPOCH 2000
#undef BCD_TO_BIN
#define BCD_TO_BIN(val) (((val)&15) + ((val)>>4)*10)
#undef BIN_TO_BCD
#define BIN_TO_BCD(val) ((((val)/10)<<4) + (val)%10)
static unsigned long rtc_base;
#define READ_RTC(x) rtc_ops->rtc_read_data(x)
#define WRITE_RTC(x, y) rtc_ops->rtc_write_data(y, x)
static unsigned long
rtc_dallas_get_time(void)
{
unsigned int year, month, day, hour, minute, second;
u8 byte, temp;
/* let us freeze external registers */
byte = READ_RTC(0xB);
byte &= 0x3f;
WRITE_RTC(0xB, byte);
/* read time data */
year = BCD_TO_BIN(READ_RTC(0xA)) + EPOCH;
month = BCD_TO_BIN(READ_RTC(0x9) & 0x1f);
day = BCD_TO_BIN(READ_RTC(0x8));
minute = BCD_TO_BIN(READ_RTC(0x2));
second = BCD_TO_BIN(READ_RTC(0x1));
/* hour is special - deal with it later */
temp = READ_RTC(0x4);
/* enable time transfer */
byte |= 0x80;
WRITE_RTC(0xB, byte);
/* calc hour */
if (temp & 0x40) {
/* 12 hour format */
hour = BCD_TO_BIN(temp & 0x1f);
if (temp & 0x20) hour += 12; /* PM */
} else {
/* 24 hour format */
hour = BCD_TO_BIN(temp & 0x3f);
}
return mktime(year, month, day, hour, minute, second);
}
static int
rtc_dallas_set_time(unsigned long t)
{
struct rtc_time tm;
u8 year, month, day, hour, minute, second;
u8 byte, temp;
/* let us freeze external registers */
byte = READ_RTC(0xB);
byte &= 0x3f;
WRITE_RTC(0xB, byte);
/* convert */
to_tm(t, &tm);
/* check each field one by one */
year = BIN_TO_BCD(tm.tm_year - EPOCH);
if (year != READ_RTC(0xA)) {
WRITE_RTC(0xA, year);
}
temp = READ_RTC(0x9);
month = BIN_TO_BCD(tm.tm_mon);
if (month != (temp & 0x1f)) {
WRITE_RTC( 0x9,
(month & 0x1f) | (temp & ~0x1f) );
}
day = BIN_TO_BCD(tm.tm_mday);
if (day != READ_RTC(0x8)) {
WRITE_RTC(0x8, day);
}
temp = READ_RTC(0x4);
if (temp & 0x40) {
/* 12 hour format */
hour = 0x40;
if (tm.tm_hour > 12) {
hour |= 0x20 | (BIN_TO_BCD(hour-12) & 0x1f);
} else {
hour |= BIN_TO_BCD(tm.tm_hour);
}
} else {
/* 24 hour format */
hour = BIN_TO_BCD(tm.tm_hour) & 0x3f;
}
if (hour != temp) WRITE_RTC(0x4, hour);
minute = BIN_TO_BCD(tm.tm_min);
if (minute != READ_RTC(0x2)) {
WRITE_RTC(0x2, minute);
}
second = BIN_TO_BCD(tm.tm_sec);
if (second != READ_RTC(0x1)) {
WRITE_RTC(0x1, second);
}
return 0;
}
void
rtc_dallas_init(unsigned long base)
{
unsigned char byte;
/* remember the base */
rtc_base = base;
db_assert((rtc_base & 0xe0000000) == KSEG1);
/* turn on RTC if it is not on */
byte = READ_RTC(0x9);
if (byte & 0x80) {
byte &= 0x7f;
WRITE_RTC(0x9, byte);
}
/* enable time transfer */
byte = READ_RTC(0xB);
byte |= 0x80;
WRITE_RTC(0xB, byte);
/* set the function pointers */
rtc_get_time = rtc_dallas_get_time;
rtc_set_time = rtc_dallas_set_time;
}
Index: Makefile
===================================================================
RCS file: /cvsroot/linux-mips/linux/drivers/char/Makefile,v
retrieving revision 1.12
retrieving revision 1.13
diff -u -d -r1.12 -r1.13
--- Makefile 2001/10/24 05:28:03 1.12
+++ Makefile 2001/10/26 16:47:44 1.13
@@ -192,6 +192,7 @@
obj-$(CONFIG_ADBMOUSE) += adbmouse.o
obj-$(CONFIG_PC110_PAD) += pc110pad.o
obj-$(CONFIG_RTC) += rtc.o
+obj-$(CONFIG_NEW_TIME_C) += rtc_dallas.o
obj-$(CONFIG_EFI_RTC) += efirtc.o
ifeq ($(CONFIG_PPC),)
obj-$(CONFIG_NVRAM) += nvram.o
|