为了正常的体验网站,请在浏览器设置里面开启Javascript功能!

修改栈返回地址,改变程序执行流程.

2018-03-31 12页 doc 42KB 12阅读

用户头像 个人认证

徐姐2018

技术学院会计学毕业后掌握基本的会计知识技能,取得会计从业资格证,多年的财务工作经验,现认多家小企的财务会计!

举报
修改栈返回地址,改变程序执行流程.修改栈中函数调用返回地址,改变程序执行流程任务:修改栈中函数调用返回地址,改变程序执行流程在本例中,通过修改函数function调用返回地址,使程序跳过执行x=1的赋值语句,从而使输出结果为0为了实现这个目标,需要1.找到函数调用返回地址在栈中的位置由于c程序中无法直接取得返回地址,本例中以buffer1地址为基址,通过计算其与返回地址在栈中地址的差值,得到返回地址(在栈中)的地址对应程序中的7、8句7ret=buffer1+12;8(*ret)+=5;buffer1和返回地址通过gdb调试得到2.计算所跳过指令与下一条指令的...
修改栈返回地址,改变程序执行流程.
修改栈中函数调用返回地址,改变程序执行流程任务:修改栈中函数调用返回地址,改变程序执行流程在本例中,通过修改函数function调用返回地址,使程序跳过执行x=1的赋值语句,从而使输出结果为0为了实现这个目标,需要1.找到函数调用返回地址在栈中的位置由于c程序中无法直接取得返回地址,本例中以buffer1地址为基址,通过计算其与返回地址在栈中地址的差值,得到返回地址(在栈中)的地址对应程序中的7、8句7ret=buffer1+12;8(*ret)+=5;buffer1和返回地址通过gdb调试得到2.计算所跳过指令与下一条指令的差值,这通过反汇编代码可以直接计算得出源程序1i#include<stdio.h>2voidfunction(inta,intb,intc)3{4charbuffer1[5];5charbuffer2[10];6int*ret;7ret=buffer1+12;8(*ret)+=5;910}11voidmain()12{13intx;14x=0;15function(1,2,3);16x=1;17printf("%d\n",x);18}编译:gcc-oe-ge.c调试:gdbe反汇编disassemblemain0x0804844e<+0>: push%ebp0x0804844f<+1>: mov%esp,%ebp0x08048451<+3>: and$0xfffffff0,%esp0x08048454<+6>: sub$0x20,%esp0x08048457<+9>: movl$0x0,0x1c(%esp)0x0804845f<+17>: movl$0x3,0x8(%esp)0x08048467<+25>: movl$0x2,0x4(%esp)0x0804846f<+33>: movl$0x1,(%esp)0x08048476<+40>: call0x8048414<function>0x0804847b<+45>: movl$0x1,0x1c(%esp)0x08048483<+53>: mov$0x8048560,%eax0x08048488<+58>: mov0x1c(%esp),%edx0x0804848c<+62>: mov%edx,0x4(%esp)0x08048490<+66>: mov%eax,(%esp)0x08048493<+69>: call0x8048338<printf@plt>0x08048498<+74>: leave0x08048499<+75>: retdisassemblefunction:0x08048414<+0>: push%ebp0x08048415<+1>: mov%esp,%ebp0x08048417<+3>: sub$0x28,%esp0x0804841a<+6>: mov%gs:0x14,%eax0x08048420<+12>: mov%eax,-0xc(%ebp)0x08048423<+15>: xor%eax,%eax0x08048425<+17>: lea-0x21(%ebp),%eax0x08048428<+20>: add$0xc,%eax0x0804842b<+23>: mov%eax,-0x1c(%ebp)0x0804842e<+26>: mov-0x1c(%ebp),%eax0x08048431<+29>: mov(%eax),%eax0x08048433<+31>: lea0x5(%eax),%edx0x08048436<+34>: mov-0x1c(%ebp),%eax0x08048439<+37>: mov%edx,(%eax)0x0804843b<+39>: mov-0xc(%ebp),%eax0x0804843e<+42>: xor%gs:0x14,%eax0x08048445<+49>: je0x804844c<function+56>0x08048447<+51>: call0x8048348<__stack_chk_fail@plt>0x0804844c<+56>: leave0x0804844d<+57>: ret下面通过设置断点和单步调试的方法找到所需地址在x=0处设置断点break14运行run寄存器情况:(gdb)inforegisterseax0xbffff3e4 -1073744924ecx0x133a3a60 322583136edx0x1 1ebx0x287ff4 2654196esp0xbffff310 0xbffff310ebp0xbffff338 0xbffff338esi0x0 0edi0x0 0eip0x8048457 0x8048457<main+9>eflags0x282 [SFIF]cs0x73 115ss0x7b 123ds0x7b 123es0x7b 123fs0x0 0gs0x33 51栈的情况:0xbffff310: 0x00288324 0x00287ff4 0x080484b0 0xbffff3380xbffff320: 0x0015e985 0x0011eb80 0x080484bb 0x00287ff40xbffff330: 0x080484b0 0x00000000下一条指令(gdb)display/i$pc=>0x8048457<main+9>: movl$0x0,0x1c(%esp)继续执行(gdb)si15 function(1,2,3);1:x/i$pc=>0x804845f<main+17>: movl$0x3,0x8(%esp)看寄存器(gdb)inforegisterseax0xbffff3e4 -1073744924ecx0x133a3a60 322583136edx0x1 1ebx0x287ff4 2654196esp0xbffff310 0xbffff310ebp0xbffff338 0xbffff338esi0x0 0edi0x0 0eip0x804845f 0x804845f<main+17>eflags0x282 [SFIF]cs0x73 115ss0x7b 123ds0x7b 123es0x7b 123fs0x0 0gs0x33 51栈(gdb)x/10x$esp0xbffff310: 0x00288324 0x00287ff4 0x080484b0 0xbffff3380xbffff320: 0x0015e985 0x0011eb80 0x080484bb 0x000000000xbffff330: 0x080484b0 0x00000000继续执行下一条指令(gdb)si0x08048467 15 function(1,2,3);1:x/i$pc=>0x8048467<main+25>: movl$0x2,0x4(%esp)寄存器(gdb)inforegisterseax0xbffff3e4 -1073744924ecx0x133a3a60 322583136edx0x1 1ebx0x287ff4 2654196esp0xbffff310 0xbffff310ebp0xbffff338 0xbffff338esi0x0 0edi0x0 0eip0x8048467 0x8048467<main+25>eflags0x282 [SFIF]cs0x73 115ss0x7b 123ds0x7b 123es0x7b 123fs0x0 0gs0x33 51栈(gdb)x/10x$esp0xbffff310: 0x00288324 0x00287ff4 0x00000003 0xbffff3380xbffff320: 0x0015e985 0x0011eb80 0x080484bb 0x000000000xbffff330: 0x080484b0 0x00000000继续下一条指令(gdb)si0x0804846f 15 function(1,2,3);1:x/i$pc=>0x804846f<main+33>: movl$0x1,(%esp)寄存器(gdb)inforegisterseax0xbffff3e4 -1073744924ecx0x133a3a60 322583136edx0x1 1ebx0x287ff4 2654196esp0xbffff310 0xbffff310ebp0xbffff338 0xbffff338esi0x0 0edi0x0 0eip0x804846f 0x804846f<main+33>eflags0x282 [SFIF]cs0x73 115ss0x7b 123ds0x7b 123es0x7b 123fs0x0 0gs0x33 51栈:(gdb)x/10x$esp0xbffff310: 0x00288324 0x00000002 0x00000003 0xbffff3380xbffff320: 0x0015e985 0x0011eb80 0x080484bb 0x000000000xbffff330: 0x080484b0 0x00000000继续下一条指令(gdb)si0x08048476 15 function(1,2,3);1:x/i$pc=>0x8048476<main+40>: call0x8048414<function>寄存器(gdb)inforegisterseax0xbffff3e4 -1073744924ecx0x133a3a60 322583136edx0x1 1ebx0x287ff4 2654196esp0xbffff310 0xbffff310ebp0xbffff338 0xbffff338esi0x0 0edi0x0 0eip0x8048476 0x8048476<main+40>eflags0x282 [SFIF]cs0x73 115ss0x7b 123ds0x7b 123es0x7b 123fs0x0 0gs0x33 51栈(参数1被压入栈)(gdb)x/10x$esp0xbffff310: 0x00000001 0x00000002 0x00000003 0xbffff3380xbffff320: 0x0015e985 0x0011eb80 0x080484bb 0x000000000xbffff330: 0x080484b0 0x00000000开始调用函数function(gdb)sifunction(a=1,b=2,c=3)ate.c:33 {1:x/i$pc=>0x8048414<function>: push%ebp寄存器:(esp值减小了4)(gdb)inforegisterseax0xbffff3e4 -1073744924ecx0x133a3a60 322583136edx0x1 1ebx0x287ff4 2654196esp0xbffff30c 0xbffff30cebp0xbffff338 0xbffff338esi0x0 0edi0x0 0eip0x8048414 0x8048414<function>eflags0x282 [SFIF]cs0x73 115ss0x7b 123ds0x7b 123es0x7b 123fs0x0 0gs0x33 51栈:(返回地址被压入栈)(gdb)x/10x$esp0xbffff30c: 0x0804847b 0x00000001 0x00000002 0x000000030xbffff31c: 0xbffff338 0x0015e985 0x0011eb80 0x080484bb0xbffff32c: 0x00000000 0x080484b0通过查看栈中,我们发现,0x0804847b原来是call返回后下一条指令的地址:0x0804847b<+45>: movl$0x1,0x1c(%esp)我们要修正的正是这个地址,其位于0xbffff30c处执行下一条指令(push%ebp)(gdb)si0x08048415 3 {1:x/i$pc=>0x8048415<function+1>: mov%esp,%ebp寄存器:(gdb)inforegisterseax0xbffff3e4 -1073744924ecx0x133a3a60 322583136edx0x1 1ebx0x287ff4 2654196esp0xbffff308 0xbffff308ebp0xbffff338 0xbffff338esi0x0 0edi0x0 0eip0x8048415 0x8048415<function+1>eflags0x282 [SFIF]cs0x73 115ss0x7b 123ds0x7b 123es0x7b 123fs0x0 0gs0x33 51栈(ebp的值入栈)(gdb)x/10x$esp0xbffff308: 0xbffff338 0x0804847b 0x00000001 0x000000020xbffff318: 0x00000003 0xbffff338 0x0015e985 0x0011eb800xbffff328: 0x080484bb 0x00000000执行下一条指令:mov%esp,%ebp(gdb)si0x08048417 3 {1:x/i$pc=>0x8048417<function+3>: sub$0x28,%esp寄存器(ebp被esp赋值)(gdb)inforegisterseax0xbffff3e4 -1073744924ecx0x133a3a60 322583136edx0x1 1ebx0x287ff4 2654196esp0xbffff308 0xbffff308ebp0xbffff308 0xbffff308esi0x0 0edi0x0 0eip0x8048417 0x8048417<function+3>eflags0x282 [SFIF]cs0x73 115ss0x7b 123ds0x7b 123es0x7b 123fs0x0 0gs0x33 51栈0xbffff308: 0xbffff338 0x0804847b 0x00000001 0x000000020xbffff318: 0x00000003 0xbffff338 0x0015e985 0x0011eb800xbffff328: 0x080484bb 0x00000000执行下一条指令(sub$0x28,%esp)(gdb)si3 {1:x/i$pc=>0x804841a<function+6>: mov%gs:0x14,%eax寄存器(gdb)inforegisterseax0xbffff3e4 -1073744924ecx0x133a3a60 322583136edx0x1 1ebx0x287ff4 2654196esp0xbffff2e0 0xbffff2e0ebp0xbffff308 0xbffff308esi0x0 0edi0x0 0eip0x804841a 0x804841a<function+6>eflags0x282 [SFIF]cs0x73 115ss0x7b 123ds0x7b 123es0x7b 123fs0x0 0gs0x33 51栈(gdb)x/10x$esp0xbffff2e0: 0x00237e49 0x0015e785 0xbffff2f8 0x00145ae50xbffff2f0: 0x00000000 0x08049ff4 0xbffff308 0x080483040xbffff300: 0x0011eb80 0x08049ff4执行下一条指令:mov%gs:0x14,%eax(gdb)si0x08048420 3 {1:x/i$pc=>0x8048420<function+12>: mov%eax,-0xc(%ebp)寄存器:(gdb)inforegisterseax0x3f8efa00 1066334720ecx0x133a3a60 322583136edx0x1 1ebx0x287ff4 2654196esp0xbffff2e0 0xbffff2e0ebp0xbffff308 0xbffff308esi0x0 0edi0x0 0eip0x8048420 0x8048420<function+12>eflags0x282 [SFIF]cs0x73 115ss0x7b 123ds0x7b 123es0x7b 123fs0x0 0gs0x33 51执行下一条指令:mov%eax,-0xc(%ebp)(gdb)si0x08048423 3 {1:x/i$pc=>0x8048423<function+15>: xor%eax,%eax寄存器:(gdb)inforegisterseax0x3f8efa00 1066334720ecx0x133a3a60 322583136edx0x1 1ebx0x287ff4 2654196esp0xbffff2e0 0xbffff2e0ebp0xbffff308 0xbffff308esi0x0 0edi0x0 0eip0x8048423 0x8048423<function+15>eflags0x282 [SFIF]cs0x73 115ss0x7b 123ds0x7b 123es0x7b 123fs0x0 0gs0x33 51栈:(gdb)x/10x$esp0xbffff2e0: 0x00237e49 0x0015e785 0xbffff2f8 0x00145ae50xbffff2f0: 0x00000000 0x08049ff4 0xbffff308 0x3f8efa000xbffff300: 0x0011eb80 0x08049ff4执行xor%eax,%eax(gdb)si7 ret=buffer1+12;1:x/i$pc=>0x8048425<function+17>: lea-0x21(%ebp),%eax寄存器:(gdb)inforegisterseax0x0 0ecx0x4a6d85dc 1248691676edx0x1 1ebx0x287ff4 2654196esp0xbffff2e0 0xbffff2e0ebp0xbffff308 0xbffff308esi0x0 0edi0x0 0eip0x8048425 0x8048425<function+17>eflags0x246 [PFZFIF]cs0x73 115ss0x7b 123ds0x7b 123es0x7b 123fs0x0 0gs0x33 51栈:(gdb)x/10x$esp0xbffff2e0: 0x00237e49 0x0015e785 0xbffff2f8 0x00145ae50xbffff2f0: 0x00000000 0x08049ff4 0xbffff308 0xfc97ed000xbffff300: 0x0011eb80 0x08049ff4下一条指令:lea-0x21(%ebp),%eax(gdb)si0x08048428 7 ret=buffer1+12;1:x/i$pc=>0x8048428<function+20>: add$0xc,%eax寄存器(0xbffff2e7即为buffer1地址)(gdb)inforegisterseax0xbffff2e7 -1073745177ecx0x4a6d85dc 1248691676edx0x1 1ebx0x287ff4 2654196esp0xbffff2e0 0xbffff2e0ebp0xbffff308 0xbffff308esi0x0 0edi0x0 0eip0x8048428 0x8048428<function+20>eflags0x246 [PFZFIF]cs0x73 115ss0x7b 123ds0x7b 123es0x7b 123fs0x0 0gs0x33 51栈(gdb)x/10x$esp0xbffff2e0: 0x00237e49 0x0015e785 0xbffff2f8 0x00145ae50xbffff2f0: 0x00000000 0x08049ff4 0xbffff308 0xfc97ed000xbffff300: 0x0011eb80 0x08049ff4差值=bffff30c-bffff2e7=25(十进制为37)0x0804847b<+45>:movl$0x1,0x1c(%esp)与下一条指令差值为8。将程序中的参数改为37和8,成功!7ret=buffer1+37;8(*ret)+=8;熟悉之后不用单步调试这么麻烦,可以迅速找到想要的地址通过观察发现,每次对变量赋值前,
/
本文档为【修改栈返回地址,改变程序执行流程.】,请使用软件OFFICE或WPS软件打开。作品中的文字与图均可以修改和编辑, 图片更改请在作品中右键图片并更换,文字修改请直接点击文字进行修改,也可以新增和删除文档中的内容。
[版权声明] 本站所有资料为用户分享产生,若发现您的权利被侵害,请联系客服邮件isharekefu@iask.cn,我们尽快处理。 本作品所展示的图片、画像、字体、音乐的版权可能需版权方额外授权,请谨慎使用。 网站提供的党政主题相关内容(国旗、国徽、党徽..)目的在于配合国家政策宣传,仅限个人学习分享使用,禁止用于任何广告和商用目的。

历史搜索

    清空历史搜索