source: trunk/minix/boot/jumpboot.s@ 20

Last change on this file since 20 was 9, checked in by Mattia Monga, 14 years ago

Minix 3.1.2a

File size: 7.4 KB
Line 
1! jumpboot 1.0 - Jump to another bootstrap Author: Kees J. Bot
2! 14 Apr 1999
3!
4! This code may be placed into any free boot sector, like the first sector
5! of an extended partition, a file system partition other than the root,
6! or even the master bootstrap. It will load and run another bootstrap whose
7! disk, partition, and slice number (not necessarily all three) are patched
8! into this code by installboot. If the ALT key is held down when this code
9! is booted then you can type the disk, partition, and slice numbers manually.
10! The manual interface is default if no numbers are patched in by installboot.
11!
12
13 o32 = 0x66 ! This assembler doesn't know 386 extensions
14 LOADOFF = 0x7C00 ! 0x0000:LOADOFF is where this code is loaded
15 BUFFER = 0x0600 ! First free memory
16 PART_TABLE = 446 ! Location of partition table within master
17 PENTRYSIZE = 16 ! Size of one partition table entry
18 MAGIC = 510 ! Location of the AA55 magic number
19
20 ! <ibm/partition.h>:
21 MINIX_PART = 0x81
22 sysind = 4
23 lowsec = 8
24
25
26.text
27
28! Find and load another bootstrap and jump to it.
29jumpboot:
30 xor ax, ax
31 mov ds, ax
32 mov es, ax
33 cli
34 mov ss, ax ! ds = es = ss = Vector segment
35 mov sp, #LOADOFF
36 sti
37
38! Move this code to safety, then jump to it.
39 mov si, sp ! si = start of this code
40 mov di, #BUFFER ! di = Buffer area
41 mov cx, #512/2 ! One sector
42 cld
43 rep movs
44 jmpf BUFFER+migrate, 0 ! To safety
45migrate:
46
47 mov bp, #BUFFER+guide ! Patched guiding characters
48altkey:
49 movb ah, #0x02 ! Keyboard shift status
50 int 0x16
51 testb al, #0x08 ! Bit 3 = ALT key
52 jz noalt ! ALT key pressed?
53again:
54 mov bp, #zero ! Ignore patched stuff
55noalt:
56
57! Follow guide characters to find the boot partition.
58 call print
59 .ascii "d?\b\0" ! Initial greeting
60
61! Disk number?
62disk:
63 movb dl, #0x80 - 0x30 ! Prepare to add an ASCII digit
64 call getch ! Get number to tell which disk
65 addb dl, al ! dl = 0x80 + (al - '0')
66 jns n0nboot ! Result should be >= 0x80
67 mov si, #BUFFER+zero-lowsec ! si = where lowsec(si) is zero
68 cmpb (bp), #0x23 ! Next guide character is '#'?
69 jne notlogical
70 lea si, 1-lowsec(bp) ! Logical sector offset follows '#'
71notlogical:
72 call load ! Load chosen sector of chosen disk
73 cmpb (bp), #0x23
74 je boot ! Run bootstrap if a logical is chosen
75
76 call print ! Intro to partition number
77 .ascii "p?\b\0"
78
79part:
80 call getch ! Get character to tell partition
81 call gettable ! Get partition table
82 call sort ! Sort partition table
83 call choose_load ! Compute chosen entry and load
84
85 cmpb sysind(si), #MINIX_PART ! Minix subpartition table possible?
86 jne waitboot
87
88 call print ! Intro to slice number
89 .ascii "s?\b\0"
90
91slice:
92 call getch ! Get character to tell slice
93 call gettable ! Get partition table
94 call choose_load ! Compute chosen entry and load
95
96waitboot:
97 call print ! Intro to nothing
98 .ascii " ?\b\0"
99 call getch ! Supposed to type RETURN now
100n0nboot:jmp nonboot ! Sorry, can't go further
101
102! Get a character, either the patched-in, or one from the keyboard.
103getch:
104 movb al, (bp) ! Get patched-in character
105 testb al, al
106 jz getkey
107 inc bp
108 jmp gotkey
109getkey: xorb ah, ah ! Wait for keypress
110 int 0x16
111gotkey: testb dl, dl ! Ignore CR if disk number not yet set
112 jns putch
113 cmpb al, #0x0D ! Carriage return?
114 je boot
115 !jmp putch
116
117! Print a character
118putch: movb ah, #0x0E ! Print character in teletype mode
119 mov bx, #0x0001 ! Page 0, foreground color
120 int 0x10
121 ret
122
123! Print a message.
124print: mov cx, si ! Save si
125 pop si ! si = String following 'call print'
126prnext: lodsb ! al = *si++ is char to be printed
127 testb al, al ! Null marks end
128 jz prdone
129 call putch
130 jmp prnext
131prdone: xchg si, cx ! Restore si
132 jmp (cx) ! Continue after the string
133
134! Return typed (or in patched data) means to run the bootstrap now in core!
135boot:
136 call print ! Make line on screen look proper
137 .ascii "\b \r\n\0"
138 jmp LOADOFF-BUFFER ! Jump to LOADOFF
139
140! Compute address of chosen partition entry from choice al into si, then
141! continue to load the boot sector of that partition.
142choose_load:
143 subb al, #0x30 ! al -= '0'
144 cmpb al, #4 ! Only four partitions
145 ja n0nboot
146 movb ah, #PENTRYSIZE
147 mulb ah ! al *= PENTRYSIZE
148 add ax, #BUFFER+PART_TABLE
149 mov si, ax ! si = &part_table[al - '0']
150 movb al, sysind(si) ! System indicator
151 testb al, al ! Unused partition?
152 jz n0nboot
153 !jmp load ! Continue to load boot sector
154
155! Load boot sector of the current partition.
156load:
157 push dx ! Save drive code
158 push es ! Next call sets es
159 movb ah, #0x08 ! Code for drive parameters
160 int 0x13
161 pop es
162 andb cl, #0x3F ! cl = max sector number (1-origin)
163 incb dh ! dh = 1 + max head number (0-origin)
164 movb al, cl ! al = cl = sectors per track
165 mulb dh ! dh = heads, ax = heads * sectors
166 mov bx, ax ! bx = sectors per cylinder = heads * sectors
167 mov ax, lowsec+0(si)
168 mov dx, lowsec+2(si) ! dx:ax = sector within drive
169 cmp dx, #[1024*255*63-255]>>16 ! Near 8G limit?
170 jae bigdisk
171 div bx ! ax = cylinder, dx = sector within cylinder
172 xchg ax, dx ! ax = sector within cylinder, dx = cylinder
173 movb ch, dl ! ch = low 8 bits of cylinder
174 divb cl ! al = head, ah = sector (0-origin)
175 xorb dl, dl ! About to shift bits 8-9 of cylinder into dl
176 shr dx, #1
177 shr dx, #1 ! dl[6..7] = high cylinder
178 orb dl, ah ! dl[0..5] = sector (0-origin)
179 movb cl, dl ! cl[0..5] = sector, cl[6..7] = high cyl
180 incb cl ! cl[0..5] = sector (1-origin)
181 pop dx ! Restore drive code in dl
182 movb dh, al ! dh = al = head
183 mov bx, #LOADOFF ! es:bx = where sector is loaded
184 mov ax, #0x0201 ! ah = Code for read / al = one sector
185 int 0x13
186 jmp rdeval ! Evaluate read result
187bigdisk:
188 mov bx, dx ! bx:ax = dx:ax = sector to read
189 pop dx ! Restore drive code in dl
190 push si ! Save si
191 mov si, #BUFFER+ext_rw ! si = extended read/write parameter packet
192 mov 8(si), ax ! Starting block number = bx:ax
193 mov 10(si), bx
194 movb ah, #0x42 ! Extended read
195 int 0x13
196 pop si ! Restore si to point to partition entry
197 !jmp rdeval
198rdeval:
199 jnc rdok
200rderr:
201 call print
202 .ascii "\r\nRead error\r\n\0"
203 jmp again
204rdok:
205 cmp LOADOFF+MAGIC, #0xAA55
206 je sigok ! Signature ok?
207nonboot:
208 call print
209 .ascii "\r\nNot bootable\r\n\0"
210 jmp again
211sigok:
212 ret
213
214! Get the partition table into my space.
215gettable:
216 mov si, #LOADOFF+PART_TABLE
217 mov di, #BUFFER+PART_TABLE
218 mov cx, #4*PENTRYSIZE/2
219 rep movs
220 ret
221
222! Sort the partition table.
223sort:
224 mov cx, #4 ! Four times is enough to sort
225bubble: mov si, #BUFFER+PART_TABLE ! First table entry
226bubble1:lea di, PENTRYSIZE(si) ! Next entry
227 cmpb sysind(si), ch ! Partition type, nonzero when in use
228 jz exchg ! Unused entries sort to the end
229inuse: mov bx, lowsec+0(di)
230 sub bx, lowsec+0(si) ! Compute di->lowsec - si->lowsec
231 mov bx, lowsec+2(di)
232 sbb bx, lowsec+2(si)
233 jae order ! In order if si->lowsec <= di->lowsec
234exchg: movb bl, (si)
235 xchgb bl, PENTRYSIZE(si) ! Exchange entries byte by byte
236 movb (si), bl
237 inc si
238 cmp si, di
239 jb exchg
240order: mov si, di
241 cmp si, #BUFFER+PART_TABLE+3*PENTRYSIZE
242 jb bubble1
243 loop bubble
244 ret
245
246.data
247
248! Extended read/write commands require a parameter packet.
249ext_rw:
250 .data1 0x10 ! Length of extended r/w packet
251 .data1 0 ! Reserved
252 .data2 1 ! Blocks to transfer (just one)
253 .data2 LOADOFF ! Buffer address offset
254 .data2 0 ! Buffer address segment
255 .data4 0 ! Starting block number low 32 bits (tbfi)
256zero: .data4 0 ! Starting block number high 32 bits
257
258 .align 2
259guide:
260! Guide characters and possibly a logical partition number patched here by
261! installboot, up to 6 bytes maximum.
Note: See TracBrowser for help on using the repository browser.