Alexandre Julliard : setupapi: Delay freeing registered dlls until they have all been processed.
Module: wine Branch: master Commit: a192b707f2d102374771ed90e6c94ea40e79a08a URL: http://source.winehq.org/git/wine.git/?a=commit;h=a192b707f2d102374771ed90e6... Author: Alexandre Julliard <julliard(a)winehq.org> Date: Fri Aug 26 13:12:26 2011 +0200 setupapi: Delay freeing registered dlls until they have all been processed. --- dlls/setupapi/install.c | 49 ++++++++++++++++++++++++++++++++++++++-------- 1 files changed, 40 insertions(+), 9 deletions(-) diff --git a/dlls/setupapi/install.c b/dlls/setupapi/install.c index 8f52a58..6ecc288 100644 --- a/dlls/setupapi/install.c +++ b/dlls/setupapi/install.c @@ -63,6 +63,9 @@ struct register_dll_info PSP_FILE_CALLBACK_W callback; PVOID callback_context; BOOL unregister; + int modules_size; + int modules_count; + HMODULE *modules; }; typedef BOOL (*iterate_fields_func)( HINF hinf, PCWSTR field, void *arg ); @@ -492,7 +495,7 @@ static BOOL registry_callback( HINF hinf, PCWSTR field, void *arg ) * * Register or unregister a dll. */ -static BOOL do_register_dll( const struct register_dll_info *info, const WCHAR *path, +static BOOL do_register_dll( struct register_dll_info *info, const WCHAR *path, INT flags, INT timeout, const WCHAR *args ) { HMODULE module; @@ -616,7 +619,23 @@ static BOOL do_register_dll( const struct register_dll_info *info, const WCHAR * } done: - if (module) FreeLibrary( module ); + if (module) + { + if (info->modules_count >= info->modules_size) + { + int new_size = max( 32, info->modules_size * 2 ); + HMODULE *new = info->modules ? + HeapReAlloc( GetProcessHeap(), 0, info->modules, new_size * sizeof(*new) ) : + HeapAlloc( GetProcessHeap(), 0, new_size * sizeof(*new) ); + if (new) + { + info->modules_size = new_size; + info->modules = new; + } + } + if (info->modules_count < info->modules_size) info->modules[info->modules_count++] = module; + else FreeLibrary( module ); + } if (info->callback) info->callback( info->callback_context, SPFILENOTIFY_ENDREGISTRATION, (UINT_PTR)&status, !info->unregister ); return TRUE; @@ -1047,11 +1066,13 @@ BOOL WINAPI SetupInstallFromInfSectionW( HWND owner, HINF hinf, PCWSTR section, PSP_FILE_CALLBACK_W callback, PVOID context, HDEVINFO devinfo, PSP_DEVINFO_DATA devinfo_data ) { + BOOL ret; + int i; + if (flags & SPINST_FILES) { struct files_callback_info info; HSPFILEQ queue; - BOOL ret; if (!(queue = SetupOpenFileQueue())) return FALSE; info.queue = queue; @@ -1086,7 +1107,10 @@ BOOL WINAPI SetupInstallFromInfSectionW( HWND owner, HINF hinf, PCWSTR section, { struct register_dll_info info; - info.unregister = FALSE; + info.unregister = FALSE; + info.modules_size = 0; + info.modules_count = 0; + info.modules = NULL; if (flags & SPINST_REGISTERCALLBACKAWARE) { info.callback = callback; @@ -1099,14 +1123,19 @@ BOOL WINAPI SetupInstallFromInfSectionW( HWND owner, HINF hinf, PCWSTR section, else return FALSE; - if (!iterate_section_fields( hinf, section, RegisterDlls, register_dlls_callback, &info )) - return FALSE; + ret = iterate_section_fields( hinf, section, RegisterDlls, register_dlls_callback, &info ); + for (i = 0; i < info.modules_count; i++) FreeLibrary( info.modules[i] ); + HeapFree( GetProcessHeap(), 0, info.modules ); + if (!ret) return FALSE; } if (flags & SPINST_UNREGSVR) { struct register_dll_info info; - info.unregister = TRUE; + info.unregister = TRUE; + info.modules_size = 0; + info.modules_count = 0; + info.modules = NULL; if (flags & SPINST_REGISTERCALLBACKAWARE) { info.callback = callback; @@ -1114,8 +1143,10 @@ BOOL WINAPI SetupInstallFromInfSectionW( HWND owner, HINF hinf, PCWSTR section, } else info.callback = NULL; - if (!iterate_section_fields( hinf, section, UnregisterDlls, register_dlls_callback, &info )) - return FALSE; + ret = iterate_section_fields( hinf, section, UnregisterDlls, register_dlls_callback, &info ); + for (i = 0; i < info.modules_count; i++) FreeLibrary( info.modules[i] ); + HeapFree( GetProcessHeap(), 0, info.modules ); + if (!ret) return FALSE; } if (flags & SPINST_REGISTRY) {
participants (1)
-
Alexandre Julliard