Annotation of sys/arch/alpha/alpha/mem.c, Revision 1.1.1.1
1.1 nbrk 1: /* $OpenBSD: mem.c,v 1.21 2006/04/13 14:41:08 brad Exp $ */
2: /* $NetBSD: mem.c,v 1.26 2000/03/29 03:48:20 simonb Exp $ */
3:
4: /*
5: * Copyright (c) 1988 University of Utah.
6: * Copyright (c) 1982, 1986, 1990, 1993
7: * The Regents of the University of California. All rights reserved.
8: *
9: * This code is derived from software contributed to Berkeley by
10: * the Systems Programming Group of the University of Utah Computer
11: * Science Department.
12: *
13: * Redistribution and use in source and binary forms, with or without
14: * modification, are permitted provided that the following conditions
15: * are met:
16: * 1. Redistributions of source code must retain the above copyright
17: * notice, this list of conditions and the following disclaimer.
18: * 2. Redistributions in binary form must reproduce the above copyright
19: * notice, this list of conditions and the following disclaimer in the
20: * documentation and/or other materials provided with the distribution.
21: * 3. Neither the name of the University nor the names of its contributors
22: * may be used to endorse or promote products derived from this software
23: * without specific prior written permission.
24: *
25: * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
26: * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
27: * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
28: * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
29: * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
30: * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
31: * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
32: * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
33: * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
34: * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
35: * SUCH DAMAGE.
36: *
37: * @(#)mem.c 8.3 (Berkeley) 1/12/94
38: */
39:
40: /*
41: * Memory special file
42: */
43:
44: #include <sys/param.h>
45: #include <sys/buf.h>
46: #include <sys/systm.h>
47: #include <sys/uio.h>
48: #include <sys/malloc.h>
49: #include <sys/msgbuf.h>
50: #include <sys/mman.h>
51: #include <sys/conf.h>
52:
53: #include <machine/cpu.h>
54:
55: #include <uvm/uvm_extern.h>
56:
57: #define mmread mmrw
58: #define mmwrite mmrw
59: cdev_decl(mm);
60:
61: caddr_t zeropage;
62:
63: /* open counter for aperture */
64: #ifdef APERTURE
65: static int ap_open_count = 0;
66: static pid_t ap_open_pid = -1;
67: extern int allowaperture;
68: #endif
69:
70: /*ARGSUSED*/
71: int
72: mmopen(dev, flag, mode, p)
73: dev_t dev;
74: int flag, mode;
75: struct proc *p;
76: {
77:
78: switch (minor(dev)) {
79: case 0:
80: case 1:
81: case 2:
82: return (0);
83: #ifdef APERTURE
84: case 4:
85: if (suser(p, 0) != 0 || !allowaperture)
86: return (EPERM);
87:
88: /* authorize only one simultaneous open() from the same pid */
89: if (ap_open_count > 0 && p->p_pid != ap_open_pid)
90: return(EPERM);
91: ap_open_count++;
92: ap_open_pid = p->p_pid;
93: return (0);
94: #endif
95: case 12:
96: return (0);
97: default:
98: return (ENXIO);
99: }
100: }
101:
102: /*ARGSUSED*/
103: int
104: mmclose(dev, flag, mode, p)
105: dev_t dev;
106: int flag, mode;
107: struct proc *p;
108: {
109:
110: #ifdef APERTURE
111: if (minor(dev) == 4) {
112: ap_open_count--;
113: ap_open_pid = -1;
114: }
115: #endif
116: return (0);
117: }
118:
119: /*ARGSUSED*/
120: int
121: mmrw(dev, uio, flags)
122: dev_t dev;
123: struct uio *uio;
124: int flags;
125: {
126: register vaddr_t o, v;
127: register int c;
128: register struct iovec *iov;
129: int error = 0, rw;
130: extern int msgbufmapped;
131:
132: while (uio->uio_resid > 0 && !error) {
133: iov = uio->uio_iov;
134: if (iov->iov_len == 0) {
135: uio->uio_iov++;
136: uio->uio_iovcnt--;
137: if (uio->uio_iovcnt < 0)
138: panic("mmrw");
139: continue;
140: }
141: switch (minor(dev)) {
142:
143: /* minor device 0 is physical memory */
144: case 0:
145: v = uio->uio_offset;
146: kmemphys:
147: if (v >= ALPHA_K0SEG_TO_PHYS((vaddr_t)msgbufp)) {
148: if (msgbufmapped == 0) {
149: printf("Message Buf not Mapped\n");
150: error = EFAULT;
151: break;
152: }
153: }
154:
155: /* Allow reads only in RAM. */
156: rw = (uio->uio_rw == UIO_READ) ? PROT_READ : PROT_WRITE;
157: if ((alpha_pa_access(v) & rw) != rw) {
158: error = EFAULT;
159: break;
160: }
161:
162: o = uio->uio_offset & PGOFSET;
163: c = min(uio->uio_resid, (int)(PAGE_SIZE - o));
164: error =
165: uiomove((caddr_t)ALPHA_PHYS_TO_K0SEG(v), c, uio);
166: break;
167:
168: /* minor device 1 is kernel memory */
169: case 1:
170: v = uio->uio_offset;
171:
172: if (v >= ALPHA_K0SEG_BASE && v <= ALPHA_K0SEG_END) {
173: v = ALPHA_K0SEG_TO_PHYS(v);
174: goto kmemphys;
175: }
176:
177: c = min(iov->iov_len, MAXPHYS);
178: if (!uvm_kernacc((caddr_t)v, c,
179: uio->uio_rw == UIO_READ ? B_READ : B_WRITE))
180: return (EFAULT);
181: error = uiomove((caddr_t)v, c, uio);
182: break;
183:
184: /* minor device 2 is EOF/rathole */
185: case 2:
186: if (uio->uio_rw == UIO_WRITE)
187: uio->uio_resid = 0;
188: return (0);
189:
190: /* minor device 12 (/dev/zero) is source of nulls on read, rathole on write */
191: case 12:
192: if (uio->uio_rw == UIO_WRITE) {
193: uio->uio_resid = 0;
194: return (0);
195: }
196: /*
197: * On the first call, allocate and zero a page
198: * of memory for use with /dev/zero.
199: */
200: if (zeropage == NULL) {
201: zeropage = (caddr_t)
202: malloc(PAGE_SIZE, M_TEMP, M_WAITOK);
203: bzero(zeropage, PAGE_SIZE);
204: }
205: c = min(iov->iov_len, PAGE_SIZE);
206: error = uiomove(zeropage, c, uio);
207: break;
208:
209: default:
210: return (ENXIO);
211: }
212: }
213: return (error);
214: }
215:
216: paddr_t
217: mmmmap(dev, off, prot)
218: dev_t dev;
219: off_t off;
220: int prot;
221: {
222: switch (minor(dev)) {
223: case 0:
224: /*
225: * /dev/mem is the only one that makes sense through this
226: * interface. For /dev/kmem any physaddr we return here
227: * could be transient and hence incorrect or invalid at
228: * a later time. /dev/null just doesn't make any sense
229: * and /dev/zero is a hack that is handled via the default
230: * pager in mmap().
231: */
232:
233: /*
234: * Allow access only in RAM.
235: */
236: if ((prot & alpha_pa_access(atop(off))) != prot)
237: return (-1);
238: return (atop(off));
239:
240: #ifdef APERTURE
241: case 4:
242: /* minor device 4 is aperture driver */
243: switch (allowaperture) {
244: case 1:
245: if ((prot & alpha_pa_access(atop(off))) != prot)
246: return (-1);
247: return atop(off);
248: default:
249: return -1;
250: }
251: #endif
252: default:
253: return -1;
254: }
255: }
256:
257: int
258: mmioctl(dev, cmd, data, flags, p)
259: dev_t dev;
260: u_long cmd;
261: caddr_t data;
262: int flags;
263: struct proc *p;
264: {
265: return (EOPNOTSUPP);
266: }
CVSweb