日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問(wèn) 生活随笔!

生活随笔

當(dāng)前位置: 首頁(yè) > 运维知识 > windows >内容正文

windows

【OS学习笔记】二十 保护模式六:保户模式下操作系统内核如何加载用户程序并运行 对应的汇编代码之主引导扇区程序

發(fā)布時(shí)間:2023/12/10 windows 26 豆豆
生活随笔 收集整理的這篇文章主要介紹了 【OS学习笔记】二十 保护模式六:保户模式下操作系统内核如何加载用户程序并运行 对应的汇编代码之主引导扇区程序 小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

本匯編代碼對(duì)應(yīng)保戶模式下操作系統(tǒng)內(nèi)核如何加載用戶程序并運(yùn)行 的實(shí)際主引導(dǎo)扇區(qū)代碼:

  • 對(duì)應(yīng)的內(nèi)核代碼在:內(nèi)核代碼
  • 對(duì)應(yīng)的用戶程序代碼在:用戶程序代碼
;代碼清單13-1;文件名:c13_mbr.asm;文件說(shuō)明:硬盤主引導(dǎo)扇區(qū)代碼 ;創(chuàng)建日期:2011-10-28 22:35 ;設(shè)置堆棧段和棧指針 core_base_address equ 0x00040000 ;常數(shù),內(nèi)核加載的起始內(nèi)存地址 core_start_sector equ 0x00000001 ;常數(shù),內(nèi)核的起始邏輯扇區(qū)號(hào) mov ax,cs mov ss,axmov sp,0x7c00;計(jì)算GDT所在的邏輯段地址mov eax,[cs:pgdt+0x7c00+0x02] ;GDT的32位物理地址 xor edx,edxmov ebx,16div ebx ;分解成16位邏輯地址 mov ds,eax ;令DS指向該段以進(jìn)行操作mov ebx,edx ;段內(nèi)起始偏移地址 ;跳過(guò)0#號(hào)描述符的槽位 ;創(chuàng)建1#描述符,這是一個(gè)數(shù)據(jù)段,對(duì)應(yīng)0~4GB的線性地址空間mov dword [ebx+0x08],0x0000ffff ;基地址為0,段界限為0xFFFFFmov dword [ebx+0x0c],0x00cf9200 ;粒度為4KB,存儲(chǔ)器段描述符 ;創(chuàng)建保護(hù)模式下初始代碼段描述符mov dword [ebx+0x10],0x7c0001ff ;基地址為0x00007c00,界限0x1FF mov dword [ebx+0x14],0x00409800 ;粒度為1個(gè)字節(jié),代碼段描述符 ;建立保護(hù)模式下的堆棧段描述符 ;基地址為0x00007C00,界限0xFFFFE mov dword [ebx+0x18],0x7c00fffe ;粒度為4KB mov dword [ebx+0x1c],0x00cf9600;建立保護(hù)模式下的顯示緩沖區(qū)描述符 mov dword [ebx+0x20],0x80007fff ;基地址為0x000B8000,界限0x07FFF mov dword [ebx+0x24],0x0040920b ;粒度為字節(jié);初始化描述符表寄存器GDTRmov word [cs: pgdt+0x7c00],39 ;描述符表的界限 lgdt [cs: pgdt+0x7c00]in al,0x92 ;南橋芯片內(nèi)的端口 or al,0000_0010Bout 0x92,al ;打開A20cli ;中斷機(jī)制尚未工作mov eax,cr0or eax,1mov cr0,eax ;設(shè)置PE位;以下進(jìn)入保護(hù)模式... ...jmp dword 0x0010:flush ;16位的描述符選擇子:32位偏移;清流水線并串行化處理器[bits 32] flush: mov eax,0x0008 ;加載數(shù)據(jù)段(0..4GB)選擇子mov ds,eaxmov eax,0x0018 ;加載堆棧段選擇子 mov ss,eaxxor esp,esp ;堆棧指針 <- 0 ;以下加載系統(tǒng)核心程序 mov edi,core_base_address mov eax,core_start_sectormov ebx,edi ;起始地址 call read_hard_disk_0 ;以下讀取程序的起始部分(一個(gè)扇區(qū)) ;以下判斷整個(gè)程序有多大mov eax,[edi] ;核心程序尺寸xor edx,edx mov ecx,512 ;512字節(jié)每扇區(qū)div ecxor edx,edxjnz @1 ;未除盡,因此結(jié)果比實(shí)際扇區(qū)數(shù)少1 dec eax ;已經(jīng)讀了一個(gè)扇區(qū),扇區(qū)總數(shù)減1 @1:or eax,eax ;考慮實(shí)際長(zhǎng)度≤512個(gè)字節(jié)的情況 jz setup ;EAX=0 ?;讀取剩余的扇區(qū)mov ecx,eax ;32位模式下的LOOP使用ECXmov eax,core_start_sectorinc eax ;從下一個(gè)邏輯扇區(qū)接著讀@2:call read_hard_disk_0inc eaxloop @2 ;循環(huán)讀,直到讀完整個(gè)內(nèi)核 setup:mov esi,[0x7c00+pgdt+0x02] ;不可以在代碼段內(nèi)尋址pgdt,但可以;通過(guò)4GB的段來(lái)訪問(wèn);建立公用例程段描述符mov eax,[edi+0x04] ;公用例程代碼段起始匯編地址mov ebx,[edi+0x08] ;核心數(shù)據(jù)段匯編地址sub ebx,eaxdec ebx ;公用例程段界限 add eax,edi ;公用例程段基地址mov ecx,0x00409800 ;字節(jié)粒度的代碼段描述符call make_gdt_descriptormov [esi+0x28],eaxmov [esi+0x2c],edx;建立核心數(shù)據(jù)段描述符mov eax,[edi+0x08] ;核心數(shù)據(jù)段起始匯編地址mov ebx,[edi+0x0c] ;核心代碼段匯編地址 sub ebx,eaxdec ebx ;核心數(shù)據(jù)段界限add eax,edi ;核心數(shù)據(jù)段基地址mov ecx,0x00409200 ;字節(jié)粒度的數(shù)據(jù)段描述符 call make_gdt_descriptormov [esi+0x30],eaxmov [esi+0x34],edx ;建立核心代碼段描述符mov eax,[edi+0x0c] ;核心代碼段起始匯編地址mov ebx,[edi+0x00] ;程序總長(zhǎng)度sub ebx,eaxdec ebx ;核心代碼段界限add eax,edi ;核心代碼段基地址mov ecx,0x00409800 ;字節(jié)粒度的代碼段描述符call make_gdt_descriptormov [esi+0x38],eaxmov [esi+0x3c],edxmov word [0x7c00+pgdt],63 ;描述符表的界限lgdt [0x7c00+pgdt] jmp far [edi+0x10] ;------------------------------------------------------------------------------- read_hard_disk_0: ;從硬盤讀取一個(gè)邏輯扇區(qū);EAX=邏輯扇區(qū)號(hào);DS:EBX=目標(biāo)緩沖區(qū)地址;返回:EBX=EBX+512 push eax push ecxpush edxpush eaxmov dx,0x1f2mov al,1out dx,al ;讀取的扇區(qū)數(shù)inc dx ;0x1f3pop eaxout dx,al ;LBA地址7~0inc dx ;0x1f4mov cl,8shr eax,clout dx,al ;LBA地址15~8inc dx ;0x1f5shr eax,clout dx,al ;LBA地址23~16inc dx ;0x1f6shr eax,clor al,0xe0 ;第一硬盤 LBA地址27~24out dx,alinc dx ;0x1f7mov al,0x20 ;讀命令out dx,al.waits:in al,dxand al,0x88cmp al,0x08jnz .waits ;不忙,且硬盤已準(zhǔn)備好數(shù)據(jù)傳輸 mov ecx,256 ;總共要讀取的字?jǐn)?shù)mov dx,0x1f0.readw:in ax,dxmov [ebx],axadd ebx,2loop .readwpop edxpop ecxpop eaxret;------------------------------------------------------------------------------- make_gdt_descriptor: ;構(gòu)造描述符;輸入:EAX=線性基地址; EBX=段界限; ECX=屬性(各屬性位都在原始; 位置,其它沒(méi)用到的位置0;返回:EDX:EAX=完整的描述符mov edx,eaxshl eax,16 or ax,bx ;描述符前32(EAX)構(gòu)造完畢and edx,0xffff0000 ;清除基地址中無(wú)關(guān)的位rol edx,8bswap edx ;裝配基址的31~2423~16 (80486+)xor bx,bxor edx,ebx ;裝配段界限的高4位or edx,ecx ;裝配屬性 ret;-------------------------------------------------------------------------------pgdt dw 0dd 0x00007e00 ;GDT的物理地址 ;------------------------------------------------------------------------------- times 510-($-$$) db 0db 0x55,0xaa

總結(jié)

以上是生活随笔為你收集整理的【OS学习笔记】二十 保护模式六:保户模式下操作系统内核如何加载用户程序并运行 对应的汇编代码之主引导扇区程序的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。

如果覺(jué)得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。