00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024 #ifndef _CRT_SECURE_NO_DEPRECATE
00025 #define _CRT_SECURE_NO_DEPRECATE 1
00026 #endif
00027
00028 #include <string.h>
00029 #include <stdlib.h>
00030 #include <time.h>
00031
00032 #include "xyssl/ssl.h"
00033
00034 static int ssl_write_client_hello( ssl_context *ssl )
00035 {
00036 int i, n;
00037 time_t t;
00038 unsigned char *buf, *p;
00039
00040 md5_starts( &ssl->hs_md5 );
00041 sha1_starts( &ssl->hs_sha1 );
00042
00043 ssl->major_ver = SSLV3_MAJOR_VERSION;
00044 ssl->minor_ver = SSLV3_MINOR_VERSION;
00045
00046
00047
00048
00049
00050
00051
00052
00053 buf = ssl->out_msg;
00054 p = buf + 4;
00055
00056 *p++ = ssl->max_ver[0] = SSLV3_MAJOR_VERSION;
00057 *p++ = ssl->max_ver[1] = TLS10_MINOR_VERSION;
00058
00059 t = time( NULL );
00060 *p++ = (unsigned char)( t >> 24 );
00061 *p++ = (unsigned char)( t >> 16 );
00062 *p++ = (unsigned char)( t >> 8 );
00063 *p++ = (unsigned char)( t );
00064
00065 for( i = 28; i > 0; i-- )
00066 *p++ = ssl->rng_f( ssl->rng_d );
00067
00068 memcpy( ssl->randbytes, buf + 6, 32 );
00069
00070
00071
00072
00073
00074
00075
00076
00077 n = ( ssl->sidlen > 0 && ssl->sidlen <= 32 )
00078 ? ssl->sidlen : 0;
00079
00080 *p++ = n;
00081 for( i = 0; i < n; i++ )
00082 *p++ = ssl->sessid[i];
00083
00084 for( n = 0; ssl->cipherlist[n] != 0; n++ );
00085 *p++ = ( n >> 7 );
00086 *p++ = ( n << 1 );
00087
00088 for( i = 0; i < n; i++ )
00089 {
00090 *p++ = ( ssl->cipherlist[i] >> 8 );
00091 *p++ = ( ssl->cipherlist[i] );
00092 }
00093
00094 *p++ = 1;
00095 *p++ = SSL_COMPRESS_NULL;
00096
00097 ssl->out_msglen = p - buf;
00098 ssl->out_msgtype = SSL_MSG_HANDSHAKE;
00099 ssl->out_msg[0] = SSL_HS_CLIENT_HELLO;
00100
00101 ssl->state++;
00102 return( ssl_write_record( ssl, 0 ) );
00103 }
00104
00105 static int ssl_parse_server_hello( ssl_context *ssl )
00106 {
00107 int ret, i, n;
00108 unsigned char *buf;
00109
00110
00111
00112
00113
00114
00115
00116
00117 buf = ssl->in_msg;
00118
00119 if( ( ret = ssl_read_record( ssl, 0 ) ) != 0 )
00120 return( ret );
00121
00122 if( ssl->in_msgtype != SSL_MSG_HANDSHAKE )
00123 return( ERR_SSL_UNEXPECTED_MESSAGE );
00124
00125 if( ssl->in_hslen < 42 ||
00126 buf[0] != SSL_HS_SERVER_HELLO ||
00127 buf[4] != SSLV3_MAJOR_VERSION )
00128 return( ERR_SSL_BAD_HS_SERVER_HELLO );
00129
00130 if( buf[5] != SSLV3_MINOR_VERSION &&
00131 buf[5] != TLS10_MINOR_VERSION )
00132 return( ERR_SSL_BAD_HS_SERVER_HELLO );
00133
00134 ssl->minor_ver = buf[5];
00135
00136 memcpy( ssl->randbytes + 32, buf + 6, 32 );
00137
00138
00139
00140
00141
00142
00143
00144 n = buf[38];
00145 if( n < 0 || n > 32 || ssl->in_hslen != 42 + n )
00146 return( ERR_SSL_BAD_HS_SERVER_HELLO );
00147
00148 ssl->cipher = ( (int) buf[39 + n] << 8 )
00149 | ( (int) buf[40 + n] );
00150
00151 if( n > 0 && memcmp( ssl->sessid, buf + 39, n ) == 0 )
00152 {
00153
00154
00155
00156 ssl->state = SSL_SERVER_CHANGE_CIPHER_SPEC;
00157 ssl->resumed = 1;
00158 ssl_derive_keys( ssl );
00159 }
00160 else
00161 {
00162 ssl->state++;
00163 ssl->resumed = 0;
00164 ssl->sidlen = n;
00165 memcpy( ssl->sessid, buf + 39, n );
00166 }
00167
00168 i = 0;
00169 while( 1 )
00170 {
00171 if( ssl->cipherlist[i] == 0 )
00172 return( ERR_SSL_NO_CIPHER_CHOSEN );
00173
00174 if( ssl->cipherlist[i++] == ssl->cipher )
00175 break;
00176 }
00177
00178 if( buf[41 + n] != SSL_COMPRESS_NULL )
00179 return( ERR_SSL_BAD_HS_SERVER_HELLO );
00180
00181 return( 0 );
00182 }
00183
00184 static int ssl_parse_server_key_exchange( ssl_context *ssl )
00185 {
00186 int ret, n;
00187 unsigned char *p, *end;
00188 unsigned char hash[36];
00189 md5_context md5;
00190 sha1_context sha1;
00191
00192 if( ssl->cipher != SSL3_EDH_RSA_DES_168_SHA &&
00193 ssl->cipher != TLS1_EDH_RSA_AES_256_SHA )
00194 {
00195 ssl->state++;
00196 return( 0 );
00197 }
00198
00199 #if defined(NO_DHM)
00200 return( ERR_SSL_FEATURE_UNAVAILABLE );
00201 #else
00202 if( ( ret = ssl_read_record( ssl, 0 ) ) != 0 )
00203 return( ret );
00204
00205 if( ssl->in_msgtype != SSL_MSG_HANDSHAKE )
00206 return( ERR_SSL_UNEXPECTED_MESSAGE );
00207
00208 if( ssl->in_msg[0] != SSL_HS_SERVER_KEY_EXCHANGE )
00209 return( ERR_SSL_BAD_HS_SERVER_KEY_EXCHANGE );
00210
00211
00212
00213
00214
00215
00216
00217
00218
00219
00220 p = ssl->in_msg + 4;
00221 end = ssl->in_msg + ssl->in_hslen;
00222
00223 if( ( ret = dhm_read_params( &ssl->dhm_ctx, &p, end ) ) != 0 )
00224 return( ERR_SSL_BAD_HS_SERVER_KEY_EXCHANGE | ret );
00225
00226 if( (int)( end - p ) != ssl->peer_cert->rsa.len )
00227 return( ERR_SSL_BAD_HS_SERVER_KEY_EXCHANGE );
00228
00229 if( ssl->dhm_ctx.len < 64 || ssl->dhm_ctx.len > 256 )
00230 return( ERR_SSL_BAD_HS_SERVER_KEY_EXCHANGE );
00231
00232
00233
00234
00235
00236
00237
00238
00239
00240
00241
00242
00243
00244
00245 n = ssl->in_hslen - ( end - p ) - 6;
00246
00247 md5_starts( &md5 );
00248 md5_update( &md5, ssl->randbytes, 64 );
00249 md5_update( &md5, ssl->in_msg + 4, n );
00250 md5_finish( &md5, hash );
00251
00252 sha1_starts( &sha1 );
00253 sha1_update( &sha1, ssl->randbytes, 64 );
00254 sha1_update( &sha1, ssl->in_msg + 4, n );
00255 sha1_finish( &sha1, hash + 16 );
00256
00257 n = ssl->peer_cert->rsa.len;
00258 if( ( ret = rsa_pkcs1_verify( &ssl->peer_cert->rsa,
00259 RSA_RAW, hash, 36, p, n ) ) != 0 )
00260 return( ret );
00261
00262 ssl->state++;
00263 return( 0 );
00264 #endif
00265 }
00266
00267 static int ssl_parse_certificate_request( ssl_context *ssl )
00268 {
00269 int ret;
00270
00271
00272
00273
00274
00275
00276
00277
00278
00279
00280
00281
00282 if( ( ret = ssl_read_record( ssl, 0 ) ) != 0 )
00283 return( ret );
00284
00285 if( ssl->in_msgtype != SSL_MSG_HANDSHAKE )
00286 return( ERR_SSL_UNEXPECTED_MESSAGE );
00287
00288 ssl->state++;
00289 ssl->client_auth = 0;
00290
00291 if( ssl->in_msg[0] == SSL_HS_CERTIFICATE_REQUEST )
00292 {
00293 ssl->client_auth++;
00294
00295
00296
00297
00298 #if 0
00299 if( ssl->own_cert == NULL )
00300 return( ERR_SSL_CERTIFICATE_REQUIRED );
00301
00302 if( ssl->own_key == NULL )
00303 return( ERR_SSL_PRIVATE_KEY_REQUIRED );
00304 #endif
00305 }
00306
00307 return( 0 );
00308 }
00309
00310 static int ssl_parse_server_hello_done( ssl_context *ssl )
00311 {
00312 int ret;
00313
00314 if( ssl->client_auth != 0 )
00315 {
00316 if( ( ret = ssl_read_record( ssl, 0 ) ) != 0 )
00317 return( ret );
00318
00319 if( ssl->in_msgtype != SSL_MSG_HANDSHAKE )
00320 return( ERR_SSL_UNEXPECTED_MESSAGE );
00321 }
00322
00323 if( ssl->in_hslen != 4 ||
00324 ssl->in_msg[0] != SSL_HS_SERVER_HELLO_DONE )
00325 return( ERR_SSL_BAD_HS_SERVER_HELLO_DONE );
00326
00327 ssl->state++;
00328 return( 0 );
00329 }
00330
00331 static int ssl_write_client_key_exchange( ssl_context *ssl )
00332 {
00333 int ret, i, n;
00334
00335 if( ssl->cipher == SSL3_EDH_RSA_DES_168_SHA ||
00336 ssl->cipher == TLS1_EDH_RSA_AES_256_SHA )
00337 {
00338 #if defined(NO_DHM)
00339 return( ERR_SSL_FEATURE_UNAVAILABLE );
00340 #else
00341
00342
00343
00344 n = ssl->dhm_ctx.len;
00345
00346 ssl->out_msg[4] = ( n >> 8 );
00347 ssl->out_msg[5] = ( n );
00348 i = 6;
00349
00350 if( ( ret = dhm_make_public( &ssl->dhm_ctx,
00351 &ssl->out_msg[i], n,
00352 ssl->rng_f,
00353 ssl->rng_d ) ) != 0 )
00354 return( ret );
00355
00356 ssl->pmslen = ssl->dhm_ctx.len;
00357
00358 if( ( ret = dhm_calc_secret( &ssl->dhm_ctx,
00359 ssl->premaster,
00360 &ssl->pmslen ) ) != 0 )
00361 return( ret );
00362 #endif
00363 }
00364 else
00365 {
00366
00367
00368
00369 memcpy( ssl->premaster, ssl->max_ver, 2 );
00370
00371 ssl->pmslen = 48;
00372
00373 for( i = 2; i < ssl->pmslen; i++ )
00374 ssl->premaster[i] = ssl->rng_f( ssl->rng_d );
00375
00376 i = 4;
00377 n = ssl->peer_cert->rsa.len;
00378
00379 if( ssl->minor_ver != SSLV3_MINOR_VERSION )
00380 {
00381 i += 2;
00382 ssl->out_msg[4] = ( n >> 8 );
00383 ssl->out_msg[5] = ( n );
00384 }
00385
00386 ret = rsa_pkcs1_encrypt( &ssl->peer_cert->rsa,
00387 ssl->premaster,
00388 ssl->pmslen,
00389 ssl->out_msg + i, n );
00390 if( ret != 0 )
00391 return( ret );
00392 }
00393
00394 ssl_derive_keys( ssl );
00395
00396 ssl->out_msglen = i + n;
00397 ssl->out_msgtype = SSL_MSG_HANDSHAKE;
00398 ssl->out_msg[0] = SSL_HS_CLIENT_KEY_EXCHANGE;
00399
00400 ssl->state++;
00401 return( ssl_write_record( ssl, 0 ) );
00402 }
00403
00404 static int ssl_write_certificate_verify( ssl_context *ssl )
00405 {
00406 int ret, n;
00407 unsigned char hash[36];
00408
00409 if( ssl->client_auth == 0 || ssl->own_key == NULL )
00410 {
00411 ssl->state++;
00412 return( 0 );
00413 }
00414
00415
00416
00417
00418 ssl_calc_verify( ssl, hash );
00419
00420 n = ssl->own_key->len;
00421 ssl->out_msg[4] = ( n >> 8 );
00422 ssl->out_msg[5] = ( n );
00423
00424 if( ( ret = rsa_pkcs1_sign( ssl->own_key, RSA_RAW, hash, 36,
00425 ssl->out_msg + 6, n ) ) != 0 )
00426 return( ret );
00427
00428 ssl->out_msglen = 6 + n;
00429 ssl->out_msgtype = SSL_MSG_HANDSHAKE;
00430 ssl->out_msg[0] = SSL_HS_CERTIFICATE_VERIFY;
00431
00432 ssl->state++;
00433 return( ssl_write_record( ssl, 0 ) );
00434 }
00435
00436 static const char _ssl_cli_src[] = "_ssl_cli_src";
00437
00438
00439
00440
00441 int ssl_client_start( ssl_context *ssl )
00442 {
00443 int ret = ssl_flush_output( ssl );
00444
00445 while( ret == 0 )
00446 {
00447 switch( ssl->state )
00448 {
00449 case SSL_HELLO_REQUEST:
00450 ssl->state = SSL_CLIENT_HELLO;
00451 break;
00452
00453
00454
00455
00456 case SSL_CLIENT_HELLO:
00457 ret = ssl_write_client_hello( ssl );
00458 break;
00459
00460
00461
00462
00463
00464
00465
00466
00467 case SSL_SERVER_HELLO:
00468 ret = ssl_parse_server_hello( ssl );
00469 break;
00470
00471 case SSL_SERVER_CERTIFICATE:
00472 ret = ssl_parse_certificate( ssl );
00473 break;
00474
00475 case SSL_SERVER_KEY_EXCHANGE:
00476 ret = ssl_parse_server_key_exchange( ssl );
00477 break;
00478
00479 case SSL_CERTIFICATE_REQUEST:
00480 ret = ssl_parse_certificate_request( ssl );
00481 break;
00482
00483 case SSL_SERVER_HELLO_DONE:
00484 ret = ssl_parse_server_hello_done( ssl );
00485 break;
00486
00487
00488
00489
00490
00491
00492
00493
00494 case SSL_CLIENT_CERTIFICATE:
00495 ret = ssl_write_certificate( ssl );
00496 break;
00497
00498 case SSL_CLIENT_KEY_EXCHANGE:
00499 ret = ssl_write_client_key_exchange( ssl );
00500 break;
00501
00502 case SSL_CERTIFICATE_VERIFY:
00503 ret = ssl_write_certificate_verify( ssl );
00504 break;
00505
00506 case SSL_CLIENT_CHANGE_CIPHER_SPEC:
00507 ret = ssl_write_change_cipher_spec( ssl );
00508 break;
00509
00510 case SSL_CLIENT_FINISHED:
00511 ret = ssl_write_finished( ssl );
00512 break;
00513
00514
00515
00516
00517
00518 case SSL_SERVER_CHANGE_CIPHER_SPEC:
00519 ret = ssl_parse_change_cipher_spec( ssl );
00520 break;
00521
00522 case SSL_SERVER_FINISHED:
00523 ret = ssl_parse_finished( ssl );
00524 break;
00525
00526 default:
00527 return( 0 );
00528 }
00529 }
00530
00531 return( ret );
00532 }