Subversion Repositories Kolibri OS

Rev

Rev 1505 | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
796 shurf 1
; FAT12 boot sector for Kolibri OS
2
;
3
; Copyright (C) Alex Nogueira Teixeira
4
; Copyright (C) Diamond
5
; Copyright (C) Dmitry Kartashov aka shurf
6
;
7
; Distributed under GPL, see file COPYING for details
8
;
9
; Version 1.0
10
 
11
lf		equ	0ah
12
cr		equ	0dh
13
 
14
pos_read_tmp	equ	0700h			;position for temporary read
15
boot_program	equ	07c00h			;position for boot code
16
seg_read_kernel	equ	01000h			;segment to kernel read
17
 
18
	jmp	start_program
19
	nop
20
 
21
; Boot Sector and BPB Structure
22
include 'floppy1440.inc'
23
;include 'floppy2880.inc'
24
 
25
start_program:
26
 
27
	xor	ax,ax
28
	mov	ss,ax
29
	mov	sp,boot_program
30
	push	ss
31
	pop	ds
32
 
33
	; print loading string
34
	mov	si,loading+boot_program
35
loop_loading:
36
	lodsb
37
	or	al,al
38
	jz	read_root_directory
39
	mov	ah,0eh
40
	mov	bx,7
41
	int	10h
42
	jmp	loop_loading
43
 
44
read_root_directory:
45
	push	ss
46
	pop	es
47
 
48
	; reading root directory
1940 art_zh 49
	; al=count root dir sectors !!!! TODO: al, max 255 sectors !!!!
796 shurf 50
	mov	ah,2				; read
51
	push	ax
52
 
53
	mov	ax,word [FirstRootDirSecNum+boot_program]
54
	call	conv_abs_to_THS			; convert abs sector (AX) to BIOS T:H:S (track:head:sector)
55
	pop	ax
56
	mov	bx,pos_read_tmp			; es:bx read buffer
57
	call	read_sector
58
 
59
	mov	si,bx				; read buffer address: es:si
60
	mov	ax,[RootDirSecs+boot_program]
61
	mul	word [BPB_BytsPerSec+boot_program]
62
	add	ax,si				; AX = end of root dir. in buffer pos_read_tmp
63
 
64
	; find kernel file in root directory
65
loop_find_dir_entry:
66
	push	si
67
	mov	cx,11
68
	mov	di,kernel_name+boot_program
69
	rep	cmpsb				; compare es:si and es:di, cx bytes long
70
	pop	si
71
	je	found_kernel_file
72
	add	si,32				; next dir. entry
73
	cmp	si,ax				; end of directory
74
	jb	loop_find_dir_entry
1940 art_zh 75
        jmp     $
796 shurf 76
 
77
	; === KERNEL FOUND. LOADING... ===
78
 
79
found_kernel_file:
80
	mov	bp,[si+01ah]			; first cluster of kernel file
81
	; 
82
	mov	[cluster1st+boot_program],bp	; starting cluster of kernel file
83
	; <\diamond>
84
 
85
	; reading first FAT table
86
	mov	ax,word [BPB_RsvdSecCnt+boot_program]	; begin first FAT abs sector number
87
	call	conv_abs_to_THS			; convert abs sector (AX) to BIOS T:H:S (track:head:sector)
88
	mov	bx,pos_read_tmp			; es:bx read position
89
	mov	ah,2				; ah=2 (read)
90
	mov	al, byte [BPB_FATSz16+boot_program]	; FAT size in sectors (TODO: max 255 sectors)
91
	call	read_sector
92
 
93
	mov	ax,seg_read_kernel
94
	mov	es,ax
1940 art_zh 95
	xor	bx,bx				; es:bx = 1000h:0000h
796 shurf 96
 
97
	; reading kernel file
98
loop_obtains_kernel_data:
1940 art_zh 99
	call	obtain_cluster	                ; read one cluster of file
796 shurf 100
 
1940 art_zh 101
	mov	ax,es
102
	add	ax,seg_inc_per_cluster          ; << =32(1.44M) or 64(2.88) >>
103
	mov	es,ax	                ; add one cluster length to segment:offset
796 shurf 104
 
105
	mov	di,bp
106
	shr	di,1
107
	pushf
108
	add	di,bp				; di = bp * 1.5
109
	add	di,pos_read_tmp
110
	mov	ax,[di]				; read next entry from FAT-chain
111
	popf
112
	jc	move_4_right
113
	and	ax,0fffh
114
	jmp	verify_end_sector
115
move_4_right:
1940 art_zh 116
	shr	ax,4
796 shurf 117
verify_end_sector:
118
	cmp	ax,0ff8h			; last cluster
119
	jae	execute_kernel
120
	mov	bp,ax
121
	jmp	loop_obtains_kernel_data
122
 
123
execute_kernel:
124
	; 
125
	mov	ax,'KL'
126
	push	0
127
	pop	ds
128
	mov	si,loader_block+boot_program
129
	; 
130
	push	word	seg_read_kernel
131
	push	word	0
132
	retf					; jmp far 1000:0000
133
 
134
 
135
;------------------------------------------
136
	; loading cluster from file to es:bx
137
obtain_cluster:
138
	; bp - cluster number to read
139
	; carry = 0 -> read OK
140
	; carry = 1 -> read ERROR
141
 
142
	; print one dot
143
	push	bx
144
	mov	ax,0e2eh			; ah=0eh (teletype), al='.'
145
	xor	bh,bh
1940 art_zh 146
	int	10h
147
;	jc	$               		; error
148
        pop     bx
796 shurf 149
 
1940 art_zh 150
writesec:
796 shurf 151
	; convert cluster number to sector number
152
	mov	ax,bp				; data cluster to read
153
	sub	ax,2
1940 art_zh 154
;>>	add	ax,ax                           ; << only for 2.88M disks! >>
155
	add	ax,word [data_start+boot_program]
796 shurf 156
	call	conv_abs_to_THS			; convert abs sector (AX) to BIOS T:H:S (track:head:sector)
1940 art_zh 157
 
796 shurf 158
patchhere:
1940 art_zh 159
	mov	ax,0x201			; ah=2 (read)
160
;>>                    	                        ; al=1(1.44) or 2(2.88)
796 shurf 161
	; read sector from disk
1940 art_zh 162
 
796 shurf 163
read_sector:
164
	push	ax bx cx dx
165
	int	13h
1940 art_zh 166
	jc	$                               ; error: stop here
796 shurf 167
	pop	dx cx bx ax
168
	retn
1940 art_zh 169
 
796 shurf 170
;------------------------------------------
1940 art_zh 171
	; converts abs. sector number (AX) to BIOS T:H:S
172
	; Returns: {pre.track number = (AX / BPB_SecPerTrk)}
173
	;	ch - track number  = pre.track number/2
174
        ;       cl - sector number = (abs.sector%BPB_SecPerTrk)+1
175
	;	dh - head number   = pre.track number%BPB_NumHeads
176
	;	dl - drive number (0 = a:)
796 shurf 177
conv_abs_to_THS:
1940 art_zh 178
	mov	cx,word [BPB_SecPerTrk+boot_program]    ; << 18 or 36 >>
796 shurf 179
	xor	dx,dx
1940 art_zh 180
	div	cx
796 shurf 181
	inc	dx
1940 art_zh 182
	mov	cl, dl				; cl = sector number
183
        xor     dx, dx
184
        shr     ax, 1
185
        rol     dx, 1           		; dh = head number
186
        mov     ch, al				; ch = track number
796 shurf 187
	retn
188
;------------------------------------------
189
 
190
loading		db	cr,lf,'Starting system ',00h
1940 art_zh 191
;error_message	db	13,10
192
kernel_name	db	'KERNEL  MNT',00h
193
FirstRootDirSecNum	dw	19      ; 1st sector of the root dir
194
RootDirSecs	dw	14              ; << = 14(1.44M) or 15(2.88M) >>
195
data_start	dw	33		; << = 33(1.44M) or 34(2.88M) >>
796 shurf 196
 
197
; 
198
write1st:
199
	push	cs
200
	pop	ds
201
	mov	byte [patchhere+1+boot_program], 3	; change ah=2 to ah=3
1940 art_zh 202
	mov	bp,[cluster1st+boot_program]
796 shurf 203
	push	1000h
204
	pop	es
205
	xor	bx,bx
206
	call	writesec
207
	mov	byte [patchhere+1+boot_program], 2	; change back ah=3 to ah=2
208
	retf
1940 art_zh 209
 
210
cluster1st	dw	?       ; 1st cluster of kernel.mnt
796 shurf 211
loader_block:
212
		db	1
213
		dw	0
214
		dw	write1st+boot_program
215
		dw	0
216
; <\diamond>
1940 art_zh 217
 
796 shurf 218
times	0x1fe-$ db 00h
219
 
220
	db	55h,0aah 			;boot signature