1 /* $NetBSD: nvram.c,v 1.16 2009/03/18 10:22:24 cegger Exp $ */
4 * Copyright (c) 1995 Leo Weppelman.
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions
10 * 1. Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
12 * 2. Redistributions in binary form must reproduce the above copyright
13 * notice, this list of conditions and the following disclaimer in the
14 * documentation and/or other materials provided with the distribution.
16 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
17 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
18 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
19 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
20 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
21 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
22 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
23 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
25 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
32 #include <sys/cdefs.h>
33 __KERNEL_RCSID(0, "$NetBSD: nvram.c,v 1.16 2009/03/18 10:22:24 cegger Exp $");
35 #include <sys/param.h>
37 #include <sys/kernel.h>
39 #include <sys/systm.h>
40 #include <sys/device.h>
44 #include <machine/iomap.h>
45 #include <machine/cpu.h>
47 #include <atari/dev/clockreg.h>
48 #include <atari/dev/nvramvar.h>
52 #define MC_NVRAM_CSUM (MC_NVRAM_START + MC_NVRAM_SIZE - 2)
55 static void nvram_set_csum(u_char csum
);
56 static int nvram_csum_valid(u_char csum
);
57 static u_char
nvram_csum(void);
60 * Auto config stuff....
62 static void nvr_attach(struct device
*, struct device
*, void *);
63 static int nvr_match(struct device
*, struct cfdata
*, void *);
65 CFATTACH_DECL(nvr
, sizeof(struct nvr_softc
),
66 nvr_match
, nvr_attach
, NULL
, NULL
);
68 extern struct cfdriver nvr_cd
;
72 nvr_match(struct device
*pdp
, struct cfdata
*cfp
, void *auxp
)
74 if (!strcmp((char *)auxp
, "nvr"))
81 nvr_attach(device_t pdp
, device_t dp
, void *auxp
)
83 struct nvr_softc
*nvr_soft
;
87 * Check the validity of the NVram contents
89 if (!nvram_csum_valid(nvram_csum())) {
90 printf(": Invalid checksum - re-initialized");
91 for (nreg
= MC_NVRAM_START
; nreg
< MC_NVRAM_CSUM
; nreg
++)
92 mc146818_write(RTC
, nreg
, 0);
93 nvram_set_csum(nvram_csum());
95 nvr_soft
= device_lookup_private(&nvr_cd
, 0);
96 nvr_soft
->nvr_flags
= NVR_CONFIGURED
;
100 * End of auto config stuff....
102 #endif /* NNVR > 0 */
105 * Kernel internal interface
108 nvr_get_byte(int byteno
)
111 struct nvr_softc
*nvr_soft
;
113 nvr_soft
= device_lookup_private(&nvr_cd
, 0);
114 if (!(nvr_soft
->nvr_flags
& NVR_CONFIGURED
))
116 return (mc146818_read(RTC
, byteno
+ MC_NVRAM_START
) & 0xff);
119 #endif /* NNVR > 0 */
125 nvram_uio(struct uio
*uio
)
130 u_char buf
[MC_NVRAM_CSUM
- MC_NVRAM_START
+ 1];
132 struct nvr_softc
*nvr_soft
;
134 nvr_soft
= device_lookup_private(&nvr_cd
,0);
135 if (!(nvr_soft
->nvr_flags
& NVR_CONFIGURED
))
139 printf("Request to transfer %d bytes offset: %d, %s nvram\n",
140 (long)uio
->uio_resid
, (long)uio
->uio_offset
,
141 (uio
->uio_rw
== UIO_READ
) ? "from" : "to");
142 #endif /* NV_DEBUG */
144 offset
= uio
->uio_offset
+ MC_NVRAM_START
;
145 nleft
= uio
->uio_resid
;
146 if (offset
+ nleft
>= MC_NVRAM_CSUM
) {
147 if (offset
== MC_NVRAM_CSUM
)
149 nleft
= MC_NVRAM_CSUM
- offset
;
154 printf("Translated: offset = %d, bytes: %d\n", (long)offset
, nleft
);
155 #endif /* NV_DEBUG */
157 if (uio
->uio_rw
== UIO_READ
) {
158 for (i
= 0, p
= buf
; i
< nleft
; i
++, p
++)
159 *p
= mc146818_read(RTC
, offset
+ i
);
161 if ((i
= uiomove(buf
, nleft
, uio
)) != 0)
163 if (uio
->uio_rw
== UIO_WRITE
) {
164 for (i
= 0, p
= buf
; i
< nleft
; i
++, p
++)
165 mc146818_write(RTC
, offset
+ i
, *p
);
166 nvram_set_csum(nvram_csum());
177 for (csum
= 0, nreg
= MC_NVRAM_START
; nreg
< MC_NVRAM_CSUM
; nreg
++)
178 csum
+= mc146818_read(RTC
, nreg
);
183 nvram_csum_valid(u_char csum
)
185 if (((~csum
& 0xff) != mc146818_read(RTC
, MC_NVRAM_CSUM
))
186 || (csum
!= mc146818_read(RTC
, MC_NVRAM_CSUM
+ 1)))
192 nvram_set_csum(u_char csum
)
194 mc146818_write(RTC
, MC_NVRAM_CSUM
, ~csum
);
195 mc146818_write(RTC
, MC_NVRAM_CSUM
+ 1, csum
);
197 #endif /* NNVR > 0 */