操作系统问题,关于函数地址空间

2020-08-21 16:41:43 +08:00
 ng29

如题, 假如进程里有函数 fun1, 再进程启动时,malloc 一页内存,拷贝 fun1 的内容到 malloc 出来的内存,称拷贝后的函数为 fun2, 调用 fun1 和 fun2 使用 不同的参数, 问 fun2 是不是可以正常执行?

考虑 fun2 是 fun1 改变了位置,如果有 jmp 指令是位置相关的,此时可不可以调整指令和字节数使得 fun2 可以正常运行直到 ret 返回。

2450 次点击
所在节点    程序员
34 条回复
ng29
2020-08-21 16:44:07 +08:00
求解
Jooooooooo
2020-08-21 16:50:28 +08:00
啥意思

两个线程运行同一段代码, 入参不一样?
ng29
2020-08-21 16:52:38 +08:00
@Jooooooooo 只有一个线程 函数代码段被 复制到另外一个地址 复制后的函数能直接用地址调用吗?
fasionchan
2020-08-21 16:53:26 +08:00
不行,malloc 出来的内存页是没有执行权限的。为什么呢?因为有一攻击叫栈溢出攻击。
hsiang271828
2020-08-21 16:55:02 +08:00
我的理解是,fun1 的内容装载在代码段,拷贝出来的二进制放在新分配的堆中,不在代码段,寻址会出错无法运行
ng29
2020-08-21 16:55:03 +08:00
@fasionchan 用 set_page_protection 加上权限以后 可以吗 ? 主要考虑 里面的地址引用 是不是需要调整 以及怎么调整
fasionchan
2020-08-21 17:06:02 +08:00
@ng29 栈地址是通过 ebp 寄存器加上偏移量计算的,应该没影响;堆地址和静态全局变量都是完整地址,应该也没影响;而 if for 语句编译后的 jmp 指令是段内跳转,通过偏移量来进行,讲道理也不会有影响。具体你可以试试看,我好些年没做底层了,可能有错漏~
fasionchan
2020-08-21 17:06:45 +08:00
@ng29 不过这样做的意义何在,做实验?
ng29
2020-08-21 17:07:37 +08:00
@hsiang271828 调用的时候,会给这段空间执行权限以及 用 拷贝后的地址作为 函数指针; 我理解理论上是可以的 我的顾虑是 代码中有 jmp 相对跳转 会不会跳转错 ,这里只能去参考 intel 的文档了。。。
ng29
2020-08-21 17:08:02 +08:00
@fasionchan hook 的时候, 改一些逻辑
ng29
2020-08-21 17:08:30 +08:00
@fasionchan 比如一样的函数,传的参数不一样
hythyt9898
2020-08-21 17:10:48 +08:00
看函数实现是不是地址无关代码( PIC )了,当然了你重新调整指令也是可以的,加壳软件都有类似流程。
Jooooooooo
2020-08-21 17:10:54 +08:00
@ng29 感觉你没有理解硬件是怎么跑代码的

线程本身的栈数据是线程自己管理的, 而运行什么代码是完全另外一块空间存放, 一般同一段代码内存里面只会有一份, 操作系统会复用的
ng29
2020-08-21 17:13:07 +08:00
@Joooooooo 我是想 故意复制一份函数代码段
fasionchan
2020-08-21 17:13:59 +08:00
@ng29 hook 一般不是定义新函数,新函数调用就函数,程序编译时连接新函数吗?之前看过微信后台的协程库 libco 的源码,里面 hook 了所有阻塞型的系统调用,你可以参考一下: https://github.com/Tencent/libco,可能会有一些启发。
ng29
2020-08-21 17:19:28 +08:00
@fasionchan 如果是动态库的话,hook 是比较好操作,但是整个项目都是静态链接的,一般是用 inline hook 把旧函数的前几个字节 改成 jmp code 调到 新函数,我这里 是想 把 旧函数 挪到另外一个地方,先备份,后面调用的时候 给一个 自己修改后的 参数(修改寄存器或者栈),准备好参数后,再调用 fun2
enenaaa
2020-08-21 17:21:55 +08:00
当然可以。 就是内存 patch 啊。fun2 能不能正常执行,要看里面的地址相关指令是否都能兼容新地址。一般有长跳的话需要在搬移后手动改汇编指令。
ng29
2020-08-21 17:24:15 +08:00
@enenaaa 指令调整的话 有没有比较完善的方案,求一个
mXw
2020-08-21 18:36:24 +08:00
你这个需求,需要修改内存权限才可以,rwx,相当于执行 shellcode ;参数的话就按照调用约定给进去就行。
secondwtq
2020-08-21 18:58:19 +08:00
一方面是这块内存的内容允不允许被执行的问题
另一方面是这块内存的内容里面有没有对非局部地址的引用

如果有 RIP relative addressing 的话就比较麻烦

这是一个专为移动设备优化的页面(即为了让你能够在 Google 搜索结果里秒开这个页面),如果你希望参与 V2EX 社区的讨论,你可以继续到 V2EX 上打开本讨论主题的完整版本。

https://www.v2ex.com/t/700313

V2EX 是创意工作者们的社区,是一个分享自己正在做的有趣事物、交流想法,可以遇见新朋友甚至新机会的地方。

V2EX is a community of developers, designers and creative people.

© 2021 V2EX