aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPali Rohár <pali.rohar@gmail.com>2019-05-23 20:22:44 +0200
committerPali Rohár <pali.rohar@gmail.com>2019-05-23 20:22:44 +0200
commita5c0031ec4ac648261553128894e157ee41889cb (patch)
tree7c9b78c218bf3a9dc4ed9d1c94a18c8637a2d28c
parent1488731c810ed76589170909da9ef07f060cef46 (diff)
downloaddlfcn-win32-a5c0031ec4ac648261553128894e157ee41889cb.tar.gz
dlfcn-win32-a5c0031ec4ac648261553128894e157ee41889cb.tar.bz2
dlfcn-win32-a5c0031ec4ac648261553128894e157ee41889cb.zip
Correctly process and indicate error from LoadLibraryExA() function
Function save_err_str() checks for error by GetLastError() call. Calling EnumProcessModules() may change or reset it. So call save_err_str() immediately after LoadLibraryExA().
-rw-r--r--dlfcn.c41
1 files changed, 25 insertions, 16 deletions
diff --git a/dlfcn.c b/dlfcn.c
index 993808d..c97a870 100644
--- a/dlfcn.c
+++ b/dlfcn.c
@@ -267,24 +267,33 @@ void *dlopen( const char *file, int mode )
267 hModule = LoadLibraryExA(lpFileName, NULL, 267 hModule = LoadLibraryExA(lpFileName, NULL,
268 LOAD_WITH_ALTERED_SEARCH_PATH ); 268 LOAD_WITH_ALTERED_SEARCH_PATH );
269 269
270 if( MyEnumProcessModules( hCurrentProc, NULL, 0, &dwProcModsAfter ) == 0 )
271 dwProcModsAfter = 0;
272
273 /* If the object was loaded with RTLD_LOCAL, add it to list of local
274 * objects, so that its symbols cannot be retrieved even if the handle for
275 * the original program file is passed. POSIX says that if the same
276 * file is specified in multiple invocations, and any of them are
277 * RTLD_GLOBAL, even if any further invocations use RTLD_LOCAL, the
278 * symbols will remain global. If number of loaded modules was not
279 * changed after calling LoadLibraryEx(), it means that library was
280 * already loaded.
281 */
282 if( !hModule ) 270 if( !hModule )
271 {
283 save_err_str( lpFileName ); 272 save_err_str( lpFileName );
284 else if( (mode & RTLD_LOCAL) && dwProcModsBefore != dwProcModsAfter ) 273 }
285 local_add( hModule ); 274 else
286 else if( !(mode & RTLD_LOCAL) && dwProcModsBefore == dwProcModsAfter ) 275 {
287 local_rem( hModule ); 276 if( MyEnumProcessModules( hCurrentProc, NULL, 0, &dwProcModsAfter ) == 0 )
277 dwProcModsAfter = 0;
278
279 /* If the object was loaded with RTLD_LOCAL, add it to list of local
280 * objects, so that its symbols cannot be retrieved even if the handle for
281 * the original program file is passed. POSIX says that if the same
282 * file is specified in multiple invocations, and any of them are
283 * RTLD_GLOBAL, even if any further invocations use RTLD_LOCAL, the
284 * symbols will remain global. If number of loaded modules was not
285 * changed after calling LoadLibraryEx(), it means that library was
286 * already loaded.
287 */
288 if( (mode & RTLD_LOCAL) && dwProcModsBefore != dwProcModsAfter )
289 {
290 local_add( hModule );
291 }
292 else if( !(mode & RTLD_LOCAL) && dwProcModsBefore == dwProcModsAfter )
293 {
294 local_rem( hModule );
295 }
296 }
288 } 297 }
289 298
290 /* Return to previous state of the error-mode bit flags. */ 299 /* Return to previous state of the error-mode bit flags. */