2
0

v3_prn.c 6.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216
  1. /*
  2. * Copyright 1999-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. /* X509 v3 extension utilities */
  10. #include <stdio.h>
  11. #include "internal/cryptlib.h"
  12. #include <openssl/conf.h>
  13. #include <openssl/x509v3.h>
  14. /* Extension printing routines */
  15. static int unknown_ext_print(BIO *out, const unsigned char *ext, int extlen,
  16. unsigned long flag, int indent, int supported);
  17. /* Print out a name+value stack */
  18. void X509V3_EXT_val_prn(BIO *out, STACK_OF(CONF_VALUE) *val, int indent,
  19. int ml)
  20. {
  21. int i;
  22. CONF_VALUE *nval;
  23. if (!val)
  24. return;
  25. if (!ml || !sk_CONF_VALUE_num(val)) {
  26. BIO_printf(out, "%*s", indent, "");
  27. if (!sk_CONF_VALUE_num(val))
  28. BIO_puts(out, "<EMPTY>\n");
  29. }
  30. for (i = 0; i < sk_CONF_VALUE_num(val); i++) {
  31. if (ml) {
  32. if (i > 0)
  33. BIO_printf(out, "\n");
  34. BIO_printf(out, "%*s", indent, "");
  35. }
  36. else if (i > 0)
  37. BIO_printf(out, ", ");
  38. nval = sk_CONF_VALUE_value(val, i);
  39. if (!nval->name)
  40. BIO_puts(out, nval->value);
  41. else if (!nval->value)
  42. BIO_puts(out, nval->name);
  43. #ifndef CHARSET_EBCDIC
  44. else
  45. BIO_printf(out, "%s:%s", nval->name, nval->value);
  46. #else
  47. else {
  48. int len;
  49. char *tmp;
  50. len = strlen(nval->value) + 1;
  51. tmp = OPENSSL_malloc(len);
  52. if (tmp != NULL) {
  53. ascii2ebcdic(tmp, nval->value, len);
  54. BIO_printf(out, "%s:%s", nval->name, tmp);
  55. OPENSSL_free(tmp);
  56. }
  57. }
  58. #endif
  59. }
  60. }
  61. /* Main routine: print out a general extension */
  62. int X509V3_EXT_print(BIO *out, X509_EXTENSION *ext, unsigned long flag,
  63. int indent)
  64. {
  65. void *ext_str = NULL;
  66. char *value = NULL;
  67. ASN1_OCTET_STRING *extoct;
  68. const unsigned char *p;
  69. int extlen;
  70. const X509V3_EXT_METHOD *method;
  71. STACK_OF(CONF_VALUE) *nval = NULL;
  72. int ok = 1;
  73. extoct = X509_EXTENSION_get_data(ext);
  74. p = ASN1_STRING_get0_data(extoct);
  75. extlen = ASN1_STRING_length(extoct);
  76. if ((method = X509V3_EXT_get(ext)) == NULL)
  77. return unknown_ext_print(out, p, extlen, flag, indent, 0);
  78. if (method->it)
  79. ext_str = ASN1_item_d2i(NULL, &p, extlen, ASN1_ITEM_ptr(method->it));
  80. else
  81. ext_str = method->d2i(NULL, &p, extlen);
  82. if (!ext_str)
  83. return unknown_ext_print(out, p, extlen, flag, indent, 1);
  84. if (method->i2s) {
  85. if ((value = method->i2s(method, ext_str)) == NULL) {
  86. ok = 0;
  87. goto err;
  88. }
  89. #ifndef CHARSET_EBCDIC
  90. BIO_printf(out, "%*s%s", indent, "", value);
  91. #else
  92. {
  93. int len;
  94. char *tmp;
  95. len = strlen(value) + 1;
  96. tmp = OPENSSL_malloc(len);
  97. if (tmp != NULL) {
  98. ascii2ebcdic(tmp, value, len);
  99. BIO_printf(out, "%*s%s", indent, "", tmp);
  100. OPENSSL_free(tmp);
  101. }
  102. }
  103. #endif
  104. } else if (method->i2v) {
  105. if ((nval = method->i2v(method, ext_str, NULL)) == NULL) {
  106. ok = 0;
  107. goto err;
  108. }
  109. X509V3_EXT_val_prn(out, nval, indent,
  110. method->ext_flags & X509V3_EXT_MULTILINE);
  111. } else if (method->i2r) {
  112. if (!method->i2r(method, ext_str, out, indent))
  113. ok = 0;
  114. } else
  115. ok = 0;
  116. err:
  117. sk_CONF_VALUE_pop_free(nval, X509V3_conf_free);
  118. OPENSSL_free(value);
  119. if (method->it)
  120. ASN1_item_free(ext_str, ASN1_ITEM_ptr(method->it));
  121. else
  122. method->ext_free(ext_str);
  123. return ok;
  124. }
  125. int X509V3_extensions_print(BIO *bp, const char *title,
  126. const STACK_OF(X509_EXTENSION) *exts,
  127. unsigned long flag, int indent)
  128. {
  129. int i, j;
  130. if (sk_X509_EXTENSION_num(exts) <= 0)
  131. return 1;
  132. if (title) {
  133. BIO_printf(bp, "%*s%s:\n", indent, "", title);
  134. indent += 4;
  135. }
  136. for (i = 0; i < sk_X509_EXTENSION_num(exts); i++) {
  137. ASN1_OBJECT *obj;
  138. X509_EXTENSION *ex;
  139. ex = sk_X509_EXTENSION_value(exts, i);
  140. obj = X509_EXTENSION_get_object(ex);
  141. if ((flag & X509_FLAG_EXTENSIONS_ONLY_KID) != 0
  142. && OBJ_obj2nid(obj) != NID_subject_key_identifier
  143. && OBJ_obj2nid(obj) != NID_authority_key_identifier)
  144. continue;
  145. if (indent && BIO_printf(bp, "%*s", indent, "") <= 0)
  146. return 0;
  147. i2a_ASN1_OBJECT(bp, obj);
  148. j = X509_EXTENSION_get_critical(ex);
  149. if (BIO_printf(bp, ": %s\n", j ? "critical" : "") <= 0)
  150. return 0;
  151. if (!X509V3_EXT_print(bp, ex, flag, indent + 4)) {
  152. BIO_printf(bp, "%*s", indent + 4, "");
  153. ASN1_STRING_print(bp, X509_EXTENSION_get_data(ex));
  154. }
  155. if (BIO_write(bp, "\n", 1) <= 0)
  156. return 0;
  157. }
  158. return 1;
  159. }
  160. static int unknown_ext_print(BIO *out, const unsigned char *ext, int extlen,
  161. unsigned long flag, int indent, int supported)
  162. {
  163. switch (flag & X509V3_EXT_UNKNOWN_MASK) {
  164. case X509V3_EXT_DEFAULT:
  165. return 0;
  166. case X509V3_EXT_ERROR_UNKNOWN:
  167. if (supported)
  168. BIO_printf(out, "%*s<Parse Error>", indent, "");
  169. else
  170. BIO_printf(out, "%*s<Not Supported>", indent, "");
  171. return 1;
  172. case X509V3_EXT_PARSE_UNKNOWN:
  173. return ASN1_parse_dump(out, ext, extlen, indent, -1);
  174. case X509V3_EXT_DUMP_UNKNOWN:
  175. return BIO_dump_indent(out, (const char *)ext, extlen, indent);
  176. default:
  177. return 1;
  178. }
  179. }
  180. #ifndef OPENSSL_NO_STDIO
  181. int X509V3_EXT_print_fp(FILE *fp, X509_EXTENSION *ext, int flag, int indent)
  182. {
  183. BIO *bio_tmp;
  184. int ret;
  185. if ((bio_tmp = BIO_new_fp(fp, BIO_NOCLOSE)) == NULL)
  186. return 0;
  187. ret = X509V3_EXT_print(bio_tmp, ext, flag, indent);
  188. BIO_free(bio_tmp);
  189. return ret;
  190. }
  191. #endif