Windows保护模式学习笔记(十)—— TLB
Windows保护模式学习笔记(十)—— TLB
- 地址解析
- 10-10-12分页
- 2-9-9-12分页
- TLB
- TLB结构
- TLB种类
- 练习1:体验TLB的存在
- 第一步:运行代码
- 第二步:设置中断门描述符
- 第三步:继续运行程序
- 实验总结
- 练习2:体验全局页的意义
- 练习3:INVLPG指令的意义
地址解析
当我们通过一个线性地址访问一个物理页(比如:MOV EAX,[0x12345678]
)时,实际上CPU未必只读了4个字节。
10-10-12分页
- CPU先通过线性地址找到对应的PDE:4个字节
- CPU再通过PDE和线性地址找到PTE:4个字节
- 最后再通过PTE找到对应物理页:4个字节
一共访问了12个字节,如果跨页可能更多。
2-9-9-12分页
- 找到PDPTE:8个字节
- 找到PDE:8个字节
- 找到PTE:8个字节
- 最后找到物理页:4个字节
一共访问了20个字节,如果跨页可能更多。
- 为了提高访问效率,只能对线性地址与其对应的物理地址做记录。
- CPU内部做了一张表,用来记录这些东西。它的效率和寄存器一样快,名字叫做TLB(Translation Lookaside Buffer)。
- 由于TLB的效率很快,因此它的大小不能太大,少则几十条,多则也只有上百条。
思考:在一个进程的4GB空间中,有无数个线性地址,但是一个TLB最多只能记录上百条记录,那么这张表真的有意义吗?
TLB
TLB结构
ATTR
:属性
在10-10-12分页模式下:ATTR = PDE属性 & PTE属性
在2-9-9-12分页模式下:ATTR = PDPTE属性 & PDE属性 & PTE属性
LRU
:统计信息
由于TLB的大小有限,因此当TLB被写满、又有新的地址即将写入时,TLB就会根据统计信息来判断哪些地址是不常用的,从而将不常用的记录从TLB中移除。
注意:
- 不同的CPU,TLB大小不同
- 只要Cr3发生变化,TLB立即刷新,一核一套TLB
- 由于操作系统的高2G映射基本不变,因此如果Cr3改了,TLB刷新的话,重建高2G以上很浪费。
所以PDE和PTE中有个G标志位(当PDE为大页时,G标志位才起作用),如果G位为1,刷新TLB时将不会刷新PDE/PTE
G位为1的页,当TLB写满时,CPU根据统计信息将不常用的地址废弃,保留最常用的地址
TLB种类
TLB在X86体系的CPU中的实际应用最早是从Intel的486CPU开始的,在X86体系的CPU中,一般都设有如下4组TLB:
第一组:缓存一般页表(4K字节页面)的指令页表缓存(Instruction-TLB);
第二组:缓存一般页表(4K字节页面)的数据页表缓存(Data-TLB);
第三组:缓存大尺寸页表(2M/4M字节页面)的指令页表缓存(Instruction-TLB);
第四组:缓存大尺寸页表(2M/4M字节页面)的数据页表缓存(Data-TLB)
注意:以下练习均采用10-10-12分页模式
练习1:体验TLB的存在
第一步:运行代码
注意:在调用门(int 0x20)执行前的任意位置设置断点,并运行至断点处
#include <stdio.h>
#include <windows.h>DWORD x, y, z;void __declspec(naked) PageOnNull() {__asm{//保存现场push ebpmov ebp, espsub esp, 0x100push ebxpush esipush edi}DWORD* pPTE; // 保存目标线性地址的 PTE 线性地址DWORD* pNullPTE; // 0 地址的 PTE 线性地址pNullPTE = (DWORD*)0xC0000000;// 挂上 0x50000000 所在位置pPTE = (DWORD*)(0xC0000000 + (0x50000000 >> 10)); *pNullPTE = *pPTE;x = *(DWORD*)0;// 挂上 0x60000000 所在位置pPTE = (DWORD*)(0xC0000000 + (0x60000000 >> 10)); *pNullPTE = *pPTE;y = *(DWORD*)0;// 刷新 TLB __asm {mov eax, cr3mov cr3, eax}// 再次读取 0 地址位置的数据z = *(DWORD*)0;__asm{//恢复现场pop edipop esipop ebxmov esp, ebppop ebpiretd}
}int main(int argc, char* argv[])
{DWORD* p5 = (DWORD*)VirtualAlloc((LPVOID)0x50000000, 4, MEM_RESERVE | MEM_COMMIT, PAGE_READWRITE);DWORD* p6 = (DWORD*)VirtualAlloc((LPVOID)0x60000000, 4, MEM_RESERVE | MEM_COMMIT, PAGE_READWRITE);if (p5 != (DWORD*)0x50000000 || p6 != (DWORD*)0x60000000){printf("Error alloc!\n");return -1;}*p5 = 0x1234;*p6 = 0x5678;__asm{// 通过中断门提权int 0x20}printf("1. 读 0 地址数据:\n");printf("*NULL = 0x%x \n\n", x);printf("2. 给 0 地址重新挂上物理页\n\n");printf("3. 重新读取 0 地址数据:\n");printf("*NULL = 0x%x \n\n", y);printf("4. 刷新 TLB \n\n");printf("5. 再次读取 0 地址数据:\n");printf("*NULL = 0x%x \n", z);return 0;
}
第二步:设置中断门描述符
首先在编辑器的反汇编界面查看PageOnNull函数的首地址
因此确定中断门描述符:0040
ee00`00081030
使用WinDbg在IDT[0x20]
处写入中断门描述符
kd> eq 8003f500 0040ee00`00081030
第三步:继续运行程序
解除WinDbg中断,使虚拟机继续运行,然后继续向下运行代码
运行结果:
实验成功!
实验总结
- 可以发现,在x被赋值完成后,即使0地址被挂上了新的物理页,再对y进行赋值,x和y输出的值是相同的。
- 但是在Cr3刷新后,0地址没有被挂上新的物理页,对z进行赋值后,z却输出了新的值。
- 这是因为Cr3刷新前,0地址第一次被x访问时,线性地址与物理地址的对应关系被写入了TLB中,因此在对y赋值时,TLB的记录没有被刷新,访问的还是原来的物理页
练习2:体验全局页的意义
略(待补充)
练习3:INVLPG指令的意义
略(待补充)
Windows保护模式学习笔记(十)—— TLB相关推荐
- Windows保护模式学习笔记(十四)—— 阶段测试
Windows保护模式学习笔记(十四)-- 阶段测试 题目一 解题步骤 题目二 解题步骤 题目一 描述:给定一个线性地址,和长度,读取内容 int ReadMemory(OUT BYTE* buffe ...
- Windows保护模式学习笔记(十二)—— 控制寄存器
Windows保护模式学习笔记(十二)-- 控制寄存器 控制寄存器 Cr0寄存器 Cr2寄存器 Cr4寄存器 控制寄存器 描述: 控制寄存器有五个,分别是:Cr0 Cr1 Cr2 Cr3 Cr4 Cr ...
- Windows保护模式学习笔记(十三)—— PWTPCD
Windows保护模式学习笔记(十三)-- PWT&PCD 要点回顾 CPU缓存 CPU缓存与TLB的区别 PWT(Page Write Through) PCD(Page Cache Dis ...
- Windows保护模式学习笔记(七)—— PDEPTE
Windows保护模式学习笔记(七)-- PDE&PTE Cr3 PDE(页目录表项) PTE(页表项) 物理页的属性 10-10-12分页的补充 实验1:证明PTE的特征1 第一步:选择一个 ...
- Windows保护模式学习笔记(九)—— 2-9-9-12分页
Windows保护模式学习笔记(九)-- 2-9-9-12分页 要点回顾 10-10-12分页 原理 环境配置 2-9-9-12分页 原理 PDPTE PDE PTE XD/NX标志位 环境配置 实验 ...
- Windows保护模式学习笔记(八)—— 页目录表基址/页表基址
Windows保护模式学习笔记(八)-- 页目录表基址/页表基址 要点回顾 一.页目录表基址 实验:拆分线性地址C0300000,并查看其对应的物理页 第一步:打开一个进程,获得它的Cr3 第二步:查 ...
- Windows保护模式学习笔记(六)—— 10-10-12分页
Windows保护模式学习笔记(六)-- 10-10-12分页 基本概念 4GB内存空间 有效地址-线性地址-物理地址 有效地址与线性地址 物理地址 控制寄存器:Cr3 10-10-12分页 实验:通 ...
- Windows保护模式学习笔记(五)—— 任务段任务门
Windows保护模式学习笔记(五)-- 任务段&任务门 要点回顾 任务段 TSS (Task-state segment ) TR段寄存器 TR段寄存器的读写 TSS段描述符 实验:加载自定 ...
- Windows保护模式学习笔记(四)—— 中断门陷阱门
Windows保护模式学习笔记(四)-- 中断门&陷阱门 要点回顾 中断描述符表(IDT) 一.中断门 实验:构造一个中断门 第一步:初步构造参数 第二步:确定 Offset in Segme ...
最新文章
- KOA2路由koa-router实现类似express router的文件结构设计---KOA入门学习
- Charles 4.2.1 HTTPS抓包
- java程序应用编写如何判断文本框里面的数据类型
- 巧用Win2003负载平衡服务实现LCS2005企业版的部署:LCS2005系列之五
- 3481. 阶乘的和
- 标星7000+,这个 Python 艺术二维码生成器厉害了!
- js进阶 13 jquery动画函数有哪些
- 使用ISA Server保护内部的web服务器
- “非IE内核浏览器”第一阶段开发计划发布
- 阶段3 2.Spring_06.Spring的新注解_1 spring的新注解-Configuration和ComponentScan
- 数据库课程设计 论坛系统—— 系统详细设计说明书
- 一个屌丝程序员的青春(二一一)
- echarts图表 tooltip提示框,xAxis X轴,formatter自定义
- saltstack return mysql_10-saltstack 数据返回到MySQL
- 基于leaflet-velocity的二维动态风场展示
- 苹果无需越狱了!通过苹果签名轻松安装IPA文件
- background-image
- linux rpm 装 mac,在linux上搭建用于mac时间机器备份的server
- 微信第三方服务平台开发(一)
- 在进行USB CDC类开发时,无法发送64整数倍的数据(续)