| OLD | NEW |
| 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file |
| 2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
| 3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
| 4 | 4 |
| 5 #include "bin/secure_socket.h" | 5 #include "bin/secure_socket.h" |
| 6 | 6 |
| 7 #include <errno.h> | 7 #include <errno.h> |
| 8 #include <fcntl.h> | 8 #include <fcntl.h> |
| 9 #include <sys/stat.h> | 9 #include <sys/stat.h> |
| 10 #include <stdio.h> | 10 #include <stdio.h> |
| 11 #include <string.h> | 11 #include <string.h> |
| 12 | 12 |
| 13 #include <key.h> |
| 14 #include <keyt.h> |
| 13 #include <nss.h> | 15 #include <nss.h> |
| 14 #include <pk11pub.h> | 16 #include <pk11pub.h> |
| 15 #include <prerror.h> | 17 #include <prerror.h> |
| 16 #include <prinit.h> | 18 #include <prinit.h> |
| 17 #include <prnetdb.h> | 19 #include <prnetdb.h> |
| 18 #include <ssl.h> | 20 #include <ssl.h> |
| 19 #include <sslproto.h> | 21 #include <sslproto.h> |
| 20 | 22 |
| 21 #include "bin/builtin.h" | 23 #include "bin/builtin.h" |
| 22 #include "bin/dartutils.h" | 24 #include "bin/dartutils.h" |
| (...skipping 274 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 297 } | 299 } |
| 298 } | 300 } |
| 299 | 301 |
| 300 | 302 |
| 301 void SSLFilter::RegisterHandshakeCompleteCallback(Dart_Handle complete) { | 303 void SSLFilter::RegisterHandshakeCompleteCallback(Dart_Handle complete) { |
| 302 ASSERT(NULL == handshake_complete_); | 304 ASSERT(NULL == handshake_complete_); |
| 303 handshake_complete_ = ThrowIfError(Dart_NewPersistentHandle(complete)); | 305 handshake_complete_ = ThrowIfError(Dart_NewPersistentHandle(complete)); |
| 304 } | 306 } |
| 305 | 307 |
| 306 | 308 |
| 307 void SSLFilter::RegisterBadCertificateCallback(Dart_Handle complete) { | 309 void SSLFilter::RegisterBadCertificateCallback(Dart_Handle callback) { |
| 308 if (NULL != bad_certificate_callback_) { | 310 if (NULL != bad_certificate_callback_) { |
| 309 Dart_DeletePersistentHandle(bad_certificate_callback_); | 311 Dart_DeletePersistentHandle(bad_certificate_callback_); |
| 310 } | 312 } |
| 311 bad_certificate_callback_ = ThrowIfError(Dart_NewPersistentHandle(complete)); | 313 bad_certificate_callback_ = ThrowIfError(Dart_NewPersistentHandle(callback)); |
| 312 } | 314 } |
| 313 | 315 |
| 314 | 316 |
| 315 void SSLFilter::InitializeLibrary(const char* certificate_database, | 317 void SSLFilter::InitializeLibrary(const char* certificate_database, |
| 316 const char* password, | 318 const char* password, |
| 317 bool use_builtin_root_certificates) { | 319 bool use_builtin_root_certificates) { |
| 318 MutexLocker locker(&mutex_); | 320 MutexLocker locker(&mutex_); |
| 319 if (!library_initialized_) { | 321 if (!library_initialized_) { |
| 320 library_initialized_ = true; | 322 library_initialized_ = true; |
| 321 password_ = strdup(password); // This one copy persists until Dart exits. | 323 password_ = strdup(password); // This one copy persists until Dart exits. |
| (...skipping 63 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 385 if (status != SECSuccess) { | 387 if (status != SECSuccess) { |
| 386 ThrowPRException("Cannot get validity times from certificate"); | 388 ThrowPRException("Cannot get validity times from certificate"); |
| 387 } | 389 } |
| 388 int64_t start_epoch_ms = start_validity / PR_USEC_PER_MSEC; | 390 int64_t start_epoch_ms = start_validity / PR_USEC_PER_MSEC; |
| 389 int64_t end_epoch_ms = end_validity / PR_USEC_PER_MSEC; | 391 int64_t end_epoch_ms = end_validity / PR_USEC_PER_MSEC; |
| 390 bool accept = CallBadCertificateCallback(bad_certificate_callback_, | 392 bool accept = CallBadCertificateCallback(bad_certificate_callback_, |
| 391 certificate->subjectName, | 393 certificate->subjectName, |
| 392 certificate->issuerName, | 394 certificate->issuerName, |
| 393 start_epoch_ms, | 395 start_epoch_ms, |
| 394 end_epoch_ms); | 396 end_epoch_ms); |
| 397 CERT_DestroyCertificate(certificate); |
| 395 return accept ? SECSuccess : SECFailure; | 398 return accept ? SECSuccess : SECFailure; |
| 396 } | 399 } |
| 397 | 400 |
| 398 | 401 |
| 399 void SSLFilter::Connect(const char* host_name, | 402 void SSLFilter::Connect(const char* host_name, |
| 400 int port, | 403 int port, |
| 401 bool is_server, | 404 bool is_server, |
| 402 const char* certificate_name) { | 405 const char* certificate_name) { |
| 403 is_server_ = is_server; | 406 is_server_ = is_server; |
| 404 if (in_handshake_) { | 407 if (in_handshake_) { |
| (...skipping 15 matching lines...) Expand all Loading... |
| 420 CERTCertificate* certificate = CERT_FindCertByNameString( | 423 CERTCertificate* certificate = CERT_FindCertByNameString( |
| 421 certificate_database, | 424 certificate_database, |
| 422 const_cast<char*>(certificate_name)); | 425 const_cast<char*>(certificate_name)); |
| 423 if (certificate == NULL) { | 426 if (certificate == NULL) { |
| 424 ThrowPRException("Cannot find server certificate by name"); | 427 ThrowPRException("Cannot find server certificate by name"); |
| 425 } | 428 } |
| 426 SECKEYPrivateKey* key = PK11_FindKeyByAnyCert( | 429 SECKEYPrivateKey* key = PK11_FindKeyByAnyCert( |
| 427 certificate, | 430 certificate, |
| 428 static_cast<void*>(const_cast<char*>(password_))); | 431 static_cast<void*>(const_cast<char*>(password_))); |
| 429 if (key == NULL) { | 432 if (key == NULL) { |
| 433 CERT_DestroyCertificate(certificate); |
| 430 if (PR_GetError() == -8177) { | 434 if (PR_GetError() == -8177) { |
| 431 ThrowPRException("Certificate database password incorrect"); | 435 ThrowPRException("Certificate database password incorrect"); |
| 432 } else { | 436 } else { |
| 433 ThrowPRException("Unsuccessful PK11_FindKeyByAnyCert call." | 437 ThrowPRException("Unsuccessful PK11_FindKeyByAnyCert call." |
| 434 " Cannot find private key for certificate"); | 438 " Cannot find private key for certificate"); |
| 435 } | 439 } |
| 436 } | 440 } |
| 437 // kt_rsa (key type RSA) is an enum constant from the NSS libraries. | 441 // kt_rsa (key type RSA) is an enum constant from the NSS libraries. |
| 438 // TODO(whesse): Allow different key types. | 442 // TODO(whesse): Allow different key types. |
| 439 status = SSL_ConfigSecureServer(filter_, certificate, key, kt_rsa); | 443 status = SSL_ConfigSecureServer(filter_, certificate, key, kt_rsa); |
| 444 CERT_DestroyCertificate(certificate); |
| 445 SECKEY_DestroyPrivateKey(key); |
| 440 if (status != SECSuccess) { | 446 if (status != SECSuccess) { |
| 441 ThrowPRException("Unsuccessful SSL_ConfigSecureServer call"); | 447 ThrowPRException("Unsuccessful SSL_ConfigSecureServer call"); |
| 442 } | 448 } |
| 443 } else { // Client. | 449 } else { // Client. |
| 444 if (SSL_SetURL(filter_, host_name) == -1) { | 450 if (SSL_SetURL(filter_, host_name) == -1) { |
| 445 ThrowPRException("Unsuccessful SetURL call"); | 451 ThrowPRException("Unsuccessful SetURL call"); |
| 446 } | 452 } |
| 447 } | 453 } |
| 448 | 454 |
| 449 // Install bad certificate callback, and pass 'this' to it if it is called. | 455 // Install bad certificate callback, and pass 'this' to it if it is called. |
| (...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 503 for (int i = 0; i < kNumBuffers; ++i) { | 509 for (int i = 0; i < kNumBuffers; ++i) { |
| 504 Dart_DeletePersistentHandle(dart_buffer_objects_[i]); | 510 Dart_DeletePersistentHandle(dart_buffer_objects_[i]); |
| 505 delete[] buffers_[i]; | 511 delete[] buffers_[i]; |
| 506 } | 512 } |
| 507 Dart_DeletePersistentHandle(string_start_); | 513 Dart_DeletePersistentHandle(string_start_); |
| 508 Dart_DeletePersistentHandle(string_length_); | 514 Dart_DeletePersistentHandle(string_length_); |
| 509 Dart_DeletePersistentHandle(handshake_complete_); | 515 Dart_DeletePersistentHandle(handshake_complete_); |
| 510 if (bad_certificate_callback_ != NULL) { | 516 if (bad_certificate_callback_ != NULL) { |
| 511 Dart_DeletePersistentHandle(bad_certificate_callback_); | 517 Dart_DeletePersistentHandle(bad_certificate_callback_); |
| 512 } | 518 } |
| 513 // TODO(whesse): Free NSS objects here. | 519 |
| 520 PR_Close(filter_); |
| 514 } | 521 } |
| 515 | 522 |
| 516 | 523 |
| 517 intptr_t SSLFilter::ProcessBuffer(int buffer_index) { | 524 intptr_t SSLFilter::ProcessBuffer(int buffer_index) { |
| 518 Dart_Handle buffer_object = dart_buffer_objects_[buffer_index]; | 525 Dart_Handle buffer_object = dart_buffer_objects_[buffer_index]; |
| 519 Dart_Handle start_object = ThrowIfError( | 526 Dart_Handle start_object = ThrowIfError( |
| 520 Dart_GetField(buffer_object, string_start_)); | 527 Dart_GetField(buffer_object, string_start_)); |
| 521 Dart_Handle length_object = ThrowIfError( | 528 Dart_Handle length_object = ThrowIfError( |
| 522 Dart_GetField(buffer_object, string_length_)); | 529 Dart_GetField(buffer_object, string_length_)); |
| 523 int64_t unsafe_start = DartUtils::GetIntegerValue(start_object); | 530 int64_t unsafe_start = DartUtils::GetIntegerValue(start_object); |
| (...skipping 81 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 605 if (PR_WOULD_BLOCK_ERROR != pr_error) { | 612 if (PR_WOULD_BLOCK_ERROR != pr_error) { |
| 606 ThrowPRException("Error reading plaintext from SSLFilter"); | 613 ThrowPRException("Error reading plaintext from SSLFilter"); |
| 607 } | 614 } |
| 608 bytes_processed = 0; | 615 bytes_processed = 0; |
| 609 } | 616 } |
| 610 break; | 617 break; |
| 611 } | 618 } |
| 612 } | 619 } |
| 613 return bytes_processed; | 620 return bytes_processed; |
| 614 } | 621 } |
| OLD | NEW |