|
From: Greg P. <gp...@us...> - 2005-02-23 19:21:21
|
Julian Seward writes: > * I found the code hard to understand (== maintain) and there is > no comprehensive statement of what it is and is not trying to > achieve. Agreed. I have memory map tracking mostly working on Mac OS X, but there are plenty of gaps in my knowledge. (For example, what do all of the SF_xxx flags really mean, and how do they apply to Darwin's memory usage?) > Since we have chosen not to virtualise the client's address space, > we have to share it. And since the client doesn't know we're there, > we have to take complete control of the address space. That much > is implemented, and it's a good idea. Note that "complete control" cannot be totally complete in a Mach environment. On Mac OS X, the kernel and other processes can insert memory regions into the client with little or no warning and no control over the destination. Existing memory regions will not be clobbered, but everything else is fair game. The Window Server in particular does this all the time, so Valgrind needs to handle this in order to be useful. One problem that results is that Valgrind must not unilaterally use mmap(MAP_FIXED) on memory that it thinks is unoccupied. The kernel could be simultaneously inserting its own mapping there, and mmap(MAP_FIXED) always clobbers whatever was there previously. The solution is probably judicious use of Mach's vm_allocate(), which will refuse to clobber existing regions, even if you demand a MAP_FIXED-style absolute address. The flexibility of a superblock system would also help greatly. When Valgrind goes to allocate new non-client memory, it would first uses vm_allocate to claim an entire superblock-size region, and only then carve up the space inside. Non-client mmap(MAP_FIXED) would always be preceded by vm_allocate() of the space underneath. Client mmap(MAP_FIXED) would need to be check to make sure it did not overlap with a non-client superblock, but otherwise would go unchanged. (If the client unexpectedly clobbers its own memory with mmap(MAP_FIXED), it's their problem.) > * As mentioned above, the Address Space Manager is fundamental > and self-contained. It is decoupled from the malloc/free manager. > It no longer deals with debug info loading/unloading. It does > nothing that requires dynamic memory allocation. The segment list > is to be held in statically allocated storage to make that possible. > That's not wonderful, but even a 1 Mb static area should hold > enough info to track several thousand segments. How many thousand? Big Mac OS X apps already routinely use a few thousand VM blocks in client space, though this would probably be smaller after Valgrind's coalescing. > * At least for Linux, stage2 is loaded into a 64M superblock > just below 0x4000'0000 (1 G). ASpaceMgr allocates superblocks > on demand, above 1G if it can for shadow memory and for Valgrind's > own use, and below 1G for the client, if possible. In particular > it tries hard not to put Valgrind or Shadow data in the area > below 1G. This is all flexible, right? Mac OS X has some entertaining address space requirements and restrictions. But a superblock system does work better than a single "client here, Valgrind there" line. > - On a 64-bit machine, all code is to be mapped in below 1 G, but > apart from that ASpaceMgr can be fairly relaxed about fragmentation > in the area above 1 G. Where does the "all code below 1G" requirement come from? Is that particular to the codegen in 64-bit Linux? Does Valgrind need it for some reason? Is it just a preference? > (3) Use a standalone ELF .o loader/linker to load all the .o's, > link and start them. > > At first (3) sounds insane, but it has a couple of advantages: It's not that insane. I wrote a system that does something similar for Palm OS, to get around its restrictions on code size and global variables. A full-blown ELF .o linker was overkill for me; instead I linked everything with --emit-relocs, and then re-relocated everything at runtime using a custom loader. There are far fewer relocation types that need to be handled at this point, and the static linker has already done all of the memory layout and most symbol resolution. > The main disadvantage is that gdb would not have a clue what it > was looking at unless we found a way to convey debug info to it. My Mac OS X launcher has this problem. gdb can see Valgrind's symbols, but can't set any breakpoints, and is easily confused about other things. gdb knows nothing about the client or its libraries. It's all rather clumsy to work with, but not the end of the world. -- Greg Parker gp...@us... |