00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037 #include "polarssl/config.h"
00038
00039 #if defined(POLARSSL_X509_USE_C)
00040
00041 #include "polarssl/x509.h"
00042 #include "polarssl/asn1.h"
00043 #include "polarssl/oid.h"
00044 #if defined(POLARSSL_PEM_PARSE_C)
00045 #include "polarssl/pem.h"
00046 #endif
00047
00048 #if defined(POLARSSL_MEMORY_C)
00049 #include "polarssl/memory.h"
00050 #else
00051 #define polarssl_malloc malloc
00052 #define polarssl_free free
00053 #endif
00054
00055 #include <string.h>
00056 #include <stdlib.h>
00057 #if defined(_WIN32) && !defined(EFIX64) && !defined(EFI32)
00058 #include <windows.h>
00059 #else
00060 #include <time.h>
00061 #endif
00062
00063 #if defined(EFIX64) || defined(EFI32)
00064 #include <stdio.h>
00065 #endif
00066
00067 #if defined(POLARSSL_FS_IO)
00068 #include <stdio.h>
00069 #if !defined(_WIN32)
00070 #include <sys/types.h>
00071 #include <sys/stat.h>
00072 #include <dirent.h>
00073 #endif
00074 #endif
00075
00076
00077
00078
00079 int x509_get_serial( unsigned char **p, const unsigned char *end,
00080 x509_buf *serial )
00081 {
00082 int ret;
00083
00084 if( ( end - *p ) < 1 )
00085 return( POLARSSL_ERR_X509_INVALID_SERIAL +
00086 POLARSSL_ERR_ASN1_OUT_OF_DATA );
00087
00088 if( **p != ( ASN1_CONTEXT_SPECIFIC | ASN1_PRIMITIVE | 2 ) &&
00089 **p != ASN1_INTEGER )
00090 return( POLARSSL_ERR_X509_INVALID_SERIAL +
00091 POLARSSL_ERR_ASN1_UNEXPECTED_TAG );
00092
00093 serial->tag = *(*p)++;
00094
00095 if( ( ret = asn1_get_len( p, end, &serial->len ) ) != 0 )
00096 return( POLARSSL_ERR_X509_INVALID_SERIAL + ret );
00097
00098 serial->p = *p;
00099 *p += serial->len;
00100
00101 return( 0 );
00102 }
00103
00104
00105
00106
00107
00108
00109
00110 int x509_get_alg_null( unsigned char **p, const unsigned char *end,
00111 x509_buf *alg )
00112 {
00113 int ret;
00114
00115 if( ( ret = asn1_get_alg_null( p, end, alg ) ) != 0 )
00116 return( POLARSSL_ERR_X509_INVALID_ALG + ret );
00117
00118 return( 0 );
00119 }
00120
00121
00122
00123
00124
00125
00126
00127
00128
00129
00130 static int x509_get_attr_type_value( unsigned char **p,
00131 const unsigned char *end,
00132 x509_name *cur )
00133 {
00134 int ret;
00135 size_t len;
00136 x509_buf *oid;
00137 x509_buf *val;
00138
00139 if( ( ret = asn1_get_tag( p, end, &len,
00140 ASN1_CONSTRUCTED | ASN1_SEQUENCE ) ) != 0 )
00141 return( POLARSSL_ERR_X509_INVALID_NAME + ret );
00142
00143 if( ( end - *p ) < 1 )
00144 return( POLARSSL_ERR_X509_INVALID_NAME +
00145 POLARSSL_ERR_ASN1_OUT_OF_DATA );
00146
00147 oid = &cur->oid;
00148 oid->tag = **p;
00149
00150 if( ( ret = asn1_get_tag( p, end, &oid->len, ASN1_OID ) ) != 0 )
00151 return( POLARSSL_ERR_X509_INVALID_NAME + ret );
00152
00153 oid->p = *p;
00154 *p += oid->len;
00155
00156 if( ( end - *p ) < 1 )
00157 return( POLARSSL_ERR_X509_INVALID_NAME +
00158 POLARSSL_ERR_ASN1_OUT_OF_DATA );
00159
00160 if( **p != ASN1_BMP_STRING && **p != ASN1_UTF8_STRING &&
00161 **p != ASN1_T61_STRING && **p != ASN1_PRINTABLE_STRING &&
00162 **p != ASN1_IA5_STRING && **p != ASN1_UNIVERSAL_STRING )
00163 return( POLARSSL_ERR_X509_INVALID_NAME +
00164 POLARSSL_ERR_ASN1_UNEXPECTED_TAG );
00165
00166 val = &cur->val;
00167 val->tag = *(*p)++;
00168
00169 if( ( ret = asn1_get_len( p, end, &val->len ) ) != 0 )
00170 return( POLARSSL_ERR_X509_INVALID_NAME + ret );
00171
00172 val->p = *p;
00173 *p += val->len;
00174
00175 cur->next = NULL;
00176
00177 return( 0 );
00178 }
00179
00180
00181
00182
00183
00184
00185
00186
00187
00188
00189
00190
00191
00192
00193
00194
00195
00196 int x509_get_name( unsigned char **p, const unsigned char *end,
00197 x509_name *cur )
00198 {
00199 int ret;
00200 size_t set_len;
00201 const unsigned char *end_set;
00202
00203
00204
00205
00206 if( ( ret = asn1_get_tag( p, end, &set_len,
00207 ASN1_CONSTRUCTED | ASN1_SET ) ) != 0 )
00208 return( POLARSSL_ERR_X509_INVALID_NAME + ret );
00209
00210 end_set = *p + set_len;
00211
00212 if( ( ret = x509_get_attr_type_value( p, end_set, cur ) ) != 0 )
00213 return( ret );
00214
00215 if( *p != end_set )
00216 return( POLARSSL_ERR_X509_FEATURE_UNAVAILABLE );
00217
00218
00219
00220
00221 if( *p == end )
00222 return( 0 );
00223
00224 cur->next = (x509_name *) polarssl_malloc( sizeof( x509_name ) );
00225
00226 if( cur->next == NULL )
00227 return( POLARSSL_ERR_X509_MALLOC_FAILED );
00228
00229 memset( cur->next, 0, sizeof( x509_name ) );
00230
00231 return( x509_get_name( p, end, cur->next ) );
00232 }
00233
00234
00235
00236
00237
00238
00239 int x509_get_time( unsigned char **p, const unsigned char *end,
00240 x509_time *time )
00241 {
00242 int ret;
00243 size_t len;
00244 char date[64];
00245 unsigned char tag;
00246
00247 if( ( end - *p ) < 1 )
00248 return( POLARSSL_ERR_X509_INVALID_DATE +
00249 POLARSSL_ERR_ASN1_OUT_OF_DATA );
00250
00251 tag = **p;
00252
00253 if ( tag == ASN1_UTC_TIME )
00254 {
00255 (*p)++;
00256 ret = asn1_get_len( p, end, &len );
00257
00258 if( ret != 0 )
00259 return( POLARSSL_ERR_X509_INVALID_DATE + ret );
00260
00261 memset( date, 0, sizeof( date ) );
00262 memcpy( date, *p, ( len < sizeof( date ) - 1 ) ?
00263 len : sizeof( date ) - 1 );
00264
00265 if( sscanf( date, "%2d%2d%2d%2d%2d%2d",
00266 &time->year, &time->mon, &time->day,
00267 &time->hour, &time->min, &time->sec ) < 5 )
00268 return( POLARSSL_ERR_X509_INVALID_DATE );
00269
00270 time->year += 100 * ( time->year < 50 );
00271 time->year += 1900;
00272
00273 *p += len;
00274
00275 return( 0 );
00276 }
00277 else if ( tag == ASN1_GENERALIZED_TIME )
00278 {
00279 (*p)++;
00280 ret = asn1_get_len( p, end, &len );
00281
00282 if( ret != 0 )
00283 return( POLARSSL_ERR_X509_INVALID_DATE + ret );
00284
00285 memset( date, 0, sizeof( date ) );
00286 memcpy( date, *p, ( len < sizeof( date ) - 1 ) ?
00287 len : sizeof( date ) - 1 );
00288
00289 if( sscanf( date, "%4d%2d%2d%2d%2d%2d",
00290 &time->year, &time->mon, &time->day,
00291 &time->hour, &time->min, &time->sec ) < 5 )
00292 return( POLARSSL_ERR_X509_INVALID_DATE );
00293
00294 *p += len;
00295
00296 return( 0 );
00297 }
00298 else
00299 return( POLARSSL_ERR_X509_INVALID_DATE +
00300 POLARSSL_ERR_ASN1_UNEXPECTED_TAG );
00301 }
00302
00303 int x509_get_sig( unsigned char **p, const unsigned char *end, x509_buf *sig )
00304 {
00305 int ret;
00306 size_t len;
00307
00308 if( ( end - *p ) < 1 )
00309 return( POLARSSL_ERR_X509_INVALID_SIGNATURE +
00310 POLARSSL_ERR_ASN1_OUT_OF_DATA );
00311
00312 sig->tag = **p;
00313
00314 if( ( ret = asn1_get_bitstring_null( p, end, &len ) ) != 0 )
00315 return( POLARSSL_ERR_X509_INVALID_SIGNATURE + ret );
00316
00317 sig->len = len;
00318 sig->p = *p;
00319
00320 *p += len;
00321
00322 return( 0 );
00323 }
00324
00325 int x509_get_sig_alg( const x509_buf *sig_oid, md_type_t *md_alg,
00326 pk_type_t *pk_alg )
00327 {
00328 int ret = oid_get_sig_alg( sig_oid, md_alg, pk_alg );
00329
00330 if( ret != 0 )
00331 return( POLARSSL_ERR_X509_UNKNOWN_SIG_ALG + ret );
00332
00333 return( 0 );
00334 }
00335
00336
00337
00338
00339
00340 int x509_get_ext( unsigned char **p, const unsigned char *end,
00341 x509_buf *ext, int tag )
00342 {
00343 int ret;
00344 size_t len;
00345
00346 if( *p == end )
00347 return( 0 );
00348
00349 ext->tag = **p;
00350
00351 if( ( ret = asn1_get_tag( p, end, &ext->len,
00352 ASN1_CONTEXT_SPECIFIC | ASN1_CONSTRUCTED | tag ) ) != 0 )
00353 return( ret );
00354
00355 ext->p = *p;
00356 end = *p + ext->len;
00357
00358
00359
00360
00361
00362
00363
00364
00365
00366 if( ( ret = asn1_get_tag( p, end, &len,
00367 ASN1_CONSTRUCTED | ASN1_SEQUENCE ) ) != 0 )
00368 return( POLARSSL_ERR_X509_INVALID_EXTENSIONS + ret );
00369
00370 if( end != *p + len )
00371 return( POLARSSL_ERR_X509_INVALID_EXTENSIONS +
00372 POLARSSL_ERR_ASN1_LENGTH_MISMATCH );
00373
00374 return( 0 );
00375 }
00376
00377 #if defined(POLARSSL_FS_IO)
00378
00379
00380
00381 int x509_load_file( const char *path, unsigned char **buf, size_t *n )
00382 {
00383 FILE *f;
00384 long size;
00385
00386 if( ( f = fopen( path, "rb" ) ) == NULL )
00387 return( POLARSSL_ERR_X509_FILE_IO_ERROR );
00388
00389 fseek( f, 0, SEEK_END );
00390 if( ( size = ftell( f ) ) == -1 )
00391 {
00392 fclose( f );
00393 return( POLARSSL_ERR_X509_FILE_IO_ERROR );
00394 }
00395 fseek( f, 0, SEEK_SET );
00396
00397 *n = (size_t) size;
00398
00399 if( *n + 1 == 0 ||
00400 ( *buf = (unsigned char *) polarssl_malloc( *n + 1 ) ) == NULL )
00401 {
00402 fclose( f );
00403 return( POLARSSL_ERR_X509_MALLOC_FAILED );
00404 }
00405
00406 if( fread( *buf, 1, *n, f ) != *n )
00407 {
00408 fclose( f );
00409 polarssl_free( *buf );
00410 return( POLARSSL_ERR_X509_FILE_IO_ERROR );
00411 }
00412
00413 fclose( f );
00414
00415 (*buf)[*n] = '\0';
00416
00417 return( 0 );
00418 }
00419 #endif
00420
00421 #if defined(_MSC_VER) && !defined snprintf && !defined(EFIX64) && \
00422 !defined(EFI32)
00423 #include <stdarg.h>
00424
00425 #if !defined vsnprintf
00426 #define vsnprintf _vsnprintf
00427 #endif // vsnprintf
00428
00429
00430
00431
00432
00433
00434
00435
00436 static int compat_snprintf(char *str, size_t size, const char *format, ...)
00437 {
00438 va_list ap;
00439 int res = -1;
00440
00441 va_start( ap, format );
00442
00443 res = vsnprintf( str, size, format, ap );
00444
00445 va_end( ap );
00446
00447
00448 if ( res < 0 )
00449 return( (int) size + 20 );
00450
00451 return res;
00452 }
00453
00454 #define snprintf compat_snprintf
00455 #endif
00456
00457 #define POLARSSL_ERR_DEBUG_BUF_TOO_SMALL -2
00458
00459 #define SAFE_SNPRINTF() \
00460 { \
00461 if( ret == -1 ) \
00462 return( -1 ); \
00463 \
00464 if ( (unsigned int) ret > n ) { \
00465 p[n - 1] = '\0'; \
00466 return POLARSSL_ERR_DEBUG_BUF_TOO_SMALL;\
00467 } \
00468 \
00469 n -= (unsigned int) ret; \
00470 p += (unsigned int) ret; \
00471 }
00472
00473
00474
00475
00476
00477 int x509_dn_gets( char *buf, size_t size, const x509_name *dn )
00478 {
00479 int ret;
00480 size_t i, n;
00481 unsigned char c;
00482 const x509_name *name;
00483 const char *short_name = NULL;
00484 char s[128], *p;
00485
00486 memset( s, 0, sizeof( s ) );
00487
00488 name = dn;
00489 p = buf;
00490 n = size;
00491
00492 while( name != NULL )
00493 {
00494 if( !name->oid.p )
00495 {
00496 name = name->next;
00497 continue;
00498 }
00499
00500 if( name != dn )
00501 {
00502 ret = snprintf( p, n, ", " );
00503 SAFE_SNPRINTF();
00504 }
00505
00506 ret = oid_get_attr_short_name( &name->oid, &short_name );
00507
00508 if( ret == 0 )
00509 ret = snprintf( p, n, "%s=", short_name );
00510 else
00511 ret = snprintf( p, n, "\?\?=" );
00512 SAFE_SNPRINTF();
00513
00514 for( i = 0; i < name->val.len; i++ )
00515 {
00516 if( i >= sizeof( s ) - 1 )
00517 break;
00518
00519 c = name->val.p[i];
00520 if( c < 32 || c == 127 || ( c > 128 && c < 160 ) )
00521 s[i] = '?';
00522 else s[i] = c;
00523 }
00524 s[i] = '\0';
00525 ret = snprintf( p, n, "%s", s );
00526 SAFE_SNPRINTF();
00527 name = name->next;
00528 }
00529
00530 return( (int) ( size - n ) );
00531 }
00532
00533
00534
00535
00536
00537 int x509_serial_gets( char *buf, size_t size, const x509_buf *serial )
00538 {
00539 int ret;
00540 size_t i, n, nr;
00541 char *p;
00542
00543 p = buf;
00544 n = size;
00545
00546 nr = ( serial->len <= 32 )
00547 ? serial->len : 28;
00548
00549 for( i = 0; i < nr; i++ )
00550 {
00551 if( i == 0 && nr > 1 && serial->p[i] == 0x0 )
00552 continue;
00553
00554 ret = snprintf( p, n, "%02X%s",
00555 serial->p[i], ( i < nr - 1 ) ? ":" : "" );
00556 SAFE_SNPRINTF();
00557 }
00558
00559 if( nr != serial->len )
00560 {
00561 ret = snprintf( p, n, "...." );
00562 SAFE_SNPRINTF();
00563 }
00564
00565 return( (int) ( size - n ) );
00566 }
00567
00568
00569
00570
00571 int x509_key_size_helper( char *buf, size_t size, const char *name )
00572 {
00573 char *p = buf;
00574 size_t n = size;
00575 int ret;
00576
00577 if( strlen( name ) + sizeof( " key size" ) > size )
00578 return POLARSSL_ERR_DEBUG_BUF_TOO_SMALL;
00579
00580 ret = snprintf( p, n, "%s key size", name );
00581 SAFE_SNPRINTF();
00582
00583 return( 0 );
00584 }
00585
00586
00587
00588
00589 const char *x509_oid_get_description( x509_buf *oid )
00590 {
00591 const char *desc = NULL;
00592 int ret;
00593
00594 ret = oid_get_extended_key_usage( oid, &desc );
00595
00596 if( ret != 0 )
00597 return( NULL );
00598
00599 return( desc );
00600 }
00601
00602
00603 int x509_oid_get_numeric_string( char *buf, size_t size, x509_buf *oid )
00604 {
00605 return oid_get_numeric_string( buf, size, oid );
00606 }
00607
00608
00609
00610
00611 #if defined(POLARSSL_HAVE_TIME)
00612 int x509_time_expired( const x509_time *to )
00613 {
00614 int year, mon, day;
00615 int hour, min, sec;
00616
00617 #if defined(_WIN32) && !defined(EFIX64) && !defined(EFI32)
00618 SYSTEMTIME st;
00619
00620 GetLocalTime(&st);
00621
00622 year = st.wYear;
00623 mon = st.wMonth;
00624 day = st.wDay;
00625 hour = st.wHour;
00626 min = st.wMinute;
00627 sec = st.wSecond;
00628 #else
00629 struct tm *lt;
00630 time_t tt;
00631
00632 tt = time( NULL );
00633 lt = localtime( &tt );
00634
00635 year = lt->tm_year + 1900;
00636 mon = lt->tm_mon + 1;
00637 day = lt->tm_mday;
00638 hour = lt->tm_hour;
00639 min = lt->tm_min;
00640 sec = lt->tm_sec;
00641 #endif
00642
00643 if( year > to->year )
00644 return( 1 );
00645
00646 if( year == to->year &&
00647 mon > to->mon )
00648 return( 1 );
00649
00650 if( year == to->year &&
00651 mon == to->mon &&
00652 day > to->day )
00653 return( 1 );
00654
00655 if( year == to->year &&
00656 mon == to->mon &&
00657 day == to->day &&
00658 hour > to->hour )
00659 return( 1 );
00660
00661 if( year == to->year &&
00662 mon == to->mon &&
00663 day == to->day &&
00664 hour == to->hour &&
00665 min > to->min )
00666 return( 1 );
00667
00668 if( year == to->year &&
00669 mon == to->mon &&
00670 day == to->day &&
00671 hour == to->hour &&
00672 min == to->min &&
00673 sec > to->sec )
00674 return( 1 );
00675
00676 return( 0 );
00677 }
00678 #else
00679 int x509_time_expired( const x509_time *to )
00680 {
00681 ((void) to);
00682 return( 0 );
00683 }
00684 #endif
00685
00686 #if defined(POLARSSL_SELF_TEST)
00687
00688 #include "polarssl/x509_crt.h"
00689 #include "polarssl/certs.h"
00690
00691
00692
00693
00694 int x509_self_test( int verbose )
00695 {
00696 #if defined(POLARSSL_CERTS_C) && defined(POLARSSL_MD5_C)
00697 int ret;
00698 int flags;
00699 x509_crt cacert;
00700 x509_crt clicert;
00701
00702 if( verbose != 0 )
00703 printf( " X.509 certificate load: " );
00704
00705 x509_crt_init( &clicert );
00706
00707 ret = x509_crt_parse( &clicert, (const unsigned char *) test_cli_crt,
00708 strlen( test_cli_crt ) );
00709 if( ret != 0 )
00710 {
00711 if( verbose != 0 )
00712 printf( "failed\n" );
00713
00714 return( ret );
00715 }
00716
00717 x509_crt_init( &cacert );
00718
00719 ret = x509_crt_parse( &cacert, (const unsigned char *) test_ca_crt,
00720 strlen( test_ca_crt ) );
00721 if( ret != 0 )
00722 {
00723 if( verbose != 0 )
00724 printf( "failed\n" );
00725
00726 return( ret );
00727 }
00728
00729 if( verbose != 0 )
00730 printf( "passed\n X.509 signature verify: ");
00731
00732 ret = x509_crt_verify( &clicert, &cacert, NULL, NULL, &flags, NULL, NULL );
00733 if( ret != 0 )
00734 {
00735 if( verbose != 0 )
00736 printf( "failed\n" );
00737
00738 printf("ret = %d, &flags = %04x\n", ret, flags);
00739
00740 return( ret );
00741 }
00742
00743 if( verbose != 0 )
00744 printf( "passed\n\n");
00745
00746 x509_crt_free( &cacert );
00747 x509_crt_free( &clicert );
00748
00749 return( 0 );
00750 #else
00751 ((void) verbose);
00752 return( POLARSSL_ERR_X509_FEATURE_UNAVAILABLE );
00753 #endif
00754 }
00755
00756 #endif
00757
00758 #endif