From 773e33a81bb0d8f0adc9a147f29b1c49438718f8 Mon Sep 17 00:00:00 2001 From: "Dale S. Rahn" Date: Tue, 9 Nov 1999 06:30:16 +0000 Subject: Add OpenBSD tags. changes to boot on Apple iMac G3 (333). ethernet address changes Locore.c OpenBSD tag hack to delay decrementer exception until after bootload, apple OFW enables interrupts during "system calls" add OF_call_method, to make ofw call by name. Apple OFW can return unexpected values from getchar calls. alloc.c OpenBSD tag boot.c OpenBSD tag updated (but still unused load symbol code). Code cleanup for egcs. cache.c OpenBSD tag use dcbst, not dcbf icbi has both arguments as registers, not constant and register. net.c OpenBSD tag netif_of.c OpenBSD tag add "local-mac-address" to methods of fetching mac address, it can be stored in that variable or in mac-address. support dma buffers, add additional return value for OF_read for network timeout purposes. ofdev.c OpenBSD tag support dma buffers, ofdev.h OpenBSD tag add dmabuf remove MAC default kernel def. ofwmagic.S OpenBSD tag openfirm.h OpenBSD tag boot.mac/Makefile Build debug, - not used for version 3 apple openfirmware, ie imacs. --- sys/arch/powerpc/stand/Locore.c | 92 ++++++++++++++++++- sys/arch/powerpc/stand/alloc.c | 1 + sys/arch/powerpc/stand/boot.c | 152 ++++++++++++++++++------------- sys/arch/powerpc/stand/boot.mac/Makefile | 4 +- sys/arch/powerpc/stand/cache.c | 5 +- sys/arch/powerpc/stand/net.c | 1 + sys/arch/powerpc/stand/netif_of.c | 10 +- sys/arch/powerpc/stand/ofdev.c | 7 ++ sys/arch/powerpc/stand/ofdev.h | 6 +- sys/arch/powerpc/stand/ofwmagic.S | 1 + sys/arch/powerpc/stand/openfirm.h | 1 + 11 files changed, 205 insertions(+), 75 deletions(-) diff --git a/sys/arch/powerpc/stand/Locore.c b/sys/arch/powerpc/stand/Locore.c index d39d5d297e1..4382013ae20 100644 --- a/sys/arch/powerpc/stand/Locore.c +++ b/sys/arch/powerpc/stand/Locore.c @@ -1,3 +1,4 @@ +/* $OpenBSD: Locore.c,v 1.7 1999/11/09 06:30:15 rahnds Exp $ */ /* $NetBSD: Locore.c,v 1.1 1997/04/16 20:29:11 thorpej Exp $ */ /* @@ -60,11 +61,41 @@ _start(vpd, res, openfirm, arg, argl) syncicache((void *)RELOC, etext - (char *)RELOC); #endif openfirmware = openfirm; /* Save entry to Open Firmware */ +#if 0 + patch_dec_intr(); +#endif setup(); main(arg, argl); exit(); } +#if 0 +void handle_decr_intr(); +__asm ( " .globl handle_decr_intr\n" + " .type handle_decr_intr@function\n" + "handle_decr_intr:\n" + " rfi\n"); + + +patch_dec_intr() +{ + int time; + unsigned int *decr_intr = (unsigned int *)0x900; + unsigned int br_instr; + + /* this hack is to prevent unexected Decrementer Exceptions + * when Apple openfirmware enables interrupts + */ + time = 0x40000000; + asm("mtdec %0" :: "r"(time)); + /* we assume that handle_decr_intr is in the first 128 Meg */ + br_instr = (18 << 23) | (unsigned int)handle_decr_intr; + *decr_intr = br_instr; + + + +} +#endif __dead void _rtt() { @@ -334,7 +365,10 @@ OF_claim(virt, size, align) 1, }; +/* #ifdef FIRMWORKSBUGS +*/ +#if 0 /* * Bug with Firmworks OFW */ @@ -346,6 +380,9 @@ OF_claim(virt, size, align) args.align = align; if (openfirmware(&args) == -1) return (void *)-1; + if (virt != 0) { + return virt; + } return args.baseaddr; } @@ -389,7 +426,7 @@ OF_milliseconds() return args.ms; } -#ifdef __notyet__ +#ifdef __notyet__ void OF_chain(virt, size, entry, arg, len) void *virt; @@ -431,12 +468,59 @@ OF_chain(virt, size, entry, arg, len) { /* * This is a REALLY dirty hack till the firmware gets this going - */ OF_release(virt, size); + */ entry(0, 0, openfirmware, arg, len); } #endif +int +#ifdef __STDC__ +OF_call_method(char *method, int ihandle, int nargs, int nreturns, ...) +#else +OF_call_method(method, ihandle, nargs, nreturns, va_alist) + char *method; + int ihandle; + int nargs; + int nreturns; + va_dcl +#endif +{ + va_list ap; + static struct { + char *name; + int nargs; + int nreturns; + char *method; + int ihandle; + int args_n_results[12]; + } args = { + "call-method", + 2, + 1, + }; + int *ip, n; + + if (nargs > 6) + return -1; + args.nargs = nargs + 2; + args.nreturns = nreturns + 1; + args.method = method; + args.ihandle = ihandle; + va_start(ap, nreturns); + for (ip = args.args_n_results + (n = nargs); --n >= 0;) + *--ip = va_arg(ap, int); + + if (openfirmware(&args) == -1) + return -1; + if (args.args_n_results[nargs]) + return args.args_n_results[nargs]; + for (ip = args.args_n_results + nargs + (n = args.nreturns); --n > 0;) + *va_arg(ap, int *) = *--ip; + va_end(ap); + return 0; +} + static int stdin; static int stdout; @@ -467,11 +551,11 @@ putchar(c) int getchar() { - unsigned char ch; + unsigned char ch = '\0'; int l; while ((l = OF_read(stdin, &ch, 1)) != 1) - if (l != -2) + if (l != -2 && l != 0) return -1; return ch; } diff --git a/sys/arch/powerpc/stand/alloc.c b/sys/arch/powerpc/stand/alloc.c index c29f286e75b..d5c6e53e209 100644 --- a/sys/arch/powerpc/stand/alloc.c +++ b/sys/arch/powerpc/stand/alloc.c @@ -1,3 +1,4 @@ +/* $OpenBSD: alloc.c,v 1.6 1999/11/09 06:30:15 rahnds Exp $ */ /* $NetBSD: alloc.c,v 1.1 1997/04/16 20:29:16 thorpej Exp $ */ /* diff --git a/sys/arch/powerpc/stand/boot.c b/sys/arch/powerpc/stand/boot.c index b7c86b273cf..fab53975cea 100644 --- a/sys/arch/powerpc/stand/boot.c +++ b/sys/arch/powerpc/stand/boot.c @@ -1,3 +1,4 @@ +/* $OpenBSD: boot.c,v 1.8 1999/11/09 06:30:15 rahnds Exp $ */ /* $NetBSD: boot.c,v 1.1 1997/04/16 20:29:17 thorpej Exp $ */ /* @@ -287,6 +288,8 @@ aout_exec(fd, hdr, entryp, esymp) } #endif /* POWERPC_BOOT_AOUT */ +#define LOAD_HDR 1 +#define LOAD_SYM 2 #ifdef POWERPC_BOOT_ELF int elf_exec(fd, elf, entryp, esymp) @@ -294,6 +297,7 @@ elf_exec(fd, elf, entryp, esymp) Elf32_Ehdr *elf; u_int32_t *entryp; void **esymp; + { Elf32_Shdr *shp; Elf32_Off off; @@ -301,6 +305,8 @@ elf_exec(fd, elf, entryp, esymp) size_t size; int i, first = 1; int n; + u_int32_t maxp = 0; /* correct type? */ + int flags = LOAD_HDR| LOAD_SYM; /* * Don't display load address for ELF; it's encoded in @@ -326,6 +332,8 @@ elf_exec(fd, elf, entryp, esymp) if (OF_claim((void *)phdr.p_vaddr, phdr.p_memsz, 0) == (void *)-1) panic("cannot claim memory"); + maxp = maxp > (phdr.p_vaddr+ phdr.p_memsz) ? + maxp : (phdr.p_vaddr+ phdr.p_memsz); if (read(fd, (void *)phdr.p_vaddr, phdr.p_filesz) != phdr.p_filesz) { printf("read segment: %s\n", strerror(errno)); @@ -337,89 +345,108 @@ elf_exec(fd, elf, entryp, esymp) if (phdr.p_filesz < phdr.p_memsz) { printf("+%lu@0x%lx", phdr.p_memsz - phdr.p_filesz, (u_long)(phdr.p_vaddr + phdr.p_filesz)); - bzero(phdr.p_vaddr + phdr.p_filesz, + bzero((void *)(phdr.p_vaddr + phdr.p_filesz), phdr.p_memsz - phdr.p_filesz); } first = 0; } + *esymp = 0; /* in case it is not set later */ - printf(" \n"); - -#if 0 /* I want to rethink this... --thorpej@netbsd.org */ +#if 0 /* - * Compute the size of the symbol table. + * Copy the ELF and section headers. */ - size = sizeof(Elf32_Ehdr) + (elf->e_shnum * sizeof(Elf32_Shdr)); - shp = addr = alloc(elf->e_shnum * sizeof(Elf32_Shdr)); - (void)lseek(fd, elf->e_shoff, SEEK_SET); - if (read(fd, addr, elf->e_shnum * sizeof(Elf32_Shdr)) != - elf->e_shnum * sizeof(Elf32_Shdr)) { - printf("read section headers: %s\n", strerror(errno)); - return (1); + maxp = roundup(maxp, sizeof(long)); + if (flags & (LOAD_HDR|COUNT_HDR)) { + if (OF_claim((void *)maxp, sizeof(Elf_Ehdr), 0) == + (void *)-1) + panic("cannot claim memory"); + elfp = maxp; + maxp += sizeof(Elf_Ehdr); } - for (i = 0; i < elf->e_shnum; i++, shp++) { - if (shp->sh_type == Elf32_sht_null) - continue; - if (shp->sh_type != Elf32_sht_symtab - && shp->sh_type != Elf32_sht_strtab) { - shp->sh_offset = 0; - shp->sh_type = Elf32_sht_nobits; - continue; + + if (flags & (LOAD_SYM|COUNT_SYM)) { + if (lseek(fd, elf->e_shoff, SEEK_SET) == -1) { + WARN(("lseek section headers")); + return 1; } - size += shp->sh_size; - } - shp = addr; + sz = elf->e_shnum * sizeof(Elf_Shdr); - /* - * Reserve memory for the symbols. - */ - if ((addr = OF_claim(0, size, NBPG)) == (void *)-1) - panic("no space for symbol table"); + if (OF_claim((void *)maxp, sizeof(Elf_Ehdr), 0) == + (void *)-1) + panic("cannot claim memory"); + shpp = maxp; + maxp += roundup(sz, sizeof(long)); - /* - * Copy the headers. - */ - elf->e_phoff = 0; - elf->e_shoff = sizeof(Elf32_Ehdr); - elf->e_phentsize = 0; - elf->e_phnum = 0; - bcopy(elf, addr, sizeof(Elf32_Ehdr)); - bcopy(shp, addr + sizeof(Elf32_Ehdr), elf->e_shnum * sizeof(Elf32_Shdr)); - free(shp, elf->e_shnum * sizeof(Elf32_Shdr)); - *ssymp = addr; + if (read(fd, shpp, sz) != sz) { + WARN(("read section headers")); + return 1; + } + /* + * Now load the symbol sections themselves. Make sure the + * sections are aligned. Don't bother with string tables if + * there are no symbol sections. + */ + off = roundup((sizeof(Elf_Ehdr) + sz), sizeof(long)); + + for (havesyms = i = 0; i < elf->e_shnum; i++) + if (shpp[i].sh_type == Elf_sht_symtab) + havesyms = 1; + + for (first = 1, i = 0; i < elf->e_shnum; i++) { + if (shpp[i].sh_type == Elf_sht_symtab || + shpp[i].sh_type == Elf_sht_strtab) { + if (havesyms && (flags & LOAD_SYM)) { + PROGRESS(("%s%ld", first ? " [" : "+", + (u_long)shpp[i].sh_size)); + if (lseek(fd, shpp[i].sh_offset, + SEEK_SET) == -1) { + WARN(("lseek symbols")); + FREE(shp, sz); + return 1; + } + if (READ(fd, maxp, shpp[i].sh_size) != + shpp[i].sh_size) { + WARN(("read symbols")); + return 1; + } + } + maxp += roundup(shpp[i].sh_size, + sizeof(long)); + shpp[i].sh_offset = off; + off += roundup(shpp[i].sh_size, sizeof(long)); + first = 0; + } + } + if (flags & LOAD_SYM) { + BCOPY(shp, shpp, sz); + + if (first == 0) + PROGRESS(("]")); + } + } /* - * Now load the symbol sections themselves. + * Frob the copied ELF header to give information relative + * to elfp. */ - shp = addr + sizeof(Elf32_Ehdr); - addr += sizeof(Elf32_Ehdr) + (elf->e_shnum * sizeof(Elf32_Shdr)); - off = sizeof(Elf32_Ehdr) + (elf->e_shnum * sizeof(Elf32_Shdr)); - for (first = 1, i = 0; i < elf->e_shnum; i++, shp++) { - if (shp->sh_type == Elf32_sht_symtab - || shp->sh_type == Elf32_sht_strtab) { - if (first) - printf("symbols @ 0x%lx ", (u_long)addr); - printf("%s%d", first ? "" : "+", shp->sh_size); - (void)lseek(fd, shp->sh_offset, SEEK_SET); - if (read(fd, addr, shp->sh_size) != shp->sh_size) { - printf("read symbols: %s\n", strerror(errno)); - return (1); - } - addr += shp->sh_size; - shp->sh_offset = off; - off += shp->sh_size; - first = 0; - } + if (flags & LOAD_HDR) { + elf->e_phoff = 0; + elf->e_shoff = sizeof(Elf_Ehdr); + elf->e_phentsize = 0; + elf->e_phnum = 0; + BCOPY(elf, elfp, sizeof(*elf)); } - *esymp = addr; -#endif /* 0 */ +#endif + printf(" \n"); + *entryp = elf->e_entry; return (0); } #endif /* POWERPC_BOOT_ELF */ -void +int main() { int chosen; @@ -482,4 +509,5 @@ main() (void)loadfile(fd, bootline); _rtt(); + return 0; } diff --git a/sys/arch/powerpc/stand/boot.mac/Makefile b/sys/arch/powerpc/stand/boot.mac/Makefile index c2cc55417c5..07b7f041de6 100644 --- a/sys/arch/powerpc/stand/boot.mac/Makefile +++ b/sys/arch/powerpc/stand/boot.mac/Makefile @@ -1,4 +1,4 @@ -# $OpenBSD: Makefile,v 1.4 1998/05/29 04:15:56 rahnds Exp $ +# $OpenBSD: Makefile,v 1.5 1999/11/09 06:30:15 rahnds Exp $ # $NetBSD: Makefile,v 1.1 1996/09/30 16:35:05 ws Exp $ R= .. @@ -8,7 +8,7 @@ ENTRY= _entry LOADADDR= 20000 PROG= boot.mac SRCS= Locore.c boot.c ofdev.c net.c netif_of.c alloc.c -#CFLAGS+= -DDEBUG -DNETIF_DEBUG +CFLAGS+= -DDEBUG -DNETIF_DEBUG CFLAGS+= -DEXEC_ELF -DXCOFF_GLUE -DMAC NOMAN= INSTALL_STRIP= diff --git a/sys/arch/powerpc/stand/cache.c b/sys/arch/powerpc/stand/cache.c index c40dead4394..e31b89b4c4a 100644 --- a/sys/arch/powerpc/stand/cache.c +++ b/sys/arch/powerpc/stand/cache.c @@ -1,3 +1,4 @@ +/* $OpenBSD: cache.c,v 1.2 1999/11/09 06:30:15 rahnds Exp $ */ #define CACHELINESIZE 32 /* For now XXX */ void @@ -9,12 +10,12 @@ syncicache(from, len) void *p = from; do { - asm volatile ("dcbst 0,%0" :: "r"(p)); + asm volatile ("dcbf %1,%0" :: "r"(p), "r"(0)); p += CACHELINESIZE; } while ((l -= CACHELINESIZE) > 0); asm volatile ("sync"); do { - asm volatile ("icbi 0,%0" :: "r"(from)); + asm volatile ("icbi %1,%0" :: "r"(from), "r"(0)); from += CACHELINESIZE; } while ((len -= CACHELINESIZE) > 0); asm volatile ("isync"); diff --git a/sys/arch/powerpc/stand/net.c b/sys/arch/powerpc/stand/net.c index 247598e7624..2e79198d91f 100644 --- a/sys/arch/powerpc/stand/net.c +++ b/sys/arch/powerpc/stand/net.c @@ -1,3 +1,4 @@ +/* $OpenBSD: net.c,v 1.4 1999/11/09 06:30:15 rahnds Exp $ */ /* $NetBSD: net.c,v 1.1 1997/04/16 20:29:18 thorpej Exp $ */ /* diff --git a/sys/arch/powerpc/stand/netif_of.c b/sys/arch/powerpc/stand/netif_of.c index 71adac09790..71a6a22a9b0 100644 --- a/sys/arch/powerpc/stand/netif_of.c +++ b/sys/arch/powerpc/stand/netif_of.c @@ -1,3 +1,4 @@ +/* $OpenBSD: netif_of.c,v 1.4 1999/11/09 06:30:15 rahnds Exp $ */ /* $NetBSD: netif_of.c,v 1.1 1997/04/16 20:29:19 thorpej Exp $ */ /* @@ -100,6 +101,8 @@ netif_open(machdep_hint) io->io_netif = &netif_of; /* Put our ethernet address in io->myea */ + OF_getprop(OF_instance_to_package(op->handle), + "local-mac-address", io->myea, sizeof io->myea) == -1 && OF_getprop(OF_instance_to_package(op->handle), "mac-address", io->myea, sizeof io->myea); @@ -176,6 +179,10 @@ netif_put(desc, pkt, len) #endif } + if (op->dmabuf) { + bcopy(pkt, op->dmabuf, sendlen); + pkt = op->dmabuf; + } rv = OF_write(op->handle, pkt, sendlen); #ifdef NETIF_DEBUG @@ -212,7 +219,8 @@ netif_get(desc, pkt, maxlen, timo) do { len = OF_read(op->handle, pkt, maxlen); - } while ((len == -2) && ((OF_milliseconds() - tick0) < tmo_ms)); + } while ((len == -2 || len == 0) && + ((OF_milliseconds() - tick0) < tmo_ms)); #ifdef NETIF_DEBUG printf("netif_get: received len=%d\n", len); diff --git a/sys/arch/powerpc/stand/ofdev.c b/sys/arch/powerpc/stand/ofdev.c index 7e30e842dd2..346f3c8c856 100644 --- a/sys/arch/powerpc/stand/ofdev.c +++ b/sys/arch/powerpc/stand/ofdev.c @@ -1,3 +1,4 @@ +/* $OpenBSD: ofdev.c,v 1.5 1999/11/09 06:30:15 rahnds Exp $ */ /* $NetBSD: ofdev.c,v 1.1 1997/04/16 20:29:20 thorpej Exp $ */ /* @@ -131,6 +132,10 @@ devclose(of) if (op->type == OFDEV_NET) net_close(op); + if (op->dmabuf) { + OF_call_method("dma-free", op->handle, 2, 0, + op->dmabuf, MAXPHYS); + } OF_close(op->handle); op->handle = -1; } @@ -289,6 +294,8 @@ devopen(of, name, file) return ENXIO; bzero(&ofdev, sizeof ofdev); ofdev.handle = handle; + ofdev.dmabuf = NULL; + OF_call_method("dma-alloc", handle, 1, 1, MAXPHYS, &ofdev.dmabuf); if (!strcmp(buf, "block")) { ofdev.type = OFDEV_DISK; ofdev.bsize = DEV_BSIZE; diff --git a/sys/arch/powerpc/stand/ofdev.h b/sys/arch/powerpc/stand/ofdev.h index 104aea6012c..77e23d32340 100644 --- a/sys/arch/powerpc/stand/ofdev.h +++ b/sys/arch/powerpc/stand/ofdev.h @@ -1,3 +1,4 @@ +/* $OpenBSD: ofdev.h,v 1.5 1999/11/09 06:30:15 rahnds Exp $ */ /* $NetBSD: ofdev.h,v 1.1 1997/04/16 20:29:22 thorpej Exp $ */ /* @@ -38,17 +39,14 @@ struct of_dev { int type; u_long partoff; int bsize; + void *dmabuf; }; /* Known types: */ #define OFDEV_NET 1 #define OFDEV_DISK 2 -#ifdef MAC -#define DEFAULT_KERNEL ":bsd" -#else #define DEFAULT_KERNEL "/bsd" -#endif extern char opened_name[]; diff --git a/sys/arch/powerpc/stand/ofwmagic.S b/sys/arch/powerpc/stand/ofwmagic.S index 4851e50eb99..4ebc494a46a 100644 --- a/sys/arch/powerpc/stand/ofwmagic.S +++ b/sys/arch/powerpc/stand/ofwmagic.S @@ -1,3 +1,4 @@ +/* $OpenBSD: ofwmagic.S,v 1.2 1999/11/09 06:30:15 rahnds Exp $ */ /* $NetBSD: ofwmagic.S,v 1.1 1997/04/16 21:19:00 thorpej Exp $ */ /*- diff --git a/sys/arch/powerpc/stand/openfirm.h b/sys/arch/powerpc/stand/openfirm.h index 3bbcd737378..06414923021 100644 --- a/sys/arch/powerpc/stand/openfirm.h +++ b/sys/arch/powerpc/stand/openfirm.h @@ -1,3 +1,4 @@ +/* $OpenBSD: openfirm.h,v 1.4 1999/11/09 06:30:15 rahnds Exp $ */ /* $NetBSD: openfirm.h,v 1.1 1997/04/16 20:29:23 thorpej Exp $ */ /* -- cgit v1.2.3