1. 概述
本篇,将真正的实现提权——当前特权级从 3 变为 0.
当然,CPU 不会让你就这么简单的从 3 环跨到 0 环。但是,CPU 又必须提供一套方法,来让你完成这个功能。
前面讲过。DPL = 0 的非一致代码段,是绝对不允许不同特权级的程序跳转进来。可是,我给以给你开个后门,让你进来,然后给你最高权限,允许你胡作非为。
这个后门,必须由我(操作系统)来指定,而且只允许你跳转到我指定的地方。
2. 调用门
前面做过 jmp 跨段实验,但是 jmp 跨段后,权限是不会变的。CPU 提供给了我们另一种方法——调用门,来达到提权的目的。可以使用 call + 调用门的段选择子,来达到提权的目的。通过调用门,可以让 3 环程序进入 0 环,也就是由用户态变成内核态。
call far 指令格式
call far cs
:eip
由于在 VC6.0 中不支持这种写法,所以可以写成下面这种形式。(buffer是一个长度为6字节的缓冲区,高2字节存放 cs 段选择子,低 4 字节存放偏移值。)
__asm
{
call fword ptr
[buffer
]
}
实际上,call far 后面跟的 eip 已经废弃。
下面的实验演示了如何读取高 2G 内存。
3. 编写 r0 函数 getData
该函数将运行在ring 0下,因为其中读取了高2G内存数据。在 main 函数执行长调用,注意VC6.0 不能直接写 call 0x48:0,编译不通过
#include <windows.h>
#include <stdio.h>
WORD g_cs0
, g_ss0
, g_ds0
, g_es0
, g_fs0
, g_gs0
;
DWORD r0_data_lowdword
, r0_data_hidword
;
__declspec(naked
) void getData() {
__asm
{
pushfd
pushad
mov g_cs0
, cs
mov g_ss0
, ss
mov g_ds0
, ds
mov g_es0
, es
mov g_fs0
, fs
mov g_gs0
, gs
mov eax
, 0x8003f048
mov eax
, [eax
]
mov r0_data_lowdword
, eax
mov eax
, 0x8003f04c
mov eax
, [eax
]
mov r0_data_hidword
, eax
popad
popfd
retf
}
}
void printData() {
printf("g_cs0=x\ng_ss0=x\ng_ds0=x\ng_es0=x\ng_fs0=x\ng_gs0=x\nr0_data(0x8003f048)=x x\n",
g_cs0
, g_ss0
, g_ds0
, g_es0
, g_fs0
, g_gs0
, r0_data_hidword
, r0_data_lowdword
);
}
int main(int argc
, char* argv
[]) {
char cs_eip
[6] = {0, 0, 0, 0, 0x48, 0};
__asm
{
call fword ptr
[cs_eip
]
}
printData();
getchar();
return 0;
}
有一点需要注意的是,call far 函数指令的格式虽然是 call far cs:eip,但是这后面的 eip 已经被废弃。而真正的 eip 是填写到了调用门中。
4. 查看函数 getData 地址
在 main 函数第一行下断点,F5 运行调试,然后在函数 getData 中右键,查看反汇编
5. 构造调用门描述符
调用门描述符结构
| 7 | 6 | 5 | 4 | 3 | 2 | 1 | 0 | 字节
|76543210|76543210|7 65 4 3210|765 43210|76543210|76543210|76543210|76543210| 比特
|-----------------|1|--|0|1100|000|-----|--------|--------|--------|--------| 占位
|offset in segment
|P
|D
|S
|TYPE
| |param
|segment selector
|offset in segment
| 含义
| 31-16 |P
| |nums
| | 15-0 |
|L
|
函数地址是 00401030,构造的调用门描述符是 0040ec00`00081030在 WinDbg 调试器中,执行 eq 命令安装描述符
6. 运行结果
7. 总结
调用门虽然是 CPU 提供给使用者提权的一种手段,但是 Windows 中却并未使用。在 Windows 中,大量使用了中断门来进行提权,包括后面的系统调用,都是采用中断的方式实现。
另外,所谓的后门,其实有很多,比如中断门,陷阱门,任务门。它们都可以实现提权。后续文章会陆续讲解。
转载请注明原文地址: https://ju.6miu.com/read-1124591.html