Annotation of sys/arch/sgi/stand/boot/arcbios.c, Revision 1.1
1.1 ! nbrk 1: /* $OpenBSD: arcbios.c,v 1.4 2004/10/20 12:49:15 pefo Exp $ */
! 2: /*-
! 3: * Copyright (c) 1996 M. Warner Losh. All rights reserved.
! 4: * Copyright (c) 1996-2004 Opsycon AB. All rights reserved.
! 5: *
! 6: * Redistribution and use in source and binary forms, with or without
! 7: * modification, are permitted provided that the following conditions
! 8: * are met:
! 9: * 1. Redistributions of source code must retain the above copyright
! 10: * notice, this list of conditions and the following disclaimer.
! 11: * 2. Redistributions in binary form must reproduce the above copyright
! 12: * notice, this list of conditions and the following disclaimer in the
! 13: * documentation and/or other materials provided with the distribution.
! 14: *
! 15: * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
! 16: * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
! 17: * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
! 18: * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
! 19: * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
! 20: * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
! 21: * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
! 22: * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
! 23: * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
! 24: * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
! 25: * SUCH DAMAGE.
! 26: */
! 27:
! 28: #include <sys/param.h>
! 29: #include <lib/libkern/libkern.h>
! 30: #include <machine/autoconf.h>
! 31: #include <mips64/arcbios.h>
! 32: #include <mips64/archtype.h>
! 33: #include <stand.h>
! 34:
! 35: #define USE_SGI_PARTITIONS 1
! 36:
! 37: void bios_configure_memory(void);
! 38: int bios_get_system_type(void);
! 39: const char *bios_get_path_component(const char *, char *, int *);
! 40:
! 41: arc_dsp_stat_t displayinfo; /* Save area for display status info. */
! 42:
! 43: static struct systypes {
! 44: char *sys_vend; /* Vendor ID if name is ambigous */
! 45: char *sys_name; /* May be left NULL if name is sufficient */
! 46: int sys_type;
! 47: } sys_types[] = {
! 48: { NULL, "PICA-61", ACER_PICA_61 },
! 49: { NULL, "NEC-R94", ACER_PICA_61 },
! 50: { NULL, "DESKTECH-TYNE", DESKSTATION_TYNE },
! 51: { NULL, "DESKTECH-ARCStation I", DESKSTATION_RPC44 },
! 52: { NULL, "Microsoft-Jazz", MAGNUM },
! 53: { NULL, "RM200PCI", SNI_RM200 },
! 54: { NULL, "SGI-IP17", SGI_CRIMSON },
! 55: { NULL, "SGI-IP19", SGI_ONYX },
! 56: { NULL, "SGI-IP20", SGI_INDIGO },
! 57: { NULL, "SGI-IP21", SGI_POWER },
! 58: { NULL, "SGI-IP22", SGI_INDY },
! 59: { NULL, "SGI-IP25", SGI_POWER10 },
! 60: { NULL, "SGI-IP26", SGI_POWERI },
! 61: { NULL, "SGI-IP32", SGI_O2 },
! 62: };
! 63:
! 64: #define KNOWNSYSTEMS (sizeof(sys_types) / sizeof(struct systypes))
! 65:
! 66: /*
! 67: * ARC Bios trampoline code.
! 68: */
! 69: #define ARC_Call(Name,Offset) \
! 70: __asm__("\n" \
! 71: " .text\n" \
! 72: " .ent " #Name "\n" \
! 73: " .align 3\n" \
! 74: " .set noreorder\n" \
! 75: " .globl " #Name "\n" \
! 76: #Name":\n" \
! 77: " lw $2, 0xffffffff80001020\n"\
! 78: " lw $2," #Offset "($2)\n"\
! 79: " jr $2\n" \
! 80: " nop\n" \
! 81: " .end " #Name "\n" );
! 82:
! 83: ARC_Call(Bios_Load, 0x00);
! 84: ARC_Call(Bios_Invoke, 0x04);
! 85: ARC_Call(Bios_Execute, 0x08);
! 86: ARC_Call(Bios_Halt, 0x0c);
! 87: ARC_Call(Bios_PowerDown, 0x10);
! 88: ARC_Call(Bios_Restart, 0x14);
! 89: ARC_Call(Bios_Reboot, 0x18);
! 90: ARC_Call(Bios_EnterInteractiveMode, 0x1c);
! 91: ARC_Call(Bios_Unused1, 0x20);
! 92: ARC_Call(Bios_GetPeer, 0x24);
! 93: ARC_Call(Bios_GetChild, 0x28);
! 94: ARC_Call(Bios_GetParent, 0x2c);
! 95: ARC_Call(Bios_GetConfigurationData, 0x30);
! 96: ARC_Call(Bios_AddChild, 0x34);
! 97: ARC_Call(Bios_DeleteComponent, 0x38);
! 98: ARC_Call(Bios_GetComponent, 0x3c);
! 99: ARC_Call(Bios_SaveConfiguration, 0x40);
! 100: ARC_Call(Bios_GetSystemId, 0x44);
! 101: ARC_Call(Bios_GetMemoryDescriptor, 0x48);
! 102: ARC_Call(Bios_Unused2, 0x4c);
! 103: ARC_Call(Bios_GetTime, 0x50);
! 104: ARC_Call(Bios_GetRelativeTime, 0x54);
! 105: ARC_Call(Bios_GetDirectoryEntry, 0x58);
! 106: ARC_Call(Bios_Open, 0x5c);
! 107: ARC_Call(Bios_Close, 0x60);
! 108: ARC_Call(Bios_Read, 0x64);
! 109: ARC_Call(Bios_GetReadStatus, 0x68);
! 110: ARC_Call(Bios_Write, 0x6c);
! 111: ARC_Call(Bios_Seek, 0x70);
! 112: ARC_Call(Bios_Mount, 0x74);
! 113: ARC_Call(Bios_GetEnvironmentVariable, 0x78);
! 114: ARC_Call(Bios_SetEnvironmentVariable, 0x7c);
! 115: ARC_Call(Bios_GetFileInformation, 0x80);
! 116: ARC_Call(Bios_SetFileInformation, 0x84);
! 117: ARC_Call(Bios_FlushAllCaches, 0x88);
! 118: ARC_Call(Bios_TestUnicodeCharacter, 0x8c);
! 119: ARC_Call(Bios_GetDisplayStatus, 0x90);
! 120:
! 121: /*
! 122: * Simple getchar/putchar interface.
! 123: */
! 124:
! 125: int
! 126: getchar()
! 127: {
! 128: char buf[4];
! 129: int cnt;
! 130:
! 131: if (Bios_Read(0, &buf[0], 1, &cnt) != 0)
! 132: return(-1);
! 133: return(buf[0] & 255);
! 134: }
! 135:
! 136: void
! 137: putchar(c)
! 138: char c;
! 139: {
! 140: char buf[4];
! 141: int cnt;
! 142:
! 143: if (c == '\n') {
! 144: buf[0] = '\r';
! 145: buf[1] = c;
! 146: cnt = 2;
! 147: if (displayinfo.CursorYPosition < displayinfo.CursorMaxYPosition)
! 148: displayinfo.CursorYPosition++;
! 149: }
! 150: else {
! 151: buf[0] = c;
! 152: cnt = 1;
! 153: }
! 154: Bios_Write(1, &buf[0], cnt, &cnt);
! 155: }
! 156:
! 157: void
! 158: bios_putstring(s)
! 159: char *s;
! 160: {
! 161: while (*s) {
! 162: putchar(*s++);
! 163: }
! 164: }
! 165:
! 166: /*
! 167: * Find out system type.
! 168: */
! 169: int
! 170: bios_get_system_type()
! 171: {
! 172: arc_config_t *cf;
! 173: arc_sid_t *sid;
! 174: int i;
! 175:
! 176: if ((ArcBiosBase32->magic != ARC_PARAM_BLK_MAGIC) &&
! 177: (ArcBiosBase32->magic != ARC_PARAM_BLK_MAGIC_BUG)) {
! 178: return(-1); /* This is not an ARC system */
! 179: }
! 180:
! 181: sid = (arc_sid_t *)Bios_GetSystemId();
! 182: cf = (arc_config_t *)Bios_GetChild(NULL);
! 183: if (cf) {
! 184: for (i = 0; i < KNOWNSYSTEMS; i++) {
! 185: if (strcmp(sys_types[i].sys_name, (char *)cf->id) != 0)
! 186: continue;
! 187: if (sys_types[i].sys_vend &&
! 188: strncmp(sys_types[i].sys_vend, sid->vendor, 8) != 0)
! 189: continue;
! 190: return (sys_types[i].sys_type); /* Found it. */
! 191: }
! 192: }
! 193:
! 194: bios_putstring("UNIDENTIFIED SYSTEM `");
! 195: if (cf)
! 196: bios_putstring((char *)cf->id);
! 197: else
! 198: bios_putstring("????????");
! 199: bios_putstring("' VENDOR `");
! 200: sid->vendor[8] = 0;
! 201: bios_putstring(sid->vendor);
! 202: bios_putstring("'. Please contact OpenBSD (www.openbsd.org).\n");
! 203: bios_putstring("Reset system to restart!\n");
! 204: while(1);
! 205: }
! 206:
! 207: /*
! 208: * Return geometry of the display. Used by pccons.c to set up the
! 209: * display configuration.
! 210: */
! 211: void
! 212: bios_display_info(xpos, ypos, xsize, ysize)
! 213: int *xpos;
! 214: int *ypos;
! 215: int *xsize;
! 216: int *ysize;
! 217: {
! 218: #ifdef __arc__
! 219: *xpos = displayinfo.CursorXPosition;
! 220: *ypos = displayinfo.CursorYPosition;
! 221: *xsize = displayinfo.CursorMaxXPosition;
! 222: *ysize = displayinfo.CursorMaxYPosition;
! 223: #endif
! 224: }
! 225:
! 226:
! 227: /*
! 228: * Decompose the device pathname and find driver.
! 229: * Returns pointer to remaining filename path in file.
! 230: */
! 231: int
! 232: devopen(struct open_file *f, const char *fname, char **file)
! 233: {
! 234: const char *cp, *ncp, *ecp;
! 235: struct devsw *dp;
! 236: int partition = 0;
! 237: char namebuf[256];
! 238: char devname[32];
! 239: int rc, i, n;
! 240:
! 241: ecp = cp = fname;
! 242:
! 243: /*
! 244: * Scan the component list and find device and partition.
! 245: */
! 246: while ((ncp = bios_get_path_component(cp, namebuf, &i)) != NULL) {
! 247: if ((strcmp(namebuf, "partition") == 0) ||
! 248: (strcmp(namebuf, "partition") == 0)) {
! 249: partition = i;
! 250: if (USE_SGI_PARTITIONS)
! 251: ecp = ncp;
! 252: } else
! 253: ecp = ncp;
! 254:
! 255: /* XXX do this with a table if more devs are added */
! 256: if (strcmp(namebuf, "scsi") == 0)
! 257: strncpy(devname, namebuf, sizeof(devname));
! 258:
! 259: cp = ncp;
! 260: }
! 261:
! 262: memcpy(namebuf, fname, ecp - fname);
! 263: namebuf[ecp - fname] = '\0';
! 264:
! 265: /*
! 266: * Dig out the driver.
! 267: */
! 268: dp = devsw;
! 269: n = ndevs;
! 270: while(n--) {
! 271: if (strcmp (devname, dp->dv_name) == 0) {
! 272: rc = (dp->dv_open)(f, namebuf, partition, 0);
! 273: if (!rc) {
! 274: f->f_dev = dp;
! 275: if (file && *cp != '\0')
! 276: *file = (char *)cp;
! 277: }
! 278: return (rc);
! 279: }
! 280: dp++;
! 281: }
! 282: return ENXIO;
! 283: }
! 284:
! 285: const char *
! 286: bios_get_path_component(const char *p, char *comp, int *no)
! 287: {
! 288: while (*p && *p != '(') {
! 289: *comp++ = *p++;
! 290: }
! 291: *comp = '\0';
! 292:
! 293: if (*p == NULL)
! 294: return NULL;
! 295:
! 296: *no = 0;
! 297: p++;
! 298: while (*p && *p != ')') {
! 299: if (*p >= '0' && *p <= '9')
! 300: *no = *no * 10 + *p++ - '0';
! 301: else
! 302: return NULL;
! 303: }
! 304: return ++p;
! 305: }
CVSweb