Annotation of sys/arch/hppa/dev/mem.c, Revision 1.1
1.1 ! nbrk 1: /* $OpenBSD: mem.c,v 1.28 2006/05/29 08:09:16 mickey Exp $ */
! 2:
! 3: /*
! 4: * Copyright (c) 1998-2004 Michael Shalayeff
! 5: * All rights reserved.
! 6: *
! 7: * Redistribution and use in source and binary forms, with or without
! 8: * modification, are permitted provided that the following conditions
! 9: * are met:
! 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.
! 15: *
! 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 OR HIS RELATIVES BE LIABLE FOR ANY DIRECT,
! 20: * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
! 21: * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
! 22: * SERVICES; LOSS OF MIND, USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
! 23: * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
! 24: * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
! 25: * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
! 26: * THE POSSIBILITY OF SUCH DAMAGE.
! 27: */
! 28: /*
! 29: * Copyright (c) 1991,1992,1994, The University of Utah and
! 30: * the Computer Systems Laboratory (CSL). All rights reserved.
! 31: *
! 32: * Subject to your agreements with CMU,
! 33: * permission to use, copy, modify and distribute this software and its
! 34: * documentation is hereby granted, provided that both the copyright
! 35: * notice and this permission notice appear in all copies of the
! 36: * software, derivative works or modified versions, and any portions
! 37: * thereof, and that both notices appear in supporting documentation.
! 38: *
! 39: * THE UNIVERSITY OF UTAH AND CSL ALLOW FREE USE OF THIS SOFTWARE IN ITS "AS
! 40: * IS" CONDITION. THE UNIVERSITY OF UTAH AND CSL DISCLAIM ANY LIABILITY OF
! 41: * ANY KIND FOR ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF THIS SOFTWARE.
! 42: *
! 43: * CSL requests users of this software to return to csl-dist@cs.utah.edu any
! 44: * improvements that they make and grant CSL redistribution rights.
! 45: *
! 46: * Utah $Hdr: mem.c 1.9 94/12/16$
! 47: */
! 48: /*
! 49: * Mach Operating System
! 50: * Copyright (c) 1992 Carnegie Mellon University
! 51: * All Rights Reserved.
! 52: *
! 53: * Permission to use, copy, modify and distribute this software and its
! 54: * documentation is hereby granted, provided that both the copyright
! 55: * notice and this permission notice appear in all copies of the
! 56: * software, derivative works or modified versions, and any portions
! 57: * thereof, and that both notices appear in supporting documentation.
! 58: *
! 59: * CARNEGIE MELLON ALLOWS FREE USE OF THIS SOFTWARE IN ITS "AS IS"
! 60: * CONDITION. CARNEGIE MELLON DISCLAIMS ANY LIABILITY OF ANY KIND FOR
! 61: * ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF THIS SOFTWARE.
! 62: *
! 63: * Carnegie Mellon requests users of this software to return to
! 64: *
! 65: * Software Distribution Coordinator or Software.Distribution@CS.CMU.EDU
! 66: * School of Computer Science
! 67: * Carnegie Mellon University
! 68: * Pittsburgh PA 15213-3890
! 69: *
! 70: * any improvements or extensions that they make and grant Carnegie Mellon
! 71: * the rights to redistribute these changes.
! 72: */
! 73:
! 74: #include <sys/param.h>
! 75: #include <sys/systm.h>
! 76: #include <sys/buf.h>
! 77: #include <sys/malloc.h>
! 78: #include <sys/proc.h>
! 79: #include <sys/uio.h>
! 80: #include <sys/types.h>
! 81: #include <sys/device.h>
! 82: #include <sys/errno.h>
! 83: #include <sys/ioctl.h>
! 84: #include <sys/file.h>
! 85:
! 86: #include <uvm/uvm.h>
! 87:
! 88: #include <machine/conf.h>
! 89: #include <machine/bus.h>
! 90: #include <machine/iomod.h>
! 91: #include <machine/autoconf.h>
! 92: #include <machine/pmap.h>
! 93:
! 94: #include <hppa/dev/cpudevs.h>
! 95: #include <hppa/dev/viper.h>
! 96:
! 97: #define VIPER_HPA 0xfffbf000
! 98:
! 99: /* registers on the PCXL2 MIOC */
! 100: struct l2_mioc {
! 101: u_int32_t pad[0x20]; /* 0x000 */
! 102: u_int32_t mioc_control; /* 0x080 MIOC control bits */
! 103: u_int32_t mioc_status; /* 0x084 MIOC status bits */
! 104: u_int32_t pad1[6]; /* 0x088 */
! 105: u_int32_t sltcv; /* 0x0a0 L2 cache control */
! 106: #define SLTCV_AVWL 0x00002000 /* extra cycle for addr valid write low */
! 107: #define SLTCV_UP4COUT 0x00001000 /* update cache on CPU castouts */
! 108: #define SLTCV_EDCEN 0x08000000 /* enable error correction */
! 109: #define SLTCV_EDTAG 0x10000000 /* enable diagtag */
! 110: #define SLTCV_CHKTP 0x20000000 /* enable parity checking */
! 111: #define SLTCV_LOWPWR 0x40000000 /* low power mode */
! 112: #define SLTCV_ENABLE 0x80000000 /* enable L2 cache */
! 113: #define SLTCV_BITS "\020\15avwl\16up4cout\24edcen\25edtag\26chktp\27lowpwr\30l2ena"
! 114: u_int32_t tagmask; /* 0x0a4 L2 cache tag mask */
! 115: u_int32_t diagtag; /* 0x0a8 L2 invalidates tag */
! 116: u_int32_t sltestat; /* 0x0ac L2 last logged tag read */
! 117: u_int32_t slteadd; /* 0x0b0 L2 pa of -- " -- */
! 118: u_int32_t pad2[3]; /* 0x0b4 */
! 119: u_int32_t mtcv; /* 0x0c0 MIOC timings */
! 120: u_int32_t ref; /* 0x0cc MIOC refresh timings */
! 121: u_int32_t pad3[4]; /* 0x0d0 */
! 122: u_int32_t mderradd; /* 0x0e0 addr of most evil mem error */
! 123: u_int32_t pad4; /* 0x0e4 */
! 124: u_int32_t dmaerr; /* 0x0e8 addr of most evil dma error */
! 125: u_int32_t dioerr; /* 0x0ec addr of most evil dio error */
! 126: u_int32_t gsc_timeout; /* 0x0f0 1-compl of GSC timeout delay */
! 127: u_int32_t hidmamem; /* 0x0f4 amount of phys mem installed */
! 128: u_int32_t pad5[2]; /* 0x0f8 */
! 129: u_int32_t memcomp[16]; /* 0x100 memory address comparators */
! 130: u_int32_t memmask[16]; /* 0x140 masks for -- " -- */
! 131: u_int32_t memtest; /* 0x180 test address decoding */
! 132: u_int32_t pad6[0xf]; /* 0x184 */
! 133: u_int32_t outchk; /* 0x1c0 address decoding output */
! 134: u_int32_t pad7[0x168]; /* 0x200 */
! 135: u_int32_t gsc15x_config; /* 0x7a0 writev enable */
! 136: };
! 137:
! 138: struct mem_softc {
! 139: struct device sc_dev;
! 140:
! 141: volatile struct vi_trs *sc_vp;
! 142: volatile struct l2_mioc *sc_l2;
! 143: };
! 144:
! 145: int memmatch(struct device *, void *, void *);
! 146: void memattach(struct device *, struct device *, void *);
! 147:
! 148: struct cfattach mem_ca = {
! 149: sizeof(struct mem_softc), memmatch, memattach
! 150: };
! 151:
! 152: struct cfdriver mem_cd = {
! 153: NULL, "mem", DV_DULL
! 154: };
! 155:
! 156: caddr_t zeropage;
! 157:
! 158: int
! 159: memmatch(parent, cfdata, aux)
! 160: struct device *parent;
! 161: void *cfdata;
! 162: void *aux;
! 163: {
! 164: register struct confargs *ca = aux;
! 165:
! 166: if (ca->ca_type.iodc_type != HPPA_TYPE_MEMORY ||
! 167: ca->ca_type.iodc_sv_model != HPPA_MEMORY_PDEP)
! 168: return 0;
! 169:
! 170: return 1;
! 171: }
! 172:
! 173: void
! 174: memattach(parent, self, aux)
! 175: struct device *parent;
! 176: struct device *self;
! 177: void *aux;
! 178: {
! 179: struct pdc_iodc_minit pdc_minit PDC_ALIGNMENT;
! 180: struct mem_softc *sc = (struct mem_softc *)self;
! 181: struct confargs *ca = aux;
! 182: int err;
! 183:
! 184: printf (":");
! 185:
! 186: /* XXX check if we are dealing w/ Viper */
! 187: if (ca->ca_hpa == (hppa_hpa_t)VIPER_HPA) {
! 188:
! 189: sc->sc_vp = (struct vi_trs *)
! 190: &((struct iomod *)ca->ca_hpa)->priv_trs;
! 191:
! 192: /* XXX other values seem to blow it up */
! 193: if (sc->sc_vp->vi_status.hw_rev == 0) {
! 194: u_int32_t vic;
! 195: int s, settimeout;
! 196:
! 197: switch (cpu_hvers) {
! 198: case HPPA_BOARD_HP715_33:
! 199: case HPPA_BOARD_HP715S_33:
! 200: case HPPA_BOARD_HP715T_33:
! 201: case HPPA_BOARD_HP715_50:
! 202: case HPPA_BOARD_HP715S_50:
! 203: case HPPA_BOARD_HP715T_50:
! 204: case HPPA_BOARD_HP715_75:
! 205: case HPPA_BOARD_HP725_50:
! 206: case HPPA_BOARD_HP725_75:
! 207: settimeout = 1;
! 208: break;
! 209: default:
! 210: settimeout = 0;
! 211: break;
! 212: }
! 213: if (sc->sc_dev.dv_cfdata->cf_flags & 1)
! 214: settimeout = !settimeout;
! 215:
! 216: printf(" viper rev %x,", sc->sc_vp->vi_status.hw_rev);
! 217: #ifdef DEBUG
! 218: printf(" ctrl %b", VI_CTRL, VI_CTRL_BITS);
! 219: #endif
! 220: s = splhigh();
! 221: vic = VI_CTRL;
! 222: vic &= ~VI_CTRL_CORE_DEN;
! 223: vic &= ~VI_CTRL_SGC0_DEN;
! 224: vic &= ~VI_CTRL_SGC1_DEN;
! 225: vic |= VI_CTRL_EISA_DEN;
! 226: vic |= VI_CTRL_CORE_PRF;
! 227:
! 228: if (settimeout && (vic & VI_CTRL_VSC_TOUT) == 0)
! 229: vic |= (850 << 19); /* clks */
! 230:
! 231: sc->sc_vp->vi_control = vic;
! 232:
! 233: __asm __volatile("stwas %1, 0(%0)"
! 234: :: "r" (&VI_CTRL), "r" (vic) : "memory");
! 235: splx(s);
! 236: #ifdef DEBUG
! 237: printf (" >> %b,", vic, VI_CTRL_BITS);
! 238: #endif
! 239: } else
! 240: sc->sc_vp = NULL;
! 241: } else
! 242: sc->sc_vp = NULL;
! 243:
! 244: if ((err = pdc_call((iodcio_t)pdc, 0, PDC_IODC, PDC_IODC_NINIT,
! 245: &pdc_minit, ca->ca_hpa, PAGE0->imm_spa_size)) < 0)
! 246: pdc_minit.max_spa = PAGE0->imm_max_mem;
! 247:
! 248: printf(" size %d", pdc_minit.max_spa / (1024*1024));
! 249: if (pdc_minit.max_spa % (1024*1024))
! 250: printf(".%d", pdc_minit.max_spa % (1024*1024));
! 251: printf("MB");
! 252:
! 253: /* L2 cache controller is a part of the memory controller on PCXL2 */
! 254: if (cpu_type == hpcxl2) {
! 255: sc->sc_l2 = (struct l2_mioc *)ca->ca_hpa;
! 256: #ifdef DEBUG
! 257: printf(", sltcv %b", sc->sc_l2->sltcv, SLTCV_BITS);
! 258: #endif
! 259: /* sc->sc_l2->sltcv |= SLTCV_UP4COUT; */
! 260: if (sc->sc_l2->sltcv & SLTCV_ENABLE) {
! 261: u_int32_t tagmask = sc->sc_l2->tagmask >> 20;
! 262:
! 263: printf(", %dMB L2 cache", tagmask + 1);
! 264: }
! 265: }
! 266:
! 267: printf("\n");
! 268: }
! 269:
! 270: void
! 271: viper_setintrwnd(mask)
! 272: u_int32_t mask;
! 273: {
! 274: register struct mem_softc *sc;
! 275:
! 276: sc = mem_cd.cd_devs[0];
! 277:
! 278: if (sc->sc_vp)
! 279: sc->sc_vp->vi_intrwd = mask;
! 280: }
! 281:
! 282: void
! 283: viper_eisa_en()
! 284: {
! 285: struct mem_softc *sc;
! 286:
! 287: sc = mem_cd.cd_devs[0];
! 288: if (sc->sc_vp) {
! 289: u_int32_t vic;
! 290: int s;
! 291:
! 292: s = splhigh();
! 293: vic = VI_CTRL;
! 294: vic &= ~VI_CTRL_EISA_DEN;
! 295: sc->sc_vp->vi_control = vic;
! 296: __asm __volatile("stwas %1, 0(%0)"
! 297: :: "r" (&VI_CTRL), "r" (vic) : "memory");
! 298: splx(s);
! 299: }
! 300: }
! 301:
! 302: int
! 303: mmopen(dev, flag, ioflag, p)
! 304: dev_t dev;
! 305: int flag;
! 306: int ioflag;
! 307: struct proc *p;
! 308: {
! 309: return (0);
! 310: }
! 311:
! 312: /*ARGSUSED*/
! 313: int
! 314: mmclose(dev, flag, mode, p)
! 315: dev_t dev;
! 316: int flag, mode;
! 317: struct proc *p;
! 318: {
! 319: return (0);
! 320: }
! 321:
! 322: int
! 323: mmrw(dev, uio, flags)
! 324: dev_t dev;
! 325: struct uio *uio;
! 326: int flags;
! 327: {
! 328: struct iovec *iov;
! 329: vaddr_t v, o;
! 330: int error = 0;
! 331: u_int c;
! 332:
! 333: while (uio->uio_resid > 0 && error == 0) {
! 334: iov = uio->uio_iov;
! 335: if (iov->iov_len == 0) {
! 336: uio->uio_iov++;
! 337: uio->uio_iovcnt--;
! 338: if (uio->uio_iovcnt < 0)
! 339: panic("mmrw");
! 340: continue;
! 341: }
! 342: switch (minor(dev)) {
! 343:
! 344: case 0: /* /dev/mem */
! 345:
! 346: /* If the address isn't in RAM, bail. */
! 347: v = uio->uio_offset;
! 348: if (btoc(v) > physmem) {
! 349: error = EFAULT;
! 350: /* this will break us out of the loop */
! 351: continue;
! 352: }
! 353: c = ctob(physmem) - v;
! 354: c = min(c, uio->uio_resid);
! 355: error = uiomove((caddr_t)v, c, uio);
! 356: break;
! 357:
! 358: case 1: /* /dev/kmem */
! 359: v = uio->uio_offset;
! 360: o = v & PGOFSET;
! 361: c = min(uio->uio_resid, (int)(PAGE_SIZE - o));
! 362: if (btoc(v) > physmem && !uvm_kernacc((caddr_t)v,
! 363: c, (uio->uio_rw == UIO_READ) ? B_READ : B_WRITE)) {
! 364: error = EFAULT;
! 365: /* this will break us out of the loop */
! 366: continue;
! 367: }
! 368: error = uiomove((caddr_t)v, c, uio);
! 369: break;
! 370:
! 371: case 2: /* /dev/null */
! 372: if (uio->uio_rw == UIO_WRITE)
! 373: uio->uio_resid = 0;
! 374: return (0);
! 375:
! 376: case 12: /* /dev/zero */
! 377: /* Write to /dev/zero is ignored. */
! 378: if (uio->uio_rw == UIO_WRITE) {
! 379: uio->uio_resid = 0;
! 380: return (0);
! 381: }
! 382: /*
! 383: * On the first call, allocate and zero a page
! 384: * of memory for use with /dev/zero.
! 385: */
! 386: if (zeropage == NULL) {
! 387: zeropage = malloc(PAGE_SIZE, M_TEMP, M_WAITOK);
! 388: bzero(zeropage, PAGE_SIZE);
! 389: }
! 390: c = min(iov->iov_len, PAGE_SIZE);
! 391: error = uiomove(zeropage, c, uio);
! 392: break;
! 393:
! 394: default:
! 395: return (ENXIO);
! 396: }
! 397: }
! 398:
! 399: return (error);
! 400: }
! 401:
! 402: paddr_t
! 403: mmmmap(dev, off, prot)
! 404: dev_t dev;
! 405: off_t off;
! 406: int prot;
! 407: {
! 408: if (minor(dev) != 0)
! 409: return (-1);
! 410:
! 411: /*
! 412: * Allow access only in RAM.
! 413: */
! 414: #if 0
! 415: if (off < ctob(firstusablepage) ||
! 416: off >= ctob(lastusablepage + 1))
! 417: return (-1);
! 418: #endif
! 419: return (atop(off));
! 420: }
! 421:
! 422: int
! 423: mmioctl(dev, cmd, data, flags, p)
! 424: dev_t dev;
! 425: u_long cmd;
! 426: caddr_t data;
! 427: int flags;
! 428: struct proc *p;
! 429: {
! 430: return (EOPNOTSUPP);
! 431: }
CVSweb