From: Francois Gouget fgouget@codeweavers.com
--- dlls/ntdll/tests/threadpool.c | 23 ++++++++++++++++++++++- 1 file changed, 22 insertions(+), 1 deletion(-)
diff --git a/dlls/ntdll/tests/threadpool.c b/dlls/ntdll/tests/threadpool.c index 008755e6e5d..c2991a2ad57 100644 --- a/dlls/ntdll/tests/threadpool.c +++ b/dlls/ntdll/tests/threadpool.c @@ -33,15 +33,17 @@ static VOID (WINAPI *pTpCallbackReleaseSemaphoreOnCompletion)(TP_CALLBACK_IN static void (WINAPI *pTpCancelAsyncIoOperation)(TP_IO *); static VOID (WINAPI *pTpDisassociateCallback)(TP_CALLBACK_INSTANCE *); static BOOL (WINAPI *pTpIsTimerSet)(TP_TIMER *); -static VOID (WINAPI *pTpReleaseWait)(TP_WAIT *); static VOID (WINAPI *pTpPostWork)(TP_WORK *); +static NTSTATUS (WINAPI *pTpQueryPoolStackInformation)(TP_POOL *,TP_POOL_STACK_INFORMATION *); static VOID (WINAPI *pTpReleaseCleanupGroup)(TP_CLEANUP_GROUP *); static VOID (WINAPI *pTpReleaseCleanupGroupMembers)(TP_CLEANUP_GROUP *,BOOL,PVOID); static void (WINAPI *pTpReleaseIoCompletion)(TP_IO *); static VOID (WINAPI *pTpReleasePool)(TP_POOL *); static VOID (WINAPI *pTpReleaseTimer)(TP_TIMER *); +static VOID (WINAPI *pTpReleaseWait)(TP_WAIT *); static VOID (WINAPI *pTpReleaseWork)(TP_WORK *); static VOID (WINAPI *pTpSetPoolMaxThreads)(TP_POOL *,DWORD); +static NTSTATUS (WINAPI *pTpSetPoolStackInformation)(TP_POOL *,TP_POOL_STACK_INFORMATION *); static VOID (WINAPI *pTpSetTimer)(TP_TIMER *,LARGE_INTEGER *,LONG,LONG); static VOID (WINAPI *pTpSetWait)(TP_WAIT *,HANDLE,LARGE_INTEGER *); static NTSTATUS (WINAPI *pTpSimpleTryPost)(PTP_SIMPLE_CALLBACK,PVOID,TP_CALLBACK_ENVIRON *); @@ -80,6 +82,7 @@ static BOOL init_threadpool(void) GET_PROC(TpDisassociateCallback); GET_PROC(TpIsTimerSet); GET_PROC(TpPostWork); + GET_PROC(TpQueryPoolStackInformation); GET_PROC(TpReleaseCleanupGroup); GET_PROC(TpReleaseCleanupGroupMembers); GET_PROC(TpReleaseIoCompletion); @@ -88,6 +91,7 @@ static BOOL init_threadpool(void) GET_PROC(TpReleaseWait); GET_PROC(TpReleaseWork); GET_PROC(TpSetPoolMaxThreads); + GET_PROC(TpSetPoolStackInformation); GET_PROC(TpSetTimer); GET_PROC(TpSetWait); GET_PROC(TpSimpleTryPost); @@ -575,6 +579,7 @@ static void CALLBACK simple2_cb(TP_CALLBACK_INSTANCE *instance, void *userdata)
static void test_tp_simple(void) { + TP_POOL_STACK_INFORMATION stack_info; TP_CALLBACK_ENVIRON environment; TP_CALLBACK_ENVIRON_V3 environment3; TP_CLEANUP_GROUP *group; @@ -678,6 +683,22 @@ static void test_tp_simple(void) pTpReleaseCleanupGroupMembers(group, TRUE, NULL); ok(userdata < 100, "expected userdata < 100, got %lu\n", userdata);
+ /* test querying and setting the stack size */ + status = pTpQueryPoolStackInformation(pool, &stack_info); + ok(!status, "TpQueryPoolStackInformation failed: %lx\n", status); + ok(stack_info.StackReserve == 2 * 1024 * 1024, "expected default StackReserve, got %ld\n", (ULONG)stack_info.StackReserve); + ok(stack_info.StackCommit == 4 * 1024, "expected default StackCommit, got %ld\n", (ULONG)stack_info.StackCommit); + + /* threadpool does not validate the stack size values */ + stack_info.StackReserve = stack_info.StackCommit = 1; + status = pTpSetPoolStackInformation(pool, &stack_info); + ok(!status, "TpQueryPoolStackInformation failed: %lx\n", status); + + status = pTpQueryPoolStackInformation(pool, &stack_info); + ok(!status, "TpQueryPoolStackInformation failed: %lx\n", status); + ok(stack_info.StackReserve == 1, "expected 1 byte StackReserve, got %ld\n", (ULONG)stack_info.StackReserve); + ok(stack_info.StackCommit == 1, "expected 1 byte StackCommit, got %ld\n", (ULONG)stack_info.StackCommit); + /* cleanup */ pTpReleaseCleanupGroup(group); pTpReleasePool(pool);
From: Francois Gouget fgouget@codeweavers.com
--- dlls/ntdll/threadpool.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
diff --git a/dlls/ntdll/threadpool.c b/dlls/ntdll/threadpool.c index 99525f831e1..c50983e83d4 100644 --- a/dlls/ntdll/threadpool.c +++ b/dlls/ntdll/threadpool.c @@ -1152,7 +1152,8 @@ static NTSTATUS tp_new_worker_thread( struct threadpool *pool ) HANDLE thread; NTSTATUS status;
- status = RtlCreateUserThread( GetCurrentProcess(), NULL, FALSE, 0, 0, 0, + status = RtlCreateUserThread( GetCurrentProcess(), NULL, FALSE, 0, + pool->stack_info.StackReserve, pool->stack_info.StackCommit, threadpool_worker_proc, pool, &thread, NULL ); if (status == STATUS_SUCCESS) {