ifuncmain3.c 2.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134
  1. /* Test STT_GNU_IFUNC symbols with dlopen:
  2. 1. Direct function call.
  3. 2. Function pointer.
  4. 3. Visibility with override.
  5. */
  6. #include <dlfcn.h>
  7. #include <stdlib.h>
  8. #include <stdio.h>
  9. extern int __attribute__ ((noinline)) foo (void);
  10. extern int __attribute__ ((noinline)) foo_hidden (void);
  11. extern int __attribute__ ((noinline)) foo_protected (void);
  12. typedef int (*foo_p) (void);
  13. int
  14. __attribute__ ((noinline))
  15. foo (void)
  16. {
  17. return -30;
  18. }
  19. int
  20. __attribute__ ((noinline))
  21. foo_hidden (void)
  22. {
  23. return -20;
  24. }
  25. int
  26. __attribute__ ((noinline))
  27. foo_protected (void)
  28. {
  29. return -40;
  30. }
  31. int
  32. main (void)
  33. {
  34. foo_p p;
  35. foo_p (*f) (void);
  36. int *ret;
  37. void *h = dlopen ("ifuncmod3.so", RTLD_LAZY);
  38. if (h == NULL)
  39. {
  40. printf ("cannot load: %s\n", dlerror ());
  41. return 1;
  42. }
  43. p = dlsym (h, "foo");
  44. if (p == NULL)
  45. {
  46. printf ("symbol not found: %s\n", dlerror ());
  47. return 1;
  48. }
  49. if ((*p) () != -1)
  50. abort ();
  51. f = dlsym (h, "get_foo_p");
  52. if (f == NULL)
  53. {
  54. printf ("symbol not found: %s\n", dlerror ());
  55. return 1;
  56. }
  57. ret = dlsym (h, "ret_foo");
  58. if (ret == NULL)
  59. {
  60. printf ("symbol not found: %s\n", dlerror ());
  61. return 1;
  62. }
  63. p = (*f) ();
  64. if (p != foo)
  65. abort ();
  66. if (foo () != -30)
  67. abort ();
  68. if (*ret != -30 || (*p) () != *ret)
  69. abort ();
  70. f = dlsym (h, "get_foo_hidden_p");
  71. if (f == NULL)
  72. {
  73. printf ("symbol not found: %s\n", dlerror ());
  74. return 1;
  75. }
  76. ret = dlsym (h, "ret_foo_hidden");
  77. if (ret == NULL)
  78. {
  79. printf ("symbol not found: %s\n", dlerror ());
  80. return 1;
  81. }
  82. p = (*f) ();
  83. if (foo_hidden () != -20)
  84. abort ();
  85. if (*ret != 1 || (*p) () != *ret)
  86. abort ();
  87. f = dlsym (h, "get_foo_protected_p");
  88. if (f == NULL)
  89. {
  90. printf ("symbol not found: %s\n", dlerror ());
  91. return 1;
  92. }
  93. ret = dlsym (h, "ret_foo_protected");
  94. if (ret == NULL)
  95. {
  96. printf ("symbol not found: %s\n", dlerror ());
  97. return 1;
  98. }
  99. p = (*f) ();
  100. if (p == foo_protected)
  101. abort ();
  102. if (foo_protected () != -40)
  103. abort ();
  104. if (*ret != 0 || (*p) () != *ret)
  105. abort ();
  106. if (dlclose (h) != 0)
  107. {
  108. printf ("cannot close: %s\n", dlerror ());
  109. return 1;
  110. }
  111. return 0;
  112. }