]> git.lizzy.rs Git - plan9front.git/blobdiff - sys/src/9/pc/main.c
devip: cleanup rudp.c
[plan9front.git] / sys / src / 9 / pc / main.c
index c947bb81605f6d85ee0bfeec42494e945de42a72..3ef3d773e2228f8a100fde7713765cd1ddde3731 100644 (file)
 #include       "reboot.h"
 
 Mach *m;
-
-/*
- * Where configuration info is left for the loaded programme.
- * This will turn into a structure as more is done by the boot loader
- * (e.g. why parse the .ini file twice?).
- * There are 3584 bytes available at CONFADDR.
- */
-#define BOOTLINE       ((char*)CONFADDR)
-#define BOOTLINELEN    64
-#define BOOTARGS       ((char*)(CONFADDR+BOOTLINELEN))
-#define        BOOTARGSLEN     (4096-0x200-BOOTLINELEN)
-#define        MAXCONF         64
-
-char bootdisk[KNAMELEN];
 Conf conf;
-char *confname[MAXCONF];
-char *confval[MAXCONF];
-int nconf;
-uchar *sp;     /* user stack of init proc */
+
 int delaylink;
 int idle_spin;
 
-static void
-multibootargs(void)
-{
-       char *cp, *ep;
-       ulong *m, l;
-
-       extern ulong *multiboot;
-
-       if(multiboot == nil)
-               return;
-
-       /* command line */
-       if((multiboot[0] & (1<<2)) != 0)
-               strncpy(BOOTLINE, KADDR(multiboot[4]), BOOTLINELEN-1);
-
-       cp = BOOTARGS;
-       ep = cp + BOOTARGSLEN-1;
-
-       /* memory map */
-       if((multiboot[0] & (1<<6)) != 0 && (l = multiboot[11]) >= 24){
-               cp = seprint(cp, ep, "*e820=");
-               m = KADDR(multiboot[12]);
-               while(m[0] >= 20 && m[0] <= l-4){
-                       uvlong base, size;
-                       m++;
-                       base = ((uvlong)m[0] | (uvlong)m[1]<<32);
-                       size = ((uvlong)m[2] | (uvlong)m[3]<<32);
-                       cp = seprint(cp, ep, "%.1lux %.16llux %.16llux ",
-                               m[4] & 0xF, base, base+size);
-                       l -= m[-1]+4;
-                       m = (ulong*)((ulong)m + m[-1]);
-               }
-               cp[-1] = '\n';
-       }
-
-       /* plan9.ini passed as the first module */
-       if((multiboot[0] & (1<<3)) != 0 && multiboot[5] > 0){
-               m = KADDR(multiboot[6]);
-               l = m[1] - m[0];
-               m = KADDR(m[0]);
-               if(cp+l > ep)
-                       l = ep - cp;
-               memmove(cp, m, l);
-               cp += l;
-       }
-       *cp = 0;
-}
-
-static void
-options(void)
-{
-       long i, n;
-       char *cp, *line[MAXCONF], *p, *q;
-
-       multibootargs();
-
-       /*
-        *  parse configuration args from dos file plan9.ini
-        */
-       cp = BOOTARGS;  /* where b.com leaves its config */
-       cp[BOOTARGSLEN-1] = 0;
-
-       /*
-        * Strip out '\r', change '\t' -> ' '.
-        */
-       p = cp;
-       for(q = cp; *q; q++){
-               if(*q == '\r')
-                       continue;
-               if(*q == '\t')
-                       *q = ' ';
-               *p++ = *q;
-       }
-       *p = 0;
-
-       n = getfields(cp, line, MAXCONF, 1, "\n");
-       for(i = 0; i < n; i++){
-               if(*line[i] == '#')
-                       continue;
-               cp = strchr(line[i], '=');
-               if(cp == nil)
-                       continue;
-               *cp++ = '\0';
-               confname[nconf] = line[i];
-               confval[nconf] = cp;
-               nconf++;
-       }
-}
-
-extern void mmuinit0(void);
 extern void (*i8237alloc)(void);
+extern void bootscreeninit(void);
+extern void multibootdebug(void);
 
 void
 main(void)
 {
        mach0init();
-       options();
+       bootargsinit();
        ioinit();
        i8250console();
        quotefmtinstall();
        screeninit();
 
        print("\nPlan 9\n");
-
+       
        trapinit0();
-       mmuinit0();
-
-       kbdinit();
        i8253init();
        cpuidentify();
        meminit();
        confinit();
-       archinit();
        xinit();
+       archinit();
+       bootscreeninit();
        if(i8237alloc != nil)
                i8237alloc();
        trapinit();
@@ -157,7 +50,6 @@ main(void)
                arch->intrinit();
        timersinit();
        mathinit();
-       kbdenable();
        if(arch->clockenable)
                arch->clockenable();
        procinit0();
@@ -167,12 +59,9 @@ main(void)
                pcimatch(0, 0, 0);
        }else
                links();
-       conf.monitor = 1;
        chandevreset();
        pageinit();
-       swapinit();
        userinit();
-       active.thunderbirdsarego = 1;
        schedinit();
 }
 
@@ -186,9 +75,8 @@ mach0init(void)
 
        machinit();
 
-       active.machs = 1;
+       active.machs[0] = 1;
        active.exiting = 0;
-       active.rebooting = 0;
 }
 
 void
@@ -219,8 +107,7 @@ machinit(void)
 void
 init0(void)
 {
-       int i;
-       char buf[2*KNAMELEN];
+       char buf[2*KNAMELEN], **sp;
 
        up->nerrlab = 0;
 
@@ -245,14 +132,15 @@ init0(void)
                        ksetenv("service", "cpu", 0);
                else
                        ksetenv("service", "terminal", 0);
-               for(i = 0; i < nconf; i++){
-                       if(confname[i][0] != '*')
-                               ksetenv(confname[i], confval[i], 0);
-                       ksetenv(confname[i], confval[i], 1);
-               }
+               setconfenv();
                poperror();
        }
        kproc("alarm", alarmkproc, 0);
+
+       sp = (char**)(USTKTOP - sizeof(Tos) - 8 - sizeof(sp[0])*4);
+       sp[3] = sp[2] = nil;
+       strcpy(sp[1] = (char*)&sp[4], "boot");
+       sp[0] = nil;
        touser(sp);
 }
 
@@ -297,10 +185,9 @@ userinit(void)
        s = newseg(SG_STACK, USTKTOP-USTKSIZE, USTKSIZE/BY2PG);
        p->seg[SSEG] = s;
        pg = newpage(0, 0, USTKTOP-BY2PG);
+       segpage(s, pg);
        v = tmpmap(pg);
        memset(v, 0, BY2PG);
-       segpage(s, pg);
-       bootargs(v);
        tmpunmap(v);
 
        /*
@@ -310,7 +197,7 @@ userinit(void)
        s->flushme++;
        p->seg[TSEG] = s;
        pg = newpage(0, 0, UTZERO);
-       memset(pg->cachectl, PG_TXTFLUSH, sizeof(pg->cachectl));
+       pg->txtflush = ~0;
        segpage(s, pg);
        v = tmpmap(pg);
        memset(v, 0, BY2PG);
@@ -320,96 +207,6 @@ userinit(void)
        ready(p);
 }
 
-uchar *
-pusharg(char *p)
-{
-       int n;
-
-       n = strlen(p)+1;
-       sp -= n;
-       memmove(sp, p, n);
-       return sp;
-}
-
-void
-bootargs(void *base)
-{
-       int i, ac;
-       uchar *av[32];
-       uchar **lsp;
-       char *cp = BOOTLINE;
-       char buf[64];
-
-       sp = (uchar*)base + BY2PG - sizeof(Tos);
-
-       ac = 0;
-       av[ac++] = pusharg("boot");
-
-       /* when boot is changed to only use rc, this code can go away */
-       cp[BOOTLINELEN-1] = 0;
-       buf[0] = 0;
-       if(strncmp(cp, "fd", 2) == 0){
-               sprint(buf, "local!#f/fd%lddisk", strtol(cp+2, 0, 0));
-               av[ac++] = pusharg(buf);
-       } else if(strncmp(cp, "sd", 2) == 0){
-               sprint(buf, "local!#S/sd%c%c/fs", *(cp+2), *(cp+3));
-               av[ac++] = pusharg(buf);
-       } else if(strncmp(cp, "ether", 5) == 0)
-               av[ac++] = pusharg("-n");
-
-       /* 4 byte word align stack */
-       sp = (uchar*)((ulong)sp & ~3);
-
-       /* build argc, argv on stack */
-       sp -= (ac+1)*sizeof(sp);
-       lsp = (uchar**)sp;
-       for(i = 0; i < ac; i++)
-               lsp[i] = av[i] + ((USTKTOP - BY2PG) - (ulong)base);
-       lsp[i] = 0;
-       sp += (USTKTOP - BY2PG) - (ulong)base;
-       sp -= BY2WD;
-}
-
-char*
-getconf(char *name)
-{
-       int i;
-
-       for(i = 0; i < nconf; i++)
-               if(cistrcmp(confname[i], name) == 0)
-                       return confval[i];
-       return 0;
-}
-
-static void
-writeconf(void)
-{
-       char *p, *q;
-       int n;
-
-       p = getconfenv();
-
-       if(waserror()) {
-               free(p);
-               nexterror();
-       }
-
-       /* convert to name=value\n format */
-       for(q=p; *q; q++) {
-               q += strlen(q);
-               *q = '=';
-               q += strlen(q);
-               *q = '\n';
-       }
-       n = q - p + 1;
-       if(n >= BOOTARGSLEN)
-               error("kernel configuration too large");
-       memset(BOOTLINE, 0, BOOTLINELEN);
-       memmove(BOOTARGS, p, n);
-       poperror();
-       free(p);
-}
-
 void
 confinit(void)
 {
@@ -446,6 +243,7 @@ confinit(void)
                if(userpcnt < 10)
                        userpcnt = 70;
                kpages = conf.npage - (conf.npage*userpcnt)/100;
+               conf.nimage = conf.nproc;
 
                /*
                 * Hack for the big boys. Only good while physmem < 4GB.
@@ -458,7 +256,6 @@ confinit(void)
                if(getconf("*imagemaxmb") == 0)
                if(kpages > (64*MB + conf.npage*sizeof(Page))/BY2PG){
                        kpages = (64*MB + conf.npage*sizeof(Page))/BY2PG;
-                       conf.nimage = 2000;
                        kpages += (conf.nproc*KSTACK)/BY2PG;
                }
        } else {
@@ -490,8 +287,7 @@ confinit(void)
 
        /*
         * Guess how much is taken by the large permanent
-        * datastructures. Mntcache and Mntrpc are not accounted for
-        * (probably ~300KB).
+        * datastructures. Mntcache and Mntrpc are not accounted for.
         */
        kpages *= BY2PG;
        kpages -= conf.upages*sizeof(Page)
@@ -514,12 +310,8 @@ confinit(void)
 }
 
 /*
- * we keep FPsave structure in sse format emulating FXSAVE / FXRSTOR
+ * we keep FPsave structure in SSE format emulating FXSAVE / FXRSTOR
  * instructions for legacy x87 fpu.
- *
- * Note that fpx87restore() and fpxsserestore() do modify the FPsave
- * data structure for conversion / realignment shuffeling. this means
- * that p->fpsave is only valid when p->fpstate == FPinactive.
  */
 void
 fpx87save(FPsave *fps)
@@ -644,32 +436,6 @@ fpx87restore(FPsave *fps)
        fpx87restore0(fps);
 }
 
-/*
- * sse fp save and restore buffers have to be 16-byte (FPalign) aligned,
- * so we shuffle the data up and down as needed or make copies.
- */
-void
-fpssesave(FPsave *fps)
-{
-       FPsave *afps;
-
-       afps = (FPsave *)ROUND(((uintptr)fps), FPalign);
-       fpssesave0(afps);
-       if(fps != afps)  /* not aligned? shuffle down from aligned buffer */
-               memmove(fps, afps, sizeof(FPssestate) - FPalign);
-}
-
-void
-fpsserestore(FPsave *fps)
-{
-       FPsave *afps;
-
-       afps = (FPsave *)ROUND(((uintptr)fps), FPalign);
-       if(fps != afps)  /* shuffle up to make aligned */
-               memmove(afps, fps, sizeof(FPssestate) - FPalign);
-       fpsserestore0(afps);
-}
-
 static char* mathmsg[] =
 {
        nil,    /* handled below */
@@ -727,8 +493,20 @@ matherror(Ureg*, void*)
        /*
         *  get floating point state to check out error
         */
-       fpenv(&up->fpsave);
-       mathnote(up->fpsave.status, up->fpsave.pc);
+       fpsave(up->fpsave);
+       up->fpstate = FPinactive;
+       mathnote(up->fpsave->fsw, up->fpsave->fpuip);
+}
+
+/*
+ *  SIMD error
+ */
+static void
+simderror(Ureg *ureg, void*)
+{
+       fpsave(up->fpsave);
+       up->fpstate = FPinactive;
+       mathnote(up->fpsave->mxcsr & 0x3f, ureg->pc);
 }
 
 /*
@@ -747,6 +525,10 @@ mathemu(Ureg *ureg, void*)
        switch(up->fpstate){
        case FPinit:
                fpinit();
+               if(fpsave == fpssesave)
+                       ldmxcsr(0x1f80);        /* no simd exceptions on 386 */
+               while(up->fpsave == nil)
+                       up->fpsave = mallocalign(sizeof(FPsave), FPalign, 0, 0);
                up->fpstate = FPactive;
                break;
        case FPinactive:
@@ -757,13 +539,13 @@ mathemu(Ureg *ureg, void*)
                 * More attention should probably be paid here to the
                 * exception masks and error summary.
                 */
-               status = up->fpsave.fsw;
-               control = up->fpsave.fcw;
+               status = up->fpsave->fsw;
+               control = up->fpsave->fcw;
                if((status & ~control) & 0x07F){
-                       mathnote(status, up->fpsave.fpuip);
+                       mathnote(status, up->fpsave->fpuip);
                        break;
                }
-               fprestore(&up->fpsave);
+               fprestore(up->fpsave);
                up->fpstate = FPactive;
                break;
        case FPactive:
@@ -790,6 +572,7 @@ mathinit(void)
                intrenable(IrqIRQ13, matherror, 0, BUSUNKNOWN, "matherror");
        trapenable(VectorCNA, mathemu, 0, "mathemu");
        trapenable(VectorCSO, mathover, 0, "mathover");
+       trapenable(VectorSIMD, simderror, 0, "simderror");
 }
 
 /*
@@ -807,6 +590,8 @@ procsetup(Proc *p)
        memset(p->gdt, 0, sizeof(p->gdt));
        p->ldt = nil;
        p->nldt = 0;
+       
+       memset(p->dr, 0, sizeof(p->dr));
 }
 
 void
@@ -831,12 +616,17 @@ procfork(Proc *p)
        s = splhi();
        switch(up->fpstate & ~FPillegal){
        case FPactive:
-               fpsave(&up->fpsave);
+               fpsave(up->fpsave);
                up->fpstate = FPinactive;
        case FPinactive:
-               p->fpsave = up->fpsave;
+               while(p->fpsave == nil)
+                       p->fpsave = mallocalign(sizeof(FPsave), FPalign, 0, 0);
+               memmove(p->fpsave, up->fpsave, sizeof(FPsave));
                p->fpstate = FPinactive;
        }
+       
+       /* clear debug registers */
+       memset(p->dr, 0, sizeof(p->dr));
        splx(s);
 }
 
@@ -844,6 +634,14 @@ void
 procrestore(Proc *p)
 {
        uvlong t;
+       
+       if(p->dr[7] != 0){
+               m->dr7 = p->dr[7];
+               putdr(p->dr);
+       }
+       
+       if(p->vmx != nil)
+               vmxprocrestore(p);
 
        if(p->kp)
                return;
@@ -860,6 +658,12 @@ void
 procsave(Proc *p)
 {
        uvlong t;
+       
+       /* we could just always putdr7(0) but accessing DR7 might be slow in a VM */
+       if(m->dr7 != 0){
+               m->dr7 = 0;
+               putdr7(0);
+       }
 
        cycles(&t);
        p->kentry -= t;
@@ -877,7 +681,7 @@ procsave(Proc *p)
                         * until the process runs again and generates an
                         * emulation fault to activate the FPU.
                         */
-                       fpsave(&p->fpsave);
+                       fpsave(p->fpsave);
                }
                p->fpstate = FPinactive;
        }
@@ -896,50 +700,6 @@ procsave(Proc *p)
        mmuflushtlb(PADDR(m->pdb));
 }
 
-static void
-shutdown(int ispanic)
-{
-       int ms, once;
-
-       lock(&active);
-       if(ispanic)
-               active.ispanic = ispanic;
-       else if(m->machno == 0 && (active.machs & (1<<m->machno)) == 0)
-               active.ispanic = 0;
-       once = active.machs & (1<<m->machno);
-       /*
-        * setting exiting will make hzclock() on each processor call exit(0),
-        * which calls shutdown(0) and arch->reset(), which on mp systems is
-        * mpshutdown, from which there is no return: the processor is idled
-        * or initiates a reboot.  clearing our bit in machs avoids calling
-        * exit(0) from hzclock() on this processor.
-        */
-       active.machs &= ~(1<<m->machno);
-       active.exiting = 1;
-       unlock(&active);
-
-       if(once)
-               iprint("cpu%d: exiting\n", m->machno);
-
-       /* wait for any other processors to shutdown */
-       spllo();
-       for(ms = 5*1000; ms > 0; ms -= TK2MS(2)){
-               delay(TK2MS(2));
-               if(active.machs == 0 && consactive() == 0)
-                       break;
-       }
-
-       if(active.ispanic){
-               if(!cpuserver)
-                       for(;;)
-                               halt();
-               if(getconf("*debug"))
-                       delay(5*60*1000);
-               else
-                       delay(10000);
-       }
-}
-
 void
 reboot(void *entry, void *code, ulong size)
 {
@@ -947,6 +707,7 @@ reboot(void *entry, void *code, ulong size)
        ulong *pdb;
 
        writeconf();
+       vmxshutdown();
 
        /*
         * the boot processor is cpu0.  execute this function on it
@@ -958,23 +719,7 @@ reboot(void *entry, void *code, ulong size)
                procwired(up, 0);
                sched();
        }
-
-       lock(&active);
-       active.rebooting = 1;
-       unlock(&active);
-
-       shutdown(0);
-
-       /*
-        * should be the only processor running now
-        */
-       if (m->machno != 0)
-               iprint("on cpu%d (not 0)!\n", m->machno);
-       if (active.machs)
-               iprint("still have active ap processors!\n");
-
-       iprint("shutting down...\n");
-       delay(200);
+       cpushutdown();
 
        splhi();
 
@@ -1004,8 +749,8 @@ reboot(void *entry, void *code, ulong size)
 
 
 void
-exit(int ispanic)
+exit(int)
 {
-       shutdown(ispanic);
+       cpushutdown();
        arch->reset();
 }