From bd5eb665976d8d0e9dc7dcadf320f83df58b3c1c Mon Sep 17 00:00:00 2001 From: David du Colombier <0intro@gmail.com> Date: Thu, 30 Aug 2001 00:00:00 +0000 Subject: [PATCH] Plan 9 from Bell Labs 2001-08-30 --- pc/ether2114x.c | 9 ++++++--- pc/mp.c | 43 +++++++++++++++++++++++++++++++++++-------- 2 files changed, 41 insertions(+), 11 deletions(-) diff --git a/pc/ether2114x.c b/pc/ether2114x.c index d11f8c7ed018112845137fc46902e5890a6d95fb..b4a6b4dbbfd0c48db2797f78408f3d917681462a 100644 --- a/pc/ether2114x.c +++ b/pc/ether2114x.c @@ -731,6 +731,9 @@ sromr(Ctlr* ctlr, int r) data = csr32r(ctlr, 19); }while((data & 0x80000000) && --i); + if(ctlr->sromsz == 0) + ctlr->sromsz = 6; + return csr32r(ctlr, 9) & 0xFFFF; } @@ -781,7 +784,6 @@ reread: if(ctlr->sromsz == 0){ ctlr->sromsz = 8-size; - ctlr->srom = malloc((1<sromsz)*sizeof(ushort)); goto reread; } @@ -1234,10 +1236,11 @@ srom(Ctlr* ctlr) * 'Digital Semiconductor 21X4 Serial ROM Format, Version 4.05, * 2-Mar-98'. Only the 2114[03] are handled, support for other * controllers can be added as needed. - * Do a dummy read first to get the size - * and allocate ctlr->srom. + * Do a dummy read first to get the size and allocate ctlr->srom. */ sromr(ctlr, 0); + if(ctlr->srom == nil) + ctlr->srom = malloc((1<sromsz)*sizeof(ushort)); for(i = 0; i < (1<sromsz); i++){ x = sromr(ctlr, i); ctlr->srom[2*i] = x; diff --git a/pc/mp.c b/pc/mp.c index ed345ac39f10a670ab7fde521a92bb094be62ac6..ffc74ab2851c154b07c4782e933e939a9d65370d 100644 --- a/pc/mp.c +++ b/pc/mp.c @@ -462,6 +462,8 @@ mpstartap(Apic* apic) void mpinit(void) { + int ncpu; + char *cp; PCMP *pcmp; uchar *e, *p; Apic *apic, *bpapic; @@ -562,11 +564,22 @@ mpinit(void) /* * Initialise the application processors. */ + if(cp = getconf("*ncpu")){ + ncpu = strtol(cp, 0, 0); + if(ncpu < 1) + ncpu = 1; + } + else + ncpu = MaxAPICNO; memmove((void*)APBOOTSTRAP, apbootstrap, sizeof(apbootstrap)); for(apic = mpapic; apic <= &mpapic[MaxAPICNO]; apic++){ + if(ncpu <= 1) + break; if((apic->flags & (PcmpBP|PcmpEN)) == PcmpEN - && apic->type == PcmpPROCESSOR) + && apic->type == PcmpPROCESSOR){ mpstartap(apic); + ncpu--; + } } /* @@ -631,17 +644,31 @@ mpintrenablex(Vctl* v, int tbdf) continue; /* - * Check not already enabled. This is a bad thing as it implies - * the same device is requesting the same interrupt to be - * enabled multiple times. The RDT read here is safe for now - * as currently interrupts are never disabled once enabled. + * Check if already enabled. Multifunction devices may share + * INT[A-D]# so, if already enabled, check the polarity matches + * and the trigger is level. + * + * Should check the devices differ only in the function number, + * but that can wait for the planned enable/disable rewrite. + * The RDT read here is safe for now as currently interrupts + * are never disabled once enabled. */ apic = aintr->apic; ioapicrdtr(apic, aintr->intr->intin, 0, &lo); if(!(lo & ApicIMASK)){ - print("mpintrenable: multiple enable irq%d, tbdf %uX\n", - v->irq, tbdf); - return -1; + vno = lo & 0xFF; + n = mpintrinit(bus, aintr->intr, vno, v->irq); + n |= ApicLOGICAL; + if(n != lo || !(n & ApicLEVEL)){ + print("mpintrenable: multiple botch irq%d, tbdf %uX, lo %8.8uX, n %8.8uX\n", + v->irq, tbdf, lo, n); + return -1; + } + + v->isr = lapicisr; + v->eoi = lapiceoi; + + return vno; } /*