|
发表于 2003-3-16 01:57:12
|
显示全部楼层
Re: 一个难度很大的问题!
最初由 WanderMan 发布
int plus(int b)
{
if (b>3) return b;
int c=1;
b=b+c;
return plus(b);
}
main(void)
{
int a=1;
plus(a);
}
当编译时,假设a的virtual address 是0x10; b的virtual address 是:0x11;c的virtual address 是:0x12;(如果不是这样的话,那么应该如何处理不同模块之间的编址?)
现在,call plus(1),在队栈中要为b and c 分配三次;那么怎样对处在不同空间的a(or b)寻址?
a=1 -------------------------------virtual address?
b=1 -------------------------------virtual address?
a=2 -------------------------------virtual address?
b=1 -------------------------------virtual address?
a=3 -------------------------------virtual address?
b=1 -------------------------------virtual address?
What can compiling program and os perform?
你这函数有着非常大的问题!!!
plus(int b)
{
...
b = b + c ; // 看!这里竟然改变了参数本身,那参数用来还有什么意义呢?
}
就按照漏洞分析这个东西,下面的栈的内容
1. main 函数一开始,栈先压如变量 a:
栈内容:栈底(1)栈顶
2. 第一次调用 plus,参数压栈,并且压入 plus 内定义的 c,同时又改变了参数 b 本身的值
栈内容:栈底(1 | 2, 1)栈顶
3. 第二次调用 plus,参数压栈,再压入定义的 c,但函数本身又改变了b 的值
栈内容:栈底(1 | 2, 1 | 3, 1)栈顶
4. 第三次调用 plus,同样执行上一步操作
栈内容:栈底(1 | 2, 1 | 3, 1 | 4, 1)栈顶
5. 第三次调用 plus 的返回,b 的值是 4,然后将本次plus 里定义的变量和参数弹出栈
栈内容:栈底(1 | 2, 1 | 3, 1)栈顶
6. 第二次调用 plus 的返回,返回值是直接用第三次返回的结果,所以仍然返回4,然后是出栈
栈内容:栈底(1 | 2, 1)栈顶
7. 第一次调用 plus 的返回,返回值为第二次返回结果:4
栈内容:栈底(1)栈顶
结论:
1. plus 一直返回 4
2. 从上述栈的分析情况,如果知道栈底的地址,其他地址就是可以知道了。不过楼主犯了一个小小的错误,参数是放在栈里面的,所以参数存放的地址应该是递减而不是递增:如果 a 是 0x10,那么 b 就是 0x0F,c 是 0x0E,如此类推。
不知道我这样表达有没有问题,请大家指教。 |
|