bio_md.c 4.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222
  1. /*
  2. * Copyright 1995-2021 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. #include <stdio.h>
  10. #include <errno.h>
  11. #include <openssl/buffer.h>
  12. #include <openssl/evp.h>
  13. #include "internal/bio.h"
  14. /*
  15. * BIO_put and BIO_get both add to the digest, BIO_gets returns the digest
  16. */
  17. static int md_write(BIO *h, char const *buf, int num);
  18. static int md_read(BIO *h, char *buf, int size);
  19. static int md_gets(BIO *h, char *str, int size);
  20. static long md_ctrl(BIO *h, int cmd, long arg1, void *arg2);
  21. static int md_new(BIO *h);
  22. static int md_free(BIO *data);
  23. static long md_callback_ctrl(BIO *h, int cmd, BIO_info_cb *fp);
  24. static const BIO_METHOD methods_md = {
  25. BIO_TYPE_MD,
  26. "message digest",
  27. bwrite_conv,
  28. md_write,
  29. bread_conv,
  30. md_read,
  31. NULL, /* md_puts, */
  32. md_gets,
  33. md_ctrl,
  34. md_new,
  35. md_free,
  36. md_callback_ctrl,
  37. };
  38. const BIO_METHOD *BIO_f_md(void)
  39. {
  40. return &methods_md;
  41. }
  42. static int md_new(BIO *bi)
  43. {
  44. EVP_MD_CTX *ctx;
  45. ctx = EVP_MD_CTX_new();
  46. if (ctx == NULL)
  47. return 0;
  48. BIO_set_init(bi, 1);
  49. BIO_set_data(bi, ctx);
  50. return 1;
  51. }
  52. static int md_free(BIO *a)
  53. {
  54. if (a == NULL)
  55. return 0;
  56. EVP_MD_CTX_free(BIO_get_data(a));
  57. BIO_set_data(a, NULL);
  58. BIO_set_init(a, 0);
  59. return 1;
  60. }
  61. static int md_read(BIO *b, char *out, int outl)
  62. {
  63. int ret = 0;
  64. EVP_MD_CTX *ctx;
  65. BIO *next;
  66. if (out == NULL)
  67. return 0;
  68. ctx = BIO_get_data(b);
  69. next = BIO_next(b);
  70. if ((ctx == NULL) || (next == NULL))
  71. return 0;
  72. ret = BIO_read(next, out, outl);
  73. if (BIO_get_init(b)) {
  74. if (ret > 0) {
  75. if (EVP_DigestUpdate(ctx, (unsigned char *)out,
  76. (unsigned int)ret) <= 0)
  77. return -1;
  78. }
  79. }
  80. BIO_clear_retry_flags(b);
  81. BIO_copy_next_retry(b);
  82. return ret;
  83. }
  84. static int md_write(BIO *b, const char *in, int inl)
  85. {
  86. int ret = 0;
  87. EVP_MD_CTX *ctx;
  88. BIO *next;
  89. if ((in == NULL) || (inl <= 0))
  90. return 0;
  91. ctx = BIO_get_data(b);
  92. next = BIO_next(b);
  93. if ((ctx != NULL) && (next != NULL))
  94. ret = BIO_write(next, in, inl);
  95. if (BIO_get_init(b)) {
  96. if (ret > 0) {
  97. if (!EVP_DigestUpdate(ctx, (const unsigned char *)in,
  98. (unsigned int)ret)) {
  99. BIO_clear_retry_flags(b);
  100. return 0;
  101. }
  102. }
  103. }
  104. if (next != NULL) {
  105. BIO_clear_retry_flags(b);
  106. BIO_copy_next_retry(b);
  107. }
  108. return ret;
  109. }
  110. static long md_ctrl(BIO *b, int cmd, long num, void *ptr)
  111. {
  112. EVP_MD_CTX *ctx, *dctx, **pctx;
  113. const EVP_MD **ppmd;
  114. EVP_MD *md;
  115. long ret = 1;
  116. BIO *dbio, *next;
  117. ctx = BIO_get_data(b);
  118. next = BIO_next(b);
  119. switch (cmd) {
  120. case BIO_CTRL_RESET:
  121. if (BIO_get_init(b))
  122. ret = EVP_DigestInit_ex(ctx, EVP_MD_CTX_get0_md(ctx), NULL);
  123. else
  124. ret = 0;
  125. if (ret > 0)
  126. ret = BIO_ctrl(next, cmd, num, ptr);
  127. break;
  128. case BIO_C_GET_MD:
  129. if (BIO_get_init(b)) {
  130. ppmd = ptr;
  131. *ppmd = EVP_MD_CTX_get0_md(ctx);
  132. } else
  133. ret = 0;
  134. break;
  135. case BIO_C_GET_MD_CTX:
  136. pctx = ptr;
  137. *pctx = ctx;
  138. BIO_set_init(b, 1);
  139. break;
  140. case BIO_C_SET_MD_CTX:
  141. if (BIO_get_init(b))
  142. BIO_set_data(b, ptr);
  143. else
  144. ret = 0;
  145. break;
  146. case BIO_C_DO_STATE_MACHINE:
  147. BIO_clear_retry_flags(b);
  148. ret = BIO_ctrl(next, cmd, num, ptr);
  149. BIO_copy_next_retry(b);
  150. break;
  151. case BIO_C_SET_MD:
  152. md = ptr;
  153. ret = EVP_DigestInit_ex(ctx, md, NULL);
  154. if (ret > 0)
  155. BIO_set_init(b, 1);
  156. break;
  157. case BIO_CTRL_DUP:
  158. dbio = ptr;
  159. dctx = BIO_get_data(dbio);
  160. if (!EVP_MD_CTX_copy_ex(dctx, ctx))
  161. return 0;
  162. BIO_set_init(b, 1);
  163. break;
  164. default:
  165. ret = BIO_ctrl(next, cmd, num, ptr);
  166. break;
  167. }
  168. return ret;
  169. }
  170. static long md_callback_ctrl(BIO *b, int cmd, BIO_info_cb *fp)
  171. {
  172. BIO *next;
  173. next = BIO_next(b);
  174. if (next == NULL)
  175. return 0;
  176. return BIO_callback_ctrl(next, cmd, fp);
  177. }
  178. static int md_gets(BIO *bp, char *buf, int size)
  179. {
  180. EVP_MD_CTX *ctx;
  181. unsigned int ret;
  182. ctx = BIO_get_data(bp);
  183. if (size < EVP_MD_CTX_get_size(ctx))
  184. return 0;
  185. if (EVP_DigestFinal_ex(ctx, (unsigned char *)buf, &ret) <= 0)
  186. return -1;
  187. return (int)ret;
  188. }