Nelze vybrat více než 25 témat Téma musí začínat písmenem nebo číslem, může obsahovat pomlčky („-“) a může být dlouhé až 35 znaků.
 
 
 
 
 
 

241 řádky
8.7 KiB

  1. /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
  2. * All rights reserved.
  3. *
  4. * This package is an SSL implementation written
  5. * by Eric Young (eay@cryptsoft.com).
  6. * The implementation was written so as to conform with Netscapes SSL.
  7. *
  8. * This library is free for commercial and non-commercial use as long as
  9. * the following conditions are aheared to. The following conditions
  10. * apply to all code found in this distribution, be it the RC4, RSA,
  11. * lhash, DES, etc., code; not just the SSL code. The SSL documentation
  12. * included with this distribution is covered by the same copyright terms
  13. * except that the holder is Tim Hudson (tjh@cryptsoft.com).
  14. *
  15. * Copyright remains Eric Young's, and as such any Copyright notices in
  16. * the code are not to be removed.
  17. * If this package is used in a product, Eric Young should be given attribution
  18. * as the author of the parts of the library used.
  19. * This can be in the form of a textual message at program startup or
  20. * in documentation (online or textual) provided with the package.
  21. *
  22. * Redistribution and use in source and binary forms, with or without
  23. * modification, are permitted provided that the following conditions
  24. * are met:
  25. * 1. Redistributions of source code must retain the copyright
  26. * notice, this list of conditions and the following disclaimer.
  27. * 2. Redistributions in binary form must reproduce the above copyright
  28. * notice, this list of conditions and the following disclaimer in the
  29. * documentation and/or other materials provided with the distribution.
  30. * 3. All advertising materials mentioning features or use of this software
  31. * must display the following acknowledgement:
  32. * "This product includes cryptographic software written by
  33. * Eric Young (eay@cryptsoft.com)"
  34. * The word 'cryptographic' can be left out if the rouines from the library
  35. * being used are not cryptographic related :-).
  36. * 4. If you include any Windows specific code (or a derivative thereof) from
  37. * the apps directory (application code) you must include an acknowledgement:
  38. * "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
  39. *
  40. * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
  41. * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
  42. * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
  43. * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
  44. * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
  45. * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
  46. * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
  47. * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
  48. * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
  49. * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
  50. * SUCH DAMAGE.
  51. *
  52. * The licence and distribution terms for any publically available version or
  53. * derivative of this code cannot be changed. i.e. this code cannot simply be
  54. * copied and put under another distribution licence
  55. * [including the GNU Public Licence.] */
  56. #include <openssl/digest.h>
  57. #include <string.h>
  58. #include <openssl/asn1.h>
  59. #include <openssl/bytestring.h>
  60. #include <openssl/nid.h>
  61. #include "../internal.h"
  62. struct nid_to_digest {
  63. int nid;
  64. const EVP_MD* (*md_func)(void);
  65. const char *short_name;
  66. const char *long_name;
  67. };
  68. static const struct nid_to_digest nid_to_digest_mapping[] = {
  69. {NID_md4, EVP_md4, SN_md4, LN_md4},
  70. {NID_md5, EVP_md5, SN_md5, LN_md5},
  71. {NID_sha1, EVP_sha1, SN_sha1, LN_sha1},
  72. {NID_sha224, EVP_sha224, SN_sha224, LN_sha224},
  73. {NID_sha256, EVP_sha256, SN_sha256, LN_sha256},
  74. {NID_sha384, EVP_sha384, SN_sha384, LN_sha384},
  75. {NID_sha512, EVP_sha512, SN_sha512, LN_sha512},
  76. {NID_md5_sha1, EVP_md5_sha1, SN_md5_sha1, LN_md5_sha1},
  77. // As a remnant of signing |EVP_MD|s, OpenSSL returned the corresponding
  78. // hash function when given a signature OID. To avoid unintended lax parsing
  79. // of hash OIDs, this is no longer supported for lookup by OID or NID.
  80. // Node.js, however, exposes |EVP_get_digestbyname|'s full behavior to
  81. // consumers so we retain it there.
  82. {NID_undef, EVP_sha1, SN_dsaWithSHA, LN_dsaWithSHA},
  83. {NID_undef, EVP_sha1, SN_dsaWithSHA1, LN_dsaWithSHA1},
  84. {NID_undef, EVP_sha1, SN_ecdsa_with_SHA1, NULL},
  85. {NID_undef, EVP_md5, SN_md5WithRSAEncryption, LN_md5WithRSAEncryption},
  86. {NID_undef, EVP_sha1, SN_sha1WithRSAEncryption, LN_sha1WithRSAEncryption},
  87. {NID_undef, EVP_sha224, SN_sha224WithRSAEncryption,
  88. LN_sha224WithRSAEncryption},
  89. {NID_undef, EVP_sha256, SN_sha256WithRSAEncryption,
  90. LN_sha256WithRSAEncryption},
  91. {NID_undef, EVP_sha384, SN_sha384WithRSAEncryption,
  92. LN_sha384WithRSAEncryption},
  93. {NID_undef, EVP_sha512, SN_sha512WithRSAEncryption,
  94. LN_sha512WithRSAEncryption},
  95. };
  96. const EVP_MD* EVP_get_digestbynid(int nid) {
  97. if (nid == NID_undef) {
  98. // Skip the |NID_undef| entries in |nid_to_digest_mapping|.
  99. return NULL;
  100. }
  101. for (unsigned i = 0; i < OPENSSL_ARRAY_SIZE(nid_to_digest_mapping); i++) {
  102. if (nid_to_digest_mapping[i].nid == nid) {
  103. return nid_to_digest_mapping[i].md_func();
  104. }
  105. }
  106. return NULL;
  107. }
  108. static const struct {
  109. uint8_t oid[9];
  110. uint8_t oid_len;
  111. int nid;
  112. } kMDOIDs[] = {
  113. // 1.2.840.113549.2.4
  114. { {0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x02, 0x04}, 8, NID_md4 },
  115. // 1.2.840.113549.2.5
  116. { {0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x02, 0x05}, 8, NID_md5 },
  117. // 1.3.14.3.2.26
  118. { {0x2b, 0x0e, 0x03, 0x02, 0x1a}, 5, NID_sha1 },
  119. // 2.16.840.1.101.3.4.2.1
  120. { {0x60, 0x86, 0x48, 0x01, 0x65, 0x03, 0x04, 0x02, 0x01}, 9, NID_sha256 },
  121. // 2.16.840.1.101.3.4.2.2
  122. { {0x60, 0x86, 0x48, 0x01, 0x65, 0x03, 0x04, 0x02, 0x02}, 9, NID_sha384 },
  123. // 2.16.840.1.101.3.4.2.3
  124. { {0x60, 0x86, 0x48, 0x01, 0x65, 0x03, 0x04, 0x02, 0x03}, 9, NID_sha512 },
  125. // 2.16.840.1.101.3.4.2.4
  126. { {0x60, 0x86, 0x48, 0x01, 0x65, 0x03, 0x04, 0x02, 0x04}, 9, NID_sha224 },
  127. };
  128. static const EVP_MD *cbs_to_md(const CBS *cbs) {
  129. for (size_t i = 0; i < OPENSSL_ARRAY_SIZE(kMDOIDs); i++) {
  130. if (CBS_len(cbs) == kMDOIDs[i].oid_len &&
  131. OPENSSL_memcmp(CBS_data(cbs), kMDOIDs[i].oid, kMDOIDs[i].oid_len) ==
  132. 0) {
  133. return EVP_get_digestbynid(kMDOIDs[i].nid);
  134. }
  135. }
  136. return NULL;
  137. }
  138. const EVP_MD *EVP_get_digestbyobj(const ASN1_OBJECT *obj) {
  139. // Handle objects with no corresponding OID.
  140. if (obj->nid != NID_undef) {
  141. return EVP_get_digestbynid(obj->nid);
  142. }
  143. CBS cbs;
  144. CBS_init(&cbs, obj->data, obj->length);
  145. return cbs_to_md(&cbs);
  146. }
  147. const EVP_MD *EVP_parse_digest_algorithm(CBS *cbs) {
  148. CBS algorithm, oid;
  149. if (!CBS_get_asn1(cbs, &algorithm, CBS_ASN1_SEQUENCE) ||
  150. !CBS_get_asn1(&algorithm, &oid, CBS_ASN1_OBJECT)) {
  151. OPENSSL_PUT_ERROR(DIGEST, DIGEST_R_DECODE_ERROR);
  152. return NULL;
  153. }
  154. const EVP_MD *ret = cbs_to_md(&oid);
  155. if (ret == NULL) {
  156. OPENSSL_PUT_ERROR(DIGEST, DIGEST_R_UNKNOWN_HASH);
  157. return NULL;
  158. }
  159. // The parameters, if present, must be NULL. Historically, whether the NULL
  160. // was included or omitted was not well-specified. When parsing an
  161. // AlgorithmIdentifier, we allow both. (Note this code is not used when
  162. // verifying RSASSA-PKCS1-v1_5 signatures.)
  163. if (CBS_len(&algorithm) > 0) {
  164. CBS param;
  165. if (!CBS_get_asn1(&algorithm, &param, CBS_ASN1_NULL) ||
  166. CBS_len(&param) != 0 ||
  167. CBS_len(&algorithm) != 0) {
  168. OPENSSL_PUT_ERROR(DIGEST, DIGEST_R_DECODE_ERROR);
  169. return NULL;
  170. }
  171. }
  172. return ret;
  173. }
  174. int EVP_marshal_digest_algorithm(CBB *cbb, const EVP_MD *md) {
  175. CBB algorithm, oid, null;
  176. if (!CBB_add_asn1(cbb, &algorithm, CBS_ASN1_SEQUENCE) ||
  177. !CBB_add_asn1(&algorithm, &oid, CBS_ASN1_OBJECT)) {
  178. OPENSSL_PUT_ERROR(DIGEST, ERR_R_MALLOC_FAILURE);
  179. return 0;
  180. }
  181. int found = 0;
  182. int nid = EVP_MD_type(md);
  183. for (size_t i = 0; i < OPENSSL_ARRAY_SIZE(kMDOIDs); i++) {
  184. if (nid == kMDOIDs[i].nid) {
  185. if (!CBB_add_bytes(&oid, kMDOIDs[i].oid, kMDOIDs[i].oid_len)) {
  186. OPENSSL_PUT_ERROR(DIGEST, ERR_R_MALLOC_FAILURE);
  187. return 0;
  188. }
  189. found = 1;
  190. break;
  191. }
  192. }
  193. if (!found) {
  194. OPENSSL_PUT_ERROR(DIGEST, DIGEST_R_UNKNOWN_HASH);
  195. return 0;
  196. }
  197. if (!CBB_add_asn1(&algorithm, &null, CBS_ASN1_NULL) ||
  198. !CBB_flush(cbb)) {
  199. OPENSSL_PUT_ERROR(DIGEST, ERR_R_MALLOC_FAILURE);
  200. return 0;
  201. }
  202. return 1;
  203. }
  204. const EVP_MD *EVP_get_digestbyname(const char *name) {
  205. for (unsigned i = 0; i < OPENSSL_ARRAY_SIZE(nid_to_digest_mapping); i++) {
  206. const char *short_name = nid_to_digest_mapping[i].short_name;
  207. const char *long_name = nid_to_digest_mapping[i].long_name;
  208. if ((short_name && strcmp(short_name, name) == 0) ||
  209. (long_name && strcmp(long_name, name) == 0)) {
  210. return nid_to_digest_mapping[i].md_func();
  211. }
  212. }
  213. return NULL;
  214. }