| Line | Source | Count |
| 1 | | - |
| 2 | | - |
| 3 | | - |
| 4 | | - |
| 5 | | - |
| 6 | | - |
| 7 | | - |
| 8 | | - |
| 9 | | - |
| 10 | | - |
| 11 | | - |
| 12 | | - |
| 13 | | - |
| 14 | | - |
| 15 | | - |
| 16 | | - |
| 17 | | - |
| 18 | | - |
| 19 | | - |
| 20 | | - |
| 21 | | - |
| 22 | | - |
| 23 | | - |
| 24 | | - |
| 25 | | - |
| 26 | | - |
| 27 | | - |
| 28 | | - |
| 29 | | - |
| 30 | | - |
| 31 | | - |
| 32 | | - |
| 33 | | - |
| 34 | | - |
| 35 | | - |
| 36 | | - |
| 37 | | - |
| 38 | | - |
| 39 | | - |
| 40 | | - |
| 41 | | - |
| 42 | | - |
| 43 | | - |
| 44 | | - |
| 45 | | - |
| 46 | | - |
| 47 | | - |
| 48 | | - |
| 49 | | - |
| 50 | | - |
| 51 | | - |
| 52 | | - |
| 53 | | - |
| 54 | | - |
| 55 | | - |
| 56 | | - |
| 57 | | - |
| 58 | | - |
| 59 | #include <limits.h> | - |
| 60 | #include <stdio.h> | - |
| 61 | | - |
| 62 | #include <openssl/asn1.h> | - |
| 63 | #include <openssl/buffer.h> | - |
| 64 | #include <openssl/err.h> | - |
| 65 | | - |
| 66 | static int asn1_d2i_read_bio(BIO *in, BUF_MEM **pb); | - |
| 67 | | - |
| 68 | #ifndef NO_OLD_ASN1 | - |
| 69 | | - |
| 70 | void * | - |
| 71 | ASN1_d2i_fp(void *(*xnew)(void), d2i_of_void *d2i, FILE *in, void **x) | - |
| 72 | { | - |
| 73 | BIO *b; | - |
| 74 | void *ret; | - |
| 75 | | - |
| 76 | if ((b = BIO_new(BIO_s_file())) == NULL) {| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 77 | ASN1error(ERR_R_BUF_LIB); | - |
| 78 | return (NULL); never executed: return ( ((void *)0) ); | 0 |
| 79 | } | - |
| 80 | BIO_set_fp(b, in, BIO_NOCLOSE); | - |
| 81 | ret = ASN1_d2i_bio(xnew, d2i, b, x); | - |
| 82 | BIO_free(b); | - |
| 83 | return (ret); never executed: return (ret); | 0 |
| 84 | } | - |
| 85 | | - |
| 86 | void * | - |
| 87 | ASN1_d2i_bio(void *(*xnew)(void), d2i_of_void *d2i, BIO *in, void **x) | - |
| 88 | { | - |
| 89 | BUF_MEM *b = NULL; | - |
| 90 | const unsigned char *p; | - |
| 91 | void *ret = NULL; | - |
| 92 | int len; | - |
| 93 | | - |
| 94 | len = asn1_d2i_read_bio(in, &b); | - |
| 95 | if (len < 0)| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 96 | goto err; never executed: goto err; | 0 |
| 97 | | - |
| 98 | p = (unsigned char *)b->data; | - |
| 99 | ret = d2i(x, &p, len); | - |
| 100 | | - |
| 101 | err: code before this statement never executed: err: | 0 |
| 102 | if (b != NULL)| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 103 | BUF_MEM_free(b); never executed: BUF_MEM_free(b); | 0 |
| 104 | return (ret); never executed: return (ret); | 0 |
| 105 | } | - |
| 106 | | - |
| 107 | #endif | - |
| 108 | | - |
| 109 | void * | - |
| 110 | ASN1_item_d2i_bio(const ASN1_ITEM *it, BIO *in, void *x) | - |
| 111 | { | - |
| 112 | BUF_MEM *b = NULL; | - |
| 113 | const unsigned char *p; | - |
| 114 | void *ret = NULL; | - |
| 115 | int len; | - |
| 116 | | - |
| 117 | len = asn1_d2i_read_bio(in, &b); | - |
| 118 | if (len < 0)| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 119 | goto err; never executed: goto err; | 0 |
| 120 | | - |
| 121 | p = (const unsigned char *)b->data; | - |
| 122 | ret = ASN1_item_d2i(x, &p, len, it); | - |
| 123 | | - |
| 124 | err: code before this statement never executed: err: | 0 |
| 125 | if (b != NULL)| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 126 | BUF_MEM_free(b); never executed: BUF_MEM_free(b); | 0 |
| 127 | return (ret); never executed: return (ret); | 0 |
| 128 | } | - |
| 129 | | - |
| 130 | void * | - |
| 131 | ASN1_item_d2i_fp(const ASN1_ITEM *it, FILE *in, void *x) | - |
| 132 | { | - |
| 133 | BIO *b; | - |
| 134 | char *ret; | - |
| 135 | | - |
| 136 | if ((b = BIO_new(BIO_s_file())) == NULL) {| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 137 | ASN1error(ERR_R_BUF_LIB); | - |
| 138 | return (NULL); never executed: return ( ((void *)0) ); | 0 |
| 139 | } | - |
| 140 | BIO_set_fp(b, in, BIO_NOCLOSE); | - |
| 141 | ret = ASN1_item_d2i_bio(it, b, x); | - |
| 142 | BIO_free(b); | - |
| 143 | return (ret); never executed: return (ret); | 0 |
| 144 | } | - |
| 145 | | - |
| 146 | #define HEADER_SIZE 8 | - |
| 147 | #define ASN1_CHUNK_INITIAL_SIZE (16 * 1024) | - |
| 148 | static int | - |
| 149 | asn1_d2i_read_bio(BIO *in, BUF_MEM **pb) | - |
| 150 | { | - |
| 151 | BUF_MEM *b; | - |
| 152 | unsigned char *p; | - |
| 153 | int i; | - |
| 154 | ASN1_const_CTX c; | - |
| 155 | size_t want = HEADER_SIZE; | - |
| 156 | int eos = 0; | - |
| 157 | size_t off = 0; | - |
| 158 | size_t len = 0; | - |
| 159 | | - |
| 160 | b = BUF_MEM_new(); | - |
| 161 | if (b == NULL) {| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 162 | ASN1error(ERR_R_MALLOC_FAILURE); | - |
| 163 | return -1; never executed: return -1; | 0 |
| 164 | } | - |
| 165 | | - |
| 166 | ERR_clear_error(); | - |
| 167 | for (;;) { | - |
| 168 | if (want >= (len - off)) {| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 169 | want -= (len - off); | - |
| 170 | | - |
| 171 | if (len + want < len ||| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 172 | !BUF_MEM_grow_clean(b, len + want)) {| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 173 | ASN1error(ERR_R_MALLOC_FAILURE); | - |
| 174 | goto err; never executed: goto err; | 0 |
| 175 | } | - |
| 176 | i = BIO_read(in, &(b->data[len]), want); | - |
| 177 | if ((i < 0) && ((len - off) == 0)) {| TRUE | never evaluated | | FALSE | never evaluated |
| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 178 | ASN1error(ASN1_R_NOT_ENOUGH_DATA); | - |
| 179 | goto err; never executed: goto err; | 0 |
| 180 | } | - |
| 181 | if (i > 0) {| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 182 | if (len + i < len) {| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 183 | ASN1error(ASN1_R_TOO_LONG); | - |
| 184 | goto err; never executed: goto err; | 0 |
| 185 | } | - |
| 186 | len += i; | - |
| 187 | } never executed: end of block | 0 |
| 188 | } never executed: end of block | 0 |
| 189 | | - |
| 190 | | - |
| 191 | p = (unsigned char *) & (b->data[off]); | - |
| 192 | c.p = p; | - |
| 193 | c.inf = ASN1_get_object(&(c.p), &(c.slen), &(c.tag), | - |
| 194 | &(c.xclass), len - off); | - |
| 195 | if (c.inf & 0x80) {| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 196 | unsigned long e; | - |
| 197 | | - |
| 198 | e = ERR_GET_REASON(ERR_peek_error()); | - |
| 199 | if (e != ASN1_R_TOO_LONG)| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 200 | goto err; never executed: goto err; | 0 |
| 201 | else | - |
| 202 | ERR_clear_error(); never executed: ERR_clear_error(); | 0 |
| 203 | } | - |
| 204 | i = c.p - p; | - |
| 205 | off += i; | - |
| 206 | | - |
| 207 | if (c.inf & 1) {| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 208 | | - |
| 209 | eos++; | - |
| 210 | if (eos < 0) {| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 211 | ASN1error(ASN1_R_HEADER_TOO_LONG); | - |
| 212 | goto err; never executed: goto err; | 0 |
| 213 | } | - |
| 214 | want = HEADER_SIZE; | - |
| 215 | } else if (eos && (c.slen == 0) && (c.tag == V_ASN1_EOC)) { never executed: end of block | TRUE | never evaluated | | FALSE | never evaluated |
| TRUE | never evaluated | | FALSE | never evaluated |
| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 216 | | - |
| 217 | eos--; | - |
| 218 | if (eos <= 0)| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 219 | break; never executed: break; | 0 |
| 220 | else | - |
| 221 | want = HEADER_SIZE; never executed: want = 8; | 0 |
| 222 | } else { | - |
| 223 | | - |
| 224 | want = c.slen; | - |
| 225 | if (want > (len - off)) {| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 226 | size_t chunk_max = ASN1_CHUNK_INITIAL_SIZE; | - |
| 227 | | - |
| 228 | want -= (len - off); | - |
| 229 | if (want > INT_MAX ||| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 230 | len+want < len) {| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 231 | ASN1error(ASN1_R_TOO_LONG); | - |
| 232 | goto err; never executed: goto err; | 0 |
| 233 | } | - |
| 234 | while (want > 0) {| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 235 | | - |
| 236 | | - |
| 237 | | - |
| 238 | | - |
| 239 | | - |
| 240 | | - |
| 241 | size_t chunk = want > chunk_max ? chunk_max : want;| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 242 | | - |
| 243 | if (!BUF_MEM_grow_clean(b, len + chunk)) {| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 244 | ASN1error(ERR_R_MALLOC_FAILURE); | - |
| 245 | goto err; never executed: goto err; | 0 |
| 246 | } | - |
| 247 | want -= chunk; | - |
| 248 | while (chunk > 0) {| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 249 | i = BIO_read(in, &(b->data[len]), chunk); | - |
| 250 | if (i <= 0) {| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 251 | ASN1error(ASN1_R_NOT_ENOUGH_DATA); | - |
| 252 | goto err; never executed: goto err; | 0 |
| 253 | } | - |
| 254 | | - |
| 255 | | - |
| 256 | | - |
| 257 | | - |
| 258 | len += i; | - |
| 259 | chunk -= i; | - |
| 260 | } never executed: end of block | 0 |
| 261 | if (chunk_max < INT_MAX/2)| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 262 | chunk_max *= 2; never executed: chunk_max *= 2; | 0 |
| 263 | } never executed: end of block | 0 |
| 264 | } never executed: end of block | 0 |
| 265 | if (off + c.slen < off) {| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 266 | ASN1error(ASN1_R_TOO_LONG); | - |
| 267 | goto err; never executed: goto err; | 0 |
| 268 | } | - |
| 269 | off += c.slen; | - |
| 270 | if (eos <= 0) {| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 271 | break; never executed: break; | 0 |
| 272 | } else | - |
| 273 | want = HEADER_SIZE; never executed: want = 8; | 0 |
| 274 | } | - |
| 275 | } | - |
| 276 | | - |
| 277 | if (off > INT_MAX) {| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 278 | ASN1error(ASN1_R_TOO_LONG); | - |
| 279 | goto err; never executed: goto err; | 0 |
| 280 | } | - |
| 281 | | - |
| 282 | *pb = b; | - |
| 283 | return off; never executed: return off; | 0 |
| 284 | | - |
| 285 | err: | - |
| 286 | if (b != NULL)| TRUE | never evaluated | | FALSE | never evaluated |
| 0 |
| 287 | BUF_MEM_free(b); never executed: BUF_MEM_free(b); | 0 |
| 288 | return -1; never executed: return -1; | 0 |
| 289 | } | - |
| | |