M boot/aux.c => boot/aux.c +15 -4
@@ 71,14 71,12 @@ fatal(char *s)
}
int
-readenv(char *name, char *buf, int len)
+readfile(char *name, char *buf, int len)
{
int f, n;
- char ename[2*NAMELEN];
- sprint(ename, "#e/%s", name);
buf[0] = 0;
- f = open(ename, OREAD);
+ f = open(name, OREAD);
if(f < 0)
return -1;
n = read(f, buf, len-1);
@@ 146,11 144,18 @@ outin(char *prompt, char *def, int len)
return n;
}
+/*
+ * get second word of the terminal environment variable. If it
+ * ends in "boot", get work of that part.
+ */
void
getconffile(char *conffile, char *terminal)
{
char *p, *q;
+ char *s;
+ int n;
+ s = conffile;
*conffile = 0;
p = terminal;
if((p = strchr(p, ' ')) == 0 || p[1] == ' ' || p[1] == 0)
@@ 160,4 165,10 @@ getconffile(char *conffile, char *terminal)
;
while(p < q)
*conffile++ = *p++;
+ *conffile = 0;
+
+ /* dump a trailig boot */
+ n = strlen(s);
+ if(n > 4 && strcmp(s + n - 4, "boot") == 0)
+ *(s+n-4) = 0;
}
M boot/boot.c => boot/boot.c +6 -2
@@ 40,6 40,10 @@ boot(int argc, char *argv[])
open("#c/cons", OWRITE);
open("#c/cons", OWRITE);
+/* for(fd = 0; fd < argc; fd++)
+ print("%s ", argv[fd]);
+ print("\n");/**/
+
ARGBEGIN{
case 'a':
aflag = 1;
@@ 62,8 66,8 @@ boot(int argc, char *argv[])
break;
}ARGEND
- readenv("cputype", cputype, sizeof(cputype));
- readenv("terminal", terminal, sizeof(cputype));
+ readfile("#e/cputype", cputype, sizeof(cputype));
+ readfile("#e/terminal", terminal, sizeof(cputype));
getconffile(conffile, terminal);
/*
M boot/boot.h => boot/boot.h +1 -1
@@ 36,7 36,7 @@ extern void newkernel(void);
extern void nop(int);
extern int outin(char*, char*, int);
extern int plumb(char*, char*, int*, char*);
-extern int readenv(char*, char*, int);
+extern int readfile(char*, char*, int);
extern int sendmsg(int, char*);
extern void session(int);
extern void setenv(char*, char*);
M gnot/fns.h => gnot/fns.h +1 -0
@@ 15,6 15,7 @@ void duartstarttimer(void);
void duartstoptimer(void);
#define evenaddr(x) /* 68020 doesn't care */
void fault68020(Ureg*, FFrame*);
+void firmware(void);
#define flushapage(x)
void flushcpucache(void);
#define flushpage(x) if(x)
M pc/main.c => pc/main.c +0 -5
@@ 390,11 390,6 @@ procrestore(Proc *p)
{
}
-void
-firmware(void)
-{
- panic("firmware");
-}
/*
* the following functions all are slightly different from
M port/portfns.h => port/portfns.h +0 -1
@@ 67,7 67,6 @@ Block* expandb(Block*, int);
int fault(ulong, int);
void fdclose(int, int);
Chan* fdtochan(int, int, int);
-void firmware(void);
int fixfault(Segment*, ulong, int, int);
void flowctl(Queue*, Block*);
void flushmmu(void);
M power/fns.h => power/fns.h +1 -0
@@ 20,6 20,7 @@ void duartxmit(int);
void evenaddr(ulong);
void faultmips(Ureg*, int, int);
ulong fcr31(void);
+void firmware(int);
void flushmmu(void);
#define flushpage(s) icflush((void*)(s), BY2PG)
void gettlb(int, ulong*);
M power/io.h => power/io.h +7 -0
@@ 110,3 110,10 @@ struct INTVEC {
#define RTC (NVRAM+0x3ff8)
#define SBEADDR ((ulong *)(UNCACHED|0x1F080000))
+
+#define PROM_RESET 0 /* run diags, check bootmode, reinit */
+#define PROM_EXEC 1 /* load new program image */
+#define PROM_RESTART 2 /* re-enter monitor command loop */
+#define PROM_REINIT 3 /* re-init monitor, then cmd loop */
+#define PROM_REBOOT 4 /* check bootmode, no config */
+#define PROM_AUTOBOOT 5 /* autoboot the system */
M power/l.s => power/l.s +2 -2
@@ 93,8 93,8 @@ TEXT newstart(SB), $0
TEXT firmware(SB), $0
- MOVW $(PROM+0x18), R1 /**/
-/* MOVW $(PROM+0x00), R1 /**/
+ SLL $3, R1
+ ADD $PROM, R1
JMP (R1)
TEXT splhi(SB), $0
M power/main.c => power/main.c +58 -54
@@ 19,14 19,14 @@ int _argc; char **_argv; char **_env;
/*
* arguments passed to initcode
*/
-char argbuf[512];
+char argbuf[128];
int argsize;
/*
- * environment passed to any kernel started by this kernel
+ * environment variables extracted from NVRAM
*/
-char envbuf[64];
-char *env[2];
+char consname[NAMELEN];
+char diskless[NAMELEN];
/*
* configuration file read by boot program
@@ 44,8 44,8 @@ main(void)
machinit();
active.exiting = 0;
active.machs = 1;
- confinit();
arginit();
+ confinit();
lockinit();
printinit();
duartspecial(0, &printq, &kbdq, 9600);
@@ 61,7 61,6 @@ main(void)
streaminit();
swapinit();
pageinit();
-print("userinit\n");
userinit();
launchinit();
schedinit();
@@ 204,7 203,6 @@ void
init0(void)
{
int i;
- ulong *sp;
Chan *c;
m->proc = u->p;
@@ 228,8 226,7 @@ init0(void)
}
kproc("alarm", alarmkproc, 0);
- sp = (ulong*)(USTKTOP - argsize);
- touser(sp);
+ touser((uchar*)(USTKTOP - sizeof(argbuf)));
}
FPsave initfp;
@@ 279,13 276,11 @@ userinit(void)
p->seg[SSEG] = s;
pg = newpage(1, 0, USTKTOP-BY2PG);
segpage(s, pg);
-
- memmove((ulong*)(pg->pa|KZERO|(BY2PG-argsize)),
- argbuf + sizeof(argbuf) - argsize, argsize);
-
- av = (char **)(pg->pa|KZERO|(BY2PG-argsize));
- for(i = 0; i < _argc; i++)
- av[i] += (char *)USTKTOP - (argbuf + sizeof(argbuf));
+ k = kmap(pg);
+ for(av = (char**)argbuf; *av; av++)
+ *av += (USTKTOP - sizeof(argbuf)) - (ulong)argbuf;
+ memmove((uchar*)VA(k) + BY2PG - sizeof(argbuf), argbuf, sizeof argbuf);
+ kunmap(k);
/*
* Text
@@ 377,7 372,7 @@ exit(void)
for(i=0; i<2000000; i++)
;
duartenable0();
- firmware();
+ firmware(conf.cntrlp ? PROM_AUTOBOOT : PROM_REINIT);
}
typedef struct Conftab {
@@ 599,59 594,68 @@ confinit(void)
* copy arguments passed by the boot kernel (or ROM) into a temporary buffer.
* we do this because the arguments are in memory that may be allocated
* to processes or kernel buffers.
+ *
+ * also grab any environment variables that might be useful
*/
-#define IPADDRENV "netaddr="
+struct{
+ char *name;
+ char *val;
+}bootenv[] = {
+ {"netaddr=", sysname},
+ {"console=", consname},
+ {"diskless=", diskless},
+};
+char *sp;
+
+char *
+pusharg(char *p)
+{
+ int n;
+
+ n = strlen(p)+1;
+ sp -= n;
+ memmove(sp, p, n);
+ return sp;
+}
+
void
arginit(void)
{
int i, n;
- int nbytes;
- int ssize;
- char *p;
- char **argv;
- char *charp;
+ char **av;
/*
- * get the system name from the environment
+ * get boot env variables
*/
- strcpy(envbuf, IPADDRENV);
- for(argv = _env; *argv; argv++){
- if(strncmp(*argv, IPADDRENV, sizeof(IPADDRENV)-1)==0){
- strcat(envbuf, (*argv) + sizeof(IPADDRENV)-1);
- break;
- }
- }
- env[0] = envbuf;
- env[1] = 0;
+ if(*sysname == 0)
+ for(av = _env; *av; av++)
+ for(i=0; i < sizeof bootenv/sizeof bootenv[0]; i++){
+ n = strlen(bootenv[i].name);
+ if(strncmp(*av, bootenv[i].name, n) == 0){
+ strncpy(bootenv[i].val, (*av)+n, NAMELEN);
+ bootenv[i].val[NAMELEN-1] = '\0';
+ break;
+ }
+ }
/*
- * trim arguments to make them fit in the buffer (argv[0] is sysname)
+ * pack args into buffer
*/
- nbytes = 0;
- _argv[0] = sysname;
+ av = (char**)argbuf;
+ sp = argbuf + sizeof(argbuf);
for(i = 0; i < _argc; i++){
- n = strlen(_argv[i]) + 1;
- ssize = BY2WD*(i+2) + ((nbytes+n+(BY2WD-1)) & ~(BY2WD-1));
- if(ssize > sizeof(argbuf))
- break;
- nbytes += n;
+ if(i && *(_argv[i]) != '-')
+ diskless[0] = 0;
+ av[i] = pusharg(_argv[i]);
}
- _argc = i;
- ssize = BY2WD*(i+1) + ((nbytes+(BY2WD-1)) & ~(BY2WD-1));
/*
- * copy arguments into the buffer
+ * if no boot method is specified, look for
+ * a default in the diskless environment variable
*/
- argv = (char**)(argbuf + sizeof(argbuf) - ssize);
- charp = (char*)(argbuf + sizeof(argbuf) - nbytes);
- for(i=0; i<_argc; i++){
- argv[i] = charp;
- n = strlen(_argv[i]) + 1;
- memmove(charp, _argv[i], n);
- charp += n;
- }
- _argv = argv;
- argsize = ssize;
+ if(diskless[0] > '1')
+ av[i++] = pusharg(diskless);
+ av[i] = 0;
}
/*
M ss/main.c => ss/main.c +0 -6
@@ 307,9 307,3 @@ lancesetup(Lance *lp)
lp->ltp = lp->lrp+lp->nrrb;
lp->tp = lp->rp+lp->nrrb;
}
-
-void
-firmware(void)
-{
- systemreset();
-}