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