进入保护模式, 使用分页机制出错
boot.S,设置GDT表, copy kernel 到0x0000, 进入保护模式.code16
.text
.global _start
.set CODE_SEL, 0x08
.set DATA_SEL, 0x10
.set GDT_ADDR, 0x80000
.set GDT_ENTRIES, 3
.set GDT_SIZE, (8*GDT_ENTRIES)
_start:
jmpl $0x7c0, $start2
gdt:
.quad 0x0000000000000000 # null selector
.quad 0x00cf9a000000ffff # cs base 0x00000000 limit 0xfffff code read/exec
.quad 0x00cf92000000ffff # ds base 0x00000000 limit 0xfffff data read/write
gdt_48:
.word .-gdt
.long GDT_ADDR
start2:
movw %cs, %ax
movw %ax, %ds
movw %ax, %es
movw %ax, %ss
movw $0x7c00, %sp
cli
cld
movb $0x0f, %ah
xorb %al, %al
int $0x10
movb $0x00, %ah
int $0x10
#target address
movw $0x1000, %ax
movw %ax, %es
movw $0x00, %bx
movb $0x02, %ah # ah: read disk
movb $0x01, %al # al: count of sectors
movb $0x00, %ch # ch: track
movb $0x02, %cl # cl: cylinder
# dl: driver num
int $0x13 # 13h: disk I/O
# ->
# move kernel to 0x0000:0000
movw $0x1000,%ax
movw %ax, %ds
movw $0x0000,%ax
movw %ax, %es
xorw %si, %si
xorw %di, %di
movw $(512>>2),%cx
rep
movsl
# move gdt to GDT_ADDR
movw $0x7c0, %ax
movw %ax, %ds # reset ds to 0x07c0
movw $gdt, %si
movw $GDT_ADDR>>4,%ax
movw %ax, %es
xorw %di, %di
movw $GDT_SIZE>>2,%cx
rep
movsl
enable_a20:
inb $0x64, %al
testb $0x2, %al
jnz enable_a20
movb $0xbf, %al
outb %al, $0x64
lgdt gdt_48
# set PE=1
movl %cr0, %eax
orl $0x1, %eax # PE = 1
movl %eax, %cr0
ljmp $CODE_SEL, $0x0
.org 510
.word 0xAA55
kernel.S, 设置分页页目录,页表,设置CR3,CR0,
然后怎么才能叫分配出一个页来使用?
就是说需要手动设置页表吗?
.text
.global _start
.org 0
_start:
jmp start2
.set CODE_SEL, 0x08 # cs 00001 000
.set DATA_SEL, 0x10 # ds 00010 000
start2:
movl $DATA_SEL, %eax
movw %ax, %ds
movw %ax, %es
movw %ax, %fs
movw %ax, %ss
movw %ax, %gs
movl $0xa0000, %esp
cld
# 0x80000 - 0x80000+GDT_SIZE : GDT
# 0x81000 - 0x82000 : page_dir
# 0x82000 - 0x83000 : page_table
# initialize page_dir 0x81000 -> 0x82000
movl $0x81000, %eax
movl $0x82007, (%eax) # page_dir 只用到这一项,其他都无效
movl $1023, %ecx
1:
addl $4, %eax
movl $6, (%eax) # page_dir 无效
decl %ecx
jnz 1b
# initialize page_table 0x82000 -> 0x83000 共表示4M
movl $0x82000, %eax
movl $0x0, %ebx
movl $1024, %ecx
next:
movl %ebx, (%eax)
addl $7, (%eax) # 加上权限就没有错误了。
addl $4, %eax
addl $0x1000, %ebx
decl %ecx
jnz next
# enable cr3
movl $0x81000, %eax
movl %eax, %cr3
movl %cr0, %eax
orl $0x80000000, %eax
movl %eax, %cr0
loop:
jmp loop
/*
.org 0x81000
.long 0x82007 # 82000 | 7
.rept 1023
.long 6 # 00000 | 6
.endr
.org 0x82000
.org 0x83000
*/
Makefile:
AS=as -Iinclude
LD=ld
.S.o:
$(AS) $< -o $*.o
all: Image
Image: boot kernel
cat boot kernel.o > Image
boot: boot.o
$(LD) --oformat binary -N -e _start -Ttext 0x0000 -o boot $<
kernel: kernel.o
$(LD) --oformat binary -N -e _start -Ttext 0x0000 -o $@ $<
clean:
rm -f Image boot boot.o kernel kernel.o
[ 本帖最后由 anhongkui 于 2007-6-20 15:12 编辑 ]
页:
[1]