diff --git a/README.md b/README.md index fdf0d11..effbd7d 100644 --- a/README.md +++ b/README.md @@ -28,10 +28,53 @@ Currently, only x86_64 is supported (but it's not too hard to add support for other instruction sets, 32-bit ELF support is a bit harder). The code looks for a `lea rdi, [rel ]` instruction near `_start`, this is often the instruction that loads `main` to pass it to `__libc_start_main` (at least on -glibc and musl it is). This then gets overwritten *at runtime by *`ld.so` due +glibc and musl it is). This then gets overwritten *at runtime by* `ld.so` due to a relocation of type `R_X86_64_PC32` targetting the `pcrel32` operand of that instruction --- all without touching any code of the executable. +The result: + +```c +int main(int argc, char** argv[]){ + printf("hello, world\n"); + return 42; +} + +extern int main2(int argc, char** argv[]); +int main2(int argc, char** argv[]) { + printf("be gay do crimes\n"); + return 69; +} +``` + +``` +$ ./hello.glibc +hello, world +$ ./manip-exe ./hello.glibc{,.manip} +``` + +```asm +$ objdump -d hello.glibc.manip + +0000000000001050 <_start>: + 1050: 31 ed xor %ebp,%ebp + 1052: 49 89 d1 mov %rdx,%r9 + 1055: 5e pop %rsi + 1056: 48 89 e2 mov %rsp,%rdx + 1059: 48 83 e4 f0 and $0xfffffffffffffff0,%rsp + 105d: 50 push %rax + 105e: 54 push %rsp + 105f: 4c 8d 05 6a 01 00 00 lea 0x16a(%rip),%r8 # 11d0 <__libc_csu_fini> + 1066: 48 8d 0d 03 01 00 00 lea 0x103(%rip),%rcx # 1170 <__libc_csu_init> + 106d: 48 8d 3d c1 00 00 00 lea 0xc1(%rip),%rdi # 1135
+ 1074: ff 15 66 2f 00 00 callq *0x2f66(%rip) # 3fe0 <__libc_start_main@GLIBC_2.2.5> +``` + +``` +$ ./hello.glibc.manip +be gay do crimes +``` + ## Usage ```sh