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