Replacing a static function in a kernel module

People,

I am trying to crack the kernel module by changing its symbol. The main idea is to replace the original function with a new function by rewriting its address in symtab. However, I found that when declaring a function as static, hacking fails. But it works with non-static function. My sample code is below:

filename: orig.c

int fun(void) { printk(KERN_ALERT "calling fun!\n"); return 0; } int evil(void) { printk(KERN_ALERT "===== EVIL ====\n"); return 0; } static int init(void) { printk(KERN_ALERT "Init Original!"); fun(); return 0; } void clean(void) { printk(KERN_ALERT "Exit Original!"); return; } module_init(init); module_exit(clean); 

Then I follow the sticky article to replace the original fun function in symtab with the evil call function, http://www.phrack.org/issues.html?issue=68&id=11

 >objdump -t orig.ko ... 000000000000001b g F .text 000000000000001b evil 0000000000000056 g F .text 0000000000000019 cleanup_module 0000000000000036 g F .text 0000000000000020 init_module 0000000000000000 g F .text 000000000000001b fun ... 

By executing the elfchger function

 >./elfchger -s fun -v 1b orig.ko [+] Opening orig.ko file... [+] Reading Elf header... >> Done! [+] Finding ".symtab" section... >> Found at 0xc630 [+] Finding ".strtab" section... >> Found at 0xc670 [+] Getting symbol' infos: >> Symbol found at 0x159f8 >> Index in symbol table: 0x1d [+] Replacing 0x00000000 with 0x0000001b... done! 

I can successfully change the table of funny characters to evil and insert a module to see the effects:

 000000000000001b g F .text 000000000000001b evil ... 000000000000001b g F .text 000000000000001b fun > insmod ./orig.ko > dmesg [ 7687.797211] Init Original! [ 7687.797215] ===== EVIL ==== 

So far, this works fine. When I change the declaration of fun as โ€œstatic int fun (void)โ€ and follow the same steps as mentioned above, I find that evil is not caused. Can someone give me some suggestion?

Thanks William

+4
source share
1 answer

Short version . Declaring a function as โ€œstaticโ€ makes it local and prevents the export of a character. Thus, the call is statically connected, and the dynamic linker does not affect the call at boot time.


Long version

Declaring a character as โ€œstaticโ€ prevents the compiler from exporting the character, making it local rather than global. You can verify this by looking at the (missing) 'g' in the objdump output or in the lower case 't' (instead of 'T') at the output of 'nm'. The compiler can also embed a local function, in which case the symbol table will not contain it at all.

Local characters must be unique only for the translation unit in which they are defined. If your module consisted of several translation units, you may have static entertainment () in each of them. Then nm or objdump of the finished .ko can contain several local characters called fun.

It also means that local characters are only valid in their respective translation unit, and can also be transmitted (in your case: called) only from within this device. Otherwise, the linker simply would not now be what you mean. Thus, the call to static fun () is already bound at compile time before loading the module.

During loading, the dynamic linker will not interfere with a strike of a local symbol or link (in particular: calls), because:

  • local communication has already been completed
  • there are potentially more characters named "fun" in everything and the dynamic linker will not be able to tell which one you had in mind
+3
source

Source: https://habr.com/ru/post/1484785/


All Articles