Skip to content

Commit

Permalink
arm: use refactored ptrace.c (see details below)
Browse files Browse the repository at this point in the history
arm's register type is user_regs, while it's user_regs_struct on x86 and
x86_64, so I had to do some defines in order to decide which type to use
at build time. other than that, the factored ptrace code seems to work
fine on all 3 architectures, as far as I can see.
  • Loading branch information
gaffe23 committed Mar 10, 2015
1 parent 0b93a60 commit c7f0ac1
Show file tree
Hide file tree
Showing 4 changed files with 16 additions and 98 deletions.
3 changes: 2 additions & 1 deletion arm/Makefile
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
CC = clang
CFLAGS = -std=gnu99 -ggdb

all: ../inject

../inject: inject.c ../utils.c
$(CC) -std=gnu99 -ggdb -ldl -o ../inject ../utils.c inject.c
$(CC) -DARM -ldl -o ../inject ../utils.c ../ptrace.c inject.c
93 changes: 2 additions & 91 deletions arm/inject.c
Original file line number Diff line number Diff line change
Expand Up @@ -9,90 +9,9 @@
#include <signal.h>
#include <wait.h>
#include <dlfcn.h>
#include "../utils.h"

void ptrace_attach(pid_t target)
{
int waitpidstatus;

if(ptrace(PTRACE_ATTACH, target, NULL, NULL) == -1)
{
fprintf(stderr, "ptrace(PTRACE_ATTACH) failed\n");
exit(1);
}

if(waitpid(target, &waitpidstatus, WUNTRACED) != target)
{
fprintf(stderr, "waitpid(%d) failed\n", target);
exit(1);
}
}

void ptrace_detach(pid_t target)
{
if(ptrace(PTRACE_DETACH, target, NULL, NULL) == -1)
{
fprintf(stderr, "ptrace(PTRACE_DETACH) failed\n");
exit(1);
}
}

void ptrace_getregs(pid_t target, struct user_regs* regs)
{
if(ptrace(PTRACE_GETREGS, target, NULL, regs) == -1)
{
fprintf(stderr, "ptrace(PTRACE_GETREGS) failed\n");
exit(1);
}
}

void ptrace_cont(pid_t target)
{
if(ptrace(PTRACE_CONT, target, NULL, NULL) == -1)
{
fprintf(stderr, "ptrace(PTRACE_CONT) failed\n");
exit(1);
}
}

void ptrace_setregs(pid_t target, struct user_regs* regs)
{
if(ptrace(PTRACE_SETREGS, target, NULL, regs) == -1)
{
fprintf(stderr, "ptrace(PTRACE_SETREGS) failed\n");
exit(1);
}
}

// used http://www.ars-informatica.com/Root/Code/2010_04_18/LinuxPTrace.aspx as a reference for this
void ptrace_read(int pid, unsigned long addr, void *vptr, int len)
{
int bytesRead = 0;
int i = 0;
long word = 0;
long *ptr = (long *) vptr;

while (bytesRead < len)
{
word = ptrace(PTRACE_PEEKTEXT, pid, addr + bytesRead, NULL);
bytesRead += sizeof(word);
ptr[i++] = word;
}
}

// used http://www.ars-informatica.com/Root/Code/2010_04_18/LinuxPTrace.aspx as a reference for this
void ptrace_write(int pid, unsigned long addr, void *vptr, int len)
{
int byteCount = 0;
int word = 0;

while (byteCount < len)
{
memcpy(&word, vptr + byteCount, sizeof(word));
word = ptrace(PTRACE_POKETEXT, pid, addr + byteCount, word);
byteCount += sizeof(word);
}
}
#include "../utils.h"
#include "../ptrace.h"

// this is the code that will actually be injected into the target process.
// this code is responsible for loading the shared library into the target
Expand Down Expand Up @@ -230,14 +149,6 @@ long getFunctionAddress(char* funcName)
return (long)funcAddr;
}

// restore backed up data and regs and let the target go on its merry way
void restoreStateAndDetach(pid_t target, unsigned long addr, void* backup, int datasize, struct user_regs oldregs)
{
ptrace_write(target, addr, backup, datasize);
ptrace_setregs(target, &oldregs);
ptrace_detach(target);
}

int main(int argc, char** argv)
{
if(argc < 3)
Expand Down
6 changes: 3 additions & 3 deletions ptrace.c
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@ void ptrace_detach(pid_t target)
}
}

void ptrace_getregs(pid_t target, struct user_regs_struct* regs)
void ptrace_getregs(pid_t target, struct REG_TYPE* regs)
{
if(ptrace(PTRACE_GETREGS, target, NULL, regs) == -1)
{
Expand All @@ -54,7 +54,7 @@ void ptrace_cont(pid_t target)
checktargetsig(target);
}

void ptrace_setregs(pid_t target, struct user_regs_struct* regs)
void ptrace_setregs(pid_t target, struct REG_TYPE* regs)
{
if(ptrace(PTRACE_SETREGS, target, NULL, regs) == -1)
{
Expand Down Expand Up @@ -129,7 +129,7 @@ void checktargetsig(int pid)
}

// restore backed up data and regs and let the target go on its merry way
void restoreStateAndDetach(pid_t target, unsigned long addr, void* backup, int datasize, struct user_regs_struct oldregs)
void restoreStateAndDetach(pid_t target, unsigned long addr, void* backup, int datasize, struct REG_TYPE oldregs)
{
ptrace_write(target, addr, backup, datasize);
ptrace_setregs(target, &oldregs);
Expand Down
12 changes: 9 additions & 3 deletions ptrace.h
Original file line number Diff line number Diff line change
@@ -1,10 +1,16 @@
#ifdef ARM
#define REG_TYPE user_regs
#else
#define REG_TYPE user_regs_struct
#endif

void ptrace_attach(pid_t target);
void ptrace_detach(pid_t target);
void ptrace_getregs(pid_t target, struct user_regs_struct* regs);
void ptrace_getregs(pid_t target, struct REG_TYPE* regs);
void ptrace_cont(pid_t target);
void ptrace_setregs(pid_t target, struct user_regs_struct* regs);
void ptrace_setregs(pid_t target, struct REG_TYPE* regs);
siginfo_t ptrace_getsiginfo(pid_t target);
void ptrace_read(int pid, unsigned long addr, void *vptr, int len);
void ptrace_write(int pid, unsigned long addr, void *vptr, int len);
void checktargetsig(int pid);
void restoreStateAndDetach(pid_t target, unsigned long addr, void* backup, int datasize, struct user_regs_struct oldregs);
void restoreStateAndDetach(pid_t target, unsigned long addr, void* backup, int datasize, struct REG_TYPE oldregs);

0 comments on commit c7f0ac1

Please sign in to comment.