Split the nvram/rtc functionality away from the clock interrupt code

and attach it as `timekeeper0 at mainbus0'.
Use the MI mk48txx nvram/rtc access functions instead of home-grown
versions.

It should now be very easy to add a character device for the benefit
of userland access to NVRAM.
This commit is contained in:
scw 2001-08-12 18:33:12 +00:00
parent 7374ebbf8c
commit bb210bda7e
14 changed files with 85 additions and 216 deletions

View File

@ -1,4 +1,4 @@
# $NetBSD: files.mvme68k,v 1.46 2001/07/27 18:40:28 scw Exp $
# $NetBSD: files.mvme68k,v 1.47 2001/08/12 18:33:12 scw Exp $
# config file for mvme68k
@ -88,6 +88,11 @@ device memc
attach memc at mainbus
file arch/mvme68k/dev/memc.c memc
# TimeKeeper NVRAM device
device timekeeper: mk48txx
attach timekeeper at mainbus
file arch/mvme68k/dev/timekeeper.c timekeeper
# Memory disk for boot tape
file dev/md_root.c memory_disk_hooks
@ -131,6 +136,7 @@ file arch/mvme68k/mvme68k/sys_machdep.c
file arch/mvme68k/mvme68k/trap.c
file arch/mvme68k/mvme68k/vm_machdep.c
file arch/m68k/m68k/cacheops.c
file dev/clock_subr.c
file dev/cons.c
file dev/cninit.c

View File

@ -1,10 +1,12 @@
# $NetBSD: std.mvme68k,v 1.9 2000/11/30 22:31:27 scw Exp $
# $NetBSD: std.mvme68k,v 1.10 2001/08/12 18:33:12 scw Exp $
#
# Options/devices that all mvme68ks should have
#
machine mvme68k m68k
timekeeper0 at mainbus0
options EXEC_AOUT # support for exec'ing a.out
options EXEC_ELF32 # support for exec'ing Elf
options EXEC_SCRIPT # support for #! scripts

View File

@ -1,4 +1,4 @@
/* $NetBSD: clock_pcc.c,v 1.9 2001/07/06 19:00:13 scw Exp $ */
/* $NetBSD: clock_pcc.c,v 1.10 2001/08/12 18:33:13 scw Exp $ */
/*-
* Copyright (c) 1996 The NetBSD Foundation, Inc.
@ -49,7 +49,6 @@
#include <machine/psl.h>
#include <machine/bus.h>
#include <mvme68k/mvme68k/clockreg.h>
#include <mvme68k/mvme68k/clockvar.h>
#include <mvme68k/dev/pccreg.h>
#include <mvme68k/dev/pccvar.h>
@ -118,28 +117,16 @@ clock_pcc_attach(parent, self, aux)
panic("clock_pcc_attach: wrong interrupt level");
clock_pcc_sc = sc;
/* Map the RTC's registers */
sc->sc_clock_args.ca_bust = pa->pa_bust;
bus_space_map(pa->pa_bust, pa->pa_offset,
MK48T_REGSIZE, 0, &sc->sc_clock_args.ca_bush);
sc->sc_clock_args.ca_arg = sc;
sc->sc_clock_args.ca_initfunc = clock_pcc_initclocks;
sc->sc_clock_args.ca_microtime = clock_pcc_microtime;
/* Do common portions of clock config. */
clock_config(self, &sc->sc_clock_args);
clock_config(self, &sc->sc_clock_args, pccintr_evcnt(pa->pa_ipl));
/* Ensure our interrupts get disabled at shutdown time. */
(void) shutdownhook_establish(clock_pcc_shutdown, NULL);
/* Register the event counters */
evcnt_attach_dynamic(&clock_profcnt, EVCNT_TYPE_INTR,
pccintr_evcnt(pa->pa_ipl), "clock", "profint");
evcnt_attach_dynamic(&clock_statcnt, EVCNT_TYPE_INTR,
pccintr_evcnt(pa->pa_ipl), "clock", "statint");
/* Attach the interrupt handlers. */
pccintr_establish(PCCV_TIMER1, clock_pcc_profintr, pa->pa_ipl,
NULL, &clock_profcnt);

View File

@ -1,4 +1,4 @@
/* $NetBSD: clock_pcctwo.c,v 1.7 2001/07/06 19:00:13 scw Exp $ */
/* $NetBSD: clock_pcctwo.c,v 1.8 2001/08/12 18:33:13 scw Exp $ */
/*-
* Copyright (c) 1999 The NetBSD Foundation, Inc.
@ -50,7 +50,6 @@
#include <machine/psl.h>
#include <machine/bus.h>
#include <mvme68k/mvme68k/clockreg.h>
#include <mvme68k/mvme68k/clockvar.h>
#include <mvme68k/dev/pcctwovar.h>
#include <mvme68k/dev/pcctworeg.h>
@ -116,17 +115,12 @@ clock_pcctwo_attach(parent, self, aux)
if (pa->pa_ipl != CLOCK_LEVEL)
panic("clock_pcctwo_attach: wrong interrupt level");
/* Map the RTC's registers */
sc->sc_clock_args.ca_bust = pa->pa_bust;
bus_space_map(pa->pa_bust, pa->pa_offset,
MK48T_REGSIZE, 0, &sc->sc_clock_args.ca_bush);
sc->sc_clock_args.ca_arg = sc;
sc->sc_clock_args.ca_initfunc = clock_pcctwo_initclocks;
sc->sc_clock_args.ca_microtime = clock_pcctwo_microtime;
/* Do common portions of clock config. */
clock_config(self, &sc->sc_clock_args);
clock_config(self, &sc->sc_clock_args, pcctwointr_evcnt(pa->pa_ipl));
/* Ensure our interrupts get disabled at shutdown time. */
(void) shutdownhook_establish(clock_pcctwo_shutdown, NULL);
@ -134,12 +128,6 @@ clock_pcctwo_attach(parent, self, aux)
sc->sc_clock_lvl = (pa->pa_ipl & PCCTWO_ICR_LEVEL_MASK) |
PCCTWO_ICR_ICLR | PCCTWO_ICR_IEN;
/* Register the event counters */
evcnt_attach_dynamic(&clock_profcnt, EVCNT_TYPE_INTR,
pcctwointr_evcnt(pa->pa_ipl), "clock", "profint");
evcnt_attach_dynamic(&clock_statcnt, EVCNT_TYPE_INTR,
pcctwointr_evcnt(pa->pa_ipl), "clock", "statint");
/* Attach the interrupt handlers. */
pcctwointr_establish(PCCTWOV_TIMER1, clock_pcctwo_profintr,
pa->pa_ipl, NULL, &clock_profcnt);

View File

@ -1,4 +1,4 @@
/* $NetBSD: mainbus.c,v 1.10 2001/07/27 18:38:54 scw Exp $ */
/* $NetBSD: mainbus.c,v 1.11 2001/08/12 18:33:13 scw Exp $ */
/*-
* Copyright (c) 2000 The NetBSD Foundation, Inc.
@ -81,6 +81,7 @@ struct mainbus_devices {
#ifdef MVME147
static struct mainbus_devices mainbusdevs_147[] = {
{"pcc", MAINBUS_PCC_OFFSET},
{"timekeeper", MAINBUS_TK147_OFFSET},
{NULL, 0}
};
#endif
@ -89,6 +90,7 @@ static struct mainbus_devices mainbusdevs_147[] = {
static struct mainbus_devices mainbusdevs_1x7[] = {
{"pcctwo", MAINBUS_PCCTWO_OFFSET},
{"vmetwo", MAINBUS_VMETWO_OFFSET},
{"timekeeper", MAINBUS_TIMEKEEPER_OFFSET},
{NULL, 0}
};
#endif

View File

@ -1,4 +1,4 @@
/* $NetBSD: mainbus.h,v 1.5 2001/07/27 18:38:54 scw Exp $ */
/* $NetBSD: mainbus.h,v 1.6 2001/08/12 18:33:13 scw Exp $ */
/*-
* Copyright (c) 2000 The NetBSD Foundation, Inc.
@ -49,7 +49,8 @@ struct mainbus_attach_args {
/*
* Mainbus offsets for devices on MVME147
*/
#define MAINBUS_PCC_OFFSET 0x0000u
#define MAINBUS_TK147_OFFSET 0x0000u
#define MAINBUS_PCC_OFFSET 0x1000u
/*
* Mainbus offsets for devices on all other boards.
@ -59,6 +60,7 @@ struct mainbus_attach_args {
#define MAINBUS_MEMC1_OFFSET 0x3000u
#define MAINBUS_MEMC2_OFFSET 0x3100u
#define MAINBUS_IPACK_OFFSET 0x18000u /* mvme162/mvme172 only */
#define MAINBUS_TIMEKEEPER_OFFSET 0x80000u
extern struct mvme68k_bus_space_tag _mainbus_space_tag;
extern struct mvme68k_bus_dma_tag _mainbus_dma_tag;

View File

@ -1,4 +1,4 @@
/* $NetBSD: pcc.c,v 1.19 2001/07/06 19:00:13 scw Exp $ */
/* $NetBSD: pcc.c,v 1.20 2001/08/12 18:33:13 scw Exp $ */
/*-
* Copyright (c) 1996, 1997 The NetBSD Foundation, Inc.
@ -112,8 +112,7 @@ struct pcc_device {
* Devices that live on the PCC, attached in this order.
*/
static struct pcc_device pcc_devices[] = {
{"clock", PCC_RTC_OFF},
{"nvram", PCC_NVRAM_OFF},
{"clock", 0},
{"zsc", PCC_ZS0_OFF},
{"zsc", PCC_ZS1_OFF},
{"le", PCC_LE_OFF},
@ -181,8 +180,7 @@ pccattach(parent, self, args)
/* Get a handle to the PCC's registers. */
sc->sc_bust = ma->ma_bust;
bus_space_map(sc->sc_bust, PCC_REG_OFF + ma->ma_offset,
PCCREG_SIZE, 0, &sc->sc_bush);
bus_space_map(sc->sc_bust, ma->ma_offset, PCCREG_SIZE, 0, &sc->sc_bush);
/* Tell the chip the base interrupt vector */
pcc_reg_write(sc, PCCREG_VECTOR_BASE, PCC_VECBASE);

View File

@ -1,4 +1,4 @@
/* $NetBSD: pccreg.h,v 1.8 2001/04/14 13:53:06 scw Exp $ */
/* $NetBSD: pccreg.h,v 1.9 2001/08/12 18:33:13 scw Exp $ */
/*
*
@ -41,15 +41,12 @@
* Offsets to the MVME147's onboard device registers.
* (Relative to the bus_space_tag_t passed in from 'mainbus')
*/
#define PCC_NVRAM_OFF 0x0000 /* offset of Mostek NVRAM/RTC chip */
#define PCC_RTC_OFF 0x07f8 /* offset of clock registers NVRAM */
#define PCC_REG_OFF 0x1000 /* offset of PCC chip registers */
#define PCC_LE_OFF 0x1800 /* offset of LANCE ethernet chip */
#define PCC_VME_OFF 0x2000 /* offset of VME chip */
#define PCC_LPT_OFF 0x2800 /* offset of parallel port register */
#define PCC_ZS0_OFF 0x3000 /* offset of first 8530 UART */
#define PCC_ZS1_OFF 0x3800 /* offset of second 8530 UART */
#define PCC_WDSC_OFF 0x4000 /* offset of 33c93 SCSI chip */
#define PCC_LE_OFF 0x0800 /* offset of LANCE ethernet chip */
#define PCC_VME_OFF 0x1000 /* offset of VME chip */
#define PCC_LPT_OFF 0x1800 /* offset of parallel port register */
#define PCC_ZS0_OFF 0x2000 /* offset of first 8530 UART */
#define PCC_ZS1_OFF 0x2800 /* offset of second 8530 UART */
#define PCC_WDSC_OFF 0x3000 /* offset of 33c93 SCSI chip */
/*
* This is needed to figure out the boot device.

View File

@ -1,4 +1,4 @@
/* $NetBSD: pcctwo.c,v 1.14 2001/07/27 18:38:55 scw Exp $ */
/* $NetBSD: pcctwo.c,v 1.15 2001/08/12 18:33:13 scw Exp $ */
/*-
* Copyright (c) 1999 The NetBSD Foundation, Inc.
@ -91,12 +91,11 @@ struct pcctwo_device {
* Devices that live on the PCCchip2, attached in this order.
*/
static struct pcctwo_device pcctwo_devices[] = {
{"clock", PCCTWO_RTC_OFF},
{"clock", 0},
{"clmpcc", PCCTWO_SCC_OFF},
{"ie", PCCTWO_IE_OFF},
{"osiop", PCCTWO_NCRSC_OFF},
{"lpt", PCCTWO_LPT_OFF},
{"nvram", PCCTWO_NVRAM_OFF},
{NULL, 0}
};
@ -125,12 +124,11 @@ static int pcctwo_vec2icsr_1x7[] = {
* Devices that live on the MCchip, attached in this order.
*/
static struct pcctwo_device mcchip_devices[] = {
{"clock", PCCTWO_RTC_OFF},
{"clock", PCCTWO_NVRAM_OFF},
{"zsc", MCCHIP_ZS0_OFF},
{"zsc", MCCHIP_ZS1_OFF},
{"ie", PCCTWO_IE_OFF},
{"osiop", PCCTWO_NCRSC_OFF},
{"nvram", PCCTWO_NVRAM_OFF},
{NULL, 0}
};

View File

@ -1,4 +1,4 @@
/* $NetBSD: pcctworeg.h,v 1.9 2001/07/27 18:38:55 scw Exp $ */
/* $NetBSD: pcctworeg.h,v 1.10 2001/08/12 18:33:13 scw Exp $ */
/*-
* Copyright (c) 1999 The NetBSD Foundation, Inc.
@ -53,8 +53,6 @@
#define PCCTWO_SCC_OFF 0x03000 /* Offset of CD2401 Serial Comms chip */
#define PCCTWO_IE_OFF 0x04000 /* Offset of 82596 LAN controller */
#define PCCTWO_NCRSC_OFF 0x05000 /* Offset of NCR53C710 SCSI chip */
#define PCCTWO_NVRAM_OFF 0x7e000 /* Offset of MK48T18 NVRAM */
#define PCCTWO_RTC_OFF 0x7fff8 /* Offset of MK48T18 RTC registers */
/*
* The two devices on mvme162's MCchip

View File

@ -1,4 +1,4 @@
/* $NetBSD: clock.c,v 1.15 2001/05/31 18:46:09 scw Exp $ */
/* $NetBSD: clock.c,v 1.16 2001/08/12 18:33:13 scw Exp $ */
/*
* Copyright (c) 1992, 1993
@ -52,14 +52,10 @@
#include <machine/psl.h>
#include <machine/bus.h>
#include <mvme68k/mvme68k/clockreg.h>
#include <mvme68k/mvme68k/clockvar.h>
#if defined(GPROF)
#include <sys/gmon.h>
#endif
static struct clock_attach_args *clock_args;
static todr_chip_handle_t todr_handle;
struct evcnt clock_profcnt;
struct evcnt clock_statcnt;
@ -76,40 +72,41 @@ struct evcnt clock_statcnt;
int clock_statvar = 8192;
int clock_statmin; /* statclock interval - (1/2 * variance) */
/*
* autoconf
*/
struct chiptime {
int sec;
int min;
int hour;
int wday;
int day;
int mon;
int year;
};
static void timetochip __P((struct chiptime *));
static long chiptotime __P((int, int, int, int, int, int));
/*
* Common parts of clock autoconfiguration.
*/
void
clock_config(dev, ca)
clock_config(dev, ca, ev)
struct device *dev;
struct clock_attach_args *ca;
struct evcnt *ev;
{
extern int delay_divisor; /* from machdep.c */
/* Hook up that which we need. */
clock_args = ca;
evcnt_attach_dynamic(&clock_profcnt, EVCNT_TYPE_INTR, ev,
dev->dv_xname, "profint");
evcnt_attach_dynamic(&clock_statcnt, EVCNT_TYPE_INTR, ev,
dev->dv_xname, "statint");
/* Print info about the clock. */
printf(": delay_divisor %d\n", delay_divisor);
}
void
clock_rtc_config(todr)
todr_chip_handle_t todr;
{
if (todr_handle)
panic("clock_config: clock already configured");
todr_handle = todr;
}
/*
* Set up the real-time and statistics clocks. Leave stathz 0 only
* if no alternative timer is available.
@ -191,101 +188,6 @@ microtime(tvp)
splx(s);
}
/*
* BCD to decimal and decimal to BCD.
*/
#define FROMBCD(x) (((x) >> 4) * 10 + ((x) & 0xf))
#define TOBCD(x) (((x) / 10 * 16) + ((x) % 10))
#define SECDAY (24 * 60 * 60)
#define SECYR (SECDAY * 365)
#define LEAPYEAR(y) (((y) & 3) == 0)
/*
* This code is defunct after 2068.
* Will Unix still be here then??
*/
const short dayyr[12] =
{ 0, 31, 59, 90, 120, 151, 181, 212, 243, 273, 304, 334 };
static long
chiptotime(sec, min, hour, day, mon, year)
int sec, min, hour, day, mon, year;
{
int days, yr;
sec = FROMBCD(sec);
min = FROMBCD(min);
hour = FROMBCD(hour);
day = FROMBCD(day);
mon = FROMBCD(mon);
year = FROMBCD(year) + YEAR0;
/* simple sanity checks */
if (year < 70 || mon < 1 || mon > 12 || day < 1 || day > 31)
return (0);
days = 0;
for (yr = 70; yr < year; yr++)
days += LEAPYEAR(yr) ? 366 : 365;
days += dayyr[mon - 1] + day - 1;
if (LEAPYEAR(yr) && mon > 2)
days++;
/* now have days since Jan 1, 1970; the rest is easy... */
return (days * SECDAY + hour * 3600 + min * 60 + sec);
}
static void
timetochip(c)
struct chiptime *c;
{
int t, t2, t3, now = time.tv_sec;
/* compute the year */
t2 = now / SECDAY;
t3 = (t2 + 2) % 7; /* day of week */
c->wday = TOBCD(t3 + 1);
t = 69;
while (t2 >= 0) { /* whittle off years */
t3 = t2;
t++;
t2 -= LEAPYEAR(t) ? 366 : 365;
}
c->year = t;
/* t3 = month + day; separate */
t = LEAPYEAR(t);
for (t2 = 1; t2 < 12; t2++)
if (t3 < dayyr[t2] + (t && t2 > 1))
break;
/* t2 is month */
c->mon = t2;
c->day = t3 - dayyr[t2 - 1] + 1;
if (t && t2 > 2)
c->day--;
/* the rest is easy */
t = now % SECDAY;
c->hour = t / 3600;
t %= 3600;
c->min = t / 60;
c->sec = t % 60;
c->sec = TOBCD(c->sec);
c->min = TOBCD(c->min);
c->hour = TOBCD(c->hour);
c->day = TOBCD(c->day);
c->mon = TOBCD(c->mon);
c->year = TOBCD(c->year - YEAR0);
}
#define rtc_read(r) bus_space_read_1(clock_args->ca_bust, \
clock_args->ca_bush, (r))
#define rtc_write(r,v) bus_space_write_1(clock_args->ca_bust, \
clock_args->ca_bush, (r), (v))
/*
* Set up the system's time, given a `reasonable' time value.
*/
@ -293,8 +195,10 @@ void
inittodr(base)
time_t base;
{
int sec, min, hour, day, mon, year;
int badbase = 0, waszero = base == 0;
int badbase = 0, waszero = (base == 0);
if (todr_handle == NULL)
panic("todr not configured");
if (base < 5 * SECYR) {
/*
@ -308,20 +212,8 @@ inittodr(base)
badbase = 1;
}
/* enable read (stop time) */
rtc_write(MK48TREG_CSR, rtc_read(MK48TREG_CSR) | CLK_READ);
sec = rtc_read(MK48TREG_SEC);
min = rtc_read(MK48TREG_MIN);
hour = rtc_read(MK48TREG_HOUR);
day = rtc_read(MK48TREG_MDAY);
mon = rtc_read(MK48TREG_MONTH);
year = rtc_read(MK48TREG_YEAR);
/* time wears on */
rtc_write(MK48TREG_CSR, rtc_read(MK48TREG_CSR) & ~CLK_READ);
if ((time.tv_sec = chiptotime(sec, min, hour, day, mon, year)) == 0) {
if (todr_gettime(todr_handle, (struct timeval *)&time) != 0 ||
time.tv_sec == 0) {
printf("WARNING: bad date in battery clock");
/*
* Believe the time in the file system for lack of
@ -353,24 +245,10 @@ inittodr(base)
void
resettodr()
{
struct chiptime c;
if (!time.tv_sec)
return;
timetochip(&c);
/* enable write */
rtc_write(MK48TREG_CSR, rtc_read(MK48TREG_CSR) | CLK_WRITE);
rtc_write(MK48TREG_SEC, c.sec);
rtc_write(MK48TREG_MIN, c.min);
rtc_write(MK48TREG_HOUR, c.hour);
rtc_write(MK48TREG_WDAY, c.wday);
rtc_write(MK48TREG_MDAY, c.day);
rtc_write(MK48TREG_MONTH, c.mon);
rtc_write(MK48TREG_YEAR, c.year);
/* load them up */
rtc_write(MK48TREG_CSR, rtc_read(MK48TREG_CSR) & ~CLK_WRITE);
if (todr_settime(todr_handle, (struct timeval *)&time) != 0)
printf("resettodr: failed to set time\n");
}

View File

@ -1,4 +1,4 @@
/* $NetBSD: clockvar.h,v 1.6 2001/04/14 13:53:06 scw Exp $ */
/* $NetBSD: clockvar.h,v 1.7 2001/08/12 18:33:13 scw Exp $ */
/*-
* Copyright (c) 1996 The NetBSD Foundation, Inc.
@ -39,6 +39,9 @@
#ifndef _MVME68K_CLOCKVAR_H
#define _MVME68K_CLOCKVAR_H
#include <dev/clock_subr.h>
#include <dev/ic/mk48txxreg.h>
/*
* Defintions exported to ASIC-specific clock attachment.
*/
@ -50,14 +53,15 @@ extern int clock_statvar;
extern int clock_statmin;
struct clock_attach_args {
bus_space_tag_t ca_bust;
bus_space_handle_t ca_bush;
void (*ca_initfunc) __P((void *, int, int));
long (*ca_microtime) __P((void *));
void *ca_arg;
};
void clock_config __P((struct device *, struct clock_attach_args *));
void clock_config __P((struct device *, struct clock_attach_args *,
struct evcnt *));
void clock_rtc_config __P((todr_chip_handle_t));
/*
* Macro to compute a new randomized interval. The intervals are
@ -72,4 +76,15 @@ void clock_config __P((struct device *, struct clock_attach_args *));
(statmin + r); \
})
/*
* Sun chose the year `68' as their base count, so that
* cl_year==0 means 1968.
*/
#define YEAR0 1968
/*
* interrupt level for clock
*/
#define CLOCK_LEVEL 5
#endif /* _MVME68K_CLOCKVAR_H */

View File

@ -1,4 +1,4 @@
/* $NetBSD: machdep.c,v 1.84 2001/07/07 07:51:38 scw Exp $ */
/* $NetBSD: machdep.c,v 1.85 2001/08/12 18:33:13 scw Exp $ */
/*
* Copyright (c) 1988 University of Utah.
@ -297,8 +297,7 @@ mvme147_init()
/*
* Set up a temporary mapping to the PCC's registers
*/
bus_space_map(bt, intiobase_phys + MAINBUS_PCC_OFFSET + PCC_REG_OFF,
PCCREG_SIZE, 0, &bh);
bus_space_map(bt, intiobase_phys + MAINBUS_PCC_OFFSET, PCCREG_SIZE, 0, &bh);
/*
* calibrate delay() using the 6.25 usec counter.

View File

@ -1,4 +1,4 @@
/* $NetBSD: pmap_bootstrap.c,v 1.15 2000/11/20 19:35:30 scw Exp $ */
/* $NetBSD: pmap_bootstrap.c,v 1.16 2001/08/12 18:33:13 scw Exp $ */
/*
* Copyright (c) 1991, 1993
@ -43,7 +43,6 @@
#include <sys/kcore.h>
#include <machine/kcore.h>
#include <machine/pte.h>
#include <mvme68k/mvme68k/clockreg.h>
#include <machine/vmparam.h>
#include <machine/cpu.h>