Do not use the PEB lock as loader lock, use a separate critical

section for that (and for the graphics drivers).
This commit is contained in:
Alexandre Julliard 2002-02-02 18:13:50 +00:00
parent 2295e87be8
commit 64781643dd
4 changed files with 43 additions and 39 deletions

View file

@ -27,7 +27,7 @@ struct graphics_driver
static struct graphics_driver *first_driver; static struct graphics_driver *first_driver;
static struct graphics_driver *display_driver; static struct graphics_driver *display_driver;
static const DC_FUNCTIONS *win16_driver; static const DC_FUNCTIONS *win16_driver;
static CRITICAL_SECTION driver_section = CRITICAL_SECTION_INIT( "driver_section" );
/********************************************************************** /**********************************************************************
* create_driver * create_driver
@ -207,13 +207,13 @@ const DC_FUNCTIONS *DRIVER_load_driver( LPCSTR name )
HMODULE module; HMODULE module;
struct graphics_driver *driver; struct graphics_driver *driver;
RtlAcquirePebLock(); RtlEnterCriticalSection( &driver_section );
/* display driver is a special case */ /* display driver is a special case */
if (!strcasecmp( name, "display" )) if (!strcasecmp( name, "display" ))
{ {
driver = load_display_driver(); driver = load_display_driver();
RtlReleasePebLock(); RtlLeaveCriticalSection( &driver_section );
return &driver->funcs; return &driver->funcs;
} }
@ -224,7 +224,7 @@ const DC_FUNCTIONS *DRIVER_load_driver( LPCSTR name )
if (driver->module == module) if (driver->module == module)
{ {
driver->count++; driver->count++;
RtlReleasePebLock(); RtlLeaveCriticalSection( &driver_section );
return &driver->funcs; return &driver->funcs;
} }
} }
@ -233,19 +233,19 @@ const DC_FUNCTIONS *DRIVER_load_driver( LPCSTR name )
if (!(module = LoadLibraryA( name ))) if (!(module = LoadLibraryA( name )))
{ {
if (!win16_driver) win16_driver = WIN16DRV_Init(); if (!win16_driver) win16_driver = WIN16DRV_Init();
RtlReleasePebLock(); RtlLeaveCriticalSection( &driver_section );
return win16_driver; return win16_driver;
} }
if (!(driver = create_driver( module ))) if (!(driver = create_driver( module )))
{ {
FreeLibrary( module ); FreeLibrary( module );
RtlReleasePebLock(); RtlLeaveCriticalSection( &driver_section );
return NULL; return NULL;
} }
TRACE( "loaded driver %p for %s\n", driver, name ); TRACE( "loaded driver %p for %s\n", driver, name );
RtlReleasePebLock(); RtlLeaveCriticalSection( &driver_section );
return &driver->funcs; return &driver->funcs;
} }
@ -259,7 +259,7 @@ const DC_FUNCTIONS *DRIVER_get_driver( const DC_FUNCTIONS *funcs )
{ {
struct graphics_driver *driver; struct graphics_driver *driver;
RtlAcquirePebLock(); RtlEnterCriticalSection( &driver_section );
if (funcs != win16_driver) if (funcs != win16_driver)
{ {
for (driver = first_driver; driver; driver = driver->next) for (driver = first_driver; driver; driver = driver->next)
@ -267,7 +267,7 @@ const DC_FUNCTIONS *DRIVER_get_driver( const DC_FUNCTIONS *funcs )
if (!driver) ERR( "driver not found, trouble ahead\n" ); if (!driver) ERR( "driver not found, trouble ahead\n" );
driver->count++; driver->count++;
} }
RtlReleasePebLock(); RtlLeaveCriticalSection( &driver_section );
return funcs; return funcs;
} }
@ -281,7 +281,7 @@ void DRIVER_release_driver( const DC_FUNCTIONS *funcs )
{ {
struct graphics_driver *driver; struct graphics_driver *driver;
RtlAcquirePebLock(); RtlEnterCriticalSection( &driver_section );
if (funcs == win16_driver) goto done; if (funcs == win16_driver) goto done;
@ -300,7 +300,7 @@ void DRIVER_release_driver( const DC_FUNCTIONS *funcs )
FreeLibrary( driver->module ); FreeLibrary( driver->module );
HeapFree( GetProcessHeap(), 0, driver ); HeapFree( GetProcessHeap(), 0, driver );
done: done:
RtlReleasePebLock(); RtlLeaveCriticalSection( &driver_section );
} }

View file

@ -29,6 +29,8 @@ static WINE_MODREF *exe_modref;
static int free_lib_count; /* recursion depth of FreeLibrary calls */ static int free_lib_count; /* recursion depth of FreeLibrary calls */
static int process_detaching; /* set on process detach to avoid deadlocks with thread detach */ static int process_detaching; /* set on process detach to avoid deadlocks with thread detach */
static CRITICAL_SECTION loader_section = CRITICAL_SECTION_INIT( "loader_section" );
/*********************************************************************** /***********************************************************************
* wait_input_idle * wait_input_idle
* *
@ -176,9 +178,13 @@ BOOL MODULE_DllProcessAttach( WINE_MODREF *wm, LPVOID lpReserved )
BOOL retv = TRUE; BOOL retv = TRUE;
int i; int i;
RtlAcquirePebLock(); RtlEnterCriticalSection( &loader_section );
if (!wm) wm = exe_modref; if (!wm)
{
wm = exe_modref;
PE_InitTls();
}
assert( wm ); assert( wm );
/* prevent infinite recursion in case of cyclical dependencies */ /* prevent infinite recursion in case of cyclical dependencies */
@ -221,7 +227,7 @@ BOOL MODULE_DllProcessAttach( WINE_MODREF *wm, LPVOID lpReserved )
TRACE("(%s,%p) - END\n", wm->modname, lpReserved ); TRACE("(%s,%p) - END\n", wm->modname, lpReserved );
done: done:
RtlReleasePebLock(); RtlLeaveCriticalSection( &loader_section );
return retv; return retv;
} }
@ -236,7 +242,7 @@ void MODULE_DllProcessDetach( BOOL bForceDetach, LPVOID lpReserved )
{ {
WINE_MODREF *wm; WINE_MODREF *wm;
RtlAcquirePebLock(); RtlEnterCriticalSection( &loader_section );
if (bForceDetach) process_detaching = 1; if (bForceDetach) process_detaching = 1;
do do
{ {
@ -258,7 +264,7 @@ void MODULE_DllProcessDetach( BOOL bForceDetach, LPVOID lpReserved )
} }
} while ( wm ); } while ( wm );
RtlReleasePebLock(); RtlLeaveCriticalSection( &loader_section );
} }
/************************************************************************* /*************************************************************************
@ -276,7 +282,9 @@ void MODULE_DllThreadAttach( LPVOID lpReserved )
if (process_detaching) return; if (process_detaching) return;
/* FIXME: there is still a race here */ /* FIXME: there is still a race here */
RtlAcquirePebLock(); RtlEnterCriticalSection( &loader_section );
PE_InitTls();
for ( wm = MODULE_modref_list; wm; wm = wm->next ) for ( wm = MODULE_modref_list; wm; wm = wm->next )
if ( !wm->next ) if ( !wm->next )
@ -292,7 +300,7 @@ void MODULE_DllThreadAttach( LPVOID lpReserved )
MODULE_InitDLL( wm, DLL_THREAD_ATTACH, lpReserved ); MODULE_InitDLL( wm, DLL_THREAD_ATTACH, lpReserved );
} }
RtlReleasePebLock(); RtlLeaveCriticalSection( &loader_section );
} }
/************************************************************************* /*************************************************************************
@ -310,7 +318,7 @@ void MODULE_DllThreadDetach( LPVOID lpReserved )
if (process_detaching) return; if (process_detaching) return;
/* FIXME: there is still a race here */ /* FIXME: there is still a race here */
RtlAcquirePebLock(); RtlEnterCriticalSection( &loader_section );
for ( wm = MODULE_modref_list; wm; wm = wm->next ) for ( wm = MODULE_modref_list; wm; wm = wm->next )
{ {
@ -322,7 +330,7 @@ void MODULE_DllThreadDetach( LPVOID lpReserved )
MODULE_InitDLL( wm, DLL_THREAD_DETACH, lpReserved ); MODULE_InitDLL( wm, DLL_THREAD_DETACH, lpReserved );
} }
RtlReleasePebLock(); RtlLeaveCriticalSection( &loader_section );
} }
/**************************************************************************** /****************************************************************************
@ -335,7 +343,7 @@ BOOL WINAPI DisableThreadLibraryCalls( HMODULE hModule )
WINE_MODREF *wm; WINE_MODREF *wm;
BOOL retval = TRUE; BOOL retval = TRUE;
RtlAcquirePebLock(); RtlEnterCriticalSection( &loader_section );
wm = MODULE32_LookupHMODULE( hModule ); wm = MODULE32_LookupHMODULE( hModule );
if ( !wm ) if ( !wm )
@ -343,7 +351,7 @@ BOOL WINAPI DisableThreadLibraryCalls( HMODULE hModule )
else else
wm->flags |= WINE_MODREF_NO_DLL_CALLS; wm->flags |= WINE_MODREF_NO_DLL_CALLS;
RtlReleasePebLock(); RtlLeaveCriticalSection( &loader_section );
return retval; return retval;
} }
@ -1231,13 +1239,13 @@ DWORD WINAPI GetModuleFileNameA(
{ {
WINE_MODREF *wm; WINE_MODREF *wm;
RtlAcquirePebLock(); RtlEnterCriticalSection( &loader_section );
lpFileName[0] = 0; lpFileName[0] = 0;
if ((wm = MODULE32_LookupHMODULE( hModule ))) if ((wm = MODULE32_LookupHMODULE( hModule )))
lstrcpynA( lpFileName, wm->filename, size ); lstrcpynA( lpFileName, wm->filename, size );
RtlReleasePebLock(); RtlLeaveCriticalSection( &loader_section );
TRACE("%s\n", lpFileName ); TRACE("%s\n", lpFileName );
return strlen(lpFileName); return strlen(lpFileName);
} }
@ -1304,7 +1312,7 @@ HMODULE WINAPI LoadLibraryExA(LPCSTR libname, HANDLE hfile, DWORD flags)
/* Fallback to normal behaviour */ /* Fallback to normal behaviour */
} }
RtlAcquirePebLock(); RtlEnterCriticalSection( &loader_section );
wm = MODULE_LoadLibraryExA( libname, hfile, flags ); wm = MODULE_LoadLibraryExA( libname, hfile, flags );
if ( wm ) if ( wm )
@ -1318,7 +1326,7 @@ HMODULE WINAPI LoadLibraryExA(LPCSTR libname, HANDLE hfile, DWORD flags)
} }
} }
RtlReleasePebLock(); RtlLeaveCriticalSection( &loader_section );
return wm ? wm->module : 0; return wm ? wm->module : 0;
} }
@ -1392,7 +1400,7 @@ WINE_MODREF *MODULE_LoadLibraryExA( LPCSTR libname, HFILE hfile, DWORD flags )
if ( !filename ) return NULL; if ( !filename ) return NULL;
*filename = 0; /* Just in case we don't set it before goto error */ *filename = 0; /* Just in case we don't set it before goto error */
RtlAcquirePebLock(); RtlEnterCriticalSection( &loader_section );
if ((flags & LOAD_WITH_ALTERED_SEARCH_PATH) && FILE_contains_path(libname)) if ((flags & LOAD_WITH_ALTERED_SEARCH_PATH) && FILE_contains_path(libname))
{ {
@ -1470,7 +1478,7 @@ WINE_MODREF *MODULE_LoadLibraryExA( LPCSTR libname, HFILE hfile, DWORD flags )
HeapFree ( GetProcessHeap(), 0, (LPSTR)libdir ); HeapFree ( GetProcessHeap(), 0, (LPSTR)libdir );
libdir = NULL; libdir = NULL;
} }
RtlReleasePebLock(); RtlLeaveCriticalSection( &loader_section );
HeapFree ( GetProcessHeap(), 0, filename ); HeapFree ( GetProcessHeap(), 0, filename );
return pwm; return pwm;
} }
@ -1522,7 +1530,7 @@ WINE_MODREF *MODULE_LoadLibraryExA( LPCSTR libname, HFILE hfile, DWORD flags )
HeapFree ( GetProcessHeap(), 0, (LPSTR)libdir ); HeapFree ( GetProcessHeap(), 0, (LPSTR)libdir );
libdir = NULL; libdir = NULL;
} }
RtlReleasePebLock(); RtlLeaveCriticalSection( &loader_section );
SetLastError( err ); /* restore last error */ SetLastError( err ); /* restore last error */
HeapFree ( GetProcessHeap(), 0, filename ); HeapFree ( GetProcessHeap(), 0, filename );
return pwm; return pwm;
@ -1538,7 +1546,7 @@ WINE_MODREF *MODULE_LoadLibraryExA( LPCSTR libname, HFILE hfile, DWORD flags )
HeapFree ( GetProcessHeap(), 0, (LPSTR)libdir ); HeapFree ( GetProcessHeap(), 0, (LPSTR)libdir );
libdir = NULL; libdir = NULL;
} }
RtlReleasePebLock(); RtlLeaveCriticalSection( &loader_section );
WARN("Failed to load module '%s'; error=0x%08lx\n", filename, GetLastError()); WARN("Failed to load module '%s'; error=0x%08lx\n", filename, GetLastError());
HeapFree ( GetProcessHeap(), 0, filename ); HeapFree ( GetProcessHeap(), 0, filename );
return NULL; return NULL;
@ -1645,13 +1653,13 @@ BOOL WINAPI FreeLibrary(HINSTANCE hLibModule)
return TRUE; return TRUE;
} }
RtlAcquirePebLock(); RtlEnterCriticalSection( &loader_section );
free_lib_count++; free_lib_count++;
if ((wm = MODULE32_LookupHMODULE( hLibModule ))) retv = MODULE_FreeLibrary( wm ); if ((wm = MODULE32_LookupHMODULE( hLibModule ))) retv = MODULE_FreeLibrary( wm );
free_lib_count--; free_lib_count--;
RtlReleasePebLock(); RtlLeaveCriticalSection( &loader_section );
return retv; return retv;
} }
@ -1829,13 +1837,13 @@ FARPROC MODULE_GetProcAddress(
else else
TRACE_(win32)("(%08lx,%p)\n",(DWORD)hModule,function); TRACE_(win32)("(%08lx,%p)\n",(DWORD)hModule,function);
RtlAcquirePebLock(); RtlEnterCriticalSection( &loader_section );
if ((wm = MODULE32_LookupHMODULE( hModule ))) if ((wm = MODULE32_LookupHMODULE( hModule )))
{ {
retproc = wm->find_export( wm, function, snoop ); retproc = wm->find_export( wm, function, snoop );
if (!retproc) SetLastError(ERROR_PROC_NOT_FOUND); if (!retproc) SetLastError(ERROR_PROC_NOT_FOUND);
} }
RtlReleasePebLock(); RtlLeaveCriticalSection( &loader_section );
return retproc; return retproc;
} }

View file

@ -111,7 +111,7 @@ extern void PTHREAD_init_done(void);
extern BOOL MAIN_MainInit(void); extern BOOL MAIN_MainInit(void);
typedef WORD WINAPI (*pUserSignalProc)( UINT, DWORD, DWORD, HMODULE16 ); typedef WORD (WINAPI *pUserSignalProc)( UINT, DWORD, DWORD, HMODULE16 );
/*********************************************************************** /***********************************************************************
* PROCESS_CallUserSignalProc * PROCESS_CallUserSignalProc
@ -367,10 +367,7 @@ static void start_process(void)
if (main_exe_file) CloseHandle( main_exe_file ); /* we no longer need it */ if (main_exe_file) CloseHandle( main_exe_file ); /* we no longer need it */
RtlAcquirePebLock();
PE_InitTls();
MODULE_DllProcessAttach( NULL, (LPVOID)1 ); MODULE_DllProcessAttach( NULL, (LPVOID)1 );
RtlReleasePebLock();
/* Note: The USIG_PROCESS_CREATE signal is supposed to be sent in the /* Note: The USIG_PROCESS_CREATE signal is supposed to be sent in the
* context of the parent process. Actually, the USER signal proc * context of the parent process. Actually, the USER signal proc

View file

@ -247,7 +247,6 @@ static void THREAD_Start(void)
DPRINTF("%08lx:Starting thread (entryproc=%p)\n", GetCurrentThreadId(), func ); DPRINTF("%08lx:Starting thread (entryproc=%p)\n", GetCurrentThreadId(), func );
PROCESS_CallUserSignalProc( USIG_THREAD_INIT, 0 ); PROCESS_CallUserSignalProc( USIG_THREAD_INIT, 0 );
PE_InitTls();
MODULE_DllThreadAttach( NULL ); MODULE_DllThreadAttach( NULL );
ExitThread( func( NtCurrentTeb()->entry_arg ) ); ExitThread( func( NtCurrentTeb()->entry_arg ) );
} }