操作系统真相还原_第5章第2节:内存分页机制

news2024/9/25 13:20:33

文章目录

  • 分段机制
  • 分页机制
    • 一级页表
    • 二级页表
    • 启用分页机制的过程
  • 启用分页机制(二级页表)
    • 详解
    • 程序
      • include.inc
      • mbr.s
      • loader.s
    • 写入硬盘
    • 启动bochs执行

分段机制


分页机制

一级页表

二级页表

启用分页机制的过程

1、准备好页目录项及页表
2、将页表地址写入控制寄存器cr3
3、寄存器cr0的PG位置1

1、

P:存在位,1表示存在于内存中,0表示不在内存中
RW:读写位,1表示可读可写,0表示可读不可写
US:访问权限位,1表示任意特权级都能访问该页,0表示特权级别为3不能访问该页
PWT:页级通写位,1表示通写方式(可提高访问效率),与高速缓存有关
PCD:页级高速缓存禁止位,1为启用高速缓存,0表示禁止高速缓存
A:访问位,1表示被CPU访问过,0表示未被CPU访问过
D:脏页位,1表示被修改过,0表示为被修改过,仅对页表项有效
PAT:页属性表位,能够在页面一级上设置内存属性,较为复杂,置0即可
G:全局位,1表示全局页,会在TLB中常驻,0表示不是全局页
AVL:操作系统可自行规定其用途

2、
cr3控制寄存器用于存储页表物理地址,所以cr3寄存器又称为页目录基址寄存器PDBR
使用mov指令在控制寄存器与通用寄存器互传数据:
mov cr[0~7], r32
mov r32, cr[0~7]

3、
将控制寄存器cr0的Page位置1,开启分页

启用分页机制(二级页表)

详解

低端3GB分配给用户空间,高端1GB分配给内核空间
第1个页目录项指向用户空间的起始位置
第769个页目录项指向内核空间的起始位置
页目录表在内存地址0x100000~0x100FFF处
第1个页表在内存地址0x101000~0x101FFF处,写入256个页表项指向低端1MB内存
第1、769个页目录项指向第1个页表
第1024个目录项指向页目录表
第770~1023个页目录项指向以内存地址0x102000为起始地址的254个页表

程序

include.inc

;--------- mbr & loader ---------
LBA_START_SECTOR equ 0x1
SECTOR_COUNT equ 0x4
LOADER_BASE_ADDR equ 0x7E0
LOADER_OFF_ADDR equ 0x0
LOADER_ADDR equ 0x7E00
ARDS_ADDR equ 0x1000

;--------- gdt ---------
DESC_G_4K   equ	  1_00000000000000000000000b   
DESC_D_32   equ	   1_0000000000000000000000b
DESC_L	    equ	    0_000000000000000000000b
DESC_AVL    equ	     0_00000000000000000000b
DESC_LIMIT_CODE2  equ 1111_0000000000000000b
DESC_LIMIT_DATA2  equ DESC_LIMIT_CODE2
DESC_LIMIT_VIDEO2  equ 0000_000000000000000b
DESC_P	    equ		  1_000000000000000b
DESC_DPL_0  equ		   00_0000000000000b
DESC_DPL_1  equ		   01_0000000000000b
DESC_DPL_2  equ		   10_0000000000000b
DESC_DPL_3  equ		   11_0000000000000b
DESC_S_CODE equ		     1_000000000000b
DESC_S_DATA equ	  DESC_S_CODE
DESC_S_sys  equ		     0_000000000000b
DESC_TYPE_CODE  equ	      1000_00000000b	;x=1,c=0,r=0,a=0 代码段是可执行的,非依从的,不可读的,已访问位a清0.  
DESC_TYPE_DATA  equ	      0010_00000000b	;x=0,e=0,w=1,a=0 数据段是不可执行的,向上扩展的,可写的,已访问位a清0.

;code section
DESC_CODE_HIGH4 equ (0x00 << 24) + DESC_G_4K + DESC_D_32 + DESC_L + DESC_AVL + DESC_LIMIT_CODE2 + DESC_P + DESC_DPL_0 + DESC_S_CODE + DESC_TYPE_CODE + 0x00

;data section
DESC_DATA_HIGH4 equ (0x00 << 24) + DESC_G_4K + DESC_D_32 + DESC_L + DESC_AVL + DESC_LIMIT_DATA2 + DESC_P + DESC_DPL_0 + DESC_S_DATA + DESC_TYPE_DATA + 0x00

;video section
DESC_VIDEO_HIGH4 equ (0x00 << 24) + DESC_G_4K + DESC_D_32 + DESC_L + DESC_AVL + DESC_LIMIT_VIDEO2 + DESC_P + DESC_DPL_0 + DESC_S_DATA + DESC_TYPE_DATA + 0x0b

;--------------   paragraph selection  ---------------
RPL0  equ   00b
RPL1  equ   01b
RPL2  equ   10b
RPL3  equ   11b
TI_GDT	 equ   000b
TI_LDT	 equ   100b

;--------------   loader & kernel   --------------
PAGE_DIR_TABLE_POS equ 0x100000

;--------------   page tab   --------------
PG_P equ 1b
PG_RW_R equ 00b
PG_RW_W equ 10b
PG_US_S equ 000b
PG_US_U equ 100b

mbr.s

;主引导程序
;------------------------------------------------------------
%include "boot.inc"
SECTION MBR vstart=0x7c00         
   mov ax,cs      
   mov ds,ax
   mov es,ax
   mov ss,ax
   mov fs,ax
   mov ax, 0xB800
   mov gs, ax
   mov sp,0x7c00

; 清屏 利用0x06号功能,上卷全部行,则可清屏。
; -----------------------------------------------------------
;INT 0x10   功能号:0x06	   功能描述:上卷窗口
;------------------------------------------------------
;输入:
;AH 功能号= 0x06
;AL = 上卷的行数(如果为0,表示全部)
;BH = 上卷行属性
;(CL,CH) = 窗口左上角的(X,Y)位置
;(DL,DH) = 窗口右下角的(X,Y)位置
;无返回值:
   mov     ax, 0x600
   mov     bx, 0x700
   mov     cx, 0           ; 左上角: (0, 0)
   mov     dx, 0x184f	   ; 右下角: (80,25),
			   ; VGA文本模式中,一行只能容纳80个字符,共25行。
			   ; 下标从0开始,所以0x18=24,0x4f=79
   int     0x10            ; int 0x10


;;;;;;;;;     打印字符串    ;;;;;;;;;;;

   mov cx, sx - msg
   mov si, msg
   mov di, 0
show_str:
   mov byte al, [si]
   mov byte ah, [sx]
   mov word [gs:di], ax
   inc si
   add di, 2
   loop show_str
   jmp L0

   msg db "enter mbr"
   sx db 0x24

;;;;;;;;;      打字字符串结束	 ;;;;;;;;;;;;;;;
L0:
   push ds
   push di
   mov eax, LBA_START_SECTOR
   push eax
   mov ax, SECTOR_COUNT
   push ax
   mov ax, LOADER_BASE_ADDR
   push ax
   mov ax, LOADER_OFF_ADDR
   push ax
   call read_disk
   add sp, 10
   pop di
   pop ds

   jmp LOADER_ADDR

;;;;;;;;;      read disk      ;;;;;;;;;

; LBA: [bp+10]
; sector count: [bp+8]
; destination: sec=[bp+6], off=[bp+4]
read_disk:
   push bp
   mov bp, sp

;sector_count
   mov dx,0x1f2
   mov ax, [bp+8]
   out dx, al

;sector_addr
   mov dx, 0x1f3
   mov ax, [bp+10]
   out dx, al

   mov dx, 0x1f4
   mov al, ah
   out dx, al

   mov dx, 0x1f5
   mov ax, [bp+12]
   out dx, al

   mov dx, 0x1f6
   mov al, ah
   and al, 0x0f
   or al, 0xe0
   out dx, al

;command_write
   mov dx, 0x1f7
   mov al, 0x20
   out dx, al

disk_test:
   nop          ;give disk a moment
   in al, dx
   and al, 0x88 ;7: BUSY, 3: READY
   cmp al, 0x08 ; (BUSY=0 & READY=1) or not?
   jnz disk_test

;data_read:   
   mov ax, [bp+8]
   mov dx, 256
   mul dx
   mov cx, ax

   mov bx, [bp+4]
   mov ax, [bp+6]
   mov ds, ax

   mov dx, 0x1f0
go_on_read:
   in ax, dx
   mov [bx], ax
   add bx,2
   loop go_on_read

   mov sp, bp
   pop bp
   ret
;;;;;;;;;      read disk      ;;;;;;;;;

   times 510-($-$$) db 0
   db 0x55,0xaa

loader.s

%include "boot.inc"
section loader vstart=LOADER_ADDR
;;;;;;;;;     打印字符串    ;;;;;;;;;;;

   mov cx, sx-msg1
   mov si, msg1
   mov di, 160
show_str:
   mov byte al, [si]
   mov byte ah, [sx]
   mov word [gs:di], ax
   inc si
   add di, 2
   loop show_str

   jmp get_memoinfo

   msg1 db "enter loader"
   sx db 0x24

;;;;;;;;;      打字字符串结束    ;;;;;;;;;;;;;;;

;----- get memory information -----
get_memoinfo:
;----- get all: 0xE820
jmp_e820:
   xor ebx, ebx
   mov edx, 0x534d4150
   mov di, ARDS_ADDR+2
ards_e820:
   mov eax, 0x0000e820
   mov ecx, 20
   int 0x15
   jc Error
   add di, cx
   inc word [ARDS_ADDR]
   cmp ebx, 0
   jnz ards_e820

show_memoinfo:
   mov ax, 0xb800
   mov gs, ax
   mov cx, [ARDS_ADDR]
   mov si, ARDS_ADDR+0x2
   mov di, 320
loop_print:

   push di
addr_info:
   mov edx, [si]
   mov di, memo_addr+22
   call BtH
   shr edx, 16
   mov di, memo_addr+18
   call BtH
   mov edx, [si+4]
   mov di, memo_addr+14
   call BtH
   shr edx, 16
   mov di, memo_addr+10
   call BtH
   
size_info:
   mov edx, [si+8]
   mov di, memo_size+22
   call BtH
   shr edx, 16
   mov di, memo_size+18
   call BtH
   mov edx, [si+12]
   mov di, memo_size+14
   call BtH
   shr edx, 16
   mov di, memo_size+10
   call BtH

type_info:
   mov edx, [si+16]
   mov di, memo_type+14
   call BtH
   shr edx, 16
   mov di, memo_type+10
   call BtH

   pop di
   push cx
   push si
   push di

   mov cx, BtH_Table-memo_addr
   mov ah, 0x24
   mov si, memo_addr
info_print:
   mov al, [si]
   mov [gs:di], ax
   inc si
   add di, 0x2
   loop info_print

   pop di
   add di, 160
   pop si
   add si, 20
   pop cx
   dec cx
   cmp cx, 0
   jne loop_print
   jmp Jmp_there

memo_addr db "ADDR:0xxxxxxxxxxxxxxxxx. "
memo_size db "SIZE:0xxxxxxxxxxxxxxxxx. "
memo_type db "TYPE:0xxxxxxxxx."
BtH_Table db "0123456789ABCDEF"

;params: dx, di
BtH:
   push ax
   push bx
   push edx
   push di
   
   mov bh, 0

   mov bl, dl
   and bl, 00001111b
   mov al, [BtH_Table+bx]
   mov [di], al
   dec di

   mov bl, dl
   shr bl, 4
   mov al, [BtH_Table+bx]
   mov [di], al
   dec di

   mov bl, dh
   and bl, 00001111b
   mov al, [BtH_Table+bx]
   mov [di], al
   dec di

   mov bl, dh
   shr bl, 4
   mov al, [BtH_Table+bx]
   mov [di], al

   pop di
   pop edx
   pop bx
   pop ax
   ret
   
Error:
   
;----- open A20 -----
Jmp_there:
   in al, 0x92
   or al, 00000010b
   out 0x92, al

;----- load gdtr-----
   lgdt [gdt_ptr]

;----- cr0 set -----
   mov eax, cr0
   or eax, 0x00000001
   mov cr0, eax

;----- clear instruction pipeline -----
   jmp dword SELECTOR_CODE:p_m_start

[bits 32]
p_m_start:
   mov ax, SELECTOR_DATA
   mov ds, ax
   mov es, ax
   mov ss, ax
   mov esp, LOADER_ADDR

   mov ax, SELECTOR_VIDEO
   mov gs, ax
   mov ecx, msg3-msg2
   mov si, msg2
   mov di, 1280
show_str2:
   mov byte al, [si]
   mov byte [gs:di], al
   inc si
   add di, 2
   loop show_str2

pagination_mode:
   call setup_page

   sgdt [gdt_ptr]
   mov eax, [gdt_ptr + 2]
   or dword [eax + 0x18 + 4], 0xc0000000
   add dword [gdt_ptr + 2], 0xc0000000

set_cr3:
   mov eax, PAGE_DIR_TABLE_POS
   mov cr3, eax

set_cr0_page:
   mov eax, cr0
   or eax, 0x80000000
   mov cr0, eax

reload_gdt:
   lgdt [gdt_ptr]

   mov ecx, GDT_BASE-msg3
   mov si, msg3
   mov di, 1440
show_str3:
   mov byte al, [si]
   mov byte [gs:di], al
   inc si
   add di, 2
   loop show_str3

   jmp $

;string
msg2 db "enter protect mode"

msg3 db "enable pagination mode"

;GDT_CREATE
GDT_BASE:
   dd 0x00000000, 0x00000000

CODE_DESC:
   dd 0x0000FFFF, DESC_CODE_HIGH4

DATA_DESC:
   dd 0x0000FFFF, DESC_DATA_HIGH4

VIDEO_DESC:
   dd 0x80000007, DESC_VIDEO_HIGH4

GDT_SIZE equ $ - GDT_BASE
GDT_LIMIT equ GDT_SIZE - 1
times 30 dq 0

;SELECTOR_SET
SELECTOR_CODE equ 0000000000001_000b + TI_GDT + RPL0
SELECTOR_DATA equ 0000000000010_000b + TI_GDT + RPL0
SELECTOR_VIDEO equ 0000000000011_000b + TI_GDT + RPL0

;GDT_pointer
gdt_ptr dw GDT_LIMIT
        dd GDT_BASE

setup_page:
   mov ecx, 1024
   mov esi, 0
clear_page_dir:
   mov dword [PAGE_DIR_TABLE_POS + 4*esi], 0
   inc esi
   loop clear_page_dir

create_pde:
   mov eax, PAGE_DIR_TABLE_POS
   add eax, 0x1000
   mov ebx, eax
set_1_769_1024_PDE:
   or eax, PG_US_U | PG_RW_W | PG_P
   mov [PAGE_DIR_TABLE_POS + 0x0], eax
   mov [PAGE_DIR_TABLE_POS + 0xc00], eax
   sub eax, 0x1000
   mov [PAGE_DIR_TABLE_POS + 0xffc], eax

   mov ecx, 254
   mov edx, PAGE_DIR_TABLE_POS
   mov edi, 769
   add eax, 0x2000
set_kernel_769~1022_PDE:
   mov [edx + 4*edi], eax
   inc edi
   add eax, 0x1000
   loop set_kernel_769~1022_PDE

set_0_PTE:
   mov ecx, 256
   mov edx, PAGE_DIR_TABLE_POS
   add edx, 0x1000
   mov edi, 0
   and eax, 0x00000111
create_pte:
   mov [edx + 4*edi], eax
   inc edi
   add eax, 0x1000
   loop create_pte
   
   ret

写入硬盘

nasm -I OS/include/ -o OS/boot/mbr.bin OS/boot/mbr.s
nasm -I OS/include/ -o OS/boot/loader.bin OS/boot/loader.s
dd if=OS/boot/mbr.bin of=bochs/hd60M.img bs=512 count=1 seek=0 conv=notrunc
dd if=OS/boot/loader.bin of=bochs/hd60M.img bs=512 count=4 seek=1 conv=notrunc

启动bochs执行

./bochs/bin/bochs -f bochs/boot.disk

页目录表详细信息:

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/175897.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

【ArcGIS微课1000例】0059:三种底图影像调色技巧案例教程

三种调整影像底图效果的技术,让你的图纸清新脱俗,做出的图更美观! 文章目录 方法一:影像源类型调整方法二:符号拉伸类型设置方法三:影像分析模块设置方法一:影像源类型调整 这种方法是最基础、最简单的一种方法,可以调整的内容有限。当大家发现导入了影像,然后影像图…

Spring Batch 基本概念和运行示例

基本概念 Spring Batch是批处理框架。 作业(Job)是状态以及状态之间转换的集合。 作业里包含步骤&#xff08;Spring Bean&#xff09;&#xff0c;每一个步骤解耦到独立的处理器中&#xff0c;并负责自己的数据&#xff0c;把所需的业务逻辑应用到数据上&#xff0c;然后把数…

【React】组件的创建与事件绑定

&#x1f4d8;前言 &#x1f6a9;&#x1f6a9;&#x1f6a9; &#x1f48e;个人主页: 阿选不出来 &#x1f4a8;&#x1f4a8;&#x1f4a8; &#x1f48e;个人简介: 一名大二在校生,学习方向前端,不定时更新自己学习道路上的一些笔记. &#x1f4a8;&#x1f4a8;&#x1f4a…

C规范编辑笔记(十三)

往期文章&#xff1a; C规范编辑笔记(一) C规范编辑笔记(二) C规范编辑笔记(三) C规范编辑笔记(四) C规范编辑笔记(五) C规范编辑笔记(六) C规范编辑笔记(七) C规范编辑笔记(八) C规范编辑笔记(九) C规则编辑笔记(十) C规范编辑笔记(十一) C规范编辑笔记(十二) 正文&#xff…

CSS背景:背景色/背景图像/背景重复/背景附着/简写背景属性(一文搞懂)

目录 CSS背景 CSS 背景色 实例 其他元素 实例 不透明度 / 透明度 实例 使用 RGBA 的透明度 实例 CSS 背景图像 实例 实例 实例 CSS 背景重复 实例 实例 CSS background-repeat: no-repeat 实例 CSS background-position 实例 CSS 背景附着 实例 实例 C…

linux系统中利用QT实现视频监控的基本方法

大家好&#xff0c;今天主要和大家分享一下&#xff0c;如何利用QT实现视频监控的基本操作。 目录 第一&#xff1a;视频监控基本简介 第二&#xff1a;实验流程图 第三&#xff1a;视频监控之服务器 第四&#xff1a;视频监控之客户端实现 第一&#xff1a;视频监控基本简…

Java基础之《netty(30)—RPC调用流程分析》

一、RPC基本介绍 1、RPC&#xff08;Remote Procedure Call&#xff09;—远程过程调用&#xff0c;是一个计算机通信协议。该协议允许运行于一台计算机的程序调用另一台计算机的子程序&#xff0c;而程序无需额外的为这个交互作用编程。 2、两个或多个应用程序都分布在不同的…

Kettle(4):excel数据抽取到mysql

1 准备工作 1.1 准备Excel文件 我这边直接使用上一篇导出的excel:file_user.xls 1.2 创建数据库 在mysql中创建数据库 1.3 在kettle中加载MySQL驱动 Kettle要想连接到MySQL&#xff0c;必须要安装一个MySQL的驱动&#xff0c;就好比我们装完操作系统要安装显卡驱动一样。加…

CMMI之工程类

工程类过程域涵盖了工程学科所共有的开发与维护活动。工程类过程域的书写使用了通用的工程术语&#xff0c;这样&#xff0c;涉及产品开发过程&#xff08;如软件工程、机械工程等&#xff09;的任何技术学科都能够将其用于过程改进。工程类过程域还将不同工程学科的关联过程整…

分享111个ASP源码,总有一款适合您

ASP源码 分享111个ASP源码&#xff0c;总有一款适合您 下面是文件的名字&#xff0c;我放了一些图片&#xff0c;文章里不是所有的图主要是放不下...&#xff0c; 111个ASP源码下载链接&#xff1a;https://pan.baidu.com/s/1Afx8CxZIGwcGWB6aUOssZg?pwdr81w 提取码&#x…

CPU缓存架构缓存一致性协议详解

一、CPU高速缓存&#xff08;Cache Memory&#xff09;1.1 CPU高速缓存CPU缓存即高速缓冲存储器&#xff0c;是位于CPU与主内存间的一种容量较小但速度很高的存储器。由于CPU的速度远高于主内存&#xff0c;CPU直接从内存中存取数据要等待一定时间周期&#xff0c;Cache中保存着…

《你当像鸟飞往你的山》教育让你内心的山更高,更广

《你当像鸟飞往你的山》教育让你内心的山更高&#xff0c;更广 塔拉韦斯特弗&#xff0c;美国作家、历史学家。1986年生于美国爱达荷州的山区。自学考取杨百翰大学&#xff0c;2009年获得剑桥大学哲学硕士学位&#xff0c;2014年获剑桥大学历史学博士学位。2018年出版处女座《你…

2023 年8个ChatGPT 的替代品

OpenAI 于 2022 年 11 月下旬推出的 ChatGPT 在网络世界引起了不小的轰动。它不仅引起了社交媒体用户的关注&#xff0c;也引起了各大媒体的关注。 这种先进的 AI 技术不仅可以根据命令生成、重写和汇总文本&#xff0c;还可以与用户进行交互。它会记住以前的对话&#xff0c;…

[论文翻译] Improving Knowledge Tracing via Pre-training Question Embeddings

摘要 知识追踪 (KT) 定义了根据学生的历史反应预测他们是否能正确回答问题的任务。尽管许多研究致力于利用问题信息&#xff0c;但问题和技能中的大量高级信息尚未被很好地提取&#xff0c;这使得以前的工作难以充分执行。在本文中&#xff0c;我们证明了通过在丰富的边信息上…

通过属性配置文件编写JDBC程序

package com.bjpowernode.jdbc;import java.sql.*; import java.util.ResourceBundle; /* 编程思想&#xff1a;将连接数据库时可变化的4条信息都写到配置文件中&#xff0c;以后需要连接其他数据库的时候&#xff0c;可直接修改配置文件&#xff0c;不用修改java程序。这4个信…

【LeetCode高频100题-3】冲冲冲(持续更新23.1.22)

文章目录62. 不同路径题意解法1 排列组合解法2 动态规划64. 最小路径和题意解法1 DFS&#xff08;剪枝也超时&#xff09;解法2 动态规划62. 不同路径 题意 一道数学题&#xff0c;排列组合/小学奥赛题。动态规划不是一般来解决最值问题的吗&#xff0c;这道题为什么会想到dp…

狂神。JVM入门学习笔记。

JVM学习 JVM常见面试题&#xff1a; 请你谈谈你对jvm的理解&#xff1f;Java8虚拟机和之前的变化更新&#xff1f;什么是OOM&#xff1f;什么是栈溢出StackOverFlowError&#xff1f;怎么分析&#xff1f;jvm的常见调优参数有哪些&#xff1f;内存快照如何抓取&#xff1f;怎么…

【JavaSE】保姆级教程|1万字+10张图学会类与对象--建议收藏

&#x1f331;博主简介&#xff1a;大一计科生&#xff0c;努力学习Java中!热爱写博客~预备程序媛 &#x1f4dc;所属专栏&#xff1a;爪洼岛冒险记【从小白到大佬之路】 ✈往期博文回顾: 【爪洼岛冒险记】第5站&#xff1a;多图解&#xff0c;超详细讲解Java中的数组、二维数组…

weston 1: 编译与运行傻瓜教程

sudo apt-get update sudo apt-get upgrade vim ~/.bashrc export WLD$HOME/install export LD_LIBRARY_PATH$WLD/lib export PKG_CONFIG_PATH$PKG_CONFIG_PATH:/home/zzj/install/lib/x86_64-linux-gnu/pkgconfig/ source ~/.bashrc 配置路径 此处根据个人电脑配置路径 …

高级Spring之BeanFactory的实现

Spring 的发展历史较为悠久&#xff0c;因此很多资料还在讲解它较旧的实现&#xff0c;这里出于怀旧的原因&#xff0c;把它们都列出来&#xff0c;供大家参考 DefaultListableBeanFactory&#xff0c;是 BeanFactory 最重要的实现&#xff0c;像控制反转和依赖注入功能&#x…