Go Mike! Good to see this work finally turn into a patch against CVS :)
On Wed, 2004-04-28 at 19:02 +0900, Mike McCormack wrote:
Description:
This patch allows platforms using exec-shield patch against the Linux kernel (eg. Fedora Core) to run Wine without disabling exec-shield.
It also fixes the prelink case, right? :)
- vars.pe_size = 0x01000000;
0x1000000? Are you sure you didn't drop a zero somewhere? That's only 16mb.... we probably want something like 0x40000000 which reserves a gig of address space. Some very large game installers can in fact get close to this level, and as it's just non-backed address space we're reserving (for a shor time) there's no real reason to be stingy.
+/*
- The _start function is the entry and exit point of this program
- It calls wld_start, passing a pointer to the args it receives
- then jumps to the address wld_start returns after removing the
- first argv[] value, and decrementing argc
- */
+void _start(void); +__asm (
- ".align 4\n"
- "\t.global _start\n"
- "\t.type _start,@function\n"
+"_start:\n"
- "\tcall wld_start\n"
"\tpush %eax\n"
"\txor %eax,%eax\n"
"\txor %ebx,%ebx\n"
"\txor %ecx,%ecx\n"
"\txor %edx,%edx\n"
- "\tret\n"
+);
You know, I wonder if we couldn't make this simpler ... well, shorter, by assuming the stack is already set up and the main binary is mapped correctly, then being careful not to disturb the linker entry stack just reserve the areas we need with a few mmap syscalls, map in the real dynamic linker and do a jump. In effect, rather than repeat the work the kernel already did for everything but the real dynamic linker, insert a small shim between them.
Thoughts?
thanks -mike
Mike Hearn wrote:
Go Mike! Good to see this work finally turn into a patch against CVS
Well, there's a few things that probably need to be done before it can be applied:
* consider turning it back into a standalone program rather than a shared object loader ... for portability, there may be platforms for which that don't work with that approach, and because Alexandre doesn't like the way that we need to change directories
* figure out how to find the base address of the preloader at link time so it's not hardcoded in the source.
* fix the case when a symbol we're searching for isn't present in the loaded image (in wld_find_symbol() ) so it doesn't crash.
* allocate the buffer to store ld-linux.so.2's ELF header dynamically using calloc()
* don't hardcode the name of ld-linux.so.2
The main problem is getting Alexandre to review it, and figure out what other things he wants addressed before it can be included. Until that happens, I'm going to maintain and periodically improve the patch so that others can use/test it.
0x1000000? Are you sure you didn't drop a zero somewhere? That's only 16mb.... we probably want something like 0x40000000 which reserves a gig of address space. Some very large game installers can in fact get close to this level, and as it's just non-backed address space we're reserving (for a shor time) there's no real reason to be stingy.
Well, we can't get it right unless we know the location of the PE that's going to be run, so the idea is that Wine will always load a simple winelib exe that calls CreateProcess first. CreateProcess passes the unix path of the PE image in WINEPEEXEPATH.
Once the location of the PE image is known, the preload reserves exactly the right amount of memory for that image.
You know, I wonder if we couldn't make this simpler ... well, shorter, by assuming the stack is already set up and the main binary is mapped correctly, then being careful not to disturb the linker entry stack just reserve the areas we need with a few mmap syscalls, map in the real dynamic linker and do a jump. In effect, rather than repeat the work the kernel already did for everything but the real dynamic linker, insert a small shim between them.
Thoughts?
That's exactly the way it works :)
Mike
On Wed, 28 Apr 2004 20:13:34 +0900, Mike McCormack wrote:
- figure out how to find the base address of the preloader at link time so it's not hardcoded in the source.
If it was dynamic we could simply walk the _DYNAMIC list, but as it's static I think /proc/self/maps is the only way. Of course, that isn't portable either :)
The main problem is getting Alexandre to review it, and figure out what other things he wants addressed before it can be included. Until that happens, I'm going to maintain and periodically improve the patch so that others can use/test it.
Cool. I don't have time to work on this anymore anyway.
Well, we can't get it right unless we know the location of the PE that's going to be run, so the idea is that Wine will always load a simple winelib exe that calls CreateProcess first. CreateProcess passes the unix path of the PE image in WINEPEEXEPATH.
Argh, more init complexity. This is going to get confusing fast :)
thanks -mike