1*26Sbill /* init_main.c 3.1 10/14/12 */ 2*26Sbill 3*26Sbill #include "../h/param.h" 4*26Sbill #include "../h/systm.h" 5*26Sbill #include "../h/dir.h" 6*26Sbill #include "../h/user.h" 7*26Sbill #include "../h/filsys.h" 8*26Sbill #include "../h/mount.h" 9*26Sbill #include "../h/map.h" 10*26Sbill #include "../h/proc.h" 11*26Sbill #include "../h/inode.h" 12*26Sbill #include "../h/seg.h" 13*26Sbill #include "../h/conf.h" 14*26Sbill #include "../h/buf.h" 15*26Sbill #include "../h/mtpr.h" 16*26Sbill #include "../h/pte.h" 17*26Sbill #include "../h/clock.h" 18*26Sbill #include "../h/vm.h" 19*26Sbill #include "../h/cmap.h" 20*26Sbill 21*26Sbill /* 22*26Sbill * Initialization code. 23*26Sbill * Called from cold start routine as 24*26Sbill * soon as a stack and segmentation 25*26Sbill * have been established. 26*26Sbill * Functions: 27*26Sbill * clear and free user core 28*26Sbill * turn on clock 29*26Sbill * hand craft 0th process 30*26Sbill * call all initialization routines 31*26Sbill * fork - process 0 to schedule 32*26Sbill * - process 2 to page out 33*26Sbill * - process 1 execute bootstrap 34*26Sbill * 35*26Sbill * loop at loc 13 (0xd) in user mode -- /etc/init 36*26Sbill * cannot be executed. 37*26Sbill */ 38*26Sbill main(firstaddr) 39*26Sbill { 40*26Sbill 41*26Sbill cpusid = mfpr(SID); /* get system identification */ 42*26Sbill #ifdef FASTVAX 43*26Sbill rqinit(); 44*26Sbill #endif 45*26Sbill startup(firstaddr); 46*26Sbill if (lotsfree == 0) 47*26Sbill lotsfree = LOTSFREE; 48*26Sbill 49*26Sbill /* 50*26Sbill * set up system process 0 (swapper) 51*26Sbill */ 52*26Sbill 53*26Sbill proc[0].p_p0br = (struct pte *)mfpr(P0BR); 54*26Sbill proc[0].p_szpt = 1; 55*26Sbill proc[0].p_addr = uaddr(&proc[0]); 56*26Sbill proc[0].p_stat = SRUN; 57*26Sbill proc[0].p_flag |= SLOAD|SSYS; 58*26Sbill proc[0].p_nice = NZERO; 59*26Sbill u.u_procp = &proc[0]; 60*26Sbill u.u_cmask = CMASK; 61*26Sbill clkstart(); 62*26Sbill 63*26Sbill /* 64*26Sbill * Initialize devices and 65*26Sbill * set up 'known' i-nodes 66*26Sbill */ 67*26Sbill 68*26Sbill ihinit(); 69*26Sbill cinit(); 70*26Sbill binit(); 71*26Sbill bswinit(); 72*26Sbill iinit(); 73*26Sbill rootdir = iget(rootdev, (ino_t)ROOTINO); 74*26Sbill rootdir->i_flag &= ~ILOCK; 75*26Sbill u.u_cdir = iget(rootdev, (ino_t)ROOTINO); 76*26Sbill u.u_cdir->i_flag &= ~ILOCK; 77*26Sbill u.u_rdir = NULL; 78*26Sbill u.u_dmap = zdmap; 79*26Sbill u.u_smap = zdmap; 80*26Sbill 81*26Sbill /* 82*26Sbill * make page-out daemon (process 2) 83*26Sbill * the daemon has ctopt(NSWBUF*CLSIZE*KLMAX) pages of page 84*26Sbill * table so that it can map dirty pages into 85*26Sbill * its address space during asychronous pushes. 86*26Sbill */ 87*26Sbill 88*26Sbill mpid = 1; 89*26Sbill proc[0].p_szpt = clrnd(ctopt(NSWBUF*CLSIZE*KLMAX + UPAGES)); 90*26Sbill proc[1].p_stat = SZOMB; /* force it to be in proc slot 2 */ 91*26Sbill if (newproc(0)) { 92*26Sbill proc[2].p_flag |= SLOAD|SSYS; 93*26Sbill proc[2].p_dsize = u.u_dsize = NSWBUF*CLSIZE*KLMAX; 94*26Sbill pageout(); 95*26Sbill } 96*26Sbill 97*26Sbill /* 98*26Sbill * make init process and 99*26Sbill * enter scheduling loop 100*26Sbill */ 101*26Sbill 102*26Sbill mpid = 0; 103*26Sbill proc[1].p_stat = 0; 104*26Sbill proc[0].p_szpt = CLSIZE; 105*26Sbill if (newproc(0)) { 106*26Sbill expand(clrnd((int)btoc(szicode)), P0BR); 107*26Sbill VOID copyout((caddr_t)icode, (caddr_t)0, (unsigned)szicode); 108*26Sbill /* 109*26Sbill * Return goes to loc. 0 of user init 110*26Sbill * code just copied out. 111*26Sbill */ 112*26Sbill return; 113*26Sbill } 114*26Sbill proc[0].p_szpt = 1; 115*26Sbill sched(); 116*26Sbill } 117*26Sbill 118*26Sbill /* 119*26Sbill * iinit is called once (from main) 120*26Sbill * very early in initialization. 121*26Sbill * It reads the root's super block 122*26Sbill * and initializes the current date 123*26Sbill * from the last modified date. 124*26Sbill * 125*26Sbill * panic: iinit -- cannot read the super 126*26Sbill * block. Usually because of an IO error. 127*26Sbill */ 128*26Sbill iinit() 129*26Sbill { 130*26Sbill register struct buf *cp, *bp; 131*26Sbill register struct filsys *fp; 132*26Sbill register unsigned i, j; 133*26Sbill 134*26Sbill (*bdevsw[major(rootdev)].d_open)(rootdev, 1); 135*26Sbill bp = bread(rootdev, SUPERB); 136*26Sbill cp = geteblk(); 137*26Sbill if(u.u_error) 138*26Sbill panic("iinit"); 139*26Sbill bcopy(bp->b_un.b_addr, cp->b_un.b_addr, sizeof(struct filsys)); 140*26Sbill brelse(bp); 141*26Sbill mount[0].m_bufp = cp; 142*26Sbill mount[0].m_dev = rootdev; 143*26Sbill fp = cp->b_un.b_filsys; 144*26Sbill fp->s_flock = 0; 145*26Sbill fp->s_ilock = 0; 146*26Sbill fp->s_ronly = 0; 147*26Sbill fp->s_lasti = 1; 148*26Sbill fp->s_nbehind = 0; 149*26Sbill /* on boot, read VAX TODR register (GMT 10 ms. 150*26Sbill * clicks into current year) and set software time 151*26Sbill * in 'int time' (GMT seconds since year YRREF) 152*26Sbill */ 153*26Sbill for (i = 0 , j = YRREF ; j < YRCURR ; j++) 154*26Sbill i += (SECYR + (j%4?0:SECDAY)) ; 155*26Sbill time = udiv(mfpr(TODR),100) + i ; 156*26Sbill bootime = time; 157*26Sbill } 158*26Sbill 159*26Sbill /* 160*26Sbill * This is the set of buffers proper, whose heads 161*26Sbill * were declared in buf.h. There can exist buffer 162*26Sbill * headers not pointing here that are used purely 163*26Sbill * as arguments to the I/O routines to describe 164*26Sbill * I/O to be done-- e.g. swap headers swbuf[] for 165*26Sbill * swapping. 166*26Sbill */ 167*26Sbill char buffers[NBUF][BSIZE+BSLOP]; 168*26Sbill 169*26Sbill /* 170*26Sbill * Initialize the buffer I/O system by freeing 171*26Sbill * all buffers and setting all device buffer lists to empty. 172*26Sbill * 173*26Sbill * SHOULD USE MEMALL HERE!!! 174*26Sbill */ 175*26Sbill binit() 176*26Sbill { 177*26Sbill register struct buf *bp; 178*26Sbill register struct buf *dp; 179*26Sbill register int i; 180*26Sbill struct bdevsw *bdp; 181*26Sbill 182*26Sbill bfreelist.b_forw = bfreelist.b_back = 183*26Sbill bfreelist.av_forw = bfreelist.av_back = &bfreelist; 184*26Sbill for (i=0; i<NBUF; i++) { 185*26Sbill bp = &buf[i]; 186*26Sbill bp->b_dev = NODEV; 187*26Sbill bp->b_un.b_addr = buffers[i]; 188*26Sbill bp->b_back = &bfreelist; 189*26Sbill bp->b_forw = bfreelist.b_forw; 190*26Sbill bfreelist.b_forw->b_back = bp; 191*26Sbill bfreelist.b_forw = bp; 192*26Sbill bp->b_flags = B_BUSY; 193*26Sbill brelse(bp); 194*26Sbill } 195*26Sbill for (bdp = bdevsw; bdp->d_open; bdp++) { 196*26Sbill dp = bdp->d_tab; 197*26Sbill if(dp) { 198*26Sbill dp->b_forw = dp; 199*26Sbill dp->b_back = dp; 200*26Sbill } 201*26Sbill nblkdev++; 202*26Sbill } 203*26Sbill } 204*26Sbill 205*26Sbill /* 206*26Sbill * Initialize linked list of free swap 207*26Sbill * headers. These do not actually point 208*26Sbill * to buffers, but rather to pages that 209*26Sbill * are being swapped in and out. 210*26Sbill */ 211*26Sbill bswinit() 212*26Sbill { 213*26Sbill register int i; 214*26Sbill 215*26Sbill bswlist.av_forw = &swbuf[0]; 216*26Sbill for (i=0; i<NSWBUF-1; i++) 217*26Sbill swbuf[i].av_forw = &swbuf[i+1]; 218*26Sbill swbuf[NSWBUF-1].av_forw = NULL; 219*26Sbill } 220