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