1*1e26076aSbostic /* boot.c 1.7 88/03/04 */ 28e3d4093Ssam 38e3d4093Ssam #include "../machine/mtpr.h" 48e3d4093Ssam 58e3d4093Ssam #include "param.h" 68e3d4093Ssam #include "inode.h" 78e3d4093Ssam #include "fs.h" 88e3d4093Ssam #include "vm.h" 98e3d4093Ssam #include "saio.h" 108e3d4093Ssam #include "reboot.h" 118e3d4093Ssam 128e3d4093Ssam #include <a.out.h> 138e3d4093Ssam 148e3d4093Ssam /* 158e3d4093Ssam * Boot program... arguments passed in r10 and r11 determine 168e3d4093Ssam * whether boot stops to ask for system name and which device 178e3d4093Ssam * boot comes from. 188e3d4093Ssam */ 198e3d4093Ssam 20977ec1dbSkarels #define DEV_DFLT 1 /* vd/dk */ 218e3d4093Ssam 228e3d4093Ssam char line[100]; 238e3d4093Ssam 2440ca8ffdSkarels extern unsigned opendev; 2540ca8ffdSkarels extern unsigned bootdev; 268e3d4093Ssam 278e3d4093Ssam main() 288e3d4093Ssam { 2940ca8ffdSkarels register char *cp; /* skip r12 */ 30*1e26076aSbostic register u_int howto, devtype; /* howto=r11, devtype=r10 */ 31*1e26076aSbostic int io, retry, type; 328e3d4093Ssam 338e3d4093Ssam #ifdef lint 348e3d4093Ssam howto = 0; devtype = 0; 358e3d4093Ssam #endif 3640ca8ffdSkarels if ((devtype & B_MAGICMASK) != B_DEVMAGIC) 3740ca8ffdSkarels devtype = DEV_DFLT << B_TYPESHIFT; /* unit, partition 0 */ 3840ca8ffdSkarels bootdev = devtype; 3940ca8ffdSkarels printf("\nBoot\n"); 408e3d4093Ssam #ifdef JUSTASK 418e3d4093Ssam howto = RB_ASKNAME|RB_SINGLE; 42988e96f5Ssam #else 43988e96f5Ssam if ((howto & RB_ASKNAME) == 0) { 4440ca8ffdSkarels type = (devtype >> B_TYPESHIFT) & B_TYPEMASK; 45*1e26076aSbostic if ((unsigned)type < ndevs && devsw[type].dv_name) 4640ca8ffdSkarels strcpy(line, UNIX); 4740ca8ffdSkarels else 4840ca8ffdSkarels howto |= RB_SINGLE|RB_ASKNAME; 49988e96f5Ssam } 508e3d4093Ssam #endif 51*1e26076aSbostic for (retry = 0;;) { 528e3d4093Ssam if (howto & RB_ASKNAME) { 538e3d4093Ssam printf(": "); 548e3d4093Ssam gets(line); 5540ca8ffdSkarels if (line[0] == 0) { 5640ca8ffdSkarels strcpy(line, UNIX); 5740ca8ffdSkarels printf(": %s\n", line); 5840ca8ffdSkarels } 598e3d4093Ssam } else 608e3d4093Ssam printf(": %s\n", line); 618e3d4093Ssam io = open(line, 0); 62988e96f5Ssam if (io >= 0) { 6340ca8ffdSkarels copyunix(howto, opendev, io); 64988e96f5Ssam close(io); 6540ca8ffdSkarels howto |= RB_SINGLE|RB_ASKNAME; 66988e96f5Ssam } 678e3d4093Ssam if (++retry > 2) 688e3d4093Ssam howto |= RB_SINGLE|RB_ASKNAME; 698e3d4093Ssam } 708e3d4093Ssam } 718e3d4093Ssam 728e3d4093Ssam /*ARGSUSED*/ 73988e96f5Ssam copyunix(howto, devtype, io) 74988e96f5Ssam register io, howto, devtype; /* NOTE ORDER */ 758e3d4093Ssam { 76097b37ecSsam register int esym; /* must be r9 */ 778e3d4093Ssam register int i; 78988e96f5Ssam register char *addr; 79097b37ecSsam struct exec x; 808e3d4093Ssam 818e3d4093Ssam i = read(io, (char *)&x, sizeof x); 828e3d4093Ssam if (i != sizeof x || 8340ca8ffdSkarels (x.a_magic != 0407 && x.a_magic != 0413 && x.a_magic != 0410)) { 8440ca8ffdSkarels printf("Bad format\n"); 8540ca8ffdSkarels return; 8640ca8ffdSkarels } 878e3d4093Ssam printf("%d", x.a_text); 888e3d4093Ssam if (x.a_magic == 0413 && lseek(io, 0x400, 0) == -1) 898e3d4093Ssam goto shread; 9078713aceSkarels if (read(io, (char *)RELOC, x.a_text) != x.a_text) 918e3d4093Ssam goto shread; 9278713aceSkarels addr = (char *)(x.a_text + RELOC); 938e3d4093Ssam if (x.a_magic == 0413 || x.a_magic == 0410) 948e3d4093Ssam while ((int)addr & CLOFSET) 958e3d4093Ssam *addr++ = 0; 968e3d4093Ssam printf("+%d", x.a_data); 978e3d4093Ssam if (read(io, addr, x.a_data) != x.a_data) 988e3d4093Ssam goto shread; 998e3d4093Ssam addr += x.a_data; 1008e3d4093Ssam printf("+%d", x.a_bss); 101097b37ecSsam if (howto & RB_KDB && x.a_syms) { 102097b37ecSsam for (i = 0; i < x.a_bss; i++) 103097b37ecSsam *addr++ = 0; 104097b37ecSsam *(int *)addr = x.a_syms; /* symbol table size */ 105097b37ecSsam addr += sizeof (int); 106097b37ecSsam printf("[+%d", x.a_syms); 107097b37ecSsam if (read(io, addr, x.a_syms) != x.a_syms) 108097b37ecSsam goto shread; 109097b37ecSsam addr += x.a_syms; 110097b37ecSsam if (read(io, addr, sizeof (int)) != sizeof (int)) 111097b37ecSsam goto shread; 112097b37ecSsam i = *(int *)addr - sizeof (int); /* string table size */ 113097b37ecSsam addr += sizeof (int); 114097b37ecSsam printf("+%d]", i); 115097b37ecSsam if (read(io, addr, i) != i) 116097b37ecSsam goto shread; 117097b37ecSsam addr += i; 118097b37ecSsam esym = roundup((int)addr, sizeof (int)); 119097b37ecSsam x.a_bss = 0; 120097b37ecSsam } else 121097b37ecSsam howto &= ~RB_KDB; 1228e3d4093Ssam x.a_bss += 32*1024; /* slop */ 1238e3d4093Ssam for (i = 0; i < x.a_bss; i++) 1248e3d4093Ssam *addr++ = 0; 1258e3d4093Ssam x.a_entry &= 0x1fffffff; 1268e3d4093Ssam printf(" start 0x%x\n", x.a_entry); 1278e3d4093Ssam mtpr(PADC, 0); /* Purge data cache */ 1288e3d4093Ssam mtpr(PACC, 0); /* Purge code cache */ 1298e3d4093Ssam mtpr(DCR, 1); /* Enable data cache */ 1308e3d4093Ssam (*((int (*)()) x.a_entry))(); 131988e96f5Ssam return; 1328e3d4093Ssam shread: 13340ca8ffdSkarels printf("Short read\n"); 13440ca8ffdSkarels return; 1358e3d4093Ssam } 136