diff --git a/_posts/2024-02-02-intel-mpk.md b/_posts/2024-02-02-intel-mpk.md new file mode 100644 index 0000000..036d8ca --- /dev/null +++ b/_posts/2024-02-02-intel-mpk.md @@ -0,0 +1,109 @@ +--- +title: 简述Intel MPK +date: 2024-02-02 +categories: + - "Intel" +tags: + - "Intel" + - "AMD" +comments: true +image: + path: /assets/img/2024-02-02-intel-mpk/forest.jpg +--- + +## 引言 + +Intel MPK(Memory Protection Keys) 是Intel推出的一种内存保护机制,可以在不修改页表的情况下,来控制线性地址所关联物理页的访问权限,本篇将说明一些基本用法和用途,在阅读本篇内容前,需要读者对x86/x64架构有基本的了解。 + +## 说明 + +* CPUID.(EAX=07H,ECX=0H):ECX.OSPKE [bit 4]) + * 判断系统是否支持PKE + +* CPUID.(EAX=07H,ECX=0H):ECX.OSPKE [bit 4]) + * 判断系统是否支持PKS + +* CR4.PKE + * 控制是否启用User-Mode(用户模式)页面的Protection Keys + +* CR4.PKS + * 控制是否启用Supervisor-Mode(管理模式)页面的Protection Keys + +* PKRU + * 一个32位的内部寄存器,控制User-Mode Protection Keys所关联的页面权限 + +* IA32_PKRS + * 一个32位的MSR,控制Supervisor-Mode Protection Keys所关联的页面权限 + +* RDPKRU + * 读取PKRU内部寄存器 + +* WRPKRU + * 写入PKRU内部寄存器 + +## Protection Key + +在禁用CR4.PKE的情况下,用户模式页表中的 `Bit 59 ~ Bit62` 是保留位 + +在启用CR4.PKE的情况下,用户模式页表中的 `Bit 59 ~ Bit62` 是Protection Key + +在禁用CR4.PKS的情况下,管理模式页表中的 `Bit 59 ~ Bit62` 是保留位 + +在启用CR4.PKS的情况下,管理模式页表中的 `Bit 59 ~ Bit62` 是Protection Key + +这4位的Protection Key范围是0~15,相当于是一个索引,被关联到PKRU或PKRS + +## PKRU + +这个寄存器类似于一个位图,存放着16对ADi与WDi,用于控制与User-Mode Protection Key关联的页面权限,这个寄存器需要通过`RDPKRU` `WRPKRU` `XSAVE` `XRSTOR` 进行控制。 + +* ADi = 1,不允许任何数据访问 +* WDi = 1,不允许用户模式数据写入(在CR0.WP复位的情况下管理模式可以写入) +* **取指操作不受PKRU影响** + +## IA32_PKRS + +这个寄存器结构与PKRU极其相似,区别在于它所控制的是Supervisor-Mode Protection Keys,并且此寄存器是一个MSR寄存器,高32位为保留位,需要通过`RDMSR` `WRMSR` 进行控制。 + +* ADi = 1,不允许任何数据访问 +* WDi = 1,不允许用户模式数据写入(在CR0.WP复位的情况下管理模式可以写入) +* **取指操作不受PKRS影响** + +## PageFault + +如果是由Protection Keys引发的#PF,那么PFEC的 `Bit 5` 则置位。 + +## 流程 + +* 首先,判断处理器是否支持PKE或PKS +* 如果支持,则置位CR4.PKE或PKS +* 通过 `WRPKRU` 将权限写入到PKRU,或者通过 `WRMSR` 将权限写入到PKRS + * 例子:如果Protection Key设置为 `0Fh(1111b)` ,那么所对应的掩码就是 `0C0000000h ` +* 然后修改页表条目中的Protection Key,将它与PKRU或PKRS关联 + +## 结尾 + +聪明的挂哥,可能已经看到加粗的几个字了,取指操作不受Protection Key影响,意味着可以分离读写与执行,可以分离读写就意味着,在使用所谓的 `无痕HOOK`的时候,性能可以大幅度提高。 + +聪明的挂哥都知道,Intel VT-x提供的EPT可以轻松的完成这项任务,但是AMD-V提供的NPT并没有这样的功能,那么结合Protection Key是否可以间接的为AMD-V提供这样的功能来平替EPT,来完成所谓的 `无痕HOOK` 呢? + +答案就在下面,诸位细品。 + +```c +nt!_HARDWARE_PTE + +0x000 Valid : Pos 0, 1 Bit + +0x000 Write : Pos 1, 1 Bit + +0x000 Owner : Pos 2, 1 Bit + +0x000 WriteThrough : Pos 3, 1 Bit + +0x000 CacheDisable : Pos 4, 1 Bit + +0x000 Accessed : Pos 5, 1 Bit + +0x000 Dirty : Pos 6, 1 Bit + +0x000 LargePage : Pos 7, 1 Bit + +0x000 Global : Pos 8, 1 Bit + +0x000 CopyOnWrite : Pos 9, 1 Bit + +0x000 Prototype : Pos 10, 1 Bit + +0x000 reserved0 : Pos 11, 1 Bit + +0x000 PageFrameNumber : Pos 12, 40 Bits + +0x000 SoftwareWsIndex : Pos 52, 11 Bits + +0x000 NoExecute : Pos 63, 1 Bit +``` diff --git a/assets/img/2024-02-02-intel-mpk/forest.jpg b/assets/img/2024-02-02-intel-mpk/forest.jpg new file mode 100644 index 0000000..9a04500 Binary files /dev/null and b/assets/img/2024-02-02-intel-mpk/forest.jpg differ