首页
社区
课程
招聘
[原创]关于指针和堆栈溢出。。
发表于: 2012-2-25 15:36 8773

[原创]关于指针和堆栈溢出。。

2012-2-25 15:36
8773

首先,我的程序是:
#include<stdio.h>
#include<stdlib.h>
int _tmain(int argc, _TCHAR* argv[])
{
        int column[] = {0};
        int** p=NULL;
        int i ,j, row ;

        printf("输入数组的行值:") ;
        scanf("%d",&row) ;
        p =(int**)malloc(sizeof(int*)*row) ;
        for(i=0;i<row;i++)
        {
                printf("请输入第%d行的元素个数:\n",i+1) ;
                scanf("%d",&column[i]) ;
                p[i] = (int*)malloc(sizeof(int)*column[i]) ;
        }
        for(i=0;i<row;i++)
        {
                for(j=0;j<column[i];j++)
                {
                        *(p[i]+j) = 1;
                }
        }
        for(i=0;i<row;i++)
        {
                for(j=0;j<column[i];j++)
                {
                        printf("%d",*(p[i]+j)) ;
                }
                printf("\n");
        }
        return 0;
}

刚开始,对_tmain开始处设断。
转到反汇编窗口,找到调用_wmain处,_wmain的下一条指令地址0x00411BD8。
另外堆栈寄存器窗口,ESP=0x0012FF6C
而内存0x0012FF6C处内容:为0x00411BD8。
说明调用_wmain后 ,把调用_wmain处的下一条指令地址入栈。
经过调试知道 column的值为0x0012ff60。
在 程序末尾下断。 相应的内容后
这个时候 看内存:
这个时候0x12FF6C 被覆盖了。。也就是返回地址被篡改了。 另外ebp也改变了。

其实。一开始 我就认为int column[] = {0};这样定义是不正确的,但是编译器通过了。所以我认为 这样定义的是一个指针。即int *column = NULL;
通过后面的赋值 ,各种覆盖。。
PS:第一次写这样的文章,各位多多包涵。虽然没有技术含量。。呵呵。
详细见附件。。


[培训]科锐逆向工程师培训第53期2025年7月8日开班!

上传的附件:
收藏
免费 6
支持
分享
最新回复 (9)
雪    币: 408
活跃值: (156)
能力值: ( LV7,RANK:110 )
在线值:
发帖
回帖
粉丝
2
column为第一个局部变量。向上作为 指针寻址 逐个覆盖ebp返回地址,导致的溢出。楼主是想表达这个意思不?
2012-2-25 18:36
0
雪    币: 134
活跃值: (1017)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
3
哥,我来**啦...
2012-2-25 19:10
0
雪    币: 69
活跃值: (252)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
wmg
4
int column[] = {0};这样就相当于int column[1]={0},索引大于0时自然就越界缓冲区溢出了,很容易就覆盖返回地址了...
2012-2-25 20:40
0
雪    币: 2503
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
5
路过 看看!!!!!!!
2012-2-25 21:28
0
雪    币: 307
活跃值: (65)
能力值: ( LV5,RANK:70 )
在线值:
发帖
回帖
粉丝
6
[QUOTE=wmg;1047776]int column[] = {0};这样就相当于int column[1]={0},索引大于0时自然就越界缓冲区溢出了,很容易就覆盖返回地址了...[/QUOTE]

嗯。。这位仁兄说的是。。int column[]={0},相当于int column[1]={0}.。我还以为int column[]={0},相当于 int* column;呢 .误人子弟,罪过啊。。
2012-3-27 19:03
0
雪    币: 307
活跃值: (65)
能力值: ( LV5,RANK:70 )
在线值:
发帖
回帖
粉丝
7
嗯。。就想表达这个意思。。也提醒我们别犯这个错误。。呵呵。。
2012-3-27 19:04
0
雪    币: 615
活跃值: (212)
能力值: ( LV9,RANK:140 )
在线值:
发帖
回帖
粉丝
8
文章讲得一点不清楚,
栈溢出是这么回事的:
函数调用时参数先从右往左依次压栈,
然后把EIP压栈,也就是下一条指令的地址压栈,
接着把EBP压栈,ESP赋值给EBP,
int column[] = {0};占4个字节+EBP4个字节共需要8个字节的栈存储空间,
这时候SUB ESP,8 向上开辟8个字节空间,
从栈顶向下写内容,
scanf读取整数数组,
读取1个int空间就已满,超过的会使栈空间不够则往下覆盖掉EBP、返回地址、参数..
另外,malloc是在堆中申请的内存块,不是在栈内申请,切记!
2012-3-27 20:12
0
雪    币: 307
活跃值: (65)
能力值: ( LV5,RANK:70 )
在线值:
发帖
回帖
粉丝
9
[QUOTE=小覃;1057600]文章讲得一点不清楚,
栈溢出是这么回事的:
函数调用时参数先从右往左依次压栈,
然后把EIP压栈,也就是下一条指令的地址压栈,
接着把EBP压栈,ESP赋值给EBP,
int column[] = {0};占4个字节+EBP4个字节共需要8个字节的栈存储空间,
这时候SUB ESP,8 ...[/QUOTE]

嗯。。这位哥们解释了堆栈溢出的原理。。
我只是想提醒大家。。
int column[]={0};
然后一个for循环
内部的scanf("%d",&column[i]);
会产生栈中返回地址覆盖。。
这是个栈溢出的小例子。。栈溢出的使用很多。网络渗透,就有的通过栈溢出,来达到返回地址给覆盖成别有用心的子程序的地址。。
2012-3-29 22:36
0
雪    币: 215
活跃值: (11)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
10
路过看看哈,学习。
2012-10-10 16:28
0
游客
登录 | 注册 方可回帖
返回