X-Git-Url: https://notaz.gp2x.de/cgi-bin/gitweb.cgi?a=blobdiff_plain;f=loader%2Fdl.c;fp=loader%2Fdl.c;h=154e01236bd173bfa7e1549e908f377f2a152bc4;hb=7fd42181a7f66b4403076cd9de98e18140a7eaf8;hp=0000000000000000000000000000000000000000;hpb=dc90c02d39fc8968d2078512e228d99e7c553267;p=ginge.git diff --git a/loader/dl.c b/loader/dl.c new file mode 100644 index 0000000..154e012 --- /dev/null +++ b/loader/dl.c @@ -0,0 +1,67 @@ +// vim:shiftwidth=2:expandtab +#define _GNU_SOURCE +#include +#include +#include +#include +#include "header.h" + +#define DL +#include "override.c" + +__attribute__((constructor)) +static void ginge_init(void) +{ + unsigned int lowest_segment = (unsigned int)-1; + unsigned int start, end; + int i, ret; + FILE *f; + + for (i = 0; i < ARRAY_SIZE(real_funcs_np); i++) { + *real_funcs_np[i].func_ptr = dlsym(RTLD_NEXT, real_funcs_np[i].name); + if (*real_funcs_np[i].func_ptr == NULL) { + fprintf(stderr, "dlsym %s: %s\n", real_funcs_np[i].name, dlerror()); + exit(1); + } + // dbg("%p %s\n", *real_funcs_np[i].func_ptr, real_funcs_np[i].name); + } + + f = fopen("/proc/self/maps", "r"); + if (f == NULL) { + perror("open /proc/self/maps"); + exit(1); + } + + ret = fscanf(f, "%x-%x %*s %*s %*s %*s %*s\n", &start, &end); + if (ret != 2) { + perror("parse maps"); + exit(1); + } + lowest_segment = start; + + // assume first entry lists program's text section. + // unprotect it in case we need some patching. + ret = mprotect((void *)start, end - start, PROT_READ|PROT_WRITE|PROT_EXEC); + if (ret != 0) + perror("warning: mprotect"); + + while (1) { + ret = fscanf(f, "%x-%*s %*s %*s %*s %*s %*s\n", &start); + if (ret <= 0) + break; + + if (start < lowest_segment) + lowest_segment = start; + } + +#if 0 + rewind(f); + char buff[256]; + while (fgets(buff, sizeof(buff), f)) + fputs(buff, stdout); +#endif + fclose(f); + + emu_init((void *)lowest_segment); +} +