Hannes Tschofenig
/
aes-gcm-test-program
Example program to test AES-GCM functionality. Used for a workshop
Embed:
(wiki syntax)
Show/hide line numbers
x509_csr.c
00001 /* 00002 * X.509 Certificate Signing Request (CSR) parsing 00003 * 00004 * Copyright (C) 2006-2014, Brainspark B.V. 00005 * 00006 * This file is part of PolarSSL (http://www.polarssl.org) 00007 * Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org> 00008 * 00009 * All rights reserved. 00010 * 00011 * This program is free software; you can redistribute it and/or modify 00012 * it under the terms of the GNU General Public License as published by 00013 * the Free Software Foundation; either version 2 of the License, or 00014 * (at your option) any later version. 00015 * 00016 * This program is distributed in the hope that it will be useful, 00017 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00018 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00019 * GNU General Public License for more details. 00020 * 00021 * You should have received a copy of the GNU General Public License along 00022 * with this program; if not, write to the Free Software Foundation, Inc., 00023 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. 00024 */ 00025 /* 00026 * The ITU-T X.509 standard defines a certificate format for PKI. 00027 * 00028 * http://www.ietf.org/rfc/rfc3279.txt 00029 * http://www.ietf.org/rfc/rfc3280.txt 00030 * 00031 * ftp://ftp.rsasecurity.com/pub/pkcs/ascii/pkcs-1v2.asc 00032 * 00033 * http://www.itu.int/ITU-T/studygroups/com17/languages/X.680-0207.pdf 00034 * http://www.itu.int/ITU-T/studygroups/com17/languages/X.690-0207.pdf 00035 */ 00036 00037 #if !defined(POLARSSL_CONFIG_FILE) 00038 #include "polarssl/config.h" 00039 #else 00040 #include POLARSSL_CONFIG_FILE 00041 #endif 00042 00043 #if defined(POLARSSL_X509_CSR_PARSE_C) 00044 00045 #include "polarssl/x509_csr.h" 00046 #include "polarssl/oid.h" 00047 #if defined(POLARSSL_PEM_PARSE_C) 00048 #include "polarssl/pem.h" 00049 #endif 00050 00051 #if defined(POLARSSL_PLATFORM_C) 00052 #include "polarssl/platform.h" 00053 #else 00054 #define polarssl_malloc malloc 00055 #define polarssl_free free 00056 #endif 00057 00058 #include <string.h> 00059 #include <stdlib.h> 00060 00061 #if defined(POLARSSL_FS_IO) || defined(EFIX64) || defined(EFI32) 00062 #include <stdio.h> 00063 #endif 00064 00065 /* 00066 * Version ::= INTEGER { v1(0) } 00067 */ 00068 static int x509_csr_get_version( unsigned char **p, 00069 const unsigned char *end, 00070 int *ver ) 00071 { 00072 int ret; 00073 00074 if( ( ret = asn1_get_int( p, end, ver ) ) != 0 ) 00075 { 00076 if( ret == POLARSSL_ERR_ASN1_UNEXPECTED_TAG ) 00077 { 00078 *ver = 0; 00079 return( 0 ); 00080 } 00081 00082 return( POLARSSL_ERR_X509_INVALID_VERSION + ret ); 00083 } 00084 00085 return( 0 ); 00086 } 00087 00088 /* 00089 * Parse a CSR 00090 */ 00091 int x509_csr_parse( x509_csr *csr, const unsigned char *buf, size_t buflen ) 00092 { 00093 int ret; 00094 size_t len; 00095 unsigned char *p, *end; 00096 #if defined(POLARSSL_PEM_PARSE_C) 00097 size_t use_len; 00098 pem_context pem; 00099 #endif 00100 00101 /* 00102 * Check for valid input 00103 */ 00104 if( csr == NULL || buf == NULL ) 00105 return( POLARSSL_ERR_X509_BAD_INPUT_DATA ); 00106 00107 x509_csr_init( csr ); 00108 00109 #if defined(POLARSSL_PEM_PARSE_C) 00110 pem_init( &pem ); 00111 ret = pem_read_buffer( &pem, 00112 "-----BEGIN CERTIFICATE REQUEST-----", 00113 "-----END CERTIFICATE REQUEST-----", 00114 buf, NULL, 0, &use_len ); 00115 00116 if( ret == 0 ) 00117 { 00118 /* 00119 * Was PEM encoded, steal PEM buffer 00120 */ 00121 p = pem.buf ; 00122 pem.buf = NULL; 00123 len = pem.buflen ; 00124 pem_free( &pem ); 00125 } 00126 else if( ret != POLARSSL_ERR_PEM_NO_HEADER_FOOTER_PRESENT ) 00127 { 00128 pem_free( &pem ); 00129 return( ret ); 00130 } 00131 else 00132 #endif /* POLARSSL_PEM_PARSE_C */ 00133 { 00134 /* 00135 * nope, copy the raw DER data 00136 */ 00137 p = (unsigned char *) polarssl_malloc( len = buflen ); 00138 00139 if( p == NULL ) 00140 return( POLARSSL_ERR_X509_MALLOC_FAILED ); 00141 00142 memcpy( p, buf, buflen ); 00143 } 00144 00145 csr->raw.p = p; 00146 csr->raw.len = len; 00147 end = p + len; 00148 00149 /* 00150 * CertificationRequest ::= SEQUENCE { 00151 * certificationRequestInfo CertificationRequestInfo, 00152 * signatureAlgorithm AlgorithmIdentifier, 00153 * signature BIT STRING 00154 * } 00155 */ 00156 if( ( ret = asn1_get_tag( &p, end, &len, 00157 ASN1_CONSTRUCTED | ASN1_SEQUENCE ) ) != 0 ) 00158 { 00159 x509_csr_free( csr ); 00160 return( POLARSSL_ERR_X509_INVALID_FORMAT ); 00161 } 00162 00163 if( len != (size_t) ( end - p ) ) 00164 { 00165 x509_csr_free( csr ); 00166 return( POLARSSL_ERR_X509_INVALID_FORMAT + 00167 POLARSSL_ERR_ASN1_LENGTH_MISMATCH ); 00168 } 00169 00170 /* 00171 * CertificationRequestInfo ::= SEQUENCE { 00172 */ 00173 csr->cri.p = p; 00174 00175 if( ( ret = asn1_get_tag( &p, end, &len, 00176 ASN1_CONSTRUCTED | ASN1_SEQUENCE ) ) != 0 ) 00177 { 00178 x509_csr_free( csr ); 00179 return( POLARSSL_ERR_X509_INVALID_FORMAT + ret ); 00180 } 00181 00182 end = p + len; 00183 csr->cri.len = end - csr->cri.p; 00184 00185 /* 00186 * Version ::= INTEGER { v1(0) } 00187 */ 00188 if( ( ret = x509_csr_get_version( &p, end, &csr->version ) ) != 0 ) 00189 { 00190 x509_csr_free( csr ); 00191 return( ret ); 00192 } 00193 00194 csr->version++; 00195 00196 if( csr->version != 1 ) 00197 { 00198 x509_csr_free( csr ); 00199 return( POLARSSL_ERR_X509_UNKNOWN_VERSION ); 00200 } 00201 00202 /* 00203 * subject Name 00204 */ 00205 csr->subject_raw.p = p; 00206 00207 if( ( ret = asn1_get_tag( &p, end, &len, 00208 ASN1_CONSTRUCTED | ASN1_SEQUENCE ) ) != 0 ) 00209 { 00210 x509_csr_free( csr ); 00211 return( POLARSSL_ERR_X509_INVALID_FORMAT + ret ); 00212 } 00213 00214 if( ( ret = x509_get_name( &p, p + len, &csr->subject ) ) != 0 ) 00215 { 00216 x509_csr_free( csr ); 00217 return( ret ); 00218 } 00219 00220 csr->subject_raw.len = p - csr->subject_raw.p; 00221 00222 /* 00223 * subjectPKInfo SubjectPublicKeyInfo 00224 */ 00225 if( ( ret = pk_parse_subpubkey( &p, end, &csr->pk ) ) != 0 ) 00226 { 00227 x509_csr_free( csr ); 00228 return( ret ); 00229 } 00230 00231 /* 00232 * attributes [0] Attributes 00233 */ 00234 if( ( ret = asn1_get_tag( &p, end, &len, 00235 ASN1_CONSTRUCTED | ASN1_CONTEXT_SPECIFIC ) ) != 0 ) 00236 { 00237 x509_csr_free( csr ); 00238 return( POLARSSL_ERR_X509_INVALID_FORMAT + ret ); 00239 } 00240 // TODO Parse Attributes / extension requests 00241 00242 p += len; 00243 00244 end = csr->raw.p + csr->raw.len; 00245 00246 /* 00247 * signatureAlgorithm AlgorithmIdentifier, 00248 * signature BIT STRING 00249 */ 00250 if( ( ret = x509_get_alg_null( &p, end, &csr->sig_oid ) ) != 0 ) 00251 { 00252 x509_csr_free( csr ); 00253 return( ret ); 00254 } 00255 00256 if( ( ret = x509_get_sig_alg( &csr->sig_oid, &csr->sig_md, 00257 &csr->sig_pk ) ) != 0 ) 00258 { 00259 x509_csr_free( csr ); 00260 return( POLARSSL_ERR_X509_UNKNOWN_SIG_ALG ); 00261 } 00262 00263 if( ( ret = x509_get_sig( &p, end, &csr->sig ) ) != 0 ) 00264 { 00265 x509_csr_free( csr ); 00266 return( ret ); 00267 } 00268 00269 if( p != end ) 00270 { 00271 x509_csr_free( csr ); 00272 return( POLARSSL_ERR_X509_INVALID_FORMAT + 00273 POLARSSL_ERR_ASN1_LENGTH_MISMATCH ); 00274 } 00275 00276 return( 0 ); 00277 } 00278 00279 #if defined(POLARSSL_FS_IO) 00280 /* 00281 * Load a CSR into the structure 00282 */ 00283 int x509_csr_parse_file( x509_csr *csr, const char *path ) 00284 { 00285 int ret; 00286 size_t n; 00287 unsigned char *buf; 00288 00289 if ( ( ret = x509_load_file( path, &buf, &n ) ) != 0 ) 00290 return( ret ); 00291 00292 ret = x509_csr_parse( csr, buf, n ); 00293 00294 memset( buf, 0, n + 1 ); 00295 polarssl_free( buf ); 00296 00297 return( ret ); 00298 } 00299 #endif /* POLARSSL_FS_IO */ 00300 00301 #if defined(_MSC_VER) && !defined snprintf && !defined(EFIX64) && \ 00302 !defined(EFI32) 00303 #include <stdarg.h> 00304 00305 #if !defined vsnprintf 00306 #define vsnprintf _vsnprintf 00307 #endif // vsnprintf 00308 00309 /* 00310 * Windows _snprintf and _vsnprintf are not compatible to linux versions. 00311 * Result value is not size of buffer needed, but -1 if no fit is possible. 00312 * 00313 * This fuction tries to 'fix' this by at least suggesting enlarging the 00314 * size by 20. 00315 */ 00316 static int compat_snprintf(char *str, size_t size, const char *format, ...) 00317 { 00318 va_list ap; 00319 int res = -1; 00320 00321 va_start( ap, format ); 00322 00323 res = vsnprintf( str, size, format, ap ); 00324 00325 va_end( ap ); 00326 00327 // No quick fix possible 00328 if ( res < 0 ) 00329 return( (int) size + 20 ); 00330 00331 return res; 00332 } 00333 00334 #define snprintf compat_snprintf 00335 #endif /* _MSC_VER && !snprintf && !EFIX64 && !EFI32 */ 00336 00337 #define POLARSSL_ERR_DEBUG_BUF_TOO_SMALL -2 00338 00339 #define SAFE_SNPRINTF() \ 00340 { \ 00341 if( ret == -1 ) \ 00342 return( -1 ); \ 00343 \ 00344 if ( (unsigned int) ret > n ) { \ 00345 p[n - 1] = '\0'; \ 00346 return POLARSSL_ERR_DEBUG_BUF_TOO_SMALL;\ 00347 } \ 00348 \ 00349 n -= (unsigned int) ret; \ 00350 p += (unsigned int) ret; \ 00351 } 00352 00353 #define BEFORE_COLON 14 00354 #define BC "14" 00355 /* 00356 * Return an informational string about the CSR. 00357 */ 00358 int x509_csr_info( char *buf, size_t size, const char *prefix, 00359 const x509_csr *csr ) 00360 { 00361 int ret; 00362 size_t n; 00363 char *p; 00364 const char *desc; 00365 char key_size_str[BEFORE_COLON]; 00366 00367 p = buf; 00368 n = size; 00369 00370 ret = snprintf( p, n, "%sCSR version : %d", 00371 prefix, csr->version ); 00372 SAFE_SNPRINTF(); 00373 00374 ret = snprintf( p, n, "\n%ssubject name : ", prefix ); 00375 SAFE_SNPRINTF(); 00376 ret = x509_dn_gets( p, n, &csr->subject ); 00377 SAFE_SNPRINTF(); 00378 00379 ret = snprintf( p, n, "\n%ssigned using : ", prefix ); 00380 SAFE_SNPRINTF(); 00381 00382 ret = oid_get_sig_alg_desc( &csr->sig_oid, &desc ); 00383 if( ret != 0 ) 00384 ret = snprintf( p, n, "???" ); 00385 else 00386 ret = snprintf( p, n, "%s", desc ); 00387 SAFE_SNPRINTF(); 00388 00389 if( ( ret = x509_key_size_helper( key_size_str, BEFORE_COLON, 00390 pk_get_name( &csr->pk ) ) ) != 0 ) 00391 { 00392 return( ret ); 00393 } 00394 00395 ret = snprintf( p, n, "\n%s%-" BC "s: %d bits\n", prefix, key_size_str, 00396 (int) pk_get_size( &csr->pk ) ); 00397 SAFE_SNPRINTF(); 00398 00399 return( (int) ( size - n ) ); 00400 } 00401 00402 /* 00403 * Initialize a CSR 00404 */ 00405 void x509_csr_init( x509_csr *csr ) 00406 { 00407 memset( csr, 0, sizeof(x509_csr) ); 00408 } 00409 00410 /* 00411 * Unallocate all CSR data 00412 */ 00413 void x509_csr_free( x509_csr *csr ) 00414 { 00415 x509_name *name_cur; 00416 x509_name *name_prv; 00417 00418 if( csr == NULL ) 00419 return; 00420 00421 pk_free( &csr->pk ); 00422 00423 name_cur = csr->subject.next; 00424 while( name_cur != NULL ) 00425 { 00426 name_prv = name_cur; 00427 name_cur = name_cur->next; 00428 memset( name_prv, 0, sizeof( x509_name ) ); 00429 polarssl_free( name_prv ); 00430 } 00431 00432 if( csr->raw.p != NULL ) 00433 { 00434 memset( csr->raw.p, 0, csr->raw.len ); 00435 polarssl_free( csr->raw.p ); 00436 } 00437 00438 memset( csr, 0, sizeof( x509_csr ) ); 00439 } 00440 00441 #endif /* POLARSSL_X509_CSR_PARSE_C */ 00442 00443
Generated on Tue Jul 12 2022 19:40:21 by 1.7.2