| Index: webrtc/base/opensslidentity.cc
|
| diff --git a/webrtc/base/opensslidentity.cc b/webrtc/base/opensslidentity.cc
|
| index ec9c00710be8be632ef8455db0d73073512ee927..58a0cd8adeb2b2f48b7851cc02493c7918108fca 100644
|
| --- a/webrtc/base/opensslidentity.cc
|
| +++ b/webrtc/base/opensslidentity.cc
|
| @@ -166,6 +166,29 @@ OpenSSLKeyPair* OpenSSLKeyPair::Generate(const KeyParams& key_params) {
|
| return new OpenSSLKeyPair(pkey);
|
| }
|
|
|
| +OpenSSLKeyPair* OpenSSLKeyPair::FromPrivateKeyPEMString(
|
| + const std::string& pem_string) {
|
| + BIO* bio = BIO_new_mem_buf(const_cast<char*>(pem_string.c_str()), -1);
|
| + if (!bio) {
|
| + LOG(LS_ERROR) << "Failed to create a new BIO buffer.";
|
| + return nullptr;
|
| + }
|
| + BIO_set_mem_eof_return(bio, 0);
|
| + EVP_PKEY* pkey =
|
| + PEM_read_bio_PrivateKey(bio, nullptr, nullptr, const_cast<char*>("\0"));
|
| + BIO_free(bio); // Frees the BIO, but not the pointed-to string.
|
| + if (!pkey) {
|
| + LOG(LS_ERROR) << "Failed to create the private key from PEM string.";
|
| + return nullptr;
|
| + }
|
| + if (EVP_PKEY_missing_parameters(pkey) != 0) {
|
| + LOG(LS_ERROR) << "The resulting key pair is missing public key parameters.";
|
| + EVP_PKEY_free(pkey);
|
| + return nullptr;
|
| + }
|
| + return new OpenSSLKeyPair(pkey);
|
| +}
|
| +
|
| OpenSSLKeyPair::~OpenSSLKeyPair() {
|
| EVP_PKEY_free(pkey_);
|
| }
|
| @@ -183,6 +206,57 @@ void OpenSSLKeyPair::AddReference() {
|
| #endif
|
| }
|
|
|
| +std::string OpenSSLKeyPair::PrivateKeyToPEMString() const {
|
| + BIO* temp_memory_bio = BIO_new(BIO_s_mem());
|
| + if (!temp_memory_bio) {
|
| + LOG_F(LS_ERROR) << "Failed to allocate temporary memory bio";
|
| + RTC_NOTREACHED();
|
| + return "";
|
| + }
|
| + if (!PEM_write_bio_PrivateKey(
|
| + temp_memory_bio, pkey_, nullptr, nullptr, 0, nullptr, nullptr)) {
|
| + LOG_F(LS_ERROR) << "Failed to write private key";
|
| + BIO_free(temp_memory_bio);
|
| + RTC_NOTREACHED();
|
| + return "";
|
| + }
|
| + BIO_write(temp_memory_bio, "\0", 1);
|
| + char* buffer;
|
| + BIO_get_mem_data(temp_memory_bio, &buffer);
|
| + std::string priv_key_str = buffer;
|
| + BIO_free(temp_memory_bio);
|
| + return priv_key_str;
|
| +}
|
| +
|
| +std::string OpenSSLKeyPair::PublicKeyToPEMString() const {
|
| + BIO* temp_memory_bio = BIO_new(BIO_s_mem());
|
| + if (!temp_memory_bio) {
|
| + LOG_F(LS_ERROR) << "Failed to allocate temporary memory bio";
|
| + RTC_NOTREACHED();
|
| + return "";
|
| + }
|
| + if (!PEM_write_bio_PUBKEY(temp_memory_bio, pkey_)) {
|
| + LOG_F(LS_ERROR) << "Failed to write public key";
|
| + BIO_free(temp_memory_bio);
|
| + RTC_NOTREACHED();
|
| + return "";
|
| + }
|
| + BIO_write(temp_memory_bio, "\0", 1);
|
| + char* buffer;
|
| + BIO_get_mem_data(temp_memory_bio, &buffer);
|
| + std::string pub_key_str = buffer;
|
| + BIO_free(temp_memory_bio);
|
| + return pub_key_str;
|
| +}
|
| +
|
| +bool OpenSSLKeyPair::operator==(const OpenSSLKeyPair& other) const {
|
| + return EVP_PKEY_cmp(this->pkey_, other.pkey_) == 1;
|
| +}
|
| +
|
| +bool OpenSSLKeyPair::operator!=(const OpenSSLKeyPair& other) const {
|
| + return !(*this == other);
|
| +}
|
| +
|
| #if !defined(NDEBUG)
|
| // Print a certificate to the log, for debugging.
|
| static void PrintCert(X509* x509) {
|
| @@ -370,6 +444,14 @@ void OpenSSLCertificate::AddReference() const {
|
| #endif
|
| }
|
|
|
| +bool OpenSSLCertificate::operator==(const OpenSSLCertificate& other) const {
|
| + return X509_cmp(this->x509_, other.x509_) == 0;
|
| +}
|
| +
|
| +bool OpenSSLCertificate::operator!=(const OpenSSLCertificate& other) const {
|
| + return !(*this == other);
|
| +}
|
| +
|
| // Documented in sslidentity.h.
|
| int64_t OpenSSLCertificate::CertificateExpirationTime() const {
|
| ASN1_TIME* expire_time = X509_get_notAfter(x509_);
|
| @@ -436,25 +518,17 @@ SSLIdentity* OpenSSLIdentity::FromPEMStrings(
|
| OpenSSLCertificate::FromPEMString(certificate));
|
| if (!cert) {
|
| LOG(LS_ERROR) << "Failed to create OpenSSLCertificate from PEM string.";
|
| - return NULL;
|
| - }
|
| -
|
| - BIO* bio = BIO_new_mem_buf(const_cast<char*>(private_key.c_str()), -1);
|
| - if (!bio) {
|
| - LOG(LS_ERROR) << "Failed to create a new BIO buffer.";
|
| - return NULL;
|
| + return nullptr;
|
| }
|
| - BIO_set_mem_eof_return(bio, 0);
|
| - EVP_PKEY* pkey =
|
| - PEM_read_bio_PrivateKey(bio, NULL, NULL, const_cast<char*>("\0"));
|
| - BIO_free(bio); // Frees the BIO, but not the pointed-to string.
|
|
|
| - if (!pkey) {
|
| - LOG(LS_ERROR) << "Failed to create the private key from PEM string.";
|
| - return NULL;
|
| + OpenSSLKeyPair* key_pair =
|
| + OpenSSLKeyPair::FromPrivateKeyPEMString(private_key);
|
| + if (!key_pair) {
|
| + LOG(LS_ERROR) << "Failed to create key pair from PEM string.";
|
| + return nullptr;
|
| }
|
|
|
| - return new OpenSSLIdentity(new OpenSSLKeyPair(pkey),
|
| + return new OpenSSLIdentity(key_pair,
|
| cert.release());
|
| }
|
|
|
| @@ -477,6 +551,23 @@ bool OpenSSLIdentity::ConfigureIdentity(SSL_CTX* ctx) {
|
| return true;
|
| }
|
|
|
| +std::string OpenSSLIdentity::PrivateKeyToPEMString() const {
|
| + return key_pair_->PrivateKeyToPEMString();
|
| +}
|
| +
|
| +std::string OpenSSLIdentity::PublicKeyToPEMString() const {
|
| + return key_pair_->PublicKeyToPEMString();
|
| +}
|
| +
|
| +bool OpenSSLIdentity::operator==(const OpenSSLIdentity& other) const {
|
| + return *this->key_pair_ == *other.key_pair_ &&
|
| + *this->certificate_ == *other.certificate_;
|
| +}
|
| +
|
| +bool OpenSSLIdentity::operator!=(const OpenSSLIdentity& other) const {
|
| + return !(*this == other);
|
| +}
|
| +
|
| } // namespace rtc
|
|
|
| #endif // HAVE_OPENSSL_SSL_H
|
|
|