// Remove padding of 'padfile' from a range of address space. void as_unpad(void *start, void *end, int padfile) { static struct stat padstat; killpad_extra extra; int res; assert(padfile > 0); res = fstat(padfile, &padstat); assert(0 == res); extra.killpad_padstat = &padstat; extra.killpad_start = start; extra.killpad_end = end; foreach_map(killpad, &extra); }
// Pad all the empty spaces in a range of address space to stop interlopers. void as_pad(void *start, void *end, int padfile) { fillgap_extra extra; extra.fillgap_start = start; extra.fillgap_end = end; extra.fillgap_padfile = padfile; foreach_map(fillgap, &extra); if (extra.fillgap_start < extra.fillgap_end) { void* res = mmap(extra.fillgap_start, extra.fillgap_end - extra.fillgap_start, PROT_NONE, MAP_FIXED|MAP_PRIVATE, padfile, 0); check_mmap(res, extra.fillgap_start, extra.fillgap_end - extra.fillgap_start); } }
static void main2(void) { int err, padfile; struct exeinfo info; extern char _end; int *esp; char buf[strlen(valgrind_lib) + sizeof(stage2) + 16]; info.exe_end = VG_PGROUNDDN(init_sp); // rounding down info.exe_base = KICKSTART_BASE; printf("info.exe_end = %p\n", info.exe_end); #ifdef HAVE_PIE info.exe_base = VG_ROUNDDN(info.exe_end - 0x02000000, 0x10000000); assert(info.exe_base >= VG_PGROUNDUP(&_end)); info.map_base = info.exe_base + 0x01000000 ; #else // If this system doesn't have PIE (position-independent executables), // we have to choose a hardwired location for stage2. // info.exe_base = VG_PGROUNDUP(&_end); printf("info.exe_base = %p\n", info.exe_base); info.map_base = KICKSTART_BASE + 0x01000000 ; printf("info.map_base = %p\n", info.map_base); #endif info.argv = NULL; snprintf(buf, sizeof(buf), "%s/%s", valgrind_lib, stage2); printf("valgrind_lib = %s\n",valgrind_lib); err = do_exec(buf, &info); if (err != 0) { fprintf(stderr, "valgrind: failed to load %s: %s\n", buf, strerror(err)); exit(1); } /* Make sure stage2's dynamic linker can't tromp on the lower part of the address space. */ padfile = as_openpadfile(); as_pad(0, (void *)info.map_base, padfile); // map base is the start of our stuff printf("init sp : %x\n", init_sp); esp = fix_auxv(init_sp, &info, padfile); printf("after fix_auxb\n"); if (1) { printf("---------- launch stage 2 ----------\n"); printf("eip=%p esp=%p\n", (void *)info.init_eip, esp); foreach_map(prmap, /*dummy*/NULL); } VG_(debugLog)(1, "stage1", "main2(): starting stage2\n"); printf("jumping to stage 2 \n"); printf("esp : %x \n eip : %x\n",esp, info.init_eip); jump_and_switch_stacks( (Addr) esp, /* stack */ (Addr) info.init_eip /* Where to jump */ ); /*NOTREACHED*/ assert(0); }