学逆向论坛

找回密码
立即注册

只需一步,快速开始

发新帖

10

积分

0

好友

1

主题

[原创图文] 聊一聊堆栈

发表于 2019-3-11 09:58:01 | 查看: 4235| 回复: 1
vc 写的程序,反汇编之后,每个call都有一部分相似代码,大体如下。
push ebp
mov ebp,esp

……

mov esp,ebp
pop ebp
retn

我们都知道,esp 在程序运行时始终是栈顶指针。程序运行的时候,esp寄存器随时在发生变化,所以在访问保存在堆栈中的“函数的局部变量和参数”时,用esp来寻找就会非常的困难。所以,调用新函数时,将esp的值保存在ebp中,再以ebp为基准,就能够快速方便的访问到函数的局部变量、参数、以及返回地址。

我们还知道,堆栈是负增长,就是最后入栈的值保存在较小的内存地址。所以我们可以总结一下规律。
1、通常情况下(32位系统,vc编译),ebp保存着调用函数最初的esp值,方便程序结束后恢复esp。
2、ebp+4 保存的是函数的返回地址。
3、ebp+8、esp+C 保存的是函数的参数。
4、ebp-4、ebp-8 。。。 保存的是函数的局部变量

再说几个跟栈有关的指令:
1、call指令:相当于push call 的下一跳政令,再jmp到call的地址,比如说 有代码 call  40000,他下面的代码地址是100004,则这个call指令相当于push 100004, jmp 40000。压入栈的这个100004 ,在函数中就会变为 ebp+4 里面的值,为啥会变成ebp+4,上面说了,这里再说一下, 函数一进去就是 push ebp 所以,esp里面存了ebp的值,刚刚压入得100004,存放在了ebp+4中,下一条mov ebp,esp 使得 ebp==esp ,这样再找压人内容时,自然就可以通过ebp+4来找到。
2、retn指令 :相当于 jmp [esp],实际上是mov eip,100004。

温馨提示:
1.如果您喜欢这篇帖子,请给作者点赞评分,点赞会增加帖子的热度,评分会给作者加学币。(评分不会扣掉您的积分,系统每天都会重置您的评分额度)。
2.回复帖子不仅是对作者的认可,还可以获得学币奖励,请尊重他人的劳动成果,拒绝做伸手党!
3.发广告、灌水回复等违规行为一经发现直接禁言,如果本帖内容涉嫌违规,请点击论坛底部的举报反馈按钮,也可以在【投诉建议】板块发帖举报。
已有 1 人评分荣耀 理由
xuenixiang + 2 赞一个!

总评分: 荣耀 + 2   查看全部评分

发表于 2019-3-11 16:27:05
EBP主要是用来体现函数局部变量的,栈帧技术就是利用EBP来实现局部变量有条不紊的调用

小黑屋|手机版|站务邮箱|学逆向论坛 ( 粤ICP备2021023307号 )|网站地图

GMT+8, 2024-11-22 07:03 , Processed in 0.124203 second(s), 42 queries .

Powered by Discuz! X3.4

Copyright © 2001-2021, Tencent Cloud.

快速回复 返回顶部 返回列表