diff options
author | Pali Rohár <pali.rohar@gmail.com> | 2019-07-25 20:34:46 +0200 |
---|---|---|
committer | Pali Rohár <pali.rohar@gmail.com> | 2019-07-25 20:34:46 +0200 |
commit | 2bb5f487922aa908d27175c5a562d34f4c6197d9 (patch) | |
tree | d3daeb4830007336d5758022ebfe3baa6bbac7e8 | |
parent | 403b240f298d2a9f85c76299f6da8750263fd43b (diff) | |
download | dlfcn-win32-2bb5f487922aa908d27175c5a562d34f4c6197d9.tar.gz dlfcn-win32-2bb5f487922aa908d27175c5a562d34f4c6197d9.tar.bz2 dlfcn-win32-2bb5f487922aa908d27175c5a562d34f4c6197d9.zip |
Fix gcc warning: ISO C forbids return between function pointer and void *
Instead of using compiler specific pragma to disable particular warning,
rewrite code which cast from function pointer to data pointer according to
POSIX dlopen() documentation. This also fix compile warning under MSVC.
According to the ISO C standard, casting between function
pointers and 'void *', as done above, produces undefined results.
POSIX.1-2003 and POSIX.1-2008 accepted this state of affairs and
proposed the following workaround:
*(void **) (&cosine) = dlsym(handle, "cos");
This (clumsy) cast conforms with the ISO C standard and will
avoid any compiler warnings.
-rw-r--r-- | dlfcn.c | 6 | ||||
-rw-r--r-- | test.c | 62 | ||||
-rw-r--r-- | testdll2.c | 2 |
3 files changed, 33 insertions, 37 deletions
@@ -454,11 +454,7 @@ end: | |||
454 | save_err_str( name ); | 454 | save_err_str( name ); |
455 | } | 455 | } |
456 | 456 | ||
457 | // warning C4054: 'type cast' : from function pointer 'FARPROC' to data pointer 'void *' | 457 | return *(void **) (&symbol); |
458 | #ifdef _MSC_VER | ||
459 | #pragma warning( suppress: 4054 ) | ||
460 | #endif | ||
461 | return (void*) symbol; | ||
462 | } | 458 | } |
463 | 459 | ||
464 | char *dlerror( void ) | 460 | char *dlerror( void ) |
@@ -241,7 +241,7 @@ int main() | |||
241 | else | 241 | else |
242 | printf( "SUCCESS\tGot global handle: %p\n", global ); | 242 | printf( "SUCCESS\tGot global handle: %p\n", global ); |
243 | 243 | ||
244 | fwrite_local = dlsym(global, "fwrite"); | 244 | *(void **) (&fwrite_local) = dlsym( global, "fwrite" ); |
245 | if (!fwrite_local) | 245 | if (!fwrite_local) |
246 | { | 246 | { |
247 | error = dlerror(); | 247 | error = dlerror(); |
@@ -252,12 +252,12 @@ int main() | |||
252 | RETURN_ERROR; | 252 | RETURN_ERROR; |
253 | } | 253 | } |
254 | else | 254 | else |
255 | printf("SUCCESS\tGot symbol from global handle: %p\n", fwrite_local); | 255 | printf( "SUCCESS\tGot symbol from global handle: %p\n", *(void **) (&fwrite_local) ); |
256 | char * hello_world = "Hello world from local fwrite!\n"; | 256 | char * hello_world = "Hello world from local fwrite!\n"; |
257 | fwrite_local(hello_world,sizeof(char),strlen(hello_world),stderr); | 257 | fwrite_local(hello_world,sizeof(char),strlen(hello_world),stderr); |
258 | fflush(stderr); | 258 | fflush(stderr); |
259 | 259 | ||
260 | fputs_default = dlsym(RTLD_DEFAULT, "fputs"); | 260 | *(void **) (&fputs_default) = dlsym( RTLD_DEFAULT, "fputs" ); |
261 | if (!fputs_default) | 261 | if (!fputs_default) |
262 | { | 262 | { |
263 | error = dlerror(); | 263 | error = dlerror(); |
@@ -268,12 +268,12 @@ int main() | |||
268 | RETURN_ERROR; | 268 | RETURN_ERROR; |
269 | } | 269 | } |
270 | else | 270 | else |
271 | printf("SUCCESS\tGot symbol from default handle: %p\n", fputs_default); | 271 | printf( "SUCCESS\tGot symbol from default handle: %p\n", *(void **) (&fputs_default) ); |
272 | char * hello_world_fputs = "Hello world from default fputs!\n"; | 272 | char * hello_world_fputs = "Hello world from default fputs!\n"; |
273 | fputs_default(hello_world_fputs, stderr); | 273 | fputs_default(hello_world_fputs, stderr); |
274 | fflush(stderr); | 274 | fflush(stderr); |
275 | 275 | ||
276 | function = dlsym( library, "function" ); | 276 | *(void **) (&function) = dlsym( library, "function" ); |
277 | if( !function ) | 277 | if( !function ) |
278 | { | 278 | { |
279 | error = dlerror( ); | 279 | error = dlerror( ); |
@@ -284,11 +284,11 @@ int main() | |||
284 | RETURN_ERROR; | 284 | RETURN_ERROR; |
285 | } | 285 | } |
286 | else | 286 | else |
287 | printf( "SUCCESS\tGot symbol from library handle: %p\n", function ); | 287 | printf( "SUCCESS\tGot symbol from library handle: %p\n", *(void **) (&function) ); |
288 | 288 | ||
289 | RUNFUNC; | 289 | RUNFUNC; |
290 | 290 | ||
291 | function2_from_library2 = dlsym( library2, "function2" ); | 291 | *(void **) (&function2_from_library2) = dlsym( library2, "function2" ); |
292 | if( !function2_from_library2 ) | 292 | if( !function2_from_library2 ) |
293 | { | 293 | { |
294 | error = dlerror( ); | 294 | error = dlerror( ); |
@@ -299,7 +299,7 @@ int main() | |||
299 | RETURN_ERROR; | 299 | RETURN_ERROR; |
300 | } | 300 | } |
301 | else | 301 | else |
302 | printf( "SUCCESS\tGot symbol from library2 handle: %p\n", function2_from_library2 ); | 302 | printf( "SUCCESS\tGot symbol from library2 handle: %p\n", *(void **) (&function2_from_library2) ); |
303 | 303 | ||
304 | ret = function2_from_library2 (); | 304 | ret = function2_from_library2 (); |
305 | if( ret != 2 ) | 305 | if( ret != 2 ) |
@@ -309,11 +309,11 @@ int main() | |||
309 | RETURN_ERROR; | 309 | RETURN_ERROR; |
310 | } | 310 | } |
311 | 311 | ||
312 | nonexistentfunction = dlsym( library, "nonexistentfunction" ); | 312 | *(void **) (&nonexistentfunction) = dlsym( library, "nonexistentfunction" ); |
313 | if( nonexistentfunction ) | 313 | if( nonexistentfunction ) |
314 | { | 314 | { |
315 | error = dlerror( ); | 315 | error = dlerror( ); |
316 | printf( "ERROR\tGot nonexistent symbol from library handle: %p\n", nonexistentfunction ); | 316 | printf( "ERROR\tGot nonexistent symbol from library handle: %p\n", *(void **) (&nonexistentfunction) ); |
317 | CLOSE_LIB; | 317 | CLOSE_LIB; |
318 | CLOSE_GLOBAL; | 318 | CLOSE_GLOBAL; |
319 | RETURN_ERROR; | 319 | RETURN_ERROR; |
@@ -327,7 +327,7 @@ int main() | |||
327 | else | 327 | else |
328 | printf( "SUCCESS\tCould not get nonexistent symbol from library handle: %s\n", error ); | 328 | printf( "SUCCESS\tCould not get nonexistent symbol from library handle: %s\n", error ); |
329 | 329 | ||
330 | function = dlsym( global, "function" ); | 330 | *(void **) (&function) = dlsym( global, "function" ); |
331 | if( !function ) | 331 | if( !function ) |
332 | { | 332 | { |
333 | error = dlerror( ); | 333 | error = dlerror( ); |
@@ -338,15 +338,15 @@ int main() | |||
338 | RETURN_ERROR; | 338 | RETURN_ERROR; |
339 | } | 339 | } |
340 | else | 340 | else |
341 | printf( "SUCCESS\tGot symbol from global handle: %p\n", function ); | 341 | printf( "SUCCESS\tGot symbol from global handle: %p\n", *(void **) (&function) ); |
342 | 342 | ||
343 | RUNFUNC; | 343 | RUNFUNC; |
344 | 344 | ||
345 | nonexistentfunction = dlsym( global, "nonexistentfunction" ); | 345 | *(void **) (&nonexistentfunction) = dlsym( global, "nonexistentfunction" ); |
346 | if( nonexistentfunction ) | 346 | if( nonexistentfunction ) |
347 | { | 347 | { |
348 | error = dlerror( ); | 348 | error = dlerror( ); |
349 | printf( "ERROR\tGot nonexistent symbol from global handle: %p\n", nonexistentfunction ); | 349 | printf( "ERROR\tGot nonexistent symbol from global handle: %p\n", *(void **) (&nonexistentfunction) ); |
350 | CLOSE_LIB; | 350 | CLOSE_LIB; |
351 | CLOSE_GLOBAL; | 351 | CLOSE_GLOBAL; |
352 | RETURN_ERROR; | 352 | RETURN_ERROR; |
@@ -392,7 +392,7 @@ int main() | |||
392 | else | 392 | else |
393 | printf( "SUCCESS\tOpened library locally: %p\n", library ); | 393 | printf( "SUCCESS\tOpened library locally: %p\n", library ); |
394 | 394 | ||
395 | function = dlsym( library, "function" ); | 395 | *(void **) (&function) = dlsym( library, "function" ); |
396 | if( !function ) | 396 | if( !function ) |
397 | { | 397 | { |
398 | error = dlerror( ); | 398 | error = dlerror( ); |
@@ -403,15 +403,15 @@ int main() | |||
403 | RETURN_ERROR; | 403 | RETURN_ERROR; |
404 | } | 404 | } |
405 | else | 405 | else |
406 | printf( "SUCCESS\tGot symbol from library handle: %p\n", function ); | 406 | printf( "SUCCESS\tGot symbol from library handle: %p\n", *(void **) (&function) ); |
407 | 407 | ||
408 | RUNFUNC; | 408 | RUNFUNC; |
409 | 409 | ||
410 | nonexistentfunction = dlsym( library, "nonexistentfunction" ); | 410 | *(void **) (&nonexistentfunction) = dlsym( library, "nonexistentfunction" ); |
411 | if( nonexistentfunction ) | 411 | if( nonexistentfunction ) |
412 | { | 412 | { |
413 | error = dlerror( ); | 413 | error = dlerror( ); |
414 | printf( "ERROR\tGot nonexistent symbol from library handle: %p\n", nonexistentfunction ); | 414 | printf( "ERROR\tGot nonexistent symbol from library handle: %p\n", *(void **) (&nonexistentfunction) ); |
415 | CLOSE_LIB; | 415 | CLOSE_LIB; |
416 | CLOSE_GLOBAL; | 416 | CLOSE_GLOBAL; |
417 | RETURN_ERROR; | 417 | RETURN_ERROR; |
@@ -425,12 +425,12 @@ int main() | |||
425 | else | 425 | else |
426 | printf( "SUCCESS\tCould not get nonexistent symbol from library handle: %s\n", error ); | 426 | printf( "SUCCESS\tCould not get nonexistent symbol from library handle: %s\n", error ); |
427 | 427 | ||
428 | function = dlsym( global, "function" ); | 428 | *(void **) (&function) = dlsym( global, "function" ); |
429 | if( function ) | 429 | if( function ) |
430 | { | 430 | { |
431 | error = dlerror( ); | 431 | error = dlerror( ); |
432 | printf( "ERROR\tGot local symbol from global handle: %s @ %p\n", | 432 | printf( "ERROR\tGot local symbol from global handle: %s @ %p\n", |
433 | error ? error : "", function ); | 433 | error ? error : "", *(void **) (&function) ); |
434 | CLOSE_LIB; | 434 | CLOSE_LIB; |
435 | CLOSE_GLOBAL; | 435 | CLOSE_GLOBAL; |
436 | RETURN_ERROR; | 436 | RETURN_ERROR; |
@@ -438,11 +438,11 @@ int main() | |||
438 | else | 438 | else |
439 | printf( "SUCCESS\tDid not get local symbol from global handle.\n" ); | 439 | printf( "SUCCESS\tDid not get local symbol from global handle.\n" ); |
440 | 440 | ||
441 | nonexistentfunction = dlsym( global, "nonexistentfunction" ); | 441 | *(void **) (&nonexistentfunction) = dlsym( global, "nonexistentfunction" ); |
442 | if( nonexistentfunction ) | 442 | if( nonexistentfunction ) |
443 | { | 443 | { |
444 | error = dlerror( ); | 444 | error = dlerror( ); |
445 | printf( "ERROR\tGot nonexistent local symbol from global handle: %p\n", nonexistentfunction ); | 445 | printf( "ERROR\tGot nonexistent local symbol from global handle: %p\n", *(void **) (&nonexistentfunction) ); |
446 | CLOSE_LIB; | 446 | CLOSE_LIB; |
447 | CLOSE_GLOBAL; | 447 | CLOSE_GLOBAL; |
448 | RETURN_ERROR; | 448 | RETURN_ERROR; |
@@ -468,7 +468,7 @@ int main() | |||
468 | else | 468 | else |
469 | printf( "SUCCESS\tOpened library globally without closing it first: %p\n", library ); | 469 | printf( "SUCCESS\tOpened library globally without closing it first: %p\n", library ); |
470 | 470 | ||
471 | function = dlsym( global, "function" ); | 471 | *(void **) (&function) = dlsym( global, "function" ); |
472 | if( !function ) | 472 | if( !function ) |
473 | { | 473 | { |
474 | error = dlerror( ); | 474 | error = dlerror( ); |
@@ -479,15 +479,15 @@ int main() | |||
479 | RETURN_ERROR; | 479 | RETURN_ERROR; |
480 | } | 480 | } |
481 | else | 481 | else |
482 | printf( "SUCCESS\tGot symbol from global handle: %p\n", function ); | 482 | printf( "SUCCESS\tGot symbol from global handle: %p\n", *(void **) (&function) ); |
483 | 483 | ||
484 | RUNFUNC; | 484 | RUNFUNC; |
485 | 485 | ||
486 | nonexistentfunction = dlsym( global, "nonexistentfunction" ); | 486 | *(void **) (&nonexistentfunction) = dlsym( global, "nonexistentfunction" ); |
487 | if( nonexistentfunction ) | 487 | if( nonexistentfunction ) |
488 | { | 488 | { |
489 | error = dlerror( ); | 489 | error = dlerror( ); |
490 | printf( "ERROR\tGot nonexistent symbol from global handle: %p\n", nonexistentfunction ); | 490 | printf( "ERROR\tGot nonexistent symbol from global handle: %p\n", *(void **) (&nonexistentfunction) ); |
491 | CLOSE_LIB; | 491 | CLOSE_LIB; |
492 | CLOSE_GLOBAL; | 492 | CLOSE_GLOBAL; |
493 | RETURN_ERROR; | 493 | RETURN_ERROR; |
@@ -518,7 +518,7 @@ int main() | |||
518 | } | 518 | } |
519 | } | 519 | } |
520 | 520 | ||
521 | function = dlsym(global, "fwrite"); | 521 | *(void **) (&function) = dlsym( global, "fwrite" ); |
522 | if (!function) | 522 | if (!function) |
523 | { | 523 | { |
524 | error = dlerror(); | 524 | error = dlerror(); |
@@ -529,7 +529,7 @@ int main() | |||
529 | RETURN_ERROR; | 529 | RETURN_ERROR; |
530 | } | 530 | } |
531 | else | 531 | else |
532 | printf("SUCCESS\tGot symbol from global handle: %p\n", function); | 532 | printf( "SUCCESS\tGot symbol from global handle: %p\n", *(void **) (&function) ); |
533 | 533 | ||
534 | 534 | ||
535 | uMode = SetErrorMode( SEM_FAILCRITICALERRORS ); | 535 | uMode = SetErrorMode( SEM_FAILCRITICALERRORS ); |
@@ -541,7 +541,7 @@ int main() | |||
541 | RETURN_ERROR; | 541 | RETURN_ERROR; |
542 | } | 542 | } |
543 | else | 543 | else |
544 | printf( "SUCCESS\tOpened library3 via WINAPI: %p\n", library3 ); | 544 | printf( "SUCCESS\tOpened library3 via WINAPI: %p\n", (void *)library3 ); |
545 | 545 | ||
546 | ret = dlclose( library ); | 546 | ret = dlclose( library ); |
547 | if( ret ) | 547 | if( ret ) |
@@ -554,7 +554,7 @@ int main() | |||
554 | else | 554 | else |
555 | printf( "SUCCESS\tClosed library.\n" ); | 555 | printf( "SUCCESS\tClosed library.\n" ); |
556 | 556 | ||
557 | function = dlsym(global, "function3"); | 557 | *(void **) (&function) = dlsym( global, "function3" ); |
558 | if (!function) | 558 | if (!function) |
559 | { | 559 | { |
560 | error = dlerror(); | 560 | error = dlerror(); |
@@ -565,7 +565,7 @@ int main() | |||
565 | RETURN_ERROR; | 565 | RETURN_ERROR; |
566 | } | 566 | } |
567 | else | 567 | else |
568 | printf("SUCCESS\tGot symbol from global handle: %p\n", function); | 568 | printf( "SUCCESS\tGot symbol from global handle: %p\n", *(void **) (&function) ); |
569 | 569 | ||
570 | RUNFUNC; | 570 | RUNFUNC; |
571 | 571 | ||
@@ -38,7 +38,7 @@ EXPORT int function2( void ) | |||
38 | char *error; | 38 | char *error; |
39 | int (*function2_orig)(void); | 39 | int (*function2_orig)(void); |
40 | printf( "Hello, world! from wrapper library\n" ); | 40 | printf( "Hello, world! from wrapper library\n" ); |
41 | function2_orig = dlsym(RTLD_NEXT, "function2"); | 41 | *(void **) (&function2_orig) = dlsym( RTLD_NEXT, "function2" ); |
42 | if (!function2_orig) | 42 | if (!function2_orig) |
43 | { | 43 | { |
44 | error = dlerror( ); | 44 | error = dlerror( ); |