This is the mail archive of the gcc-help@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

RE: Binary rewriting of indirect function calls


-----Original Message-----
From: gcc-help-owner@gcc.gnu.org [mailto:gcc-help-owner@gcc.gnu.org] On Behalf Of Abhinav Srivastava
Sent: Wednesday, November 18, 2009 7:05 PM
To: gcc-help@gcc.gnu.org
Subject: Binary rewriting of indirect function calls

>>Hi all,

>>In one of my projects, I am trying to do binary rewriting of Linux kernel on an x86-32 machine. To be more precise, I am actually targeting call instructions, and the goal is to re-write in-memory call instructions with the address of a different call site (trampoline).

>>The main problem that I am facing is related to indirect function calls. Most of the indirect call instructions in the kernel code are of 2 or 3 bytes, and modifying these call instructions with direct call instructions (5 bytes) seems impossible to me.

>>I was thinking of adding some "NOP" instructions after each indirect call in the kernel code so that I could replace an indirect call instruction with a direct one. To achieve that, instead of modifying the source code of the kernel and adding asm("nop"), I would like to do this at the compiler level.

>>Related to this, I have two questions: 

>>1) what are the ways in which an indirect call instruction can be overwritten by a direct call instruction inside the memory?

>>2) Is it possible to modify gcc in such a way that it generates some "NOP" instructions after each indirect function calls? 

>>I am completely new to this thing, and any help, ideas, and code pointers would be highly appreciated.

>>Thanks,
>>Abhinav



Is there a specific reason you are working at modifying binaries? 

If you have access to the source you can use gcc to insert the trampolines for you. 

>>2) Is it possible to modify gcc in such a way that it generates some "NOP" instructions after each indirect function calls?
  You can modify the machine description for your target architecture in gcc to add no ops to the indirect call instructions. 

If you want to use gcc to add trampolines...

There are a few ways to go about this. A quick way would be to utilize the -finstrument-functions option on gcc. This actually inserts a trampoline into all functions. It goes about it a little differently then what you have described as your desired approach. Instead of inserting the trampoline at the call instruction, the call to the trampoline is inserted after the entry of a function. 

Here is a section from .text of an objdump

000000000040e6e0 <makeargv>:
  40e6e0:	55                   	push   %rbp
  40e6e1:	bf e0 e6 40 00       	mov    $0x40e6e0,%edi
  40e6e6:	bd a0 f9 61 00       	mov    $0x61f9a0,%ebp
  40e6eb:	53                   	push   %rbx
  40e6ec:	48 83 ec 08          	sub    $0x8,%rsp
  40e6f0:	48 8b 74 24 18       	mov    0x18(%rsp),%rsi
  40e6f5:	e8 76 21 00 00       	callq  410870 <__cyg_profile_func_enter>


Notice what happens here. Once in the function makeargv the code saves the stack registers then calls the function "__cyg_profile_func_enter". When the "__cyg_profile_func_enter is done executing it will return to the line just after the call to it. 

By using this method you would eliminate the need to trap for different types of calls, Direct, indirect, etc. The reason is that instead of modifying the call you are modifying the functions themselves. 

If this method looks like it will work then read up on finstrument-functions.




Another approach would be to us the trampoline mechanism provided by gcc. To use this you have to make some changes to the machine description for the back end of gcc and recompile. To read more on this go here http://gcc.gnu.org/onlinedocs/gccint/Trampolines.html.

Hope this helps,
Dale Reese 


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]