Date: Thu, 20 Nov 2008 17:07:39 GMT From: Nathan Whitehorn <nwhitehorn@FreeBSD.org> To: Perforce Change Reviews <perforce@freebsd.org> Subject: PERFORCE change 153267 for review Message-ID: <200811201707.mAKH7dcT045326@repoman.freebsd.org>
next in thread | raw e-mail | index | archive | help
http://perforce.freebsd.org/chv.cgi?CH=153267 Change 153267 by nwhitehorn@nwhitehorn_trantor on 2008/11/20 17:07:25 Make ofw_real work on kernels with options SMP by making the bounce page static. On SMP systems, we can get OF calls after the MMU is on but before the VM is up. This means contigmalloc() is not available. This is not a good solution, but I can't think of anything else. Also: style(9) Affected files ... .. //depot/projects/ppc-g5/sys/powerpc/aim/mmu_oea64.c#9 edit .. //depot/projects/ppc-g5/sys/powerpc/ofw/ofw_real.c#3 edit Differences ... ==== //depot/projects/ppc-g5/sys/powerpc/aim/mmu_oea64.c#9 (text+ko) ==== @@ -297,13 +297,14 @@ * PVO data. */ struct pvo_head *moea64_pvo_table; /* pvo entries by pteg index */ +/* lists of unmanaged pages */ struct pvo_head moea64_pvo_kunmanaged = - LIST_HEAD_INITIALIZER(moea64_pvo_kunmanaged); /* list of unmanaged pages */ + LIST_HEAD_INITIALIZER(moea64_pvo_kunmanaged); struct pvo_head moea64_pvo_unmanaged = - LIST_HEAD_INITIALIZER(moea64_pvo_unmanaged); /* list of unmanaged pages */ + LIST_HEAD_INITIALIZER(moea64_pvo_unmanaged); -uma_zone_t moea64_upvo_zone; /* zone for pvo entries for unmanaged pages */ -uma_zone_t moea64_mpvo_zone; /* zone for pvo entries for managed pages */ +uma_zone_t moea64_upvo_zone; /* zone for pvo entries for unmanaged pages */ +uma_zone_t moea64_mpvo_zone; /* zone for pvo entries for managed pages */ vm_offset_t pvo_allocator_start; vm_offset_t pvo_allocator_end; ==== //depot/projects/ppc-g5/sys/powerpc/ofw/ofw_real.c#3 (text+ko) ==== @@ -60,7 +60,6 @@ #include <sys/param.h> #include <sys/kernel.h> -#include <sys/malloc.h> #include <sys/lock.h> #include <sys/mutex.h> #include <sys/systm.h> @@ -147,15 +146,22 @@ }; OFW_DEF(ofw_real); -MALLOC_DEFINE(M_OFWREAL, "ofwreal", "Open Firmware Real Mode Bounce Page"); - static int (*openfirmware)(void *); static vm_offset_t of_bounce_phys; static caddr_t of_bounce_virt; static off_t of_bounce_offset; +static size_t of_bounce_size; static struct mtx of_bounce_mtx; +/* + * We need a statically allocated bounce buffer to handle the case when + * there are Open Firmware calls after the MMU has been enabled but before + * the VM has been initialized to the point that we can allocate memory. + * Make it 4K and 8 byte aligned. + */ +static uint64_t of_bounce_buffer[512]; + static void ofw_real_start(void) { @@ -180,9 +186,10 @@ if (!pmap_bootstrapped) return (cell_t)buf; - of_bounce_virt = contigmalloc(PAGE_SIZE, M_OFWREAL, 0, - 0, BUS_SPACE_MAXADDR_32BIT, PAGE_SIZE, PAGE_SIZE); - of_bounce_phys = vtophys(of_bounce_virt); + of_bounce_virt = (caddr_t)of_bounce_buffer; + of_bounce_size = sizeof(of_bounce_buffer); + + of_bounce_phys = vtophys(of_bounce_buffer); } /* @@ -191,6 +198,9 @@ */ of_bounce_offset += of_bounce_offset % sizeof(register_t); + if (of_bounce_offset + len > of_bounce_size) + return 0; + memcpy(of_bounce_virt + of_bounce_offset, buf, len); phys = of_bounce_phys + of_bounce_offset; @@ -204,7 +214,7 @@ { mtx_assert(&of_bounce_mtx, MA_OWNED); - if (!pmap_bootstrapped) + if (of_bounce_virt == NULL) return; memcpy(buf,of_bounce_virt + (physaddr - of_bounce_phys),len); @@ -243,8 +253,8 @@ ofw_real_start(); - args.service = ofw_real_map(name,strlen(name) + 1); - if (openfirmware(&args) == -1) { + args.service = ofw_real_map(name, strlen(name) + 1); + if (args.service == 0 || openfirmware(&args) == -1) { ofw_real_stop(); return (-1); } @@ -365,7 +375,7 @@ args.package = package; args.propname = ofw_real_map(propname, strlen(propname) + 1); - if (openfirmware(&args) == -1) { + if (args.propname == 0 || openfirmware(&args) == -1) { ofw_real_stop(); return (-1); } @@ -396,14 +406,14 @@ ofw_real_start(); args.package = package; - args.propname = ofw_real_map(propname,strlen(propname) + 1); - args.buf = ofw_real_map(buf,buflen); + args.propname = ofw_real_map(propname, strlen(propname) + 1); + args.buf = ofw_real_map(buf, buflen); args.buflen = buflen; - if (openfirmware(&args) == -1) { + if (args.propname == 0 || args.buf == 0 || openfirmware(&args) == -1) { ofw_real_stop(); return (-1); } - ofw_real_unmap(args.buf,buf,buflen); + ofw_real_unmap(args.buf, buf, buflen); ofw_real_stop(); return (args.size); @@ -431,13 +441,13 @@ ofw_real_start(); args.package = package; - args.previous = ofw_real_map(previous,strlen(previous) + 1); - args.buf = ofw_real_map(buf,size); - if (openfirmware(&args) == -1) { + args.previous = ofw_real_map(previous, strlen(previous) + 1); + args.buf = ofw_real_map(buf, size); + if (args.previous == 0 || args.buf == 0 || openfirmware(&args) == -1) { ofw_real_stop(); return (-1); } - ofw_real_unmap(args.buf,buf,size); + ofw_real_unmap(args.buf, buf, size); ofw_real_stop(); return (args.flag); @@ -467,10 +477,10 @@ ofw_real_start(); args.package = package; - args.propname = ofw_real_map(propname,strlen(propname) + 1); - args.buf = ofw_real_map(buf,len); + args.propname = ofw_real_map(propname, strlen(propname) + 1); + args.buf = ofw_real_map(buf, len); args.len = len; - if (openfirmware(&args) == -1) { + if (args.propname == 0 || args.buf == 0 || openfirmware(&args) == -1) { ofw_real_stop(); return (-1); } @@ -498,14 +508,14 @@ ofw_real_start(); - args.device = ofw_real_map(device,strlen(device) + 1); - args.buf = ofw_real_map(buf,len); + args.device = ofw_real_map(device, strlen(device) + 1); + args.buf = ofw_real_map(buf, len); args.len = len; - if (openfirmware(&args) == -1) { + if (args.device == 0 || args.buf == 0 || openfirmware(&args) == -1) { ofw_real_stop(); return (-1); } - ofw_real_unmap(args.buf,buf,len); + ofw_real_unmap(args.buf, buf, len); ofw_real_stop(); return (args.size); @@ -529,8 +539,8 @@ ofw_real_start(); - args.device = ofw_real_map(device,strlen(device) + 1); - if (openfirmware(&args) == -1) { + args.device = ofw_real_map(device, strlen(device) + 1); + if (args.device == 0 || openfirmware(&args) == -1) { ofw_real_stop(); return (-1); } @@ -559,13 +569,13 @@ ofw_real_start(); args.instance = instance; - args.buf = ofw_real_map(buf,len); + args.buf = ofw_real_map(buf, len); args.len = len; - if (openfirmware(&args) == -1) { + if (args.buf == 0 || openfirmware(&args) == -1) { ofw_real_stop(); return (-1); } - ofw_real_unmap(args.buf,buf,len); + ofw_real_unmap(args.buf, buf, len); ofw_real_stop(); return (args.size); @@ -592,13 +602,13 @@ ofw_real_start(); args.package = package; - args.buf = ofw_real_map(buf,len); + args.buf = ofw_real_map(buf, len); args.len = len; - if (openfirmware(&args) == -1) { + if (args.buf == 0 || openfirmware(&args) == -1) { ofw_real_stop(); return (-1); } - ofw_real_unmap(args.buf,buf,len); + ofw_real_unmap(args.buf, buf, len); ofw_real_stop(); return (args.size); @@ -631,13 +641,13 @@ ofw_real_start(); args.nargs = nargs + 2; args.nreturns = nreturns + 1; - args.method = ofw_real_map(method,strlen(method) + 1); + args.method = ofw_real_map(method, strlen(method) + 1); args.instance = instance; ap = args_and_returns; for (cp = args.args_n_results + (n = nargs); --n >= 0;) *--cp = *(ap++); - if (openfirmware(&args) == -1) { + if (args.method == 0 || openfirmware(&args) == -1) { ofw_real_stop(); return (-1); } @@ -671,8 +681,9 @@ ofw_real_start(); - args.device = ofw_real_map(device,strlen(device) + 1); - if (openfirmware(&args) == -1 || args.instance == 0) { + args.device = ofw_real_map(device, strlen(device) + 1); + if (args.device == 0 || openfirmware(&args) == -1 + || args.instance == 0) { ofw_real_stop(); return (-1); } @@ -719,13 +730,13 @@ ofw_real_start(); args.instance = instance; - args.addr = ofw_real_map(addr,len); + args.addr = ofw_real_map(addr, len); args.len = len; - if (openfirmware(&args) == -1) { + if (args.addr == 0 || openfirmware(&args) == -1) { ofw_real_stop(); return (-1); } - ofw_real_unmap(args.addr,addr,len); + ofw_real_unmap(args.addr, addr, len); ofw_real_stop(); return (args.actual); @@ -752,9 +763,9 @@ ofw_real_start(); args.instance = instance; - args.addr = ofw_real_map(addr,len); + args.addr = ofw_real_map(addr, len); args.len = len; - if (openfirmware(&args) == -1) { + if (args.addr == 0 || openfirmware(&args) == -1) { ofw_real_stop(); return (-1); }
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?200811201707.mAKH7dcT045326>