3 #include "../port/lib.h"
11 #include "rebootcode.i"
14 * Where configuration info is left for the loaded programme.
15 * This will turn into a structure as more is done by the boot loader
16 * (e.g. why parse the .ini file twice?).
17 * There are 3584 bytes available at CONFADDR.
19 #define BOOTARGS ((char*)CONFADDR)
20 #define BOOTARGSLEN (16*KiB) /* limit in devenv.c */
22 #define MAXCONFLINE 160
24 #define isascii(c) ((uchar)(c) > 0 && (uchar)(c) < 0177)
26 uintptr kseg0 = KZERO;
27 Mach* machaddr[MAXMACH];
32 /* store plan9.ini contents here at least until we stash them in #ec */
33 static char confname[MAXCONF][KNAMELEN];
34 static char confval[MAXCONF][MAXCONFLINE];
38 uchar sandbox[64*1024+BY2PG];
46 for(i = 0; i < nconf; i++)
47 if(cistrcmp(confname[i], name) == 0)
64 addconf(char *name, char *val)
70 if(val == nil || nconf >= MAXCONF)
73 strecpy(confname[i], confname[i]+sizeof(confname[i]), name);
76 strecpy(confval[i], confval[i]+sizeof(confval[i]), val);
92 /* convert to name=value\n format */
101 error("kernel configuration too large");
102 memmove(BOOTARGS, p, n);
108 * assumes that we have loaded our /cfg/pxe/mac file at 0x1000 with
109 * tftp in u-boot. no longer uses malloc, so can be called early.
116 k = (char *)CONFADDR;
120 for(; k && *k != '\0'; k = next) {
121 if (!isascii(*k)) /* sanity check */
123 next = strchr(k, '\n');
127 if (*k == '\0' || *k == '\n' || *k == '#')
131 continue; /* mal-formed line */
140 typedef struct Spiregs Spiregs;
142 ulong ictl; /* interface ctl */
143 ulong icfg; /* interface config */
144 ulong out; /* data out */
145 ulong in; /* data in */
146 ulong ic; /* interrupt cause */
147 ulong im; /* interrupt mask */
149 ulong dwrcfg; /* direct write config */
150 ulong dwrhdr; /* direct write header */
155 Csnact = 1<<0, /* serial memory activated */
158 Bytelen = 1<<5, /* 2^(this_bit) bytes per transfer */
159 Dirrdcmd= 1<<10, /* flag: fast read */
163 dumpbytes(uchar *bp, long max)
166 for (; max > 0; max--)
167 iprint("%02.2ux ", *bp++);
174 Spiregs *rp = (Spiregs *)soc.spi;
178 rp->icfg |= Dirrdcmd | 3<<8; /* fast reads, 4-byte addresses */
179 rp->icfg &= ~Bytelen; /* one-byte reads */
182 // print("spi flash at %#ux: memory reads enabled\n", PHYSSPIFLASH);
185 void archconsole(void);
189 isaconfig(char *, int, ISAConf *)
195 * entered from l.s with mmu enabled.
197 * we may have to realign the data segment; apparently 5l -H0 -R4096
198 * does not pad the text segment. on the other hand, we may have been
199 * loaded by another kernel.
201 * be careful not to touch the data segment until we know it's aligned.
206 extern char bdata[], edata[], end[], etext[];
207 static ulong vfy = 0xcafebabe;
210 if (vfy != 0xcafebabe)
211 memmove(bdata, etext, edata - bdata);
212 if (vfy != 0xcafebabe) {
214 panic("misaligned data segment");
216 memset(edata, 0, end - edata); /* zero bss */
228 /* want plan9.ini to be able to affect memory sizing in confinit */
229 plan9iniinit(); /* before we step on plan9.ini in low memory */
232 /* xinit would print if it could */
236 * Printinit will cause the first malloc call.
237 * (printinit->qopen->malloc) unless any of the
238 * above (like clockintr) do an irqenable, which
240 * If the system dies here it's probably due
241 * to malloc(->xalloc) not being initialised
242 * correctly, or the data segment is misaligned
243 * (it's amazing how far you can get with
244 * things like that completely broken).
246 * (Should be) boilerplate from here on.
252 uartkirkwoodconsole();
253 /* only now can we print */
254 print("from Bell Labs\n\n");
257 print("sandbox: 64K at physical %#lux, mapped to 0xf10b0000\n",
258 PADDR((uintptr)sandbox & ~(BY2PG-1)));
268 chandevreset(); /* most devices are discovered here */
273 panic("schedinit returned");
281 cputype2name(name, sizeof name);
282 print("cpu%d: %lldMHz ARM %s\n", m->machno, m->cpuhz/1000000, name);
288 memset(m, 0, sizeof(Mach));
290 machaddr[m->machno] = m;
304 * exit kernel either on a panic or user request
315 * the new kernel is already loaded at address `code'
316 * of size `size' and entry point `entry'.
319 reboot(void *entry, void *code, ulong size)
321 void (*f)(ulong, ulong, ulong);
326 /* turn off buffered serial console */
329 /* shutdown devices */
332 /* call off the dog */
337 /* setup reboot trampoline function */
338 f = (void*)REBOOTADDR;
339 memmove(f, rebootcode, sizeof(rebootcode));
343 /* off we go - never to return */
346 (*f)(PADDR(entry), PADDR(code), size);
350 * starting place for first process
355 char buf[2*KNAMELEN], **sp;
361 snprint(buf, sizeof(buf), "%s %s", "ARM", conffile);
362 ksetenv("terminal", buf, 0);
363 ksetenv("cputype", "arm", 0);
365 ksetenv("service", "cpu", 0);
367 ksetenv("service", "terminal", 0);
369 /* convert plan9.ini variables to #e and #ec */
370 for(i = 0; i < nconf; i++) {
371 ksetenv(confname[i], confval[i], 0);
372 ksetenv(confname[i], confval[i], 1);
376 kproc("alarm", alarmkproc, 0);
378 sp = (char**)(USTKTOP - sizeof(Tos) - 8 - sizeof(sp[0])*4);
379 sp[3] = sp[2] = sp[1] = nil;
380 strcpy(sp[0] = (char*)&sp[4], "boot");
384 Conf conf; /* XXX - must go - gag */
386 Confmem sheevamem[] = {
388 * Memory available to Plan 9:
389 * the 8K is reserved for ethernet dma access violations to scribble on.
391 { .base = 0, .limit = 512*MB - 8*1024, },
402 * Copy the physical memory configuration to Conf.mem.
404 if(nelem(sheevamem) > nelem(conf.mem)){
405 iprint("memory configuration botch\n");
408 memmove(conf.mem, sheevamem, sizeof(sheevamem));
411 pa = PADDR(PGROUND((uintptr)end));
414 * we assume that the kernel is at the beginning of one of the
415 * contiguous chunks of memory and fits therein.
417 for(i=0; i<nelem(conf.mem); i++){
418 /* take kernel out of allocatable space */
419 if(pa > conf.mem[i].base && pa < conf.mem[i].limit)
420 conf.mem[i].base = pa;
422 conf.mem[i].npage = (conf.mem[i].limit - conf.mem[i].base)/BY2PG;
423 conf.npage += conf.mem[i].npage;
426 conf.upages = (conf.npage*90)/100;
427 conf.ialloc = ((conf.npage-conf.upages)/2)*BY2PG;
429 /* only one processor */
432 /* set up other configuration parameters */
433 conf.nproc = 100 + ((conf.npage*BY2PG)/MB)*5;
436 if(conf.nproc > 2000)
438 conf.nswap = conf.npage*3;
442 conf.copymode = 0; /* copy on write */
445 * Guess how much is taken by the large permanent
446 * datastructures. Mntcache and Mntrpc are not accounted for.
448 kpages = conf.npage - conf.upages;
450 kpages -= conf.upages*sizeof(Page)
451 + conf.nproc*sizeof(Proc)
452 + conf.nimage*sizeof(Image)
454 + conf.nswppo*sizeof(Page*);
455 mainmem->maxsize = kpages;
458 * give terminals lots of image memory, too; the dynamic
459 * allocation will balance the load properly, hopefully.
460 * be careful with 32-bit overflow.
462 imagmem->maxsize = kpages;
466 cmpswap(long *addr, long old, long new)
468 return cas32(addr, old, new);
472 setupwatchpts(Proc *, Watchpt *, int n)
475 error("no watchpoints");