前几天无聊上网,发现一篇这样文章,
http://www.nsfocus.net/index.php?act=magazine&do=view&mid=1291
C++中通过溢出覆盖虚函数指针列表执行代码
他这里面,
//test.cpp
#include<iostream.h>
class ClassTest
{
public:
long buff[1]; //大小为1
virtual void test(void)
{
cout << "ClassTest test()" << endl;
}
};
void entry(void)
{
cout << "Why are u here ?!" << endl;
}
int main(void)
{
ClassTest a,*p =&a;
long addr[] = {0,0,0,(long)entry}; //构建的虚函数表
//test() -> entry()
a.buff[1] = ( long ) addr;// 溢出,操作了虚函数列表指针
a.test(); //静态联编的,不会有事
p->test(); //动态联编的,到我们的函数表去找地址,
// 结果就变成了调用函数 entry()
}
我觉得用得着这么麻烦吗,还要写个buff
我这个方式和他一样,重新搞个
虚函数列表指针
实际上他这个还有个问题,entry没有指定函数的类型,及这个地方的函数要和类成员函数的类型一致,
需要__stdcall不然就只有一个参数
我写的,应该要漂亮一点
#include <stdio.h>
#include <string.h>
class testa
{
public:
virtual int fun(int x,int y)=0;
};
class testd:public testa
{
public:
int fun(int x,int y)
{
return x+y;
}
};
int __stdcall gfun(int x,int y)
{
return x-y;
}
int main()
{
long *p=new long;
p[0]=(long)gfun;
testa *d=new testd();;
memcpy(d,&p,sizeof(long));
printf("%d",d->fun(2,3));
delete d;
delete p;
return 0;
}