??xml version="1.0" encoding="utf-8" standalone="yes"?>
那么如果一个段是expandupward的,他的offset只能?到limitQ而如果是expanddownward的,offset是从limit到FFFFQ且该栈的增长方向是limit-->FFFFQ即Q数据在内存中L从低地址攑ֈ高地址
今天受益匪浅.....我塞Q如果不是在|络上搜索到的这句话Q我自己~写的Kernelq程怎么也调试不好?br />今天太高兴了Q终于把Kernel的进E机制调整好了!Q!截个图,庆祝一下?br />不过截图有个错误Q就是应该是Process的,而不是ThreadQ这两个东西有本质区别?br />
]]>
org 0x100
[bits 16]
jmp loaderStart
_GRAPH_SEG_OFFSET_ equ 0xb800
_RootEntCnt_ equ 0xe0
BS_OEMName db 'XXXXXXXX'
BPB_BytsPerSec dw 0x200
BPB_SecPerClus db 1
BPB_RsvdSecCnt dw 1
BPB_NumFATs db 2
BPB_RootEntCnt dw _RootEntCnt_
BPB_totSec16 dw 0xb40
BPB_Media db 0xf0
BPB_FATSz16 dw 9
BPB_SecPerTrk dw 0x12
BPB_NumHeads dw 2
BPB_HiddSec dd 0
BPB_totSec32 dd 0
BS_DrvNum db 0
BS_Reserved1 db 0
BS_BootSig db 0x29
BS_VolID dd 0
BS_VolLab db '11111111111'
BS_FileSysType db 'FAT12 '
parameters:
screenPo dd 0
STR_LEN equ 12
bootStr db 'Loading... '
noLoaderStr db 'No Kernel...'
ready db 'Ready '
KernelBase equ 0x8000
KernelOffset equ 0x0
rootEntryNum db _RootEntCnt_
loaderName db 'KERNEL BIN'
loaderStart:
mov ax,cs
mov ds,ax
mov es,ax
mov ss,ax
mov sp,0100
mov ax,_GRAPH_SEG_OFFSET_
mov gs,ax
mov dh,0
call displayStr
xor ah,ah
mov dl,[BS_DrvNum]
int 0x13
mov ax,KernelBase
mov es,ax
mov bx,0
mov ax,19
mov cl,14
call readSector
xor edi,edi
anotherFile:
xor esi,esi
cmp byte [rootEntryNum],0
je noLoader
nextChar:
mov al,byte [es:edi]
cmp byte [ds:loaderName+si],al
jne notThisFile
cmp si,10
je found
inc esi
inc edi
jmp nextChar
notThisFile:
shr edi,5
inc edi
shl edi,5
dec byte [rootEntryNum]
jmp anotherFile
noLoader:
mov dh,1
call displayStr
jmp $
found:
mov dh,2
call displayStr
mov ax,word [es:edi+(0x10)]
mov cl,1
push ax
mov ax,KernelBase
mov es,ax
mov ebx,KernelOffset
pop ax
readEntry:
cmp ax,0xfff
je readEnd
push ax
add ax,19+14-2
call readSector
pop ax
add ebx,512
call getFATEntry
jmp readEntry
readEnd:
jmp toProtectMode
displayStr:
; dh: String index
push cx
push ax
push bx
push esi
push edi
mov cx,STR_LEN
mov edi,dword [screenPo]
mov esi,bootStr
xor eax,eax
mov al,dh
mov bl,STR_LEN
mul bl
add esi,eax
.1:
lodsb
mov [gs:edi],al
inc edi
inc edi
loop .1
mov dword [screenPo],edi
pop edi
pop esi
pop bx
pop ax
pop cx
ret
readSector: ;ax: starting sector cl:number of sectors
; ah 0x2 al:number of sector to read
; bx: es:bx
; ch:cylinder cl:start sector
; dh:head num dl:Drive
push bp
mov bp,sp
push cx
push dx
push ax
mov dl,[BPB_SecPerTrk]
div dl
mov cl,ah
inc cl
mov ch,al
shr ch,1
mov dh,al
and dh,1
mov dl,byte [BS_DrvNum]
.1:
mov ah,2
mov al,byte [bp-2]
int 0x13
jc .1
pop ax
pop dx
pop cx
pop bp
ret
getFATEntry:
FATBaseInMem equ 0x7000
;ax is the entry number
;return ax is the next entry
push es
push bx
push dx
push cx
mov bx,FATBaseInMem
mov es,bx
mov bx,3
mul bx ;dx:ax
mov bx,2
div bx ;dx is the rest
push dx
xor dx,dx
mov bx,[BPB_BytsPerSec]
div bx
mov cl,2
xor bx,bx
add ax,1
call readSector
mov bx,dx; mov byte index
pop dx
xor ax,ax
cmp dx,0
jne oddPart
mov ax,word [es:bx]
and ax,0x0fff
jmp after
oddPart:
mov ax,word [es:bx]
shr ax,4
after:
pop cx
pop dx
pop bx
pop es
ret
toProtectMode:
jmp start
%macro Descriptor 3
dw %2 & 0xffff
dw %1 & 0xffff
db (%1 >> 16) & 0xff
dw ((%2 & 0x0f0000) >> 8) | (%3 & 0xf0ff)
db (%1 >> 24) & 0xff
%endmacro
DummyGDT: Descriptor 0,0,0
CodeGDT: Descriptor 0,0xfffff,1100000010011010b
DataGDT: Descriptor 0,0xfffff,1000000010010010b
ScreenGDT: Descriptor 0xb8000,0xffff,0000000010010010b
GDTPtr dw $-DummyGDT-1
dd 0x9000*0x10+DummyGDT
CodeSelector equ CodeGDT-DummyGDT
DataSelector equ DataGDT-DummyGDT
ScreenSelector equ ScreenGDT-DummyGDT
start:
call killMotor
cli
mov dh,2
call displayStr
lgdt [GDTPtr]
in al,0x92
or al,10b
out 0x92,al
mov eax,cr0
or eax,1
mov cr0,eax
jmp dword CodeSelector:(0x9000*0x10+ProtectMode)
killMotor:
push dx
mov dx,0x3f2
mov al,0
out dx,al
pop dx
ret
[bits 32]
ProtectMode:
mov ax,ScreenSelector
mov gs,ax
xor edi,edi
.again:
inc byte [gs:edi]
jmp .again
mov ah,0
mov dl,0
int 0x13
mov ax,0x7f0
mov es,ax
mov ah,2
mov ch,0
mov dh,0
mov al,1
mov cl,2
mov dl,0
mov ebx,0
int 0x13
mov ax,0xb800
mov gs,ax
jmp 0x7f00
times 510-($-$$) db 0
dw 0xaa55
again:
.1:
inc byte [gs:8]
jmp .1
times 1024-($-$$) db 0
q个E序的执行成功说明有一D늚内存地址是不能够被int 0x13讉K的。但是具体是Z么需要进一步思考?/p>
mov ax,0x7d00; original: mov ax,0xb800
mov es,ax
mov ah,2
mov ch,0
mov dh,0
mov al,1
mov cl,1
mov dl,0
mov ebx,0
int 0x13
mov ah,0x4c
int 0x21
q么短短的程?在原先把盘W一扇区的数据蝲入到B800Q?000从屏q显C出来却执行完成后B800Q?000却没有数据,而如果修改了地址?d00却可以,q是Z么呢Q?/font>
需要的命o行:
nasm -f elf -o dest.o src.asm
gcc -c -o dest2.o src2.c (-c 的意思是仅仅compile)
ld -s -o final.o dest.o dest1.o
bootStart:
xor ax,ax
mov ds,ax
mov ss,ax
mov sp,0x7c00
mov bp,sp
; Init the DRIVE
; Boot drive number is stored in DX(lower part)
mov [drive],dl
again:
mov cx,200
againChar:
call putString
loop againChar
mov al,[page]
inc al
mov [page],al
cmp al,0x8
jne again
mov cx,0x9
xor al,al
mov [page],al
check:
mov ah,0x05
int 0x10
xor ah,ah
int 0x16
mov al,[page]
inc al
mov [page],al
loop check
db 0xea
dw 0x0000, 0xffff
data db '012345678'
putString:
mov si,[page]
mov al,[data+si]
mov ah,0x0a
mov bl,0x07
mov bh,[page]
int 0x10
retn
;************************
; Here are the data part
;************************
drive db 0
page db 0
times 510-($-$$) db 0
dw 0xaa55