SANTUARIO-496 - DSA verification crashes OpenSSL on invalid combinations of key content

git-svn-id: https://svn.apache.org/repos/asf/santuario/xml-security-cpp/trunk@1843562 13f79535-47bb-0310-9956-ffa450edef68
diff --git a/xsec/enc/OpenSSL/OpenSSLCryptoKeyDSA.cpp b/xsec/enc/OpenSSL/OpenSSLCryptoKeyDSA.cpp
index a33f38e..c01200a 100644
--- a/xsec/enc/OpenSSL/OpenSSLCryptoKeyDSA.cpp
+++ b/xsec/enc/OpenSSL/OpenSSLCryptoKeyDSA.cpp
@@ -257,11 +257,16 @@
     // Use the currently loaded key to validate the Base64 encoded signature
 
     if (mp_dsaKey == NULL) {
-
         throw XSECCryptoException(XSECCryptoException::DSAError,
             "OpenSSL:DSA - Attempt to validate signature with empty key");
     }
 
+    XSECCryptoKey::KeyType keyType = getKeyType();
+    if (keyType != KEY_DSA_PAIR && keyType != KEY_DSA_PUBLIC) {
+        throw XSECCryptoException(XSECCryptoException::DSAError,
+            "OpenSSL:DSA - Attempt to validate signature without public key");
+    }
+
     char* cleanedBase64Signature;
     unsigned int cleanedBase64SignatureLen = 0;
 
@@ -289,10 +294,10 @@
                           cleanedBase64SignatureLen);
 
     if (rc < 0) {
-
         throw XSECCryptoException(XSECCryptoException::DSAError,
             "OpenSSL:DSA - Error during Base64 Decode");
     }
+
     int t = 0;
 
     EVP_DecodeFinal(dctx.of(), &sigVal[sigValLen], &t);
@@ -363,14 +368,18 @@
     // Sign a pre-calculated hash using this key
 
     if (mp_dsaKey == NULL) {
-
         throw XSECCryptoException(XSECCryptoException::DSAError,
             "OpenSSL:DSA - Attempt to sign data with empty key");
     }
 
-    DSA_SIG * dsa_sig;
+    KeyType keyType = getKeyType();
+    if (keyType != KEY_DSA_PAIR && keyType != KEY_DSA_PRIVATE) {
+        throw XSECCryptoException(XSECCryptoException::DSAError,
+            "OpenSSL:DSA - Attempt to sign data without private key");
+    }
 
-    dsa_sig = DSA_do_sign(hashBuf, hashLen, mp_dsaKey);
+
+    DSA_SIG* dsa_sig = DSA_do_sign(hashBuf, hashLen, mp_dsaKey);
 
     if (dsa_sig == NULL) {
 
@@ -392,19 +401,15 @@
     unsigned int rawLen = BN_bn2bin(dsaSigR, rawSigBuf);
 
     if (rawLen <= 0) {
-
         throw XSECCryptoException(XSECCryptoException::DSAError,
             "OpenSSL:DSA - Error converting signature to raw buffer");
-
     }
 
     unsigned int rawLenS = BN_bn2bin(dsaSigS, (unsigned char *) &rawSigBuf[rawLen]);
 
     if (rawLenS <= 0) {
-
         throw XSECCryptoException(XSECCryptoException::DSAError,
             "OpenSSL:DSA - Error converting signature to raw buffer");
-
     }
 
     rawLen += rawLenS;
@@ -427,7 +432,6 @@
     BIO_free_all(b64);
 
     if (sigValLen <= 0) {
-
         throw XSECCryptoException(XSECCryptoException::DSAError,
             "OpenSSL:DSA - Error base64 encoding signature");
     }
diff --git a/xsec/enc/OpenSSL/OpenSSLCryptoKeyEC.cpp b/xsec/enc/OpenSSL/OpenSSLCryptoKeyEC.cpp
index 7be050a..491731d 100644
--- a/xsec/enc/OpenSSL/OpenSSLCryptoKeyEC.cpp
+++ b/xsec/enc/OpenSSL/OpenSSLCryptoKeyEC.cpp
@@ -152,11 +152,16 @@
     // Use the currently loaded key to validate the Base64 encoded signature
 
     if (mp_ecKey == NULL) {
-
         throw XSECCryptoException(XSECCryptoException::ECError,
             "OpenSSL:EC - Attempt to validate signature with empty key");
     }
 
+    KeyType keyType = getKeyType();
+    if (keyType != KEY_EC_PAIR && keyType != KEY_EC_PUBLIC) {
+        throw XSECCryptoException(XSECCryptoException::ECError,
+            "OpenSSL:EC - Attempt to validate signature without public key");
+    }
+
     char * cleanedBase64Signature;
     unsigned int cleanedBase64SignatureLen = 0;
 
@@ -183,10 +188,10 @@
                           cleanedBase64SignatureLen);
 
     if (rc < 0) {
-
         throw XSECCryptoException(XSECCryptoException::ECError,
             "OpenSSL:EC - Error during Base64 Decode");
     }
+
     int t = 0;
 
     EVP_DecodeFinal(dctx.of(), &sigVal[sigValLen], &t);
@@ -239,10 +244,13 @@
             "OpenSSL:EC - Attempt to sign data with empty key");
     }
 
-    ECDSA_SIG * ecdsa_sig;
+    KeyType keyType = getKeyType();
+    if (keyType != KEY_EC_PAIR && keyType != KEY_EC_PRIVATE) {
+        throw XSECCryptoException(XSECCryptoException::ECError,
+            "OpenSSL:EC - Attempt to sign data without private key");
+    }
 
-    ecdsa_sig = ECDSA_do_sign(hashBuf, hashLen, mp_ecKey);
-
+    ECDSA_SIG* ecdsa_sig  = ECDSA_do_sign(hashBuf, hashLen, mp_ecKey);
     if (ecdsa_sig == NULL) {
         throw XSECCryptoException(XSECCryptoException::ECError,
             "OpenSSL:EC - Error signing data");
diff --git a/xsec/enc/OpenSSL/OpenSSLCryptoKeyRSA.cpp b/xsec/enc/OpenSSL/OpenSSLCryptoKeyRSA.cpp
index 3a52607..b59a923 100644
--- a/xsec/enc/OpenSSL/OpenSSLCryptoKeyRSA.cpp
+++ b/xsec/enc/OpenSSL/OpenSSLCryptoKeyRSA.cpp
@@ -449,6 +449,12 @@
             "OpenSSL:RSA - Attempt to validate signature with empty key");
     }
 
+    XSECCryptoKey::KeyType keyType = getKeyType();
+    if (keyType != KEY_RSA_PAIR && keyType != KEY_RSA_PUBLIC) {
+        throw XSECCryptoException(XSECCryptoException::RSAError,
+            "OpenSSL:RSA - Attempt to validate signature without public key");
+    }
+
     char* cleanedBase64Signature;
     unsigned int cleanedBase64SignatureLen = 0;
 
@@ -568,6 +574,12 @@
             "OpenSSL:RSA - Attempt to sign data with empty key");
     }
 
+    KeyType keyType = getKeyType();
+    if (keyType != KEY_RSA_PAIR && keyType != KEY_RSA_PRIVATE) {
+        throw XSECCryptoException(XSECCryptoException::RSAError,
+            "OpenSSL:RSA - Attempt to sign data without private key");
+    }
+
     // Build the buffer to be encrypted by prepending the SHA1 OID to the hash
 
     unsigned char* encryptBuf;