err_prn.c 6.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206
  1. /*
  2. * Copyright 1995-2020 The OpenSSL Project Authors. All Rights Reserved.
  3. *
  4. * Licensed under the Apache License 2.0 (the "License"). You may not use
  5. * this file except in compliance with the License. You can obtain a copy
  6. * in the file LICENSE in the source distribution or at
  7. * https://www.openssl.org/source/license.html
  8. */
  9. /* TODO: When ERR_STATE becomes opaque, this musts be removed */
  10. #define OSSL_FORCE_ERR_STATE
  11. #include <stdio.h>
  12. #include "internal/cryptlib.h"
  13. #include <openssl/crypto.h>
  14. #include <openssl/buffer.h>
  15. #include <openssl/err.h>
  16. #include "err_local.h"
  17. #define ERR_PRINT_BUF_SIZE 4096
  18. void ERR_print_errors_cb(int (*cb) (const char *str, size_t len, void *u),
  19. void *u)
  20. {
  21. CRYPTO_THREAD_ID tid = CRYPTO_THREAD_get_current_id();
  22. unsigned long l;
  23. const char *file, *data, *func;
  24. int line, flags;
  25. while ((l = ERR_get_error_all(&file, &line, &func, &data, &flags)) != 0) {
  26. char buf[ERR_PRINT_BUF_SIZE], *hex;
  27. const char *lib, *reason = NULL;
  28. char rsbuf[256];
  29. unsigned long r = ERR_GET_REASON(l);
  30. lib = ERR_lib_error_string(l);
  31. /*
  32. * ERR_reason_error_string() can't safely return system error strings,
  33. * since it would call openssl_strerror_r(), which needs a buffer for
  34. * thread safety. So for system errors, we call openssl_strerror_r()
  35. * directly instead.
  36. */
  37. if (ERR_SYSTEM_ERROR(l)) {
  38. if (openssl_strerror_r(r, rsbuf, sizeof(rsbuf)))
  39. reason = rsbuf;
  40. } else {
  41. reason = ERR_reason_error_string(l);
  42. }
  43. if (func == NULL)
  44. func = "unknown function";
  45. if (reason == NULL) {
  46. BIO_snprintf(rsbuf, sizeof(rsbuf), "reason(%lu)", r);
  47. reason = rsbuf;
  48. }
  49. if ((flags & ERR_TXT_STRING) == 0)
  50. data = "";
  51. hex = openssl_buf2hexstr_sep((const unsigned char *)&tid, sizeof(tid),
  52. '\0');
  53. BIO_snprintf(buf, sizeof(buf), "%s:error::%s:%s:%s:%s:%d:%s\n",
  54. hex == NULL ? "<null>" : hex, lib, func, reason, file,
  55. line, data);
  56. OPENSSL_free(hex);
  57. if (cb(buf, strlen(buf), u) <= 0)
  58. break; /* abort outputting the error report */
  59. }
  60. }
  61. /* auxiliary function for incrementally reporting texts via the error queue */
  62. static void put_error(int lib, const char *func, int reason,
  63. const char *file, int line)
  64. {
  65. ERR_new();
  66. ERR_set_debug(file, line, func);
  67. ERR_set_error(lib, reason, NULL /* no data here, so fmt is NULL */);
  68. }
  69. #define TYPICAL_MAX_OUTPUT_BEFORE_DATA 100
  70. #define MAX_DATA_LEN (ERR_PRINT_BUF_SIZE - TYPICAL_MAX_OUTPUT_BEFORE_DATA)
  71. void ERR_add_error_txt(const char *separator, const char *txt)
  72. {
  73. const char *file = NULL;
  74. int line;
  75. const char *func = NULL;
  76. const char *data = NULL;
  77. int flags;
  78. unsigned long err = ERR_peek_last_error();
  79. if (separator == NULL)
  80. separator = "";
  81. if (err == 0)
  82. put_error(ERR_LIB_NONE, NULL, 0, "", 0);
  83. do {
  84. size_t available_len, data_len;
  85. const char *curr = txt, *next = txt;
  86. const char *leading_separator = separator;
  87. int trailing_separator = 0;
  88. char *tmp;
  89. ERR_peek_last_error_all(&file, &line, &func, &data, &flags);
  90. if ((flags & ERR_TXT_STRING) == 0) {
  91. data = "";
  92. leading_separator = "";
  93. }
  94. data_len = strlen(data);
  95. /* workaround for limit of ERR_print_errors_cb() */
  96. if (data_len >= MAX_DATA_LEN
  97. || strlen(separator) >= (size_t)(MAX_DATA_LEN - data_len))
  98. available_len = 0;
  99. else
  100. available_len = MAX_DATA_LEN - data_len - strlen(separator) - 1;
  101. /* MAX_DATA_LEN > available_len >= 0 */
  102. if (*separator == '\0') {
  103. const size_t len_next = strlen(next);
  104. if (len_next <= available_len) {
  105. next += len_next;
  106. curr = NULL; /* no need to split */
  107. } else {
  108. next += available_len;
  109. curr = next; /* will split at this point */
  110. }
  111. } else {
  112. while (*next != '\0' && (size_t)(next - txt) <= available_len) {
  113. curr = next;
  114. next = strstr(curr, separator);
  115. if (next != NULL) {
  116. next += strlen(separator);
  117. trailing_separator = *next == '\0';
  118. } else {
  119. next = curr + strlen(curr);
  120. }
  121. }
  122. if ((size_t)(next - txt) <= available_len)
  123. curr = NULL; /* the above loop implies *next == '\0' */
  124. }
  125. if (curr != NULL) {
  126. /* split error msg at curr since error data would get too long */
  127. if (curr != txt) {
  128. tmp = OPENSSL_strndup(txt, curr - txt);
  129. if (tmp == NULL)
  130. return;
  131. ERR_add_error_data(2, separator, tmp);
  132. OPENSSL_free(tmp);
  133. }
  134. put_error(ERR_GET_LIB(err), func, err, file, line);
  135. txt = curr;
  136. } else {
  137. if (trailing_separator) {
  138. tmp = OPENSSL_strndup(txt, next - strlen(separator) - txt);
  139. if (tmp == NULL)
  140. return;
  141. /* output txt without the trailing separator */
  142. ERR_add_error_data(2, leading_separator, tmp);
  143. OPENSSL_free(tmp);
  144. } else {
  145. ERR_add_error_data(2, leading_separator, txt);
  146. }
  147. txt = next; /* finished */
  148. }
  149. } while (*txt != '\0');
  150. }
  151. void ERR_add_error_mem_bio(const char *separator, BIO *bio)
  152. {
  153. if (bio != NULL) {
  154. char *str;
  155. long len = BIO_get_mem_data(bio, &str);
  156. if (len > 0) {
  157. if (str[len - 1] != '\0') {
  158. if (BIO_write(bio, "", 1) <= 0)
  159. return;
  160. len = BIO_get_mem_data(bio, &str);
  161. }
  162. if (len > 1)
  163. ERR_add_error_txt(separator, str);
  164. }
  165. }
  166. }
  167. static int print_bio(const char *str, size_t len, void *bp)
  168. {
  169. return BIO_write((BIO *)bp, str, len);
  170. }
  171. void ERR_print_errors(BIO *bp)
  172. {
  173. ERR_print_errors_cb(print_bio, bp);
  174. }
  175. #ifndef OPENSSL_NO_STDIO
  176. void ERR_print_errors_fp(FILE *fp)
  177. {
  178. BIO *bio = BIO_new_fp(fp, BIO_NOCLOSE);
  179. if (bio == NULL)
  180. return;
  181. ERR_print_errors_cb(print_bio, bio);
  182. BIO_free(bio);
  183. }
  184. #endif