Module: wine Branch: master Commit: 600694546f6805c2e1a88a05e056a8b00d187d6e URL: http://source.winehq.org/git/wine.git/?a=commit;h=600694546f6805c2e1a88a05e0...
Author: Alexandre Julliard julliard@winehq.org Date: Tue Apr 1 14:11:44 2008 +0200
ntdll: Moved stack allocation for thread and process to a common routine in virtual.c.
---
dlls/ntdll/loader.c | 45 ++++------------------------------------- dlls/ntdll/ntdll_misc.h | 1 + dlls/ntdll/thread.c | 16 +-------------- dlls/ntdll/virtual.c | 50 +++++++++++++++++++++++++++++++++++++++++++++++ 4 files changed, 57 insertions(+), 55 deletions(-)
diff --git a/dlls/ntdll/loader.c b/dlls/ntdll/loader.c index 3b60d60..1091c32 100644 --- a/dlls/ntdll/loader.c +++ b/dlls/ntdll/loader.c @@ -27,9 +27,6 @@ #ifdef HAVE_SYS_MMAN_H # include <sys/mman.h> #endif -#ifdef HAVE_VALGRIND_MEMCHECK_H -# include <valgrind/memcheck.h> -#endif
#define NONAMELESSUNION #define NONAMELESSSTRUCT @@ -2320,42 +2317,6 @@ PIMAGE_NT_HEADERS WINAPI RtlImageNtHeader(HMODULE hModule)
/*********************************************************************** - * alloc_process_stack - * - * Allocate the stack of new process. - */ -static NTSTATUS alloc_process_stack( IMAGE_NT_HEADERS *nt ) -{ - NTSTATUS status; - void *base = NULL; - SIZE_T stack_size, page_size = getpagesize(); - - stack_size = max( nt->OptionalHeader.SizeOfStackReserve, nt->OptionalHeader.SizeOfStackCommit ); - stack_size += page_size; /* for the guard page */ - stack_size = (stack_size + 0xffff) & ~0xffff; /* round to 64K boundary */ - if (stack_size < 1024 * 1024) stack_size = 1024 * 1024; /* Xlib needs a large stack */ - - if ((status = NtAllocateVirtualMemory( GetCurrentProcess(), &base, 16, &stack_size, - MEM_COMMIT, PAGE_READWRITE ))) - return status; - - /* note: limit is lower than base since the stack grows down */ - NtCurrentTeb()->DeallocationStack = base; - NtCurrentTeb()->Tib.StackBase = (char *)base + stack_size; - NtCurrentTeb()->Tib.StackLimit = (char *)base + page_size; - -#ifdef VALGRIND_STACK_REGISTER - /* no need to de-register the stack as it's the one of the main thread */ - VALGRIND_STACK_REGISTER(NtCurrentTeb()->Tib.StackLimit, NtCurrentTeb()->Tib.StackBase); -#endif - - /* setup guard page */ - NtProtectVirtualMemory( GetCurrentProcess(), &base, &page_size, PAGE_NOACCESS, NULL ); - return STATUS_SUCCESS; -} - - -/*********************************************************************** * attach_process_dlls * * Initial attach to all the dlls loaded by the process. @@ -2387,6 +2348,7 @@ void WINAPI LdrInitializeThunk( ULONG unknown1, ULONG unknown2, ULONG unknown3, NTSTATUS status; WINE_MODREF *wm; LPCWSTR load_path; + SIZE_T stack_size; PEB *peb = NtCurrentTeb()->Peb; IMAGE_NT_HEADERS *nt = RtlImageNtHeader( peb->ImageBaseAddress );
@@ -2409,7 +2371,10 @@ void WINAPI LdrInitializeThunk( ULONG unknown1, ULONG unknown2, ULONG unknown3, RemoveEntryList( &wm->ldr.InLoadOrderModuleList ); InsertHeadList( &peb->LdrData->InLoadOrderModuleList, &wm->ldr.InLoadOrderModuleList );
- if ((status = alloc_process_stack( nt )) != STATUS_SUCCESS) goto error; + stack_size = max( nt->OptionalHeader.SizeOfStackReserve, nt->OptionalHeader.SizeOfStackCommit ); + if (stack_size < 1024 * 1024) stack_size = 1024 * 1024; /* Xlib needs a large stack */ + + if ((status = virtual_alloc_thread_stack( NULL, stack_size )) != STATUS_SUCCESS) goto error; if ((status = server_init_process_done()) != STATUS_SUCCESS) goto error;
actctx_init(); diff --git a/dlls/ntdll/ntdll_misc.h b/dlls/ntdll/ntdll_misc.h index 8c04557..3a12b8f 100644 --- a/dlls/ntdll/ntdll_misc.h +++ b/dlls/ntdll/ntdll_misc.h @@ -133,6 +133,7 @@ extern NTSTATUS DIR_get_unix_cwd( char **cwd ); extern unsigned int DIR_get_drives_info( struct drive_info info[MAX_DOS_DRIVES] );
/* virtual memory */ +extern NTSTATUS virtual_alloc_thread_stack( void *base, SIZE_T stack_size ); extern NTSTATUS VIRTUAL_HandleFault(LPCVOID addr); extern void VIRTUAL_SetForceExec( BOOL enable ); extern void VIRTUAL_UseLargeAddressSpace(void); diff --git a/dlls/ntdll/thread.c b/dlls/ntdll/thread.c index 65283e0..4298e95 100644 --- a/dlls/ntdll/thread.c +++ b/dlls/ntdll/thread.c @@ -418,7 +418,6 @@ static void start_thread( struct wine_pthread_thread_info *info ) PRTL_THREAD_START_ROUTINE func = startup_info->entry_point; void *arg = startup_info->entry_arg; struct debug_info debug_info; - SIZE_T size, page_size = getpagesize();
debug_info.str_pos = debug_info.strings; debug_info.out_pos = debug_info.output; @@ -428,20 +427,7 @@ static void start_thread( struct wine_pthread_thread_info *info ) SIGNAL_Init(); server_init_thread( info->pid, info->tid, func ); pthread_functions.init_thread( info ); - - /* allocate a memory view for the stack */ - size = info->stack_size; - teb->DeallocationStack = info->stack_base; - NtAllocateVirtualMemory( NtCurrentProcess(), &teb->DeallocationStack, 0, - &size, MEM_SYSTEM, PAGE_READWRITE ); - /* limit is lower than base since the stack grows down */ - teb->Tib.StackBase = (char *)info->stack_base + info->stack_size; - teb->Tib.StackLimit = (char *)info->stack_base + page_size; - - /* setup the guard page */ - size = page_size; - NtProtectVirtualMemory( NtCurrentProcess(), &teb->DeallocationStack, &size, PAGE_NOACCESS, NULL ); - + virtual_alloc_thread_stack( info->stack_base, info->stack_size ); pthread_functions.sigprocmask( SIG_UNBLOCK, &server_block_set, NULL );
RtlAcquirePebLock(); diff --git a/dlls/ntdll/virtual.c b/dlls/ntdll/virtual.c index 1c44d49..548e819 100644 --- a/dlls/ntdll/virtual.c +++ b/dlls/ntdll/virtual.c @@ -41,6 +41,9 @@ #ifdef HAVE_SYS_MMAN_H # include <sys/mman.h> #endif +#ifdef HAVE_VALGRIND_MEMCHECK_H +# include <valgrind/memcheck.h> +#endif
#define NONAMELESSUNION #define NONAMELESSSTRUCT @@ -1253,6 +1256,53 @@ void virtual_init_threading(void)
/*********************************************************************** + * virtual_alloc_thread_stack + */ +NTSTATUS virtual_alloc_thread_stack( void *base, SIZE_T size ) +{ + FILE_VIEW *view; + NTSTATUS status; + sigset_t sigset; + + server_enter_uninterrupted_section( &csVirtual, &sigset ); + + if (base) /* already allocated, create a system view */ + { + size = ROUND_SIZE( base, size ); + base = ROUND_ADDR( base, page_mask ); + if ((status = create_view( &view, base, size, + VPROT_READ | VPROT_WRITE | VPROT_COMMITTED )) != STATUS_SUCCESS) + goto done; + view->flags |= VFLAG_VALLOC | VFLAG_SYSTEM; + } + else + { + size = (size + 0xffff) & ~0xffff; /* round to 64K boundary */ + if ((status = map_view( &view, NULL, size, 0xffff, 0, + VPROT_READ | VPROT_WRITE | VPROT_COMMITTED )) != STATUS_SUCCESS) + goto done; + view->flags |= VFLAG_VALLOC; +#ifdef VALGRIND_STACK_REGISTER + /* no need to de-register the stack as it's the one of the main thread */ + VALGRIND_STACK_REGISTER( view->base, (char *)view->base + view->size ); +#endif + } + + /* setup no access guard page */ + VIRTUAL_SetProt( view, view->base, page_size, VPROT_COMMITTED ); + + /* note: limit is lower than base since the stack grows down */ + NtCurrentTeb()->DeallocationStack = view->base; + NtCurrentTeb()->Tib.StackBase = (char *)view->base + view->size; + NtCurrentTeb()->Tib.StackLimit = (char *)view->base + page_size; + +done: + server_leave_uninterrupted_section( &csVirtual, &sigset ); + return status; +} + + +/*********************************************************************** * VIRTUAL_HandleFault */ NTSTATUS VIRTUAL_HandleFault( LPCVOID addr )