缓冲区溢出利用时出现Reference Error的问题咨询
缓冲区溢出利用时出现Reference Error的问题咨询
嘿,看起来你在编写缓冲区溢出 exploit 时碰到了棘手的问题,我来帮你梳理下思路~
你提到在利用这行代码的缓冲区溢出漏洞时:
memcpy(&local_1d,*(void **)local_10[1],(ulong)*(uint *)(local_10[1] + 8));
溢出的数据不仅覆盖了目标栈区域,还不小心改写了local_10变量,进而触发了引用错误。这在栈溢出 exploit 编写里其实是很常见的坑,我给你拆解下问题和解决方向:
问题根源
local_10是栈上的指针变量,和local_1d这个缓冲区在栈上是相邻布局的。当你往local_1d写入的数据长度超过它的容量时,溢出的字节会顺着栈的增长方向(具体取决于架构,比如x86通常是从高地址往低地址增长)覆盖后续的栈变量,首当其冲的就是local_10。一旦local_10被改成了非法值,后续代码里对local_10[1]的引用(等价于*(local_10 + 1))就会变成访问不存在的内存地址,直接触发引用错误。
几个可行的解决思路
- 精准计算溢出偏移,避免覆盖
local_10:先通过反汇编或者调试器(比如GDB)分析栈的精确布局,算出从local_1d缓冲区到local_10变量之间的字节数(注意栈对齐的影响,比如x86下通常是4字节或8字节对齐)。构造payload时,只写入刚好到你想要控制的位置(比如返回地址)的长度,不要碰local_10所在的栈区域。 - 在payload中保留
local_10的原始合法值:如果你的payload必须覆盖到local_10的区域,那先在调试环境里拿到local_10的原始有效地址,然后在payload对应的偏移位置写入这个原始值。这样后续代码引用local_10时还是用的合法地址,就不会触发错误了。 - 提前劫持程序执行流:如果你的最终目标是控制程序执行(比如执行shellcode),那可以优先覆盖返回地址,让程序直接跳转到你注入的代码段,这样后续引用
local_10的代码根本不会被执行,自然也就不会出现错误了。
调试小技巧
建议用GDB搭配pwndbg或者peda这类插件,单步跟踪程序执行,实时查看栈上的变量变化,这样能精准掌握每个变量的栈偏移和溢出的影响范围,帮你快速定位问题。
备注:内容来源于stack exchange,提问作者AES




