台海新闻网

一步步编写操作系统 60 cpu的IO特权级2 什么是驱动程序

6ddba41d1f4f4182a6dd292bcd4968c8

可以通过在操作系统加载时指定整个eflags来设置用户程序。操作系统如何设置自己的IOPL?即使内核IOPL为0,也必须将其写入eflags寄存器才能生效。不幸的是,没有对eflags寄存器的直接读/写指令,但可以通过将数据从堆栈弹出到eflags寄存器来修改它。您可以使用pushf指令将整个eflags压入堆栈,然后修改堆栈中的相应位,然后使用popf指令弹出eflags寄存器。另一个可以利用堆栈的指令是iretd。当itred指令从中断返回时,堆栈中相应位置的数据作为eflags的内容弹出到eflags寄存器中。因此,可以更改IOPL的指令只是popf和iretd指令,它们仍然只能在0权限下执行。如果此指令在不同的权限级别执行,则处理器不会引发异常,但没有任何反应。

我们来看看IO位图的全部内容。

如果,在数字上,CPL IOPL,程序不能完全无法执行任何IO操作,它有点奇怪,它似乎与我们的逻辑不一致,事实上,这是有道理的。

如前所述,IOPL是所有IO端口的交换机。但是,此开关仍留有访问空间。如果开关打开,则可以访问所有65536端口。如果开关关闭,则值为CPL> IOPL。 IO位图,用于设置某些端口的访问权限。换句话说,它首先在整体上关闭然后部分打开。这有点像设置防火墙规则。默认情况下,禁止所有访问。您要发布的端口是单独打开的。

为什么处理器允许这样做?原因是要加快速度。

如果所有的IO端口访问都要经过内核的话,由低特权级转向高特权级时是需要保存任务上下文环境的,这个过程也是要消耗处理器时间,随着端口访问多起来,时间成本还是很可观的。这一典型的应用就是硬件的驱动程序,它位于特权级1。

驱动程序就是通过IN,OUT等IO指令直接访问硬件的程序,它为上层程序提供对硬件的控制访问,相当于硬件的代理,程序员通过它就免去了学习硬件控制的相关知识,简化了程序设计。

所以说,驱动程序肯定是要直接控制IO端口的,尽管它可以像的Linux那样位于0特权级,但它?挥?1特权级时,依然可以直接操作硬件端口。

即使是在3特权级下,也要考虑某些需要快速反应的场合,比如某个应用程序需要快速的以硬件交互,所以处理器允许通过I/O位图来为3特权级程序打开某些端口的控制。这些规则同样适用于2特权级,也就是说在任意特权级下,处理器都可以通过I/O位图为相应特权级的程序开启特定的端口。

欲知I/O位图是怎么回事,咱们先把位图的概念明确。

XX位图是位图。地图是一种映射。建立映射。与地图一样,图表上的区域代表实际的地理范围。有点儿。位图通过位映射到实际对象。位图结构的操作单元是位,因此位图实际上是一系列二进制01数字。位图的操作是读取和写入相应的位。对处理器内存的访问以字节为单位。直接操作位,所以对于位图的操作,只需将位所在的字节放入存储器中,如果要将位置设置为1,可以使用1来执行或'计算位,如果你想要使用此位清零0,可以使用0对该位执行'和'操作。之后,我们将不可避免地操作位图并在以后练习。

英特尔处理器最多支持65536个端口,允许任务通过I/O位图打开特定端口。位图中的每个位代表相应的端口。例如,第0位表示第0个端口,第65535位。 65536端口号占用65536端口号占用的位图大小为63356/8=8192字节,即8 KB。如果I/O位图中的相应位设置为0,则可以访问相应的端口。否则,禁止该端口。图

87ba60b3d07242ba8c871934791a25bb

同样,I/O位图仅对CPL的值有效> IOPL,表示当前权限级别低于IOPL。如果当前权限级别大于或等于IOPL,则可以不受限制地访问任何端口。

[续]