把函数复制到堆上并运行的方法

239 篇文章 2 订阅
147 篇文章 1 订阅
有需求见此贴,所谓的动态执行 http://bbs.chinaunix.net/thread-1235365-1-1.html  

实现如下: 

[table=95%][tr][td][font=FixedSys]void add(int a, int b) 

        printf("a+b=%d\n", a+b); 


char *get_call_addr(char *p, int len)  

       while(len-- && (*p != (char)0xe8 )) 
               p++; 

       if (len) 
               return p; 
       else 
               return 0; 


void set_call(int call_addr, int fun_addr) 

        int ip = call_addr + 5; 
        int set_call_addr = call_addr + 1; 
       (*(int *)set_call_addr) = fun_addr - ip; 



int main() 

         char *p = (char *)malloc(100); 
          
         memcpy(p, add, 100); 

         void (*pf)(int, int) = (void(*)(int, int))p; 

          char *call_addr = get_call_addr(p, 100); 
          if (call_addr) { 
                  set_call((int)call_addr, (int)printf); 
                  pf(10, 20); 
          } 

         return 0; 

[/font][/td][/tr][/table] 

上面的代码能实现,将函数复制到 malloc 出来的内存里正确执行,原理就是修改里面的 call 指令偏移值。 
这里能正确运行,但这种方法并不保险。 
实际情况可能是:1、编译器产生的代码是多变的。2、刚刚好其它指令里没有 0xe8 这个机器码,要经过很多重判断(否则是话就大错特错了,:mrgreen: ) 


二、还有就是用直接调用的方法,或类似方法 

[table=95%][tr][td][font=FixedSys]void foo() 

          printf("I'm foo()...\n"); 


int main() 

          char *p = (char *)malloc(20); 
          int pf = (int)foo; 

          p[0] = 0xff; 
          p[1] = 0x15; 
          *((int *)&p[2]) = (int)&pf; 
          p[6] = 0xc3; 

          (void (*)())p(); 

          return 0; 

[/font][/td][/tr][/table] 

虽然,正确调用得到了保证,但要传递参数的话,要多动点脑子:)

http://www.chinaunix.net/old_jh/23/1237275.html

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值