diff options
author | Silvio Traversaro <silvio@traversaro.it> | 2019-05-06 21:02:00 +0200 |
---|---|---|
committer | GitHub <noreply@github.com> | 2019-05-06 21:02:00 +0200 |
commit | 84295c9afc0b42a61cf687d54c3bd5e286fd5176 (patch) | |
tree | fbc516853834d82eab68552b7ddcf0f0698ef43d /dlfcn.c | |
parent | 278c782a3205dbe49de4233b3bd1e68687a9998b (diff) | |
parent | e0a5832163960d3eb95fc0514be1bd99e51caf0c (diff) | |
download | dlfcn-win32-84295c9afc0b42a61cf687d54c3bd5e286fd5176.tar.gz dlfcn-win32-84295c9afc0b42a61cf687d54c3bd5e286fd5176.tar.bz2 dlfcn-win32-84295c9afc0b42a61cf687d54c3bd5e286fd5176.zip |
Merge pull request #50 from pali/master
Simplify UNICODE build
Diffstat (limited to 'dlfcn.c')
-rw-r--r-- | dlfcn.c | 127 |
1 files changed, 32 insertions, 95 deletions
@@ -46,19 +46,6 @@ | |||
46 | #endif | 46 | #endif |
47 | #include "dlfcn.h" | 47 | #include "dlfcn.h" |
48 | 48 | ||
49 | #if ((defined(_WIN32) || defined(WIN32)) && (defined(_MSC_VER)) ) | ||
50 | #define snprintf sprintf_s | ||
51 | #endif | ||
52 | |||
53 | #ifdef UNICODE | ||
54 | #include <wchar.h> | ||
55 | #define CHAR wchar_t | ||
56 | #define UNICODE_L(s) L##s | ||
57 | #else | ||
58 | #define CHAR char | ||
59 | #define UNICODE_L(s) s | ||
60 | #endif | ||
61 | |||
62 | /* Note: | 49 | /* Note: |
63 | * MSDN says these functions are not thread-safe. We make no efforts to have | 50 | * MSDN says these functions are not thread-safe. We make no efforts to have |
64 | * any kind of thread safety. | 51 | * any kind of thread safety. |
@@ -142,49 +129,45 @@ static void local_rem( HMODULE hModule ) | |||
142 | * MSDN says the buffer cannot be larger than 64K bytes, so we set it to | 129 | * MSDN says the buffer cannot be larger than 64K bytes, so we set it to |
143 | * the limit. | 130 | * the limit. |
144 | */ | 131 | */ |
145 | static CHAR error_buffer[65535]; | 132 | static char error_buffer[65535]; |
146 | static CHAR *current_error; | 133 | static char *current_error; |
147 | static char dlerror_buffer[65536]; | 134 | static char dlerror_buffer[65536]; |
148 | 135 | ||
149 | static int copy_string( CHAR *dest, int dest_size, const CHAR *src ) | 136 | static void save_err_str( const char *str ) |
150 | { | ||
151 | int i = 0; | ||
152 | |||
153 | /* gcc should optimize this out */ | ||
154 | if( !src || !dest ) | ||
155 | return 0; | ||
156 | |||
157 | for( i = 0 ; i < dest_size-1 ; i++ ) | ||
158 | { | ||
159 | if( !src[i] ) | ||
160 | break; | ||
161 | else | ||
162 | dest[i] = src[i]; | ||
163 | } | ||
164 | dest[i] = '\0'; | ||
165 | |||
166 | return i; | ||
167 | } | ||
168 | |||
169 | static void save_err_str( const CHAR *str ) | ||
170 | { | 137 | { |
171 | DWORD dwMessageId; | 138 | DWORD dwMessageId; |
172 | DWORD pos; | 139 | DWORD ret; |
140 | size_t pos, len; | ||
173 | 141 | ||
174 | dwMessageId = GetLastError( ); | 142 | dwMessageId = GetLastError( ); |
175 | 143 | ||
176 | if( dwMessageId == 0 ) | 144 | if( dwMessageId == 0 ) |
177 | return; | 145 | return; |
178 | 146 | ||
147 | len = strlen( str ); | ||
148 | if( len > sizeof( error_buffer ) - 5 ) | ||
149 | len = sizeof( error_buffer ) - 5; | ||
150 | |||
179 | /* Format error message to: | 151 | /* Format error message to: |
180 | * "<argument to function that failed>": <Windows localized error message> | 152 | * "<argument to function that failed>": <Windows localized error message> |
181 | */ | 153 | */ |
182 | pos = copy_string( error_buffer, sizeof(error_buffer), UNICODE_L("\"") ); | 154 | pos = 0; |
183 | pos += copy_string( error_buffer+pos, sizeof(error_buffer)-pos, str ); | 155 | error_buffer[pos++] = '"'; |
184 | pos += copy_string( error_buffer+pos, sizeof(error_buffer)-pos, UNICODE_L("\": ") ); | 156 | memcpy( error_buffer+pos, str, len ); |
185 | pos += FormatMessage( FORMAT_MESSAGE_FROM_SYSTEM, NULL, dwMessageId, | 157 | pos += len; |
158 | error_buffer[pos++] = '"'; | ||
159 | error_buffer[pos++] = ':'; | ||
160 | error_buffer[pos++] = ' '; | ||
161 | |||
162 | ret = FormatMessageA( FORMAT_MESSAGE_FROM_SYSTEM, NULL, dwMessageId, | ||
186 | MAKELANGID( LANG_NEUTRAL, SUBLANG_DEFAULT ), | 163 | MAKELANGID( LANG_NEUTRAL, SUBLANG_DEFAULT ), |
187 | error_buffer+pos, sizeof(error_buffer)-pos, NULL ); | 164 | error_buffer+pos, (DWORD) (sizeof(error_buffer)-pos), NULL ); |
165 | pos += ret; | ||
166 | |||
167 | /* When FormatMessageA() fails it returns zero and does not touch buffer | ||
168 | * so add trailing null byte */ | ||
169 | if( ret == 0 ) | ||
170 | error_buffer[pos] = '\0'; | ||
188 | 171 | ||
189 | if( pos > 1 ) | 172 | if( pos > 1 ) |
190 | { | 173 | { |
@@ -198,19 +181,13 @@ static void save_err_str( const CHAR *str ) | |||
198 | 181 | ||
199 | static void save_err_ptr_str( const void *ptr ) | 182 | static void save_err_ptr_str( const void *ptr ) |
200 | { | 183 | { |
201 | CHAR ptr_buf[19]; /* 0x<pointer> up to 64 bits. */ | 184 | char ptr_buf[19]; /* 0x<pointer> up to 64 bits. */ |
202 | |||
203 | #ifdef UNICODE | ||
204 | |||
205 | # if ((defined(_WIN32) || defined(WIN32)) && (defined(_MSC_VER)) ) | ||
206 | swprintf_s( ptr_buf, 19, UNICODE_L("0x%p"), ptr ); | ||
207 | # else | ||
208 | swprintf(ptr_buf, 19, UNICODE_L("0x%p"), ptr); | ||
209 | # endif | ||
210 | 185 | ||
211 | #else | 186 | #ifdef _MSC_VER |
212 | snprintf( ptr_buf, 19, "0x%p", ptr ); | 187 | /* Supress warning C4996: 'sprintf': This function or variable may be unsafe */ |
188 | #pragma warning( suppress: 4996 ) | ||
213 | #endif | 189 | #endif |
190 | sprintf( ptr_buf, "0x%p", ptr ); | ||
214 | 191 | ||
215 | save_err_str( ptr_buf ); | 192 | save_err_str( ptr_buf ); |
216 | } | 193 | } |
@@ -246,7 +223,7 @@ void *dlopen( const char *file, int mode ) | |||
246 | { | 223 | { |
247 | HANDLE hCurrentProc; | 224 | HANDLE hCurrentProc; |
248 | DWORD dwProcModsBefore, dwProcModsAfter; | 225 | DWORD dwProcModsBefore, dwProcModsAfter; |
249 | CHAR lpFileName[MAX_PATH]; | 226 | char lpFileName[MAX_PATH]; |
250 | size_t i; | 227 | size_t i; |
251 | 228 | ||
252 | /* MSDN says backslashes *must* be used instead of forward slashes. */ | 229 | /* MSDN says backslashes *must* be used instead of forward slashes. */ |
@@ -271,7 +248,7 @@ void *dlopen( const char *file, int mode ) | |||
271 | * to UNIX's search paths (start with system folders instead of current | 248 | * to UNIX's search paths (start with system folders instead of current |
272 | * folder). | 249 | * folder). |
273 | */ | 250 | */ |
274 | hModule = LoadLibraryEx(lpFileName, NULL, | 251 | hModule = LoadLibraryExA(lpFileName, NULL, |
275 | LOAD_WITH_ALTERED_SEARCH_PATH ); | 252 | LOAD_WITH_ALTERED_SEARCH_PATH ); |
276 | 253 | ||
277 | if( EnumProcessModules( hCurrentProc, NULL, 0, &dwProcModsAfter ) == 0 ) | 254 | if( EnumProcessModules( hCurrentProc, NULL, 0, &dwProcModsAfter ) == 0 ) |
@@ -331,11 +308,6 @@ void *dlsym( void *handle, const char *name ) | |||
331 | HMODULE hModule; | 308 | HMODULE hModule; |
332 | HANDLE hCurrentProc; | 309 | HANDLE hCurrentProc; |
333 | 310 | ||
334 | #ifdef UNICODE | ||
335 | wchar_t namew[MAX_PATH]; | ||
336 | wmemset(namew, 0, MAX_PATH); | ||
337 | #endif | ||
338 | |||
339 | current_error = NULL; | 311 | current_error = NULL; |
340 | symbol = NULL; | 312 | symbol = NULL; |
341 | hCaller = NULL; | 313 | hCaller = NULL; |
@@ -426,23 +398,7 @@ void *dlsym( void *handle, const char *name ) | |||
426 | end: | 398 | end: |
427 | if( symbol == NULL ) | 399 | if( symbol == NULL ) |
428 | { | 400 | { |
429 | #ifdef UNICODE | ||
430 | size_t converted_chars; | ||
431 | |||
432 | size_t str_len = strlen(name) + 1; | ||
433 | |||
434 | #if ((defined(_WIN32) || defined(WIN32)) && (defined(_MSC_VER)) ) | ||
435 | errno_t err = mbstowcs_s(&converted_chars, namew, str_len, name, str_len); | ||
436 | if (err != 0) | ||
437 | return NULL; | ||
438 | #else | ||
439 | mbstowcs(namew, name, str_len); | ||
440 | #endif | ||
441 | |||
442 | save_err_str( namew ); | ||
443 | #else | ||
444 | save_err_str( name ); | 401 | save_err_str( name ); |
445 | #endif | ||
446 | } | 402 | } |
447 | 403 | ||
448 | // warning C4054: 'type cast' : from function pointer 'FARPROC' to data pointer 'void *' | 404 | // warning C4054: 'type cast' : from function pointer 'FARPROC' to data pointer 'void *' |
@@ -462,26 +418,7 @@ char *dlerror( void ) | |||
462 | return NULL; | 418 | return NULL; |
463 | } | 419 | } |
464 | 420 | ||
465 | #ifdef UNICODE | ||
466 | errno_t err = 0; | ||
467 | size_t converted_chars = 0; | ||
468 | size_t str_len = wcslen(current_error) + 1; | ||
469 | memset(error_pointer, 0, 65535); | ||
470 | |||
471 | # if ((defined(_WIN32) || defined(WIN32)) && (defined(_MSC_VER)) ) | ||
472 | err = wcstombs_s(&converted_chars, | ||
473 | error_pointer, str_len * sizeof(char), | ||
474 | current_error, str_len * sizeof(wchar_t)); | ||
475 | |||
476 | if (err != 0) | ||
477 | return NULL; | ||
478 | # else | ||
479 | wcstombs(error_pointer, current_error, str_len); | ||
480 | # endif | ||
481 | |||
482 | #else | ||
483 | memcpy(error_pointer, current_error, strlen(current_error) + 1); | 421 | memcpy(error_pointer, current_error, strlen(current_error) + 1); |
484 | #endif | ||
485 | 422 | ||
486 | /* POSIX says that invoking dlerror( ) a second time, immediately following | 423 | /* POSIX says that invoking dlerror( ) a second time, immediately following |
487 | * a prior invocation, shall result in NULL being returned. | 424 | * a prior invocation, shall result in NULL being returned. |