我有一個bootsector,旨在從軟盤鏡像中加載一個名為BOOT.BIN的檔案。但是我不知道如何從檔案中讀取一個以上的扇區。 FAT 12的位置是0x10000。 BOOT.BIN檔案將被放在0x40000處。 代碼:
foundfile:
mov word ax,[es:di 0x0f] 。
push ax ;保存檔案組
;現在來分析一下這個胖子
mov dx,second_boot_segment
mov es,dx
xor bx,bx
read_file_sector:
pop ax ;檢索檔案簇
mov byte dl,[drive_num].
mov cx,ax
添加cx,31
push ax ;保存群組號碼
mov al,1
呼叫 readdisk
pop ax ;找回群集編號
find_clusters:
push es
push bx
mov cx,fat_segment
mov es,cx
xor bx,bx
xor dx,dx
mov cx,3
mul cx
縮減ax,1
;ax現在是(clusternum*3)/2
測驗ax,1
jz short evennum
oddnum。
shr ax,4
jmp short find_clusters_continued
evennum:
and ax,0x0fff
find_clusters_continued:
cmp ax,0x0ff0
jae short finishedread ;讀取所有的檔案
mov word ax,[es:bx].
pop bx
pop es
push ax
add bx,512 ;下一個扇區
jmp short read_file_sector
讀完了。
jmp second_boot_segment:0000
jmp fatalerror
======================================================================== readdisk和其他函式:
readdisk: ;輸入:es:bx表示磁盤資料的存盤位置,al表示扇區,cx表示lba,drive_num表示驅動器 輸出:錯誤時的carry標志,ah是回傳型別,al是讀取的扇區數
push dx ;保存dx
呼叫lbatochs
mov byte dl,[drive_num]
mov ah,2
int 13h
jc 短暫重置磁盤
mov byte dl,[drive_num].
pop dx ;恢復dx
回傳
Resetdisk:
push ax
mov ah,0
int 13h
jc短fatalerror
pop ax
jmp short readdisk
fatalerror:
mov ax,0x0003 ;ah = 0 al = 3
int 10h
mov si,boot_error
mov ax,0xb800
mov es,ax
xor bx,bx
cld
printloop。
lodsb
or al,al ;是最后讀到的字符
jz short infloop
mov ah,0x0f ;顏色
mov word [es:bx],ax ;寫到vram上
add bl,2 ;只要文本小于256位元組,就可以作業。
jmp short printloop
lbatochs: ;輸入:cx為lba,輸出:cx為圓柱體和扇區,dh為頭部
push ax ;留待以后使用
push bx ;保存bx
;找到臨時變數
xor dx,dx
mov ax,cx ;ax現在有lba
push ax ;保存lba
mov word bx,[sects_per_track] ;每個軌道的扇區
div bx ;ax現在是臨時變數
;圓柱體
push ax ;保存temp
xor dx,dx
mov word bx,[num_heads] ;頭的數量
div bx ;ax現在是圓柱體
mov cx,ax ;cx存盤圓柱體
pop ax ;取回temp
cx現在是圓柱體
;頭
push dx ;頭部已經在dx中
;部門
pop dx ;彈出dx以獲得它下面的堆疊值
pop ax ;取回lba
push dx ;把dx推回去
push cx ;保存圓柱體
xor dx,dx
mov word bx,[sects_per_track]。
div bx
inc dx ;dx現在有扇區
mov bx,dx ;現在bx有扇區了
pop cx
pop dx
;把引數放在一起
mov ch,cl ;圓柱體在ch中
mov cl,bl ;部門在cl中
mov dh,dl ; head in dh
mov dl,0 ;擦除dl
pop bx ;加載舊的bx
pop ax ;加載舊的ax
ret
````這個讀盤代碼很可能沒有引起問題,因為我已經用這個方法加載了許多其他扇區。
uj5u.com熱心網友回復:
int 13h與ah=02應該采取al中的節數,見http://www.ctyme.com/intr/rb-0607.htm。 目前,在呼叫readdisk之前,你做了mov al,1,并且這個值在呼叫lbatochs時被保留下來,所以你讀到了1個扇區。
如果你想要42個扇區,請將其改為mov al, 42。 或者以其他方式重構readdisk。
uj5u.com熱心網友回復:
readfat: mov byte dl,[es:bx].
這條指令毫無意義! 在那個地方沒有什么有用的東西可以讀(還沒有)。
但是,我不知道如何從檔案中讀取一個以上的扇區。
原因是,你的代碼忘記了實際回環到readfat標簽。一旦你加載了一個下一個簇數,你需要跳回回圈的頂部,而不是立即遠跳到BOOT.BIN二進制。
注意,僅僅插入缺少的jmp是不夠的! 因為必要的add bx, 512會被pop bx指令破壞,所有的向量將到達彼此的頂部。
因為
這個讀取磁盤的代碼很可能不會導致問題,因為我已經用它加載了許多其他扇區。
我沒有調查你代碼的這一部分。看看接下來的重寫是否對你有用:
foundfile:
mov ax, [es:di 0x0F] ; dirFirstCluster
mov bx, 0x4000
mov es, bx
xor bx, bx
READSECTOR:
push es ; (1)
push bx ; (2)
推送ax;(3)
加ax, 31
mov cx, ax
mov al, 1
呼叫readdisk
pop ax ; (3)
mov dx, 3
mul dx
shr ax, 1
jnc short evenclus
oddclus。
縮減ax, 4
偶數。
and ax, 0x0FFF
cmp ax, 0x0FF8
jae finishedread
mov bx, 0x1000 ; FAT
mov es, bx
mov bx, ax
mov ax, [es:bx] ;跟隨群集的數量
pop bx ; (2)
pop es ; (1)
JMP READSECTOR <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<;<;<;<;<;<;<;<;<;<;&;<;&;&;&;&。
讀完了。
jmp 0x4000:0000
jmp fatalerror
uj5u.com熱心網友回復:
我已經想出了如何自己寫回圈的方法。
下面是代碼。
如果你想看的話,下面是代碼:
foundfile:
mov word ax,[es:di 0x0f] 。
push ax ;保存檔案組
;現在來分析一下這個胖子
mov dx,second_boot_segment
mov es,dx ;second_boot_segment
xor bx,bx ;es的偏移量
xor di,di ;讀取fat時es的偏移量
read_file_sector:
pop cx ;獲取檔案簇并放入cx中
add cx,31
push ax ;再次保存集群
mov byte al,[sects_per_cluster] ;集群大小
呼叫 readdisk
pop ax ;取回集群
推送es
find_cluster:
mov cx,3
xor dx,dx
mul cx ;將群集數乘以3
shr ax,1 ;將群集數除以2
mov cx,fat_segment
mov es,cx
mov di,ax
mov word ax,[es:di]
jnc短的evenclus
oddclus。
縮減ax,4
jmp short continue_findcluster
偶數。
and ax,0x0fff
continue_findcluster:
cmp ax,0x0ff0
jae finishedread
添加bx,512
pop es
push ax ;為回圈保存集群
jmp short read_file_sector
讀完了。
jmp second_boot_segment:0000
jmp fatalerror
轉載請註明出處,本文鏈接:https://www.uj5u.com/gongcheng/320410.html
標籤:
