【Linux0.11 源码历险记 2】《保护模式》

2023-05-16

继续跟着stup.s 来看:

	lidt	idt_48		; load idt with 0,0
	lgdt	gdt_48		; load gdt with whatever appropriate
	...
idt_48:
	.word	0			; idt limit=0
	.word	0,0			; idt base=0L

gdt_48:
	.word	0x800		; gdt limit=2048, 256 GDT entries
	.word	512+gdt,0x9	; gdt base = 0X9xxxx

在实模式下,ds 是段基址,但是在保护模式下,段基址是放在gdt里的,利用ds到gdt里取出每一段的段基址,同时还有一些其他的信息。下面就是一个段描述符的价绍,其实我在另一篇帖子也提到过(https://blog.csdn.net/lyk82698/article/details/127609577)
在这里插入图片描述
现在去找一个地址,就不再是简单的 ds + 偏移地址了。而是 ds 先去全局描述符表里找到对应的段描述符,然后根据段描述符里的内容作为段基址,结合偏移地址确定最终地址。而全局描述符表的位置,就放在寄存器 gdtr 里面。

47-1615-0
gdt起始地址gdt的长度限制

因此根据下面设置gdtr 表示gdt的限制和起始地址

gdt_48:
	.word	0x800		; gdt limit=2048, 256 GDT entries
	.word	512+gdt,0x9	; gdt base = 0X9xxxx

其中现在的 gdt 如图:

gdt:
	.word	0,0,0,0		; dummy

	.word	0x07FF		; 8Mb - limit=2047 (2048*4096=8Mb)
	.word	0x0000		; base address=0
	.word	0x9A00		; code read/exec
	.word	0x00C0		; granularity=4096, 386

	.word	0x07FF		; 8Mb - limit=2047 (2048*4096=8Mb)
	.word	0x0000		; base address=0
	.word	0x9200		; data read/write
	.word	0x00C0		; granularity=4096, 386

下面开A20 进入保护模式;

	call	empty_8042    ! 测试8042状态寄存器,等待输入缓冲器空,
	mov	al,#0xD1		  ! command write 0xD1命令码表示写数据到8042的P2端口
	out	#0x64,al

	call	empty_8042    !等待输入缓冲器空,看命令是否被接受
	mov	al,#0xDF		  ! A20 on
	out	#0x60,al
	call	empty_8042    !若此时输入缓冲器为空,则表示A20线也选通 

为了兼容。早期8086CPU 只有20根线,到32位后,需要向前兼容,一开始是限制地址只能20位的,这里就打开限制。

 well, that went ok, I hope. Now we have to reprogram the interrupts :-(
; we put them right after the intel-reserved hardware interrupts, at
; int 0x20-0x2F. There they won't mess up anything. Sadly IBM really
; messed this up with the original PC, and they haven't been able to
; rectify it afterwards. Thus the bios puts interrupts at 0x08-0x0f,
; which is used for the internal hardware interrupts as well. We just
; have to reprogram the 8259's, and it isn't fun.

	mov	al,#0x11		; initialization sequence
	out	#0x20,al		; send it to 8259A-1
	.word	0x00eb,0x00eb		; jmp $+2, jmp $+2
	out	#0xA0,al		; and to 8259A-2
	.word	0x00eb,0x00eb
	mov	al,#0x20		; start of hardware int's (0x20)
	out	#0x21,al
	.word	0x00eb,0x00eb
	mov	al,#0x28		; start of hardware int's 2 (0x28)
	out	#0xA1,al
	.word	0x00eb,0x00eb
	mov	al,#0x04		; 8259-1 is master
	out	#0x21,al
	.word	0x00eb,0x00eb
	mov	al,#0x02		; 8259-2 is slave
	out	#0xA1,al
	.word	0x00eb,0x00eb
	mov	al,#0x01		; 8086 mode for both
	out	#0x21,al
	.word	0x00eb,0x00eb
	out	#0xA1,al
	.word	0x00eb,0x00eb
	mov	al,#0xFF		; mask off all interrupts for now
	out	#0x21,al
	.word	0x00eb,0x00eb
	out	#0xA1,al

上面就是对8259进行编码。具体咱就不看了。

下面就正式进入保护模式:

mov ax,#0x0001  ; protected mode (PE) bit
lmsw ax      ; This is it;
jmpi 0,8     ; jmp offset 0 of segment 8 (cs)

前两行,将 cr0 这个寄存器的位 0 置 1,模式就从实模式切换到保护模式了。进入保护模式,DS,CS等就变成了段选择子,他们相当于GDT的索引,进入GDT进行选择,同时还带着特权等级。

jmpi 0,8     ; jmp offset 0 of segment 8 (cs)

再往后,又是一个段间跳转指令 jmpi,后面的 8 表示 cs(代码段寄存器)的值,0 表示偏移地址。请注意,此时已经是保护模式了,之前也说过,保护模式下内存寻址方式变了,段寄存器里的值被当做段选择子。

8 用二进制表示就是
00000,0000,0000,1000

对照上面段选择子的结构,可以知道描述符索引值是 1,也就是要去全局描述符表(gdt)中找第一项段描述符。
所以,这里取的就是这个代码段描述符,段基址是 0,偏移也是 0,那加一块就还是 0 咯,所以最终这个跳转指令,就是跳转到内存地址的 0 地址处,开始执行。

下面就要进入 head.s 去执行了。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

【Linux0.11 源码历险记 2】《保护模式》 的相关文章

  • Gazebo的xacro文件添加各种plugins

    官网地址 xff1a http gazebosim org tutorials tut 61 ros gzplugins Tutorial Using Gazebo plugins with ROS Gazebo plugins give
  • ROS中spawn_model方式加载xacro文件,设置模型的位置(xyz,rpy)

    例如加载turtlebot机器人launch文件如下 xff1a 在gazebo仿真中最后都是通过这种方式加载xacro文件的 lt launch gt lt arg name 61 34 base 34 gt lt arg name 61
  • BT1120

    BT1120是高清晰度电视 HDTV 演播室信号数字接口 图像数据是怎么用二进制数据组织在一起的呢 xff1f 个人理解 xff1a 在BT1120标准中说明的图像数据指的是图像的有效尺寸的数据 因为我们看到编码信号包括图像数据和图像基准码
  • 2021-10-22 常用的串口通讯协议

    串口通讯是什么 学术解释是 xff0c 通过总线在一个时间点连续发送一位数据的方法 如同弓箭手频繁射出弓箭一般 xff0c 嗖 嗖 嗖 串口通讯协议是什么 说的大白话一点 xff0c 就是串口通信时所使用的协议传输方式 串口通讯协议有几种呢
  • curl 命令详解

    curl 是一种命令行工具 xff0c 作用是发出网络请求 xff0c 然后获取数据 xff0c 显示在 34 标准输出 34 xff08 stdout xff09 上面 它支持多种协议 xff0c 下面列举其常用功能 一 查看网页源码 直
  • RS485/云台控制(PTZ)学习文档

    RS485 云台控制 xff08 PTZ xff09 学习文档 zxf 一 项目任务 xff1a 在linux环境下通过RS485串口实现对云台镜头的各种控制 xff08 包括摄像头的打开 xff0c 关闭 xff0c 各个方向的运动及运动
  • 为何某些公司不允许使用C++STL

    点击蓝字 关注我们 最初开始禁用 C 43 43 STL xff0c 是因为早期项目编码实践中留下的惯例 xff0c 被后来的程序员继承下来 老项目中这种选择尤其地多 不过如果有人将其上升到公司行为在不同项目中全面禁用 STL xff0c
  • C++vector用法总结

    点击蓝字 关注我们 来源自网络 xff0c 侵删 一 vector 1 vector 说明 1 xff09 vector是C 43 43 标准模板库中的部分内容 xff0c 它是一个多功能的 xff0c 能够操作多种数据结构和算法的模板类和
  • halcon中的Pose

    Pose 姿态描述的是一个刚性的3D转换 xff0c 即 xff0c 一种由任意平移和旋转组成的变换 在Halcon中 xff0c 一个pose是具有7个参数的元组 xff1a 3个参数描述平移 xff08 TransX TransY Tr
  • halcon中阈值分割算子用法

    1 threshold Image Region MinGray MaxGray xff1a 通过给定的阈值区间对图像进行分割 效果图 xff1a read image Audi2 39 audi2 39 fill interlace Au
  • HALCON guided_filter导向滤波算子分析

    1 guided filter Image ImageGuide ImageGuided Radius Amplitude 可应用在图像增强 xff0c HDR压缩 图像抠图及图像去雾等场景 参数 xff1a Radius xff1a 滤光

随机推荐

  • halcon edges_image算子分析

    edges image Image ImaAmp ImaDir Filter Alpha NMS Low High xff1a 使用Deriche Lanser Shen或者Canny 滤波器进行边缘提取 参数 xff1a Image xf
  • C# NModbus的主从站开发以及Modbus Slave、Modbus Poll工具的使用

    NModbus的主站开发 1 开发环境要求 xff1a PC端作为主站 xff0c 控制器作为从站 2 PC端初始化代码 xff1a serialPort 61 new SerialPort serialPort PortName 61 3
  • OpenCVSharp Mat.Set<T>修改像素颜色

    笔记 xff1a Mat Set lt T gt 方法修改图像中的颜色 xff0c T的类型不能是Scalar 应为Vec3b xff0c 否则颜色修改失败 C 代码 xff1a Mat labs 61 new Mat int counts
  • VSCode idea 配置xml文件的dtd约束文件

    如上图配置XML文件的智能提示功能通过dtd文件 xff1a 1 通过VSCode 的扩展功能下载XML插件 xff08 注意 xff1a 插件内是包含dtd文件配置功能 xff09 配置方式 xff1a 1 DOCTYPE xff1a l
  • 关于0xAA和0x55

    许多串口通讯中测试或握手信号使用AA或55这两个特殊的十六进制数 xff0c 在许多PIC内部的 EEPROM 改写也使用这两个数作为敲门砖 xff0c 初学者可能不解何为 xff0c 其实如果将这两个数展开成二进制就可明白为什么 xff1
  • APS .Net MVC 之APIController与Controller的区别

    APIControllerController开发模式WebAPIMVC命名空间System Web HttpSystem Web Mvc返回方式json text或者xml texthtml textaction的默认请求方式postpo
  • DBeaver连接informix数据库乱码

    在工具栏选择数据库 驱动管理 informix编辑 xff0c 示例URL中添加NEWCODESET 61 utf8 8859 1 819 CLIENT LOCALE 61 en US utf8 DB LOCALE 61 en US 885
  • c语言——http编程

    HTTP协议简介 超文本传输协议是一种用于分布式 协作式和超媒体信息系统的应用层协议 HTTP是一个客户端终端 xff08 用户 xff09 和服务器端 xff08 网站 xff09 请求和应答的标准 xff08 一般基于TCP xff09
  • 串口开发之环形缓冲区

    01 简介 串口的基本应用 xff0c 使用串口中断接收数据 xff0c 串口中断发送回包 xff08 一般可以使用非中断形式发送回包 xff0c 在数据接收不频繁的应用中 串口接收中断保证串口数据及时响应 xff0c 使用非中断方式发送回
  • stl中的智能指针类详解

    C 43 43 98 03的尝试 std xff1a xff1a auto ptr C 43 43 11标准废弃了std xff1a xff1a auto ptr xff08 在C 43 43 17标准中被移除 xff09 xff0c 取而
  • 对于ROS的工作空间的理解(一)

    对于每一个任务 xff0c 可以在根目录下为它分配一个工作空间 mkdir p catkin ws src xff08 src 源码 xff09 cd catkin ws catkin make 编译 xff0c 生成devel xff08
  • stc-isp协议

    一 数据封装格式 包头 标示 数据包长度 命令字 内容 校验 包尾 1 包头 xff1a 2字节 xff0c 固定为 xff1a 0x46 xff0c 0xB9 2 标示 xff1a 1字节 xff0c 分两种 xff0c ARM发给MCU
  • 干货!串口通讯的起始、数据、停止位都是怎么分配的?

    串口是串行接口 xff08 serial port xff09 的简称 xff0c 也称为串行通信接口或COM接口 串口通信是指采用串行通信协议 xff08 serial communication xff09 在一条信号线上将数据一个比特
  • Linux 下char转换为wchar_t(窄字符转换位宽字符)

    LInux下使用mbstowcs函数可以将char转化为wchar t 函数含义 xff1a convert a multibyte string to a wide char string 说明 xff1a The behaviour o
  • Linux服务器 安装Pytorch GPU版本

    实验室服务器重做系统之后 xff0c 之间搭建的Python环境已甚嚣尘上 xff0c 只好从头再来 但是过程中遇到很多莫名其妙的bug xff0c 特此立章记录 xff0c 望对他人有所帮助 作为一个深度学习的初学者 xff0c 个人对所
  • 鼠标悬停效果 PPT制作

    鼠标悬停效果实现 在制作PPT时 xff0c 有时候需要实现鼠标的悬停效果 xff0c 即将鼠标放置在某个按钮或图片上 xff0c 实现动态变化的效果 目标是 xff1a 当鼠标悬停在一些人物名字上时 xff0c 出现该人物的个人信息 具体
  • 谷歌学术——下载论文

    一些同学在找论文的时候 xff0c 在学校数据库找不到 xff0c 因此可以使用谷歌学术来找 但是国内被墙了 xff0c 无法访问 xff0c 所以可以使用镜像服务器 首先进入谷歌镜像 xff1a 镜像网站 xff08 https ac s
  • Ubuntu 22.04 安装vm-tools

    安装过程一路心酸 xff0c 大家慎重 在Vmware中新建虚拟机之后 xff0c 发现没有办法传输文件和进行随窗口的视图变化 xff0c 打算安装vm tools 但是在Ubuntu 22 04 中 xff0c 如果使用Vmware自带的
  • LD文件 详解

    ld 组合了许多对象文件和归档文件 xff0c 重新定位它们的数据并绑定符号引用 通常编译程序的最后一步是运行 ld 每个可加载或可分配的输出节都有两个地址 第一个是 VMA xff0c 即虚拟内存地址 这是运行输出文件时该节所拥有的地址
  • 【Linux0.11 源码历险记 2】《保护模式》

    继续跟着stup s 来看 xff1a lidt idt 48 load idt with 0 0 lgdt gdt 48 load gdt with whatever appropriate idt 48 word 0 idt limit