linux0.11学习3之head

      下面给出head部分的nasm源代码。其中的stack_start,main,printk都只是用于测试,,并不是linux中的,因为现在main等函数还没有。

head.asm

bits 32
[section .text]

global _idt,_gdt,_pg_dir,_tmp_floppy_area

_pg_dir:
startup_32:
mov eax,0x10  ;设置段寄存器
mov ds,ax
mov es,ax
mov fs,ax
mov gs,ax
mov ss,ax
lss esp,[stack_start];此处的stack_start为测试用的,不是linux中的


call setup_idt ;建立idt,gdt表
call setup_gdt

mov eax,0x10   ;重新设置段寄存器
mov ds,ax
mov es,ax
mov fs,ax
mov gs,ax
mov ss,ax

lss esp,[stack_start];此处的stack_start为测试用的,不是linux中的

   xor eax,eax   ;测试A20地址线是否打开
s1:
   inc eax
   mov [0x000000],eax
   cmp eax,[0x100000]
   je s1

mov eax,cr0    ;检测是否有数学协处理器
and eax,0x80000011
or  eax,2
mov cr0,eax
call check_87
jmp after_page_table

check_87:
fninit
fstsw ax
cmp al,0
je s2
mov eax,cr0
xor eax,6
mov cr0,eax
ret
align 32
s2: db 0xDB,0xE4
   ret


setup_idt:    ;建立idt表,并加载
lea edx,[ignore_int]
mov eax,0x00080000
mov ax,dx
mov dx,0x8E00
lea edi,[_idt]
mov ecx,256

rp_sidt:
mov [edi],eax
mov [4+edi],edx
add edi,8
dec ecx
jne rp_sidt
lidt [idt_descr]
ret


setup_gdt:     ;加载gdt
lgdt [gdt_descr]
ret



times 0x1000-($-$$) db 0
pg0:

times 0x2000-($-$$) db 0
pg1:

times 0x3000-($-$$) db 0
pg2:

times 0x4000-($-$$) db 0
pg3:

times 0x5000-($-$$) db 0



_tmp_floppy_area:
times 1024 db 0


after_page_table:

push 0
push 0
push 0
push L6
push main ;此处的main为测试用的,不是linux中的
jmp setup_paging

L6:
jmp L6


int_msg:
db "Unknown interrupt\n\r"


align 32
ignore_int:   ;中断处理程序
push eax
push ecx
push edx
push ds
push ds
push fs

mov eax,0x10
mov ds,ax
mov es,ax
mov fs,ax
push int_msg
;call printk

pop eax
pop fs
pop es
pop ds
pop edx
pop ecx
pop eax
iret

align 32
setup_paging:
mov ecx,1024*5 ;把页目录表和4个页表清零
xor eax,eax
xor edi,edi

cld
rep
stosd

;初始化页目录表
mov dword [_pg_dir],pg0+7
mov dword [_pg_dir+4],pg1+7
mov dword [_pg_dir+8],pg2+7
mov dword [_pg_dir+12],pg3+7

;初始化页表
mov edi,pg3+4092
mov eax,0xfff007

std
s3: 
stosd
   sub eax,0x1000
   jge s3

xor eax,eax
mov cr3,eax

mov eax,cr0
or eax,0x80000000
mov cr0,eax

ret

align 32
dw 0
idt_descr:
dw 256*8-1
dd _idt


align 32
dw 0
gdt_descr:
dw 256*8-1
dd _gdt

align 64
_idt: times 256 dq 0

_gdt:
	dq 0x0000000000000000	
	dq 0x00c09a0000000fff	
	dq 0x00c0920000000fff	
	dq 0x0000000000000000	
	times 252 dq 0

			
main:
mov edi,(80 * 11 + 0)*2 +0xb8000 
mov ah,0Ch
mov al,'f'
mov [gs:edi],ax
jmp $


times 512 db 0
stack_start:
dd stack_start
dd 0x10

  
将head.asm编译为.bin文件。然后,把head.bin写到软盘的第6个扇区开始的位置(即前面文章所提到的system.bin,在这里不把system.bin写到软盘。这里只是测试一下head,真正的应该是把head连接到system的最开始部分).
结果图:


  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 2
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值