I'd like to copy and call a function, but the code below segfaults when calling the buffer. What do I have to change? (Linux, x86)
#include <string.h>
#include <malloc.h>
#include <stdio.h>
int foo () { return 12; }
void foo_end () {}
int main () {
int s = (unsigned long long) foo_end - (unsigned long long) foo;
int (*f) () = (int (*)()) malloc (s);
memcpy ((void*) f, (const void*) foo, s);
printf ("%d %d\n", f (), foo ());
}
EDIT: Working solution:
#include <string.h>
#include <malloc.h>
#include <stdio.h>
#include <sys/mman.h>
#include <unistd.h>
int foo () { return 12; }
void foo_end () {}
int main () {
int s = (unsigned long long) foo_end - (unsigned long long) foo;
int (*f) () = (int (*)()) malloc (s);
memcpy ((void*) f, (const void*) foo, s);
long ps = sysconf (_SC_PAGESIZE);
void *fp = (void*) ((unsigned long long) f & ~((unsigned long long) (ps-1)));
if (mprotect ((void*) fp, ps, PROT_READ | PROT_WRITE | PROT_EXEC)) return -1;
printf ("%d %d\n", f (), foo ());
}