rpc_thread.c 3.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166
  1. /*
  2. * Copyright (C) 2000-2006 Erik Andersen <andersen@uclibc.org>
  3. *
  4. * Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
  5. */
  6. #define __FORCE_GLIBC
  7. #include <features.h>
  8. #include <stdio.h>
  9. #include <assert.h>
  10. #include "rpc_private.h"
  11. #ifdef __UCLIBC_HAS_THREADS__
  12. #include <bits/libc-tsd.h>
  13. #include <bits/libc-lock.h>
  14. /* Variable used in non-threaded applications or for the first thread. */
  15. static struct rpc_thread_variables __libc_tsd_RPC_VARS_mem;
  16. __libc_tsd_define (, RPC_VARS)
  17. /*
  18. * Task-variable destructor
  19. */
  20. void
  21. __rpc_thread_destroy (void)
  22. {
  23. struct rpc_thread_variables *tvp = __libc_tsd_get (RPC_VARS);
  24. if (tvp != NULL && tvp != &__libc_tsd_RPC_VARS_mem) {
  25. __rpc_thread_svc_cleanup ();
  26. __rpc_thread_clnt_cleanup ();
  27. /*__rpc_thread_key_cleanup (); */
  28. free (tvp->authnone_private_s);
  29. free (tvp->clnt_perr_buf_s);
  30. free (tvp->clntraw_private_s);
  31. free (tvp->svcraw_private_s);
  32. free (tvp->authdes_cache_s);
  33. free (tvp->authdes_lru_s);
  34. free (tvp);
  35. __libc_tsd_set (RPC_VARS, NULL);
  36. }
  37. }
  38. /*
  39. * Initialize RPC multi-threaded operation
  40. */
  41. static void
  42. rpc_thread_multi (void)
  43. {
  44. __libc_tsd_set (RPC_VARS, &__libc_tsd_RPC_VARS_mem);
  45. }
  46. struct rpc_thread_variables attribute_hidden *
  47. __rpc_thread_variables (void)
  48. {
  49. __libc_once_define (static, once);
  50. struct rpc_thread_variables *tvp;
  51. tvp = __libc_tsd_get (RPC_VARS);
  52. if (tvp == NULL) {
  53. __libc_once (once, rpc_thread_multi);
  54. tvp = __libc_tsd_get (RPC_VARS);
  55. if (tvp == NULL) {
  56. tvp = calloc (1, sizeof *tvp);
  57. if (tvp != NULL)
  58. __libc_tsd_set (RPC_VARS, tvp);
  59. else
  60. tvp = __libc_tsd_get (RPC_VARS);
  61. }
  62. }
  63. return tvp;
  64. }
  65. /* Global variables If we're single-threaded, or if this is the first
  66. thread using the variable, use the existing global variable. This
  67. provides backwards compatability for existing applications which
  68. dynamically link against this code. */
  69. #undef svc_fdset
  70. #undef rpc_createerr
  71. #undef svc_pollfd
  72. #undef svc_max_pollfd
  73. fd_set *
  74. __rpc_thread_svc_fdset (void)
  75. {
  76. struct rpc_thread_variables *tvp;
  77. tvp = __rpc_thread_variables ();
  78. if (tvp == &__libc_tsd_RPC_VARS_mem)
  79. return &svc_fdset;
  80. return &tvp->svc_fdset_s;
  81. }
  82. struct rpc_createerr *
  83. __rpc_thread_createerr (void)
  84. {
  85. struct rpc_thread_variables *tvp;
  86. tvp = __rpc_thread_variables ();
  87. if (tvp == &__libc_tsd_RPC_VARS_mem)
  88. return &rpc_createerr;
  89. return &tvp->rpc_createerr_s;
  90. }
  91. struct pollfd **
  92. __rpc_thread_svc_pollfd (void)
  93. {
  94. struct rpc_thread_variables *tvp;
  95. tvp = __rpc_thread_variables ();
  96. if (tvp == &__libc_tsd_RPC_VARS_mem)
  97. return &svc_pollfd;
  98. return &tvp->svc_pollfd_s;
  99. }
  100. int *
  101. __rpc_thread_svc_max_pollfd (void)
  102. {
  103. struct rpc_thread_variables *tvp;
  104. tvp = __rpc_thread_variables ();
  105. if (tvp == &__libc_tsd_RPC_VARS_mem)
  106. return &svc_max_pollfd;
  107. return &tvp->svc_max_pollfd_s;
  108. }
  109. #else
  110. #undef svc_fdset
  111. #undef rpc_createerr
  112. #undef svc_pollfd
  113. #undef svc_max_pollfd
  114. extern fd_set svc_fdset;
  115. fd_set * __rpc_thread_svc_fdset (void)
  116. {
  117. return &(svc_fdset);
  118. }
  119. extern struct rpc_createerr rpc_createerr;
  120. struct rpc_createerr * __rpc_thread_createerr (void)
  121. {
  122. return &(rpc_createerr);
  123. }
  124. extern struct pollfd *svc_pollfd;
  125. struct pollfd ** __rpc_thread_svc_pollfd (void)
  126. {
  127. return &(svc_pollfd);
  128. }
  129. extern int svc_max_pollfd;
  130. int * __rpc_thread_svc_max_pollfd (void)
  131. {
  132. return &(svc_max_pollfd);
  133. }
  134. #endif /* __UCLIBC_HAS_THREADS__ */
  135. libc_hidden_def(__rpc_thread_svc_fdset)
  136. libc_hidden_def(__rpc_thread_createerr)
  137. libc_hidden_def(__rpc_thread_svc_pollfd)
  138. libc_hidden_def(__rpc_thread_svc_max_pollfd)