Planet Coaster allocates 128KB of stack (both reserve and commit) but then tries to use at least one page more. Testing shows that native Windows always allocates at least 1MB of stack, for both 32-bit and 64-bit programs.
Signed-off-by: Zebediah Figura zfigura@codeweavers.com --- dlls/kernel32/fiber.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
diff --git a/dlls/kernel32/fiber.c b/dlls/kernel32/fiber.c index 151a6765a8bf..526ae57f2f42 100644 --- a/dlls/kernel32/fiber.c +++ b/dlls/kernel32/fiber.c @@ -97,7 +97,8 @@ LPVOID WINAPI CreateFiberEx( SIZE_T stack_commit, SIZE_T stack_reserve, DWORD fl }
/* FIXME: should use the thread stack allocation routines here */ - if (!stack_reserve) stack_reserve = 1024*1024; + /* some applications try to use more stack than they allocate */ + stack_reserve = max(stack_reserve, 1024 * 1024); if(!(fiber->stack_allocation = VirtualAlloc( 0, stack_reserve, MEM_COMMIT, PAGE_READWRITE ))) { HeapFree( GetProcessHeap(), 0, fiber );
Signed-off-by: Zebediah Figura zfigura@codeweavers.com --- dlls/kernel32/fiber.c | 13 +++++++++---- 1 file changed, 9 insertions(+), 4 deletions(-)
diff --git a/dlls/kernel32/fiber.c b/dlls/kernel32/fiber.c index 526ae57f2f42..8a3de81bb8ea 100644 --- a/dlls/kernel32/fiber.c +++ b/dlls/kernel32/fiber.c @@ -89,6 +89,8 @@ LPVOID WINAPI CreateFiberEx( SIZE_T stack_commit, SIZE_T stack_reserve, DWORD fl LPFIBER_START_ROUTINE start, LPVOID param ) { struct fiber_data *fiber; + SYSTEM_INFO si; + DWORD prev;
if (!(fiber = HeapAlloc( GetProcessHeap(), 0, sizeof(*fiber) ))) { @@ -96,16 +98,19 @@ LPVOID WINAPI CreateFiberEx( SIZE_T stack_commit, SIZE_T stack_reserve, DWORD fl return NULL; }
+ GetSystemInfo(&si); + /* FIXME: should use the thread stack allocation routines here */ /* some applications try to use more stack than they allocate */ - stack_reserve = max(stack_reserve, 1024 * 1024); - if(!(fiber->stack_allocation = VirtualAlloc( 0, stack_reserve, MEM_COMMIT, PAGE_READWRITE ))) + stack_reserve = max(stack_reserve, 1024 * 1024 - 3 * si.dwPageSize); + if(!(fiber->stack_allocation = VirtualAlloc( 0, stack_reserve + 3 * si.dwPageSize, MEM_COMMIT, PAGE_READWRITE ))) { HeapFree( GetProcessHeap(), 0, fiber ); return NULL; } - fiber->stack_base = (char *)fiber->stack_allocation + stack_reserve; - fiber->stack_limit = fiber->stack_allocation; + VirtualProtect(fiber->stack_allocation, 3 * si.dwPageSize, PAGE_NOACCESS, &prev); + fiber->stack_base = (char *)fiber->stack_allocation + 3 * si.dwPageSize + stack_reserve; + fiber->stack_limit = (char *)fiber->stack_allocation + 3 * si.dwPageSize; fiber->param = param; fiber->except = (void *)-1; fiber->start = start;
Zebediah Figura zfigura@codeweavers.com writes:
@@ -96,16 +98,19 @@ LPVOID WINAPI CreateFiberEx( SIZE_T stack_commit, SIZE_T stack_reserve, DWORD fl return NULL; }
- GetSystemInfo(&si);
- /* FIXME: should use the thread stack allocation routines here */ /* some applications try to use more stack than they allocate */
- stack_reserve = max(stack_reserve, 1024 * 1024);
- if(!(fiber->stack_allocation = VirtualAlloc( 0, stack_reserve, MEM_COMMIT, PAGE_READWRITE )))
- stack_reserve = max(stack_reserve, 1024 * 1024 - 3 * si.dwPageSize);
- if(!(fiber->stack_allocation = VirtualAlloc( 0, stack_reserve + 3 * si.dwPageSize, MEM_COMMIT, PAGE_READWRITE ))) { HeapFree( GetProcessHeap(), 0, fiber ); return NULL; }
- fiber->stack_base = (char *)fiber->stack_allocation + stack_reserve;
- fiber->stack_limit = fiber->stack_allocation;
- VirtualProtect(fiber->stack_allocation, 3 * si.dwPageSize, PAGE_NOACCESS, &prev);
- fiber->stack_base = (char *)fiber->stack_allocation + 3 * si.dwPageSize + stack_reserve;
- fiber->stack_limit = (char *)fiber->stack_allocation + 3 * si.dwPageSize;
Like the FIXME says, this should reuse the thread stack allocation routines, instead of reinventing them.
Currently it's implemented in virtual_alloc_thread_stack(), but this could be adapted and exported as RtlCreateUserStack().
On 6/12/19 3:36 PM, Alexandre Julliard wrote:
Zebediah Figura zfigura@codeweavers.com writes:
@@ -96,16 +98,19 @@ LPVOID WINAPI CreateFiberEx( SIZE_T stack_commit, SIZE_T stack_reserve, DWORD fl return NULL; }
- GetSystemInfo(&si);
/* FIXME: should use the thread stack allocation routines here */ /* some applications try to use more stack than they allocate */
- stack_reserve = max(stack_reserve, 1024 * 1024);
- if(!(fiber->stack_allocation = VirtualAlloc( 0, stack_reserve, MEM_COMMIT, PAGE_READWRITE )))
- stack_reserve = max(stack_reserve, 1024 * 1024 - 3 * si.dwPageSize);
- if(!(fiber->stack_allocation = VirtualAlloc( 0, stack_reserve + 3 * si.dwPageSize, MEM_COMMIT, PAGE_READWRITE ))) { HeapFree( GetProcessHeap(), 0, fiber ); return NULL; }
- fiber->stack_base = (char *)fiber->stack_allocation + stack_reserve;
- fiber->stack_limit = fiber->stack_allocation;
- VirtualProtect(fiber->stack_allocation, 3 * si.dwPageSize, PAGE_NOACCESS, &prev);
- fiber->stack_base = (char *)fiber->stack_allocation + 3 * si.dwPageSize + stack_reserve;
- fiber->stack_limit = (char *)fiber->stack_allocation + 3 * si.dwPageSize;
Like the FIXME says, this should reuse the thread stack allocation routines, instead of reinventing them.
Currently it's implemented in virtual_alloc_thread_stack(), but this could be adapted and exported as RtlCreateUserStack().
Sure, I'll use that approach instead.