libasteriskssl.c 5.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210
  1. /*
  2. * Asterisk -- An open source telephony toolkit.
  3. *
  4. * Copyright (C) 2009-2018, Digium, Inc.
  5. *
  6. * Russell Bryant <russell@digium.com>
  7. *
  8. * See http://www.asterisk.org for more information about
  9. * the Asterisk project. Please do not directly contact
  10. * any of the maintainers of this project for assistance;
  11. * the project provides a web site, mailing lists and IRC
  12. * channels for your use.
  13. *
  14. * This program is free software, distributed under the terms of
  15. * the GNU General Public License Version 2. See the LICENSE file
  16. * at the top of the source tree.
  17. */
  18. /*!
  19. * \file
  20. * \brief Common OpenSSL support code
  21. *
  22. * \author Russell Bryant <russell@digium.com>
  23. */
  24. #include "asterisk.h"
  25. #include "asterisk/_private.h" /* ast_ssl_init() */
  26. #ifdef HAVE_OPENSSL
  27. #include <openssl/opensslv.h> /* for OPENSSL_VERSION_NUMBER */
  28. #endif
  29. #if defined(HAVE_OPENSSL) && \
  30. (defined(LIBRESSL_VERSION_NUMBER) || OPENSSL_VERSION_NUMBER < 0x10100000L)
  31. #include <dlfcn.h> /* for dlerror, dlsym, RTLD_NEXT */
  32. #include <openssl/crypto.h> /* for CRYPTO_num_locks, CRYPTO_set_id_call... */
  33. #include <openssl/err.h> /* for ERR_free_strings */
  34. #include <openssl/ssl.h> /* for SSL_library_init, SSL_load_error_str... */
  35. #if OPENSSL_VERSION_NUMBER < 0x10000000L
  36. #include <pthread.h> /* for pthread_self */
  37. #endif
  38. #include "asterisk/lock.h" /* for ast_mutex_t, ast_mutex_init, ast_mut... */
  39. #include "asterisk/logger.h" /* for ast_debug, ast_log, LOG_ERROR */
  40. #include "asterisk/utils.h" /* for ast_calloc */
  41. #define get_OpenSSL_function(func) do { real_##func = dlsym(RTLD_NEXT, __stringify(func)); } while(0)
  42. static int startup_complete;
  43. static ast_mutex_t *ssl_locks;
  44. static int ssl_num_locks;
  45. #if OPENSSL_VERSION_NUMBER < 0x10000000L
  46. static unsigned long ssl_threadid(void)
  47. {
  48. return (unsigned long) pthread_self();
  49. }
  50. #endif
  51. static void ssl_lock(int mode, int n, const char *file, int line)
  52. {
  53. if (n < 0 || n >= ssl_num_locks) {
  54. ast_log(LOG_ERROR, "OpenSSL is full of LIES!!! - "
  55. "ssl_num_locks '%d' - n '%d'\n",
  56. ssl_num_locks, n);
  57. return;
  58. }
  59. if (mode & 0x1) {
  60. ast_mutex_lock(&ssl_locks[n]);
  61. } else {
  62. ast_mutex_unlock(&ssl_locks[n]);
  63. }
  64. }
  65. int SSL_library_init(void)
  66. {
  67. #if defined(AST_DEVMODE)
  68. if (startup_complete) {
  69. ast_debug(1, "Called after startup... ignoring!\n");
  70. }
  71. #endif
  72. return 1;
  73. }
  74. void SSL_load_error_strings(void)
  75. {
  76. #if defined(AST_DEVMODE)
  77. if (startup_complete) {
  78. ast_debug(1, "Called after startup... ignoring!\n");
  79. }
  80. #endif
  81. }
  82. #if OPENSSL_VERSION_NUMBER < 0x10000000L
  83. void CRYPTO_set_id_callback(unsigned long (*func)(void))
  84. {
  85. #if defined(AST_DEVMODE)
  86. if (startup_complete) {
  87. ast_debug(1, "Called after startup... ignoring!\n");
  88. }
  89. #endif
  90. }
  91. #endif
  92. void CRYPTO_set_locking_callback(void (*func)(int mode,int type, const char *file, int line))
  93. {
  94. #if defined(AST_DEVMODE)
  95. if (startup_complete) {
  96. ast_debug(1, "Called after startup... ignoring!\n");
  97. }
  98. #endif
  99. }
  100. void ERR_free_strings(void)
  101. {
  102. /* we can't allow this to be called, ever */
  103. }
  104. /*!
  105. * \internal
  106. * \brief Common OpenSSL initialization for all of Asterisk.
  107. *
  108. * Not needed for OpenSSL versions >= 1.1.0
  109. */
  110. int ast_ssl_init(void)
  111. {
  112. unsigned int i;
  113. int (*real_SSL_library_init)(void);
  114. #if OPENSSL_VERSION_NUMBER < 0x10000000L
  115. void (*real_CRYPTO_set_id_callback)(unsigned long (*)(void));
  116. #endif
  117. void (*real_CRYPTO_set_locking_callback)(void (*)(int, int, const char *, int));
  118. void (*real_SSL_load_error_strings)(void);
  119. const char *errstr;
  120. /* clear any previous dynamic linker errors */
  121. dlerror();
  122. get_OpenSSL_function(SSL_library_init);
  123. if ((errstr = dlerror()) != NULL) {
  124. ast_debug(1, "unable to get real address of SSL_library_init: %s\n", errstr);
  125. /* there is no way to continue in this situation... SSL will
  126. * likely be broken in this process
  127. */
  128. return -1;
  129. } else {
  130. real_SSL_library_init();
  131. }
  132. /* Make OpenSSL usage thread-safe. */
  133. #if OPENSSL_VERSION_NUMBER < 0x10000000L
  134. dlerror();
  135. get_OpenSSL_function(CRYPTO_set_id_callback);
  136. if ((errstr = dlerror()) != NULL) {
  137. ast_debug(1, "unable to get real address of CRYPTO_set_id_callback: %s\n", errstr);
  138. /* there is no way to continue in this situation... SSL will
  139. * likely be broken in this process
  140. */
  141. return -1;
  142. } else {
  143. real_CRYPTO_set_id_callback(ssl_threadid);
  144. }
  145. #endif
  146. dlerror();
  147. get_OpenSSL_function(CRYPTO_set_locking_callback);
  148. if ((errstr = dlerror()) != NULL) {
  149. ast_debug(1, "unable to get real address of CRYPTO_set_locking_callback: %s\n", errstr);
  150. /* there is no way to continue in this situation... SSL will
  151. * likely be broken in this process
  152. */
  153. return -1;
  154. } else {
  155. ssl_num_locks = CRYPTO_num_locks();
  156. if (!(ssl_locks = ast_calloc(ssl_num_locks, sizeof(ssl_locks[0])))) {
  157. return -1;
  158. }
  159. for (i = 0; i < ssl_num_locks; i++) {
  160. ast_mutex_init(&ssl_locks[i]);
  161. }
  162. real_CRYPTO_set_locking_callback(ssl_lock);
  163. }
  164. /* after this point, we don't check for errors from the dlsym() calls,
  165. * under the assumption that if the ones above were successful, all
  166. * the rest will be too. this assumption holds as long as OpenSSL still
  167. * provides all of these functions.
  168. */
  169. get_OpenSSL_function(SSL_load_error_strings);
  170. real_SSL_load_error_strings();
  171. startup_complete = 1;
  172. return 0;
  173. }
  174. #else
  175. int ast_ssl_init(void)
  176. {
  177. return 0;
  178. }
  179. #endif