* @param key2 second key to compare
* @return true iff the keys match
*/
- static bool matches(const XSECCryptoKey* key1, const XSECCryptoKey* key2);
+ static bool matches(const XSECCryptoKey& key1, const XSECCryptoKey& key2);
/**
* Returns the base64-encoded DER encoding of a public key in SubjectPublicKeyInfo format.
*
- * @param key the credential containing the key to encode
- * @return the base64 encoded key value in a malloc'd string
+ * @param key the credential containing the key to encode
+ * @param nowrap if true, any linefeeds will be stripped from the result
+ * @return the base64 encoded key value
*/
- static char* getDEREncoding(const Credential& cred);
+ static std::string getDEREncoding(const Credential& cred, bool nowrap=true);
/**
* Returns the base64-encoded DER encoding of a public key in SubjectPublicKeyInfo format.
*
* @param key the key to encode
- * @return the base64 encoded key value in a malloc'd string
+ * @param nowrap if true, any linefeeds will be stripped from the result
+ * @return the base64 encoded key value
*/
- static char* getDEREncoding(const XSECCryptoKey& key);
+ static std::string getDEREncoding(const XSECCryptoKey& key, bool nowrap=true);
/**
* Returns the base64-encoded DER encoding of a certifiate's public key in SubjectPublicKeyInfo format.
*
* @param cert the certificate's key to encode
- * @return the base64 encoded key value in a malloc'd string
+ * @param nowrap if true, any linefeeds will be stripped from the result
+ * @return the base64 encoded key value
*/
- static char* getDEREncoding(const XSECCryptoX509& cert);
+ static std::string getDEREncoding(const XSECCryptoX509& cert, bool nowrap=true);
};
};
return loadCRLsFromFile(crls, backing, format);
}
-bool SecurityHelper::matches(const XSECCryptoKey* key1, const XSECCryptoKey* key2)
+bool SecurityHelper::matches(const XSECCryptoKey& key1, const XSECCryptoKey& key2)
{
- if (key1->getProviderName()!=DSIGConstants::s_unicodeStrPROVOpenSSL ||
- key2->getProviderName()!=DSIGConstants::s_unicodeStrPROVOpenSSL) {
+ if (key1.getProviderName()!=DSIGConstants::s_unicodeStrPROVOpenSSL ||
+ key2.getProviderName()!=DSIGConstants::s_unicodeStrPROVOpenSSL) {
Category::getInstance(XMLTOOLING_LOGCAT".SecurityHelper").warn("comparison of non-OpenSSL keys not supported");
return false;
}
// If one key is public or both, just compare the public key half.
- if (key1->getKeyType()==XSECCryptoKey::KEY_RSA_PUBLIC || key1->getKeyType()==XSECCryptoKey::KEY_RSA_PAIR) {
- if (key2->getKeyType()!=XSECCryptoKey::KEY_RSA_PUBLIC && key2->getKeyType()!=XSECCryptoKey::KEY_RSA_PAIR)
+ if (key1.getKeyType()==XSECCryptoKey::KEY_RSA_PUBLIC || key1.getKeyType()==XSECCryptoKey::KEY_RSA_PAIR) {
+ if (key2.getKeyType()!=XSECCryptoKey::KEY_RSA_PUBLIC && key2.getKeyType()!=XSECCryptoKey::KEY_RSA_PAIR)
return false;
- const RSA* rsa1 = static_cast<const OpenSSLCryptoKeyRSA*>(key1)->getOpenSSLRSA();
- const RSA* rsa2 = static_cast<const OpenSSLCryptoKeyRSA*>(key2)->getOpenSSLRSA();
- return (BN_cmp(rsa1->n,rsa2->n) == 0 && BN_cmp(rsa1->e,rsa2->e) == 0);
+ const RSA* rsa1 = static_cast<const OpenSSLCryptoKeyRSA&>(key1).getOpenSSLRSA();
+ const RSA* rsa2 = static_cast<const OpenSSLCryptoKeyRSA&>(key2).getOpenSSLRSA();
+ return (rsa1 && rsa2 && BN_cmp(rsa1->n,rsa2->n) == 0 && BN_cmp(rsa1->e,rsa2->e) == 0);
}
// For a private key, compare the private half.
- if (key1->getKeyType()==XSECCryptoKey::KEY_RSA_PRIVATE) {
- if (key2->getKeyType()!=XSECCryptoKey::KEY_RSA_PRIVATE && key2->getKeyType()!=XSECCryptoKey::KEY_RSA_PAIR)
+ if (key1.getKeyType()==XSECCryptoKey::KEY_RSA_PRIVATE) {
+ if (key2.getKeyType()!=XSECCryptoKey::KEY_RSA_PRIVATE && key2.getKeyType()!=XSECCryptoKey::KEY_RSA_PAIR)
return false;
- const RSA* rsa1 = static_cast<const OpenSSLCryptoKeyRSA*>(key1)->getOpenSSLRSA();
- const RSA* rsa2 = static_cast<const OpenSSLCryptoKeyRSA*>(key2)->getOpenSSLRSA();
- return (BN_cmp(rsa1->n,rsa2->n) == 0 && BN_cmp(rsa1->d,rsa2->d) == 0);
+ const RSA* rsa1 = static_cast<const OpenSSLCryptoKeyRSA&>(key1).getOpenSSLRSA();
+ const RSA* rsa2 = static_cast<const OpenSSLCryptoKeyRSA&>(key2).getOpenSSLRSA();
+ return (rsa1 && rsa2 && BN_cmp(rsa1->n,rsa2->n) == 0 && BN_cmp(rsa1->d,rsa2->d) == 0);
}
// If one key is public or both, just compare the public key half.
- if (key1->getKeyType()==XSECCryptoKey::KEY_DSA_PUBLIC || key1->getKeyType()==XSECCryptoKey::KEY_DSA_PAIR) {
- if (key2->getKeyType()!=XSECCryptoKey::KEY_DSA_PUBLIC && key2->getKeyType()!=XSECCryptoKey::KEY_DSA_PAIR)
+ if (key1.getKeyType()==XSECCryptoKey::KEY_DSA_PUBLIC || key1.getKeyType()==XSECCryptoKey::KEY_DSA_PAIR) {
+ if (key2.getKeyType()!=XSECCryptoKey::KEY_DSA_PUBLIC && key2.getKeyType()!=XSECCryptoKey::KEY_DSA_PAIR)
return false;
- const DSA* dsa1 = static_cast<const OpenSSLCryptoKeyDSA*>(key1)->getOpenSSLDSA();
- const DSA* dsa2 = static_cast<const OpenSSLCryptoKeyDSA*>(key2)->getOpenSSLDSA();
- return (BN_cmp(dsa1->pub_key,dsa2->pub_key) == 0);
+ const DSA* dsa1 = static_cast<const OpenSSLCryptoKeyDSA&>(key1).getOpenSSLDSA();
+ const DSA* dsa2 = static_cast<const OpenSSLCryptoKeyDSA&>(key2).getOpenSSLDSA();
+ return (dsa1 && dsa2 && BN_cmp(dsa1->pub_key,dsa2->pub_key) == 0);
}
// For a private key, compare the private half.
- if (key1->getKeyType()==XSECCryptoKey::KEY_DSA_PRIVATE) {
- if (key2->getKeyType()!=XSECCryptoKey::KEY_DSA_PRIVATE && key2->getKeyType()!=XSECCryptoKey::KEY_DSA_PAIR)
+ if (key1.getKeyType()==XSECCryptoKey::KEY_DSA_PRIVATE) {
+ if (key2.getKeyType()!=XSECCryptoKey::KEY_DSA_PRIVATE && key2.getKeyType()!=XSECCryptoKey::KEY_DSA_PAIR)
return false;
- const DSA* dsa1 = static_cast<const OpenSSLCryptoKeyDSA*>(key1)->getOpenSSLDSA();
- const DSA* dsa2 = static_cast<const OpenSSLCryptoKeyDSA*>(key2)->getOpenSSLDSA();
- return (BN_cmp(dsa1->priv_key,dsa2->priv_key) == 0);
+ const DSA* dsa1 = static_cast<const OpenSSLCryptoKeyDSA&>(key1).getOpenSSLDSA();
+ const DSA* dsa2 = static_cast<const OpenSSLCryptoKeyDSA&>(key2).getOpenSSLDSA();
+ return (dsa1 && dsa2 && BN_cmp(dsa1->priv_key,dsa2->priv_key) == 0);
}
Category::getInstance(XMLTOOLING_LOGCAT".SecurityHelper").warn("unsupported key type for comparison");
return false;
}
-char* SecurityHelper::getDEREncoding(const XSECCryptoKey& key)
+string SecurityHelper::getDEREncoding(const XSECCryptoKey& key, bool nowrap)
{
- char* ret=NULL;
+ string ret;
if (key.getProviderName()!=DSIGConstants::s_unicodeStrPROVOpenSSL) {
Category::getInstance(XMLTOOLING_LOGCAT".SecurityHelper").warn("encoding of non-OpenSSL keys not supported");
return ret;
}
BIO* base64 = BIO_new(BIO_f_base64());
- BIO_set_flags(base64, BIO_FLAGS_BASE64_NO_NL);
+ if (nowrap)
+ BIO_set_flags(base64, BIO_FLAGS_BASE64_NO_NL);
BIO* mem = BIO_new(BIO_s_mem());
BIO_push(base64, mem);
i2d_RSA_PUBKEY_bio(base64, const_cast<RSA*>(rsa));
BIO_flush(base64);
BUF_MEM* bptr=NULL;
BIO_get_mem_ptr(base64, &bptr);
- if (bptr && bptr->length > 0) {
- ret = (char*)malloc(sizeof(char)*(bptr->length+1));
- if (ret) {
- strncpy(ret, bptr->data, bptr->length);
- ret[bptr->length]=0;
- }
- }
+ if (bptr && bptr->length > 0)
+ ret.append(bptr->data, bptr->length);
BIO_free_all(base64);
}
else if (key.getKeyType() == XSECCryptoKey::KEY_DSA_PUBLIC || key.getKeyType() == XSECCryptoKey::KEY_DSA_PAIR) {
return ret;
}
BIO* base64 = BIO_new(BIO_f_base64());
- BIO_set_flags(base64, BIO_FLAGS_BASE64_NO_NL);
+ if (nowrap)
+ BIO_set_flags(base64, BIO_FLAGS_BASE64_NO_NL);
BIO* mem = BIO_new(BIO_s_mem());
BIO_push(base64, mem);
i2d_DSA_PUBKEY_bio(base64, const_cast<DSA*>(dsa));
BIO_flush(base64);
BUF_MEM* bptr=NULL;
BIO_get_mem_ptr(base64, &bptr);
- if (bptr && bptr->length > 0) {
- ret = (char*)malloc(sizeof(char)*(bptr->length+1));
- if (ret) {
- strncpy(ret, bptr->data, bptr->length);
- ret[bptr->length]=0;
- }
- }
+ if (bptr && bptr->length > 0)
+ ret.append(bptr->data, bptr->length);
BIO_free_all(base64);
}
else {
return ret;
}
-char* SecurityHelper::getDEREncoding(const XSECCryptoX509& cert)
+string SecurityHelper::getDEREncoding(const XSECCryptoX509& cert, bool nowrap)
{
- char* ret=NULL;
+ string ret;
if (cert.getProviderName()!=DSIGConstants::s_unicodeStrPROVOpenSSL) {
Category::getInstance(XMLTOOLING_LOGCAT".SecurityHelper").warn("encoding of non-OpenSSL keys not supported");
EVP_PKEY* key = X509_get_pubkey(const_cast<X509*>(x));
BIO* base64 = BIO_new(BIO_f_base64());
- BIO_set_flags(base64, BIO_FLAGS_BASE64_NO_NL);
+ if (nowrap)
+ BIO_set_flags(base64, BIO_FLAGS_BASE64_NO_NL);
BIO* mem = BIO_new(BIO_s_mem());
BIO_push(base64, mem);
i2d_PUBKEY_bio(base64, key);
BIO_flush(base64);
BUF_MEM* bptr=NULL;
BIO_get_mem_ptr(base64, &bptr);
- if (bptr && bptr->length > 0) {
- ret = (char*)malloc(sizeof(char)*(bptr->length+1));
- if (ret) {
- strncpy(ret, bptr->data, bptr->length);
- ret[bptr->length]=0;
- }
- }
+ if (bptr && bptr->length > 0)
+ ret.append(bptr->data, bptr->length);
BIO_free_all(base64);
return ret;
}
-char* SecurityHelper::getDEREncoding(const Credential& cred)
+string SecurityHelper::getDEREncoding(const Credential& cred, bool nowrap)
{
const X509Credential* x509 = dynamic_cast<const X509Credential*>(&cred);
if (x509 && !x509->getEntityCertificateChain().empty())
- return getDEREncoding(*(x509->getEntityCertificateChain().front()));
+ return getDEREncoding(*(x509->getEntityCertificateChain().front()), nowrap);
else if (cred.getPublicKey())
- return getDEREncoding(*(cred.getPublicKey()));
- return NULL;
+ return getDEREncoding(*(cred.getPublicKey()), nowrap);
+ return "";
}
pathname = data_path + "test.pfx";
auto_ptr<XSECCryptoKey> key3(SecurityHelper::loadKeyFromFile(pathname.c_str(), NULL, "password"));
- TSM_ASSERT("PEM/DER keys did not match", SecurityHelper::matches(key1.get(), key2.get()));
- TSM_ASSERT("DER/PKCS12 keys did not match", SecurityHelper::matches(key2.get(), key3.get()));
+ TSM_ASSERT("PEM/DER keys did not match", SecurityHelper::matches(*key1.get(), *key2.get()));
+ TSM_ASSERT("DER/PKCS12 keys did not match", SecurityHelper::matches(*key2.get(), *key3.get()));
pathname = data_path + "key2.pem";
auto_ptr<XSECCryptoKey> key4(SecurityHelper::loadKeyFromFile(pathname.c_str()));
- TSM_ASSERT("Different keys matched", !SecurityHelper::matches(key3.get(), key4.get()));
+ TSM_ASSERT("Different keys matched", !SecurityHelper::matches(*key3.get(), *key4.get()));
}
void testKeysFromURLs() {
auto_ptr<SOAPTransport> t3(getTransport("https://spaces.internet2.edu/download/attachments/5305/test.pfx"));
auto_ptr<XSECCryptoKey> key3(SecurityHelper::loadKeyFromURL(*t3.get(), pathname.c_str(), NULL, "password"));
- TSM_ASSERT("PEM/DER keys did not match", SecurityHelper::matches(key1.get(), key2.get()));
- TSM_ASSERT("DER/PKCS12 keys did not match", SecurityHelper::matches(key2.get(), key3.get()));
+ TSM_ASSERT("PEM/DER keys did not match", SecurityHelper::matches(*key1.get(), *key2.get()));
+ TSM_ASSERT("DER/PKCS12 keys did not match", SecurityHelper::matches(*key2.get(), *key3.get()));
}
void testCertificatesFromFiles() {
auto_ptr<XSECCryptoKey> key2(certs[1]->clonePublicKey());
auto_ptr<XSECCryptoKey> key3(certs[2]->clonePublicKey());
- TSM_ASSERT("PEM/DER keys did not match", SecurityHelper::matches(key1.get(), key2.get()));
- TSM_ASSERT("DER/PKCS12 keys did not match", SecurityHelper::matches(key2.get(), key3.get()));
+ TSM_ASSERT("PEM/DER keys did not match", SecurityHelper::matches(*key1.get(), *key2.get()));
+ TSM_ASSERT("DER/PKCS12 keys did not match", SecurityHelper::matches(*key2.get(), *key3.get()));
- char* enc1 = SecurityHelper::getDEREncoding(*certs[2]);
- char* enc2 = SecurityHelper::getDEREncoding(*key1.get());
- TSM_ASSERT("Certificate and its key produced different DER encodings", !strcmp(enc1, enc2));
- if (enc1) free(enc1);
- if (enc2) free(enc2);
+ TSM_ASSERT_EQUALS(
+ "Certificate and its key produced different DER encodings",
+ SecurityHelper::getDEREncoding(*certs[2]), SecurityHelper::getDEREncoding(*key1.get())
+ );
for_each(certs.begin(), certs.end(), xmltooling::cleanup<XSECCryptoX509>());
certs.clear();
auto_ptr<XSECCryptoKey> key2(certs[0]->clonePublicKey());
auto_ptr<XSECCryptoKey> key3(certs[0]->clonePublicKey());
- TSM_ASSERT("PEM/DER keys did not match", SecurityHelper::matches(key1.get(), key2.get()));
- TSM_ASSERT("DER/PKCS12 keys did not match", SecurityHelper::matches(key2.get(), key3.get()));
+ TSM_ASSERT("PEM/DER keys did not match", SecurityHelper::matches(*key1.get(), *key2.get()));
+ TSM_ASSERT("DER/PKCS12 keys did not match", SecurityHelper::matches(*key2.get(), *key3.get()));
for_each(certs.begin(), certs.end(), xmltooling::cleanup<XSECCryptoX509>());
certs.clear();