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 57#include <openssl/asn1.h> 58 59#include <string.h> 60#include <limits.h> 61 62#include <openssl/err.h> 63#include <openssl/mem.h> 64 65#include "../internal.h" 66 67 68ASN1_INTEGER *ASN1_INTEGER_dup(const ASN1_INTEGER *x) 69{ 70 return M_ASN1_INTEGER_dup(x); 71} 72 73int ASN1_INTEGER_cmp(const ASN1_INTEGER *x, const ASN1_INTEGER *y) 74{ 75 int neg, ret; 76 /* Compare signs */ 77 neg = x->type & V_ASN1_NEG; 78 if (neg != (y->type & V_ASN1_NEG)) { 79 if (neg) 80 return -1; 81 else 82 return 1; 83 } 84 85 ret = ASN1_STRING_cmp(x, y); 86 87 if (neg) 88 return -ret; 89 else 90 return ret; 91} 92 93/* 94 * This converts an ASN1 INTEGER into its content encoding. 95 * The internal representation is an ASN1_STRING whose data is a big endian 96 * representation of the value, ignoring the sign. The sign is determined by 97 * the type: V_ASN1_INTEGER for positive and V_ASN1_NEG_INTEGER for negative. 98 * 99 * Positive integers are no problem: they are almost the same as the DER 100 * encoding, except if the first byte is >= 0x80 we need to add a zero pad. 101 * 102 * Negative integers are a bit trickier... 103 * The DER representation of negative integers is in 2s complement form. 104 * The internal form is converted by complementing each octet and finally 105 * adding one to the result. This can be done less messily with a little trick. 106 * If the internal form has trailing zeroes then they will become FF by the 107 * complement and 0 by the add one (due to carry) so just copy as many trailing 108 * zeros to the destination as there are in the source. The carry will add one 109 * to the last none zero octet: so complement this octet and add one and finally 110 * complement any left over until you get to the start of the string. 111 * 112 * Padding is a little trickier too. If the first bytes is > 0x80 then we pad 113 * with 0xff. However if the first byte is 0x80 and one of the following bytes 114 * is non-zero we pad with 0xff. The reason for this distinction is that 0x80 115 * followed by optional zeros isn't padded. 116 */ 117 118int i2c_ASN1_INTEGER(ASN1_INTEGER *a, unsigned char **pp) 119{ 120 int pad = 0, ret, i, neg; 121 unsigned char *p, *n, pb = 0; 122 123 if (a == NULL) 124 return (0); 125 neg = a->type & V_ASN1_NEG; 126 if (a->length == 0) 127 ret = 1; 128 else { 129 ret = a->length; 130 i = a->data[0]; 131 if (ret == 1 && i == 0) 132 neg = 0; 133 if (!neg && (i > 127)) { 134 pad = 1; 135 pb = 0; 136 } else if (neg) { 137 if (i > 128) { 138 pad = 1; 139 pb = 0xFF; 140 } else if (i == 128) { 141 /* 142 * Special case: if any other bytes non zero we pad: 143 * otherwise we don't. 144 */ 145 for (i = 1; i < a->length; i++) 146 if (a->data[i]) { 147 pad = 1; 148 pb = 0xFF; 149 break; 150 } 151 } 152 } 153 ret += pad; 154 } 155 if (pp == NULL) 156 return (ret); 157 p = *pp; 158 159 if (pad) 160 *(p++) = pb; 161 if (a->length == 0) 162 *(p++) = 0; 163 else if (!neg) 164 OPENSSL_memcpy(p, a->data, (unsigned int)a->length); 165 else { 166 /* Begin at the end of the encoding */ 167 n = a->data + a->length - 1; 168 p += a->length - 1; 169 i = a->length; 170 /* Copy zeros to destination as long as source is zero */ 171 while (!*n && i > 1) { 172 *(p--) = 0; 173 n--; 174 i--; 175 } 176 /* Complement and increment next octet */ 177 *(p--) = ((*(n--)) ^ 0xff) + 1; 178 i--; 179 /* Complement any octets left */ 180 for (; i > 0; i--) 181 *(p--) = *(n--) ^ 0xff; 182 } 183 184 *pp += ret; 185 return (ret); 186} 187 188/* Convert just ASN1 INTEGER content octets to ASN1_INTEGER structure */ 189 190ASN1_INTEGER *c2i_ASN1_INTEGER(ASN1_INTEGER **a, const unsigned char **pp, 191 long len) 192{ 193 ASN1_INTEGER *ret = NULL; 194 const unsigned char *p, *pend; 195 unsigned char *to, *s; 196 int i; 197 198 if ((a == NULL) || ((*a) == NULL)) { 199 if ((ret = M_ASN1_INTEGER_new()) == NULL) 200 return (NULL); 201 ret->type = V_ASN1_INTEGER; 202 } else 203 ret = (*a); 204 205 p = *pp; 206 pend = p + len; 207 208 /* 209 * We must OPENSSL_malloc stuff, even for 0 bytes otherwise it signifies 210 * a missing NULL parameter. 211 */ 212 s = (unsigned char *)OPENSSL_malloc((int)len + 1); 213 if (s == NULL) { 214 i = ERR_R_MALLOC_FAILURE; 215 goto err; 216 } 217 to = s; 218 if (!len) { 219 /* 220 * Strictly speaking this is an illegal INTEGER but we tolerate it. 221 */ 222 ret->type = V_ASN1_INTEGER; 223 } else if (*p & 0x80) { /* a negative number */ 224 ret->type = V_ASN1_NEG_INTEGER; 225 if ((*p == 0xff) && (len != 1)) { 226 p++; 227 len--; 228 } 229 i = len; 230 p += i - 1; 231 to += i - 1; 232 while ((!*p) && i) { 233 *(to--) = 0; 234 i--; 235 p--; 236 } 237 /* 238 * Special case: if all zeros then the number will be of the form FF 239 * followed by n zero bytes: this corresponds to 1 followed by n zero 240 * bytes. We've already written n zeros so we just append an extra 241 * one and set the first byte to a 1. This is treated separately 242 * because it is the only case where the number of bytes is larger 243 * than len. 244 */ 245 if (!i) { 246 *s = 1; 247 s[len] = 0; 248 len++; 249 } else { 250 *(to--) = (*(p--) ^ 0xff) + 1; 251 i--; 252 for (; i > 0; i--) 253 *(to--) = *(p--) ^ 0xff; 254 } 255 } else { 256 ret->type = V_ASN1_INTEGER; 257 if ((*p == 0) && (len != 1)) { 258 p++; 259 len--; 260 } 261 OPENSSL_memcpy(s, p, (int)len); 262 } 263 264 if (ret->data != NULL) 265 OPENSSL_free(ret->data); 266 ret->data = s; 267 ret->length = (int)len; 268 if (a != NULL) 269 (*a) = ret; 270 *pp = pend; 271 return (ret); 272 err: 273 OPENSSL_PUT_ERROR(ASN1, i); 274 if ((ret != NULL) && ((a == NULL) || (*a != ret))) 275 M_ASN1_INTEGER_free(ret); 276 return (NULL); 277} 278 279/* 280 * This is a version of d2i_ASN1_INTEGER that ignores the sign bit of ASN1 281 * integers: some broken software can encode a positive INTEGER with its MSB 282 * set as negative (it doesn't add a padding zero). 283 */ 284 285ASN1_INTEGER *d2i_ASN1_UINTEGER(ASN1_INTEGER **a, const unsigned char **pp, 286 long length) 287{ 288 ASN1_INTEGER *ret = NULL; 289 const unsigned char *p; 290 unsigned char *s; 291 long len; 292 int inf, tag, xclass; 293 int i; 294 295 if ((a == NULL) || ((*a) == NULL)) { 296 if ((ret = M_ASN1_INTEGER_new()) == NULL) 297 return (NULL); 298 ret->type = V_ASN1_INTEGER; 299 } else 300 ret = (*a); 301 302 p = *pp; 303 inf = ASN1_get_object(&p, &len, &tag, &xclass, length); 304 if (inf & 0x80) { 305 i = ASN1_R_BAD_OBJECT_HEADER; 306 goto err; 307 } 308 309 if (tag != V_ASN1_INTEGER) { 310 i = ASN1_R_EXPECTING_AN_INTEGER; 311 goto err; 312 } 313 314 /* 315 * We must OPENSSL_malloc stuff, even for 0 bytes otherwise it signifies 316 * a missing NULL parameter. 317 */ 318 s = (unsigned char *)OPENSSL_malloc((int)len + 1); 319 if (s == NULL) { 320 i = ERR_R_MALLOC_FAILURE; 321 goto err; 322 } 323 ret->type = V_ASN1_INTEGER; 324 if (len) { 325 if ((*p == 0) && (len != 1)) { 326 p++; 327 len--; 328 } 329 OPENSSL_memcpy(s, p, (int)len); 330 p += len; 331 } 332 333 if (ret->data != NULL) 334 OPENSSL_free(ret->data); 335 ret->data = s; 336 ret->length = (int)len; 337 if (a != NULL) 338 (*a) = ret; 339 *pp = p; 340 return (ret); 341 err: 342 OPENSSL_PUT_ERROR(ASN1, i); 343 if ((ret != NULL) && ((a == NULL) || (*a != ret))) 344 M_ASN1_INTEGER_free(ret); 345 return (NULL); 346} 347 348int ASN1_INTEGER_set(ASN1_INTEGER *a, long v) 349{ 350 if (v >= 0) { 351 return ASN1_INTEGER_set_uint64(a, (uint64_t) v); 352 } 353 354 if (!ASN1_INTEGER_set_uint64(a, 0 - (uint64_t) v)) { 355 return 0; 356 } 357 358 a->type = V_ASN1_NEG_INTEGER; 359 return 1; 360} 361 362int ASN1_INTEGER_set_uint64(ASN1_INTEGER *out, uint64_t v) 363{ 364 uint8_t *const newdata = OPENSSL_malloc(sizeof(uint64_t)); 365 if (newdata == NULL) { 366 OPENSSL_PUT_ERROR(ASN1, ERR_R_MALLOC_FAILURE); 367 return 0; 368 } 369 370 OPENSSL_free(out->data); 371 out->data = newdata; 372 v = CRYPTO_bswap8(v); 373 memcpy(out->data, &v, sizeof(v)); 374 375 out->type = V_ASN1_INTEGER; 376 377 size_t leading_zeros; 378 for (leading_zeros = 0; leading_zeros < sizeof(uint64_t) - 1; 379 leading_zeros++) { 380 if (out->data[leading_zeros] != 0) { 381 break; 382 } 383 } 384 385 out->length = sizeof(uint64_t) - leading_zeros; 386 OPENSSL_memmove(out->data, out->data + leading_zeros, out->length); 387 388 return 1; 389} 390 391long ASN1_INTEGER_get(const ASN1_INTEGER *a) 392{ 393 int neg = 0, i; 394 395 if (a == NULL) 396 return (0L); 397 i = a->type; 398 if (i == V_ASN1_NEG_INTEGER) 399 neg = 1; 400 else if (i != V_ASN1_INTEGER) 401 return -1; 402 403 OPENSSL_COMPILE_ASSERT(sizeof(uint64_t) >= sizeof(long), 404 long_larger_than_uint64_t); 405 406 if (a->length > (int)sizeof(uint64_t)) { 407 /* hmm... a bit ugly, return all ones */ 408 return -1; 409 } 410 411 uint64_t r64 = 0; 412 if (a->data != NULL) { 413 for (i = 0; i < a->length; i++) { 414 r64 <<= 8; 415 r64 |= (unsigned char)a->data[i]; 416 } 417 418 if (r64 > LONG_MAX) { 419 return -1; 420 } 421 } 422 423 long r = (long) r64; 424 if (neg) 425 r = -r; 426 427 return r; 428} 429 430ASN1_INTEGER *BN_to_ASN1_INTEGER(const BIGNUM *bn, ASN1_INTEGER *ai) 431{ 432 ASN1_INTEGER *ret; 433 int len, j; 434 435 if (ai == NULL) 436 ret = M_ASN1_INTEGER_new(); 437 else 438 ret = ai; 439 if (ret == NULL) { 440 OPENSSL_PUT_ERROR(ASN1, ASN1_R_NESTED_ASN1_ERROR); 441 goto err; 442 } 443 if (BN_is_negative(bn) && !BN_is_zero(bn)) 444 ret->type = V_ASN1_NEG_INTEGER; 445 else 446 ret->type = V_ASN1_INTEGER; 447 j = BN_num_bits(bn); 448 len = ((j == 0) ? 0 : ((j / 8) + 1)); 449 if (ret->length < len + 4) { 450 unsigned char *new_data = OPENSSL_realloc(ret->data, len + 4); 451 if (!new_data) { 452 OPENSSL_PUT_ERROR(ASN1, ERR_R_MALLOC_FAILURE); 453 goto err; 454 } 455 ret->data = new_data; 456 } 457 ret->length = BN_bn2bin(bn, ret->data); 458 /* Correct zero case */ 459 if (!ret->length) { 460 ret->data[0] = 0; 461 ret->length = 1; 462 } 463 return (ret); 464 err: 465 if (ret != ai) 466 M_ASN1_INTEGER_free(ret); 467 return (NULL); 468} 469 470BIGNUM *ASN1_INTEGER_to_BN(const ASN1_INTEGER *ai, BIGNUM *bn) 471{ 472 BIGNUM *ret; 473 474 if ((ret = BN_bin2bn(ai->data, ai->length, bn)) == NULL) 475 OPENSSL_PUT_ERROR(ASN1, ASN1_R_BN_LIB); 476 else if (ai->type == V_ASN1_NEG_INTEGER) 477 BN_set_negative(ret, 1); 478 return (ret); 479} 480