Fix for programs that store VirtualQueryEx results in signed integers (eg. The Borland Linker)
Troy Rollo
wine at troy.rollo.name
Tue Mar 2 21:47:02 CST 2004
ChangeLog:
Add work-around for programs that store the size from a
VirtualQueryEx in a signed integer. This makes the Borland
linker work. Also add comments describing how the address
space is laid out on various versions of Windows in case
it becomes necessary at a later time to more closely emulate
the Windows behaviour.
-------------- next part --------------
Index: dlls/kernel/process.c
===================================================================
RCS file: /home/wine/wine/dlls/kernel/process.c,v
retrieving revision 1.46
diff -u -r1.46 process.c
--- dlls/kernel/process.c 20 Feb 2004 20:19:24 -0000 1.46
+++ dlls/kernel/process.c 3 Mar 2004 03:44:32 -0000
@@ -323,6 +323,48 @@
debugstr_w(name), nt->OptionalHeader.AddressOfEntryPoint );
}
+
+ /* We need to prevent the existence of a block of memory (allocated
+ * or unallocated) that exceeds 0x80000000 in size, to deal with broken
+ * programs that call VirtualQueryEx and then store the size of the block
+ * in a signed integer.
+ */
+ VirtualAlloc((LPVOID) 0x7ffff000, 0x1000, MEM_RESERVE, 0);
+
+ /* In an ideal world we would limit the address space here to what is available
+ * on Windows:
+ *
+ * Win95 series: 0x00020000-0xbfffffff
+ * NT series, 2GB mode: 0x00020000-0x7ffeffff
+ * NT series, 3GB mode: 0x00020000-0xbffeffff
+ *
+ * When NT running in 3GB mode encounters an executable that does not have the
+ * IMAGE_FILE_LARGE_ADDRESS_AWARE bit set in the file header characteristics, it
+ * reserves 0x80000000-0xbffeffff with VirtualAlloc and MEM_RESERVED.
+ *
+ * The problem with emulating this is that on Linux the top of the stack is at
+ * 0xbfffffff and below, so reserving even the balance of this range would
+ * artificially limit stack growth. We could move the stack, but it's too late
+ * to do that here because there will be pointers to things on the stack
+ * that will be affected - moving the stack would need to be done in main() in
+ * loader/main.c, which would then be responsible for moving it back (this would
+ * be done with mremap and subsequent adjustment to the stack pointer).
+ *
+ * If the stack were to be moved, it might end up at 0x00130000, expanding down,
+ * as it does on NT. This would require moving the wine-* executable to a higher
+ * address, as it currently loads at 0x00110000, and its first malloc takes its
+ * address space usage past 0x00130000.
+ *
+ * This is all possible - wine-* could be linked so as to load higher in memory,
+ * and main in loader/main.c could move the stack using mremap. This would
+ * enable a more faithful reproduction of Windows' behaviour, provided a harmless
+ * location could be found for the wine-* executable.
+ *
+ * If this were to be done, the ADDRESS_SPACE_LIMIT constant in
+ * dlls/ntdll/virtual.c might be more appropriately given as the end of the
+ * address space on the emulated operating system (requiring a variable).
+ */
+
drive_type = GetDriveTypeW( name );
/* don't keep the file handle open on removable media */
if (drive_type == DRIVE_REMOVABLE || drive_type == DRIVE_CDROM)
More information about the wine-patches
mailing list