bool replace_certain_rels(char *libpath, char* fucation_name[], u4 newFun_ptr[], int size) { LOGV("get into replace_all_rels"); FILE *m = NULL; char maps[80]; char line[200]; char soaddrs[20]; char soaddr[10]; char soname[60]; char prop[10]; long soaddval; long base; int result = false; memset(maps, 0, sizeof(maps)); memset(soaddrs, 0, sizeof(soaddrs)); memset(soaddr, 0, sizeof(soaddr)); sprintf(maps, "/proc/self/maps", 1); m = fopen(maps, "r"); if (!m) { LOGE("open maps error"); return result; } while (fgets(line, sizeof(line), m)) { int found = 0; struct elf_info einfo; long tmpaddr = 0; if (strstr(line, ".so") == NULL) continue; if (strstr(line, "r-xp") == NULL) continue; if (strstr(line, libpath) != NULL) { found = 1; } if (!found) { continue; } sscanf(line, "%s %s %*s %*s %*s %s", soaddrs, prop, soname); sscanf(soaddrs, "%[^-]", soaddr); LOGV("#### %s %s %s\n", soaddr, prop, soname); base = strtoul(soaddr, NULL, 16); puint(base); get_elf_info(1, base, &einfo); int i =0; for(i=0; i<size; i++) { tmpaddr = find_sym_in_rel(&einfo, fucation_name[i]); if (tmpaddr != 0) { memcpy((void*)tmpaddr, (void*)newFun_ptr[i], 4); LOGV(" the function %s is hook sucessfully",fucation_name[i]); } else { return result; LOGV(" the function %s is hook fail",fucation_name[i]); } } result = true; return result; } }
int main (int argc, char *argv[]) { int pid; struct link_map *map; char sym_name[256]; unsigned long sym_addr; unsigned long new_addr, old_addr, rel_addr; pid = atoi (argv[1]); ptrace_attach (pid); map = get_linkmap (pid); sym_addr = find_symbol (pid, map, "_dl_open"); printf ("found _dl_open at addr %p\n", sym_addr); call_dl_open (pid, sym_addr, "/home/joker/JustForFun/Injectso/passwd/so.so"); /* 找到我们的新函数newread的地址 */ strcpy (sym_name, "newread"); /* intercept */ sym_addr = find_symbol (pid, map, sym_name); printf ("%s addr\t %p\n", sym_name, sym_addr); /* 找到read的RELOCATION地址 */ strcpy (sym_name, "read"); rel_addr = find_sym_in_rel (pid, sym_name); printf ("%s rel addr\t %p\n", sym_name, rel_addr); /* 找到用于保存read地址的指针 */ strcpy (sym_name, "oldread"); old_addr = find_symbol (pid, map, sym_name); printf ("%s addr\t %p\n", sym_name, old_addr); /* 函数重定向 */ puts ("intercept..."); /* intercept */ ptrace_read (pid, rel_addr, &new_addr, sizeof (new_addr)); ptrace_write (pid, old_addr, &new_addr, sizeof (new_addr)); ptrace_write (pid, rel_addr, &sym_addr, sizeof (sym_addr)); puts ("injectso ok"); /* 脱离进程 */ ptrace_detach (pid); exit (0); }
void call_shit(struct elf_info *einfo) { unsigned long addr2 = 0; unsigned long rel_addr = find_sym_in_rel(einfo, "math_shit"); regs_t regs; ptrace_read(einfo->pid, rel_addr, &addr2, sizeof(long)); printf("math_shit rel addr\t %lx\n", rel_addr); printf("addr2 is \t %lx\n", addr2); ptrace_readreg(einfo->pid, ®s); ptrace_dump_regs(®s,"before call to call_shit\n"); #ifdef THUMB regs.ARM_lr = 1; #else regs.ARM_lr = 0; #endif regs.ARM_r0 = 5; regs.ARM_r1 = 6; regs.ARM_r2 = 7; regs.ARM_r3 = 8; { int a5 = 9; ptrace_push(einfo->pid, ®s, &a5, 4); ptrace_push(einfo->pid, ®s, &a5, 4); ptrace_push(einfo->pid, ®s, &a5, 4); ptrace_push(einfo->pid, ®s, &a5, 4); ptrace_push(einfo->pid, ®s, &a5, 4); ptrace_push(einfo->pid, ®s, &a5, 4); ptrace_push(einfo->pid, ®s, &a5, 4); ptrace_push(einfo->pid, ®s, &a5, 4); ptrace_push(einfo->pid, ®s, &a5, 4); a5 = 10; ptrace_push(einfo->pid, ®s, &a5, 4); } regs.ARM_pc = addr2; ptrace_writereg(einfo->pid, ®s); ptrace_cont(einfo->pid); printf("done %d\n", ptrace_wait_for_signal(einfo->pid,SIGSEGV)); ptrace_readreg(einfo->pid, ®s); ptrace_dump_regs(®s,"before return call_shit\n"); }