blautenb 2003/10/03 02:50:06
Modified: c/src/xenc XENCCipher.hpp XENCEncryptedType.hpp
c/src/xenc/impl XENCAlgorithmHandlerDefault.cpp
XENCAlgorithmHandlerDefault.hpp XENCCipherImpl.cpp
XENCCipherImpl.hpp XENCEncryptedDataImpl.hpp
XENCEncryptedTypeImpl.cpp XENCEncryptedTypeImpl.hpp
Log:
Updates to support creating an EncryptedKey (AES KeyWrap)
Revision Changes Path
1.6 +56 -1 xml-security/c/src/xenc/XENCCipher.hpp
Index: XENCCipher.hpp
===================================================================
RCS file: /home/cvs/xml-security/c/src/xenc/XENCCipher.hpp,v
retrieving revision 1.5
retrieving revision 1.6
diff -u -r1.5 -r1.6
--- XENCCipher.hpp 17 Sep 2003 10:10:21 -0000 1.5
+++ XENCCipher.hpp 3 Oct 2003 09:50:05 -0000 1.6
@@ -82,6 +82,7 @@
class XSECCryptoKey;
class XENCEncryptedData;
+class XENCEncryptedKey;
class XSECKeyInfoResolver;
/**
@@ -148,6 +149,23 @@
XERCES_CPP_NAMESPACE_QUALIFIER DOMElement * element
) = 0;
+ /**
+ * \brief Decrypt a key
+ *
+ * Reads in the passed in KeyInfo structure for an EncryptedKey and
+ * decrypts the key to a buffer.
+ *
+ * @param encryptedKey the already loaded encryptedKey structure
+ * @param rawKey Buffer to place the decrypted key into
+ * @param maxKeySize Maximum number of bytes to place in the buffer
+ */
+
+ virtual int decryptKey(
+ XENCEncryptedKey * encryptedKey,
+ XMLByte * rawKey,
+ int maxKeySize
+ ) = 0;
+
//@}
/** @name Encryption Functions */
@@ -178,6 +196,28 @@
const XMLCh * algorithmURI = NULL
) = 0;
+ /**
+ * \brief Encrypt a buffer of data as a key
+ *
+ * Encrypts the passed in data and creates an EncryptedKey element
+ *
+ * @param keyBuffer The key data to encrypt
+ * @param keyLen Bytes to encrypt
+ * @param em The encryptionMethod to use for this encryption. Use
+ * ENCRYPT_NONE if a user defined type is required.
+ * @param algorithmURI If ENCRYPT_NONE is used for em, this will be
+ * used as the algorithm URI.
+ *
+ * @returns The EncryptedKey element
+ */
+
+ virtual XENCEncryptedKey * encryptKey(
+ const unsigned char * keyBuffer,
+ unsigned int keyLen,
+ encryptionMethod em,
+ const XMLCh * algorithmURI = NULL
+ ) = 0;
+
//@}
/** @name Getter Functions */
//@{
@@ -231,6 +271,21 @@
*/
virtual void setKey(XSECCryptoKey * key) = 0;
+
+ /**
+ * \brief Set Key Encryption Key for next operation
+ *
+ * Set the passed in key for the next key decryption/encryption
+ * operation.
+ *
+ * @note This key will only be used to decrypt EncryptedKey elements.
+ * To set a key for decrypting an EncryptedData use #setKey instead.
+ *
+ * @param key Key to use
+ * @note This function will take ownership of the key and delete it
when done.
+ */
+
+ virtual void setKEK(XSECCryptoKey * key) = 0;
/**
* \brief Register a KeyInfoResolver
1.6 +14 -1 xml-security/c/src/xenc/XENCEncryptedType.hpp
Index: XENCEncryptedType.hpp
===================================================================
RCS file: /home/cvs/xml-security/c/src/xenc/XENCEncryptedType.hpp,v
retrieving revision 1.5
retrieving revision 1.6
diff -u -r1.5 -r1.6
--- XENCEncryptedType.hpp 17 Sep 2003 10:10:21 -0000 1.5
+++ XENCEncryptedType.hpp 3 Oct 2003 09:50:05 -0000 1.6
@@ -80,6 +80,7 @@
class DSIGKeyInfoList;
class DSIGKeyInfoName;
class XENCEncryptionMethod;
+class XENCEncryptedKey;
/**
* @ingroup xenc
@@ -199,6 +200,18 @@
virtual DSIGKeyInfoName * appendKeyName(const XMLCh * name, bool
isDName = false) = 0;
+ /**
+ * \brief Append an already created EncryptedKey.
+ *
+ * Add an already created EncryptedKey.
+ *
+ * @note The encryptedKey becomes the property of the owning
EncryptedType
+ * object and will be deleted upon its destruction.
+ *
+ * @param encryptedKey A pointer to the encrypted Key
+ */
+
+ virtual void appendEncryptedKey(XENCEncryptedKey * encryptedKey) = 0;
//@}
private:
1.2 +345 -4
xml-security/c/src/xenc/impl/XENCAlgorithmHandlerDefault.cpp
Index: XENCAlgorithmHandlerDefault.cpp
===================================================================
RCS file:
/home/cvs/xml-security/c/src/xenc/impl/XENCAlgorithmHandlerDefault.cpp,v
retrieving revision 1.1
retrieving revision 1.2
diff -u -r1.1 -r1.2
--- XENCAlgorithmHandlerDefault.cpp 15 Sep 2003 11:53:37 -0000 1.1
+++ XENCAlgorithmHandlerDefault.cpp 3 Oct 2003 09:50:05 -0000 1.2
@@ -82,9 +82,36 @@
#include "XENCAlgorithmHandlerDefault.hpp"
#include <xercesc/dom/DOM.hpp>
+#include <xercesc/util/Janitor.hpp>
XERCES_CPP_NAMESPACE_USE
+#define _MY_MAX_KEY_SIZE 2048
+
+unsigned char s_3DES_CMS_IV [] = {
+ 0x4a,
+ 0xdd,
+ 0xa2,
+ 0x2c,
+ 0x79,
+ 0xe8,
+ 0x21,
+ 0x05
+};
+
+unsigned char s_AES_IV [] = {
+
+ 0xA6,
+ 0xA6,
+ 0xA6,
+ 0xA6,
+ 0xA6,
+ 0xA6,
+ 0xA6,
+ 0xA6
+
+};
+
//
--------------------------------------------------------------------------------
// Internal functions
//
--------------------------------------------------------------------------------
@@ -106,13 +133,235 @@
}
+unsigned int XENCAlgorithmHandlerDefault::unwrapKeyAES(
+ TXFMChain * cipherText,
+ XSECCryptoKey * key,
+ safeBuffer & result) {
+
+ // Cat the encrypted key
+ XMLByte buf[_MY_MAX_KEY_SIZE];
+ XMLByte aesBuf[16];
+ XMLByte aesOutBuf[16];
+ TXFMBase * b = cipherText->getLastTxfm();
+ int sz = b->readBytes(buf, _MY_MAX_KEY_SIZE);
+
+ if (sz <= 0) {
+ throw XSECException(XSECException::CipherError,
+ "XENCAlgorithmHandlerDefault - AES Wrapped Key not
found");
+ }
+
+ if (sz == _MY_MAX_KEY_SIZE) {
+ throw XSECException(XSECException::CipherError,
+ "XENCAlgorithmHandlerDefault - Key to decrypt too
big!");
+ }
+
+ // Find number of blocks, and ensure we are a multiple of 64 bits
+ if (sz % 8 != 0) {
+ throw XSECException(XSECException::CipherError,
+ "XENCAlgorithmHandlerDefault - AES wrapped key not a
multiple of 64");
+ }
+
+ // Do the decrypt - this cast will throw if wrong, but we should
+ // not have been able to get through algorithm checks otherwise
+ XSECCryptoSymmetricKey * sk = dynamic_cast<XSECCryptoSymmetricKey
*>(key);
+
+ int blocks = sz / 8;
+ int n = blocks - 1;
+ for (int j = 5; j >= 0; j--) {
+ for (int i = n ; i > 0 ; --i) {
+
+ // Gather blocks to decrypt
+ // A
+ memcpy(aesBuf, buf, 8);
+ // Ri
+ memcpy(&aesBuf[8], &buf[8 * i], 8);
+ // A mod t
+ aesBuf[7] ^= ((n * j) + i);
+
+ // do decrypt
+ sk->decryptInit();
+ int sz = sk->decrypt(aesBuf, aesOutBuf, 16, 16);
+ sz += sk->decryptFinish(&aesOutBuf[sz], 16 - sz);
+
+ if (sz != 16) {
+ throw XSECException(XSECException::CipherError,
+ "XENCAlgorithmHandlerDefault - Error
performing decrypt in AES Unwrap");
+ }
+
+ // Copy back to where we are
+ // A
+ memcpy(buf, aesOutBuf, 8);
+ // Ri
+ memcpy(&buf[8 * i], &aesOutBuf[8], 8);
+
+ }
+ }
+
+ // Check is valid
+ if (memcmp(buf, s_AES_IV, 8) != 0) {
+ throw XSECException(XSECException::CipherError,
+ "XENCAlgorithmHandlerDefault - decrypt failed - AES IV
is not correct");
+ }
+
+ // Copy to safebuffer
+ result.sbMemcpyIn(&buf[8], n * 8);
+
+ return n * 8;
+}
+
+bool XENCAlgorithmHandlerDefault::wrapKeyAES(
+ TXFMChain * cipherText,
+ XSECCryptoKey * key,
+ safeBuffer & result) {
+
+ // get the raw key
+ XMLByte buf[_MY_MAX_KEY_SIZE + 8];
+ memcpy(buf, s_AES_IV, 8);
+ XMLByte aesBuf[16];
+ XMLByte aesOutBuf[16];
+ TXFMBase * b = cipherText->getLastTxfm();
+ int sz = b->readBytes(&buf[8], _MY_MAX_KEY_SIZE);
+
+ if (sz <= 0) {
+ throw XSECException(XSECException::CipherError,
+ "XENCAlgorithmHandlerDefault - Key not found");
+ }
+
+ if (sz == _MY_MAX_KEY_SIZE) {
+ throw XSECException(XSECException::CipherError,
+ "XENCAlgorithmHandlerDefault - Key to encrypt too
big!");
+ }
+
+ // Find number of blocks, and ensure we are a multiple of 64 bits
+ if (sz % 8 != 0) {
+ throw XSECException(XSECException::CipherError,
+ "XENCAlgorithmHandlerDefault - AES wrapped key not a
multiple of 64");
+ }
+
+ // Do the decrypt - this cast will throw if wrong, but we should
+ // not have been able to get through algorithm checks otherwise
+ XSECCryptoSymmetricKey * sk = dynamic_cast<XSECCryptoSymmetricKey
*>(key);
+
+ int n = sz / 8;
+ int blocks = n + 1;
+
+ for (int j = 0; j <= 5; ++j) {
+ for (int i = 1 ; i <= n ; ++i) {
+
+ // Gather blocks to decrypt
+ // A
+ memcpy(aesBuf, buf, 8);
+ // Ri
+ memcpy(&aesBuf[8], &buf[8 * i], 8);
+
+ // do encrypt
+ sk->encryptInit();
+ int sz = sk->encrypt(aesBuf, aesOutBuf, 16, 16);
+ sz += sk->encryptFinish(&aesOutBuf[sz], 16 - sz);
+
+ if (sz != 16) {
+ throw XSECException(XSECException::CipherError,
+ "XENCAlgorithmHandlerDefault - Error
performing encrypt in AES wrap");
+ }
+
+ // Copy back to where we are
+ // A
+ memcpy(buf, aesOutBuf, 8);
+ // A mod t
+ buf[7] ^= ((n * j) + i);
+ // Ri
+ memcpy(&buf[8 * i], &aesOutBuf[8], 8);
+
+ }
+ }
+
+ // Now we have to base64 encode
+ XSECCryptoBase64 * b64 = XSECPlatformUtils::g_cryptoProvider->base64();
+
+ if (!b64) {
+
+ throw XSECException(XSECException::CryptoProviderError,
+ "XENCAlgorithmHandlerDefault - Error getting
base64 encoder in AES wrap");
+
+ }
+
+ Janitor<XSECCryptoBase64> j_b64(b64);
+ unsigned char * b64Buffer;
+ int bufLen = ((n + 1) * 8) * 3;
+ XSECnew(b64Buffer, unsigned char[bufLen + 1]);// Overkill
+ ArrayJanitor<unsigned char> j_b64Buffer(b64Buffer);
+
+ b64->encodeInit();
+ int outputLen = b64->encode (buf, (n+1) * 8, b64Buffer, bufLen);
+ outputLen += b64->encodeFinish(&b64Buffer[outputLen], bufLen -
outputLen);
+ b64Buffer[outputLen] = '\0';
+
+ // Copy to safebuffer
+ result.sbStrcpyIn((const char *) b64Buffer);
+
+ return true;
+}
+
+#if 0
+
+Keep for DES keywrap
+
+ // Perform an unwrap on the key
+ safeBuffer cipherSB;
+
+ // Set the IV
+ cipherSB.sbMemcpyIn(s_CMSIV, 8);
+
+ // Cat the encrypted key
+ XMLByte buf[_MY_MAX_KEY_SIZE];
+ TXFMBase * b = cipherText->getLastTxfm();
+ int offset = 8;
+ int sz = b->readBytes(buf, _MY_MAX_KEY_SIZE);
+
+ while (sz > 0) {
+ cipherSB.sbMemcpyIn(offset, buf, sz);
+ offset += sz;
+ sz = b->readBytes(buf, _MY_MAX_KEY_SIZE);
+ }
+
+ if (offset > _MY_MAX_KEY_SIZE) {
+ throw XSECException(XSECException::CipherError,
+ "XENCAlgorithmHandlerDefault - Key to decrypt
too big!");
+ }
+
+ // Do the decrypt - this cast will throw if wrong, but we should
+ // not have been able to get through algorithm checks otherwise
+ XSECCryptoSymmetricKey * sk =
dynamic_cast<XSECCryptoSymmetricKey *>(key);
+
+ sk->decryptInit(false); // No padding
+ // If key is bigger than this, then we have a problem
+ sz = sk->decrypt(cipherSB.rawBuffer(), buf, offset,
_MY_MAX_KEY_SIZE);
+
+ sz += sk->decryptFinish(&buf[sz], _MY_MAX_KEY_SIZE - sz);
+
+ if (sz <= 0) {
+ throw XSECException(XSECException::CipherError,
+ "XENCAlgorithmHandlerDefault - Error decrypting
key!");
+ }
+
+ // We now have the first cut, reverse the key
+ XMLByte buf2[_MY_MAX_KEY_SIZE];
+ for (int i = 0; i < sz; ++ i) {
+ buf2[sz - i] = buf[i];
+ }
+ // decrypt again
+ sk->decryptInit(false);
+ offset = sk->decrypt(buf2, buf, sz, _MY_MAX_KEY_SIZE);
+ offset += sk->decryptFinish(&buf[offset], _MY_MAX_KEY_SIZE -
offset);
+
+#endif
//
--------------------------------------------------------------------------------
// SafeBuffer decryption
//
--------------------------------------------------------------------------------
-bool XENCAlgorithmHandlerDefault::decryptToSafeBuffer(
+unsigned int XENCAlgorithmHandlerDefault::decryptToSafeBuffer(
TXFMChain * cipherText,
XENCEncryptionMethod * encryptionMethod,
XSECCryptoKey * key,
@@ -120,6 +369,32 @@
safeBuffer & result
) {
+ bool isAESKeyWrap = false;
+
+ // Is this a keyWrap URI?
+ if (strEquals(encryptionMethod->getAlgorithm(),
DSIGConstants::s_unicodeStrURIKW_AES128)) {
+
+ if (key->getKeyType() != XSECCryptoKey::KEY_SYMMETRIC ||
+ dynamic_cast<XSECCryptoSymmetricKey
*>(key)->getSymmetricKeyType() !=
+ XSECCryptoSymmetricKey::KEY_AES_ECB_128) {
+
+ throw XSECException(XSECException::CipherError,
+ "XENCAlgorithmHandlerDefault - 128bit AES
Algorithm, but not a AES (ECB) 128 bit key");
+
+ }
+
+ isAESKeyWrap = true;
+
+ }
+
+ if (isAESKeyWrap == true) {
+
+ return unwrapKeyAES(cipherText, key, result);
+
+ }
+
+
+
// The default case is to just do a standard, padded block decrypt.
// So the only thing we have to do is ensure key type matches URI.
@@ -136,9 +411,20 @@
// Do the decrypt to the safeBuffer
result.sbStrcpyIn("");
- result << cipherText->getLastTxfm();
+ unsigned int offset = 0;
+ XMLByte buf[1024];
+ TXFMBase * b = cipherText->getLastTxfm();
+
+ int bytesRead = b->readBytes(buf, 1024);
+ while (bytesRead > 0) {
+ result.sbMemcpyIn(offset, buf, bytesRead);
+ offset += bytesRead;
+ bytesRead = b->readBytes(buf, 1024);
+ }
- return true;
+ result[offset] = '\0';
+
+ return offset;
}
@@ -154,6 +440,32 @@
safeBuffer & result
) {
+
+ bool isAESKeyWrap = false;
+
+ // Is this a keyWrap URI?
+ if (strEquals(encryptionMethod->getAlgorithm(),
DSIGConstants::s_unicodeStrURIKW_AES128)) {
+
+ if (key->getKeyType() != XSECCryptoKey::KEY_SYMMETRIC ||
+ dynamic_cast<XSECCryptoSymmetricKey
*>(key)->getSymmetricKeyType() !=
+ XSECCryptoSymmetricKey::KEY_AES_ECB_128) {
+
+ throw XSECException(XSECException::CipherError,
+ "XENCAlgorithmHandlerDefault - 128bit AES
Algorithm, but not a AES (ECB) 128 bit key");
+
+ }
+
+ isAESKeyWrap = true;
+
+ }
+
+ if (isAESKeyWrap == true) {
+
+ return wrapKeyAES(plainText, key, result);
+
+ }
+
+
// Check the URI and key match
mapURIToKey(encryptionMethod->getAlgorithm(), key);
@@ -176,6 +488,35 @@
return true;
}
+//
--------------------------------------------------------------------------------
+// Key Creation
+//
--------------------------------------------------------------------------------
+
+XSECCryptoKey * XENCAlgorithmHandlerDefault::createKeyForURI(
+ const XMLCh * uri,
+ unsigned char * keyBuffer,
+ unsigned int keyLen
+ ) {
+
+ if (strEquals(uri, DSIGConstants::s_unicodeStrURI3DES_CBC)) {
+
+ // 3 Key 3DES in CBC mode.
+ XSECCryptoSymmetricKey * sk =
+
XSECPlatformUtils::g_cryptoProvider->keySymmetric(XSECCryptoSymmetricKey::KEY_3DES_CBC_192);
+
+ sk->setKey(keyBuffer, keyLen);
+
+ return sk;
+
+ }
+
+ throw XSECException(XSECException::CipherError,
+ "XENCAlgorithmHandlerDefault - URI Provided, but cannot create
associated key");
+
+ return NULL;
+
+}
+
//
--------------------------------------------------------------------------------
// Clone
1.2 +17 -2
xml-security/c/src/xenc/impl/XENCAlgorithmHandlerDefault.hpp
Index: XENCAlgorithmHandlerDefault.hpp
===================================================================
RCS file:
/home/cvs/xml-security/c/src/xenc/impl/XENCAlgorithmHandlerDefault.hpp,v
retrieving revision 1.1
retrieving revision 1.2
diff -u -r1.1 -r1.2
--- XENCAlgorithmHandlerDefault.hpp 15 Sep 2003 11:53:37 -0000 1.1
+++ XENCAlgorithmHandlerDefault.hpp 3 Oct 2003 09:50:05 -0000 1.2
@@ -89,7 +89,7 @@
virtual ~XENCAlgorithmHandlerDefault() {};
- virtual bool decryptToSafeBuffer(
+ virtual unsigned int decryptToSafeBuffer(
TXFMChain * cipherText,
XENCEncryptionMethod * encryptionMethod,
XSECCryptoKey * key,
@@ -105,11 +105,26 @@
safeBuffer & result
);
+ virtual XSECCryptoKey * createKeyForURI(
+ const XMLCh * uri,
+ unsigned char * keyBuffer,
+ unsigned int keyLen
+ );
+
virtual XSECAlgorithmHandler * clone(void) const;
private:
void mapURIToKey(const XMLCh * uri, XSECCryptoKey * key);
+ unsigned int unwrapKeyAES(
+ TXFMChain * cipherText,
+ XSECCryptoKey * key,
+ safeBuffer & result);
+ bool wrapKeyAES(
+ TXFMChain * cipherText,
+ XSECCryptoKey * key,
+ safeBuffer & result);
+
};
1.6 +243 -2 xml-security/c/src/xenc/impl/XENCCipherImpl.cpp
Index: XENCCipherImpl.cpp
===================================================================
RCS file: /home/cvs/xml-security/c/src/xenc/impl/XENCCipherImpl.cpp,v
retrieving revision 1.5
retrieving revision 1.6
diff -u -r1.5 -r1.6
--- XENCCipherImpl.cpp 17 Sep 2003 10:10:22 -0000 1.5
+++ XENCCipherImpl.cpp 3 Oct 2003 09:50:05 -0000 1.6
@@ -74,6 +74,7 @@
#include <xsec/transformers/TXFMChain.hpp>
#include <xsec/transformers/TXFMBase.hpp>
#include <xsec/transformers/TXFMC14n.hpp>
+#include <xsec/transformers/TXFMSB.hpp>
#include <xsec/transformers/TXFMDocObject.hpp>
#include <xsec/utils/XSECDOMUtils.hpp>
#include <xsec/framework/XSECEnv.hpp>
@@ -84,6 +85,7 @@
#include "XENCCipherImpl.hpp"
#include "XENCEncryptedDataImpl.hpp"
+#include "XENCEncryptedKeyImpl.hpp"
#include "XENCEncryptionMethodImpl.hpp"
#include "XENCAlgorithmHandlerDefault.hpp"
@@ -143,6 +145,7 @@
mp_doc(doc),
mp_encryptedData(NULL),
mp_key(NULL),
+mp_kek(NULL),
mp_keyInfoResolver(NULL) {
XSECnew(mp_env, XSECEnv(doc));
@@ -158,6 +161,9 @@
if (mp_key != NULL)
delete mp_key;
+ if (mp_kek != NULL)
+ delete mp_kek;
+
if (mp_env != NULL)
delete mp_env;
@@ -177,6 +183,7 @@
// Register default encryption algorithm handlers
XSECPlatformUtils::registerAlgorithmHandler(DSIGConstants::s_unicodeStrURI3DES_CBC,
def);
+
XSECPlatformUtils::registerAlgorithmHandler(DSIGConstants::s_unicodeStrURIKW_AES128,
def);
}
@@ -217,6 +224,27 @@
return mp_encryptedData;
}
+//
--------------------------------------------------------------------------------
+// Keys
+//
--------------------------------------------------------------------------------
+
+void XENCCipherImpl::setKey(XSECCryptoKey * key) {
+
+ if (mp_key != NULL)
+ delete mp_key;
+
+ mp_key = key;
+
+}
+
+void XENCCipherImpl::setKEK(XSECCryptoKey * key) {
+
+ if (mp_kek != NULL)
+ delete mp_kek;
+
+ mp_kek = key;
+
+}
//
--------------------------------------------------------------------------------
// Serialise/Deserialise an element
@@ -355,6 +383,8 @@
DOMDocument * XENCCipherImpl::decryptElement(DOMElement * element) {
+ XSECAlgorithmHandler *handler;
+
// First of all load the element
if (mp_encryptedData != NULL)
delete mp_encryptedData;
@@ -373,6 +403,43 @@
if (mp_key == NULL) {
+ // See if we can decrypt a key in the KeyInfo list
+ DSIGKeyInfoList * kil =
mp_encryptedData->getKeyInfoList();
+ int kLen = kil->getSize();
+
+ for (int i = 0; i < kLen ; ++ i) {
+
+ if (kil->item(i)->getKeyInfoType() ==
DSIGKeyInfo::KEYINFO_ENCRYPTEDKEY) {
+
+ XENCEncryptedKey * ek =
dynamic_cast<XENCEncryptedKey*>(kil->item(i));
+ XMLByte buffer[1024];
+ int keySize = decryptKey(ek, buffer,
1024);
+
+ if (keySize > 0) {
+ // Try to map the key
+
+ XENCEncryptionMethod *
encryptionMethod =
+
mp_encryptedData->getEncryptionMethod();
+
+ if (encryptionMethod != NULL) {
+
+ handler =
+
XSECPlatformUtils::g_algorithmMapper->mapURIToHandler(
+
mp_encryptedData->getEncryptionMethod()->getAlgorithm());
+
+ if (handler != NULL)
+ mp_key =
handler->createKeyForURI(
+
mp_encryptedData->getEncryptionMethod()->getAlgorithm(),
+
buffer,
+
keySize);
+ }
+ }
+ }
+ }
+ }
+
+ if (mp_key == NULL) {
+
throw XSECException(XSECException::CipherError,
"XENCCipherImpl::decryptElement - No key set
and cannot resolve");
}
@@ -384,7 +451,6 @@
// Get the Algorithm handler for the algorithm
XENCEncryptionMethod * encryptionMethod =
mp_encryptedData->getEncryptionMethod();
- XSECAlgorithmHandler *handler;
if (encryptionMethod != NULL) {
@@ -442,6 +508,181 @@
return mp_env->getParentDocument();
+}
+
+//
--------------------------------------------------------------------------------
+// Decrypt a key in an XENCEncryptedKey element
+//
--------------------------------------------------------------------------------
+
+int XENCCipherImpl::decryptKey(XENCEncryptedKey * encryptedKey, XMLByte *
rawKey, int maxKeySize) {
+
+ // Make sure we have a key before we do anything else too drastic
+ if (mp_kek == NULL) {
+
+ if (mp_keyInfoResolver != NULL)
+ mp_kek =
mp_keyInfoResolver->resolveKey(encryptedKey->getKeyInfoList());
+
+ if (mp_kek == NULL) {
+
+ throw XSECException(XSECException::CipherError,
+ "XENCCipherImpl::decryptKey - No KEK set and
cannot resolve");
+ }
+ }
+
+ // Get the raw encrypted data
+ TXFMChain * c = dynamic_cast<XENCEncryptedKeyImpl
*>(encryptedKey)->createCipherTXFMChain();
+ Janitor<TXFMChain> j_c(c);
+
+ // Get the Algorithm handler for the algorithm
+ XENCEncryptionMethod * encryptionMethod =
encryptedKey->getEncryptionMethod();
+ XSECAlgorithmHandler *handler;
+
+ if (encryptionMethod != NULL) {
+
+ handler =
+ XSECPlatformUtils::g_algorithmMapper->mapURIToHandler(
+
encryptedKey->getEncryptionMethod()->getAlgorithm());
+
+ }
+
+ else {
+
+ handler =
+ XSECPlatformUtils::g_algorithmMapper->mapURIToHandler(
+
XSECAlgorithmMapper::s_defaultEncryptionMapping);
+
+ }
+
+ safeBuffer sb("");
+ unsigned int keySize;
+
+ if (handler != NULL) {
+
+ keySize = handler->decryptToSafeBuffer(c,
+ encryptedKey->getEncryptionMethod(),
+ mp_kek,
+ mp_env->getParentDocument(),
+ sb);
+ }
+ else {
+
+ // Very strange if we get here - any problems should throw an
+ // exception in the AlgorithmMapper.
+
+ throw XSECException(XSECException::CipherError,
+ "XENCCipherImpl::decryptElement - Error retrieving a
handler for algorithm");
+
+ }
+
+ keySize = (keySize < maxKeySize ? keySize : maxKeySize);
+ memcpy(rawKey, sb.rawBuffer(), keySize);
+
+ return keySize;
+}
+
+//
--------------------------------------------------------------------------------
+// Encrypt a key
+//
--------------------------------------------------------------------------------
+
+XENCEncryptedKey * XENCCipherImpl::encryptKey(
+ const unsigned char * keyBuffer,
+ unsigned int keyLen,
+ encryptionMethod em,
+ const XMLCh * algorithmURI) {
+
+ if (mp_kek == NULL) {
+ throw XSECException(XSECException::CipherError,
+ "XENCCipherImpl::encryptKey - No KEK set");
+ }
+
+ // Map the encryption method to a URI
+ safeBuffer algorithmSB;
+ const XMLCh * algorithm;
+
+ if (em == ENCRYPT_NONE) {
+ algorithm = algorithmURI;
+ }
+ else {
+ if (encryptionMethod2URI(algorithmSB, em) != true) {
+ throw XSECException(XSECException::CipherError,
+ "XENCCipherImpl::encryptKey - Unknown
encryption method");
+ }
+ algorithm = algorithmSB.sbStrToXMLCh();
+ }
+
+ // Create the element with a dummy encrypted value
+
+ XENCEncryptedKeyImpl * encryptedKey;
+
+ XSECnew(encryptedKey, XENCEncryptedKeyImpl(mp_env));
+ Janitor<XENCEncryptedKeyImpl> j_encryptedKey(encryptedKey);
+
+ encryptedKey->createBlankEncryptedKey(
+ XENCCipherData::VALUE_TYPE,
+ algorithm,
+ s_noData);
+
+
+ // Create a transform chain to do pass the key to the encrypto
+
+ safeBuffer rawKey;
+ rawKey.isSensitive();
+ rawKey.sbMemcpyIn(keyBuffer, keyLen);
+
+ TXFMSB * tsb;
+ XSECnew(tsb, TXFMSB(mp_doc));
+
+ TXFMChain * c;
+ XSECnew(c, TXFMChain(tsb));
+ Janitor<TXFMChain> j_c(c);
+
+ tsb->setInput(rawKey, keyLen);
+
+ // Perform the encryption
+ XSECAlgorithmHandler *handler;
+
+ if (algorithm != NULL) {
+
+ handler =
+
XSECPlatformUtils::g_algorithmMapper->mapURIToHandler(algorithm);
+
+ }
+
+ else {
+
+ handler =
+ XSECPlatformUtils::g_algorithmMapper->mapURIToHandler(
+
XSECAlgorithmMapper::s_defaultEncryptionMapping);
+
+ }
+
+ safeBuffer sb;
+
+ if (handler != NULL) {
+
+ handler->encryptToSafeBuffer(c,
+ encryptedKey->getEncryptionMethod(),
+ mp_kek,
+ mp_env->getParentDocument(),
+ sb);
+ }
+ else {
+
+ // Very strange if we get here - any problems should throw an
+ // exception in the AlgorithmMapper.
+
+ throw XSECException(XSECException::CipherError,
+ "XENCCipherImpl::encryptKey - Error retrieving a
handler for algorithm");
+
+ }
+
+ // Set the value
+ XENCCipherValue * val = encryptedKey->getCipherData()->getCipherValue();
+
+ val->setCipherString(sb.sbStrToXMLCh());
+
+ j_encryptedKey.release();
+ return encryptedKey;
}
//
--------------------------------------------------------------------------------
1.7 +20 -2 xml-security/c/src/xenc/impl/XENCCipherImpl.hpp
Index: XENCCipherImpl.hpp
===================================================================
RCS file: /home/cvs/xml-security/c/src/xenc/impl/XENCCipherImpl.hpp,v
retrieving revision 1.6
retrieving revision 1.7
diff -u -r1.6 -r1.7
--- XENCCipherImpl.hpp 17 Sep 2003 10:10:22 -0000 1.6
+++ XENCCipherImpl.hpp 3 Oct 2003 09:50:05 -0000 1.7
@@ -96,12 +96,26 @@
XERCES_CPP_NAMESPACE_QUALIFIER DOMDocument *
decryptElement(XERCES_CPP_NAMESPACE_QUALIFIER DOMElement *
element);
+ // Decrypting Keys
+ virtual int decryptKey(XENCEncryptedKey * encryptedKey,
+ XMLByte * rawKey,
+ int maxKeySize);
+
// Implementation for encryption Elements
XERCES_CPP_NAMESPACE_QUALIFIER DOMDocument * encryptElement(
XERCES_CPP_NAMESPACE_QUALIFIER DOMElement * element,
encryptionMethod em,
const XMLCh * uri = NULL);
+ // Encrypt a key
+ virtual XENCEncryptedKey * encryptKey(
+ const unsigned char * keyBuffer,
+ unsigned int keyLen,
+ encryptionMethod em,
+ const XMLCh * algorithmURI = NULL
+ );
+
+
// Getter methods
XERCES_CPP_NAMESPACE_QUALIFIER DOMDocument * getDocument(void)
{return mp_doc;}
@@ -109,7 +123,8 @@
virtual XENCEncryptedData * getEncryptedData(void);
// Setter methods
- void setKey(XSECCryptoKey * key) {mp_key = key;}
+ void setKey(XSECCryptoKey * key);
+ void setKEK(XSECCryptoKey * key);
void setKeyInfoResolver(const XSECKeyInfoResolver * resolver);
void setXENCNSPrefix(const XMLCh * prefix);
@@ -149,6 +164,9 @@
// Key
XSECCryptoKey * mp_key;
+
+ // KEK
+ XSECCryptoKey * mp_kek;
// Environment
XSECEnv * mp_env;
1.6 +3 -1 xml-security/c/src/xenc/impl/XENCEncryptedDataImpl.hpp
Index: XENCEncryptedDataImpl.hpp
===================================================================
RCS file: /home/cvs/xml-security/c/src/xenc/impl/XENCEncryptedDataImpl.hpp,v
retrieving revision 1.5
retrieving revision 1.6
diff -u -r1.5 -r1.6
--- XENCEncryptedDataImpl.hpp 17 Sep 2003 10:10:22 -0000 1.5
+++ XENCEncryptedDataImpl.hpp 3 Oct 2003 09:50:05 -0000 1.6
@@ -114,6 +114,8 @@
{return XENCEncryptedTypeImpl::appendKeyName(name, isDName);}
virtual XERCES_CPP_NAMESPACE_QUALIFIER DOMNode * getDOMNode(void)
{return XENCEncryptedTypeImpl::getDOMNode();}
+ virtual void appendEncryptedKey(XENCEncryptedKey * encryptedKey)
+ {XENCEncryptedTypeImpl::appendEncryptedKey(encryptedKey);}
private:
1.6 +10 -1 xml-security/c/src/xenc/impl/XENCEncryptedTypeImpl.cpp
Index: XENCEncryptedTypeImpl.cpp
===================================================================
RCS file: /home/cvs/xml-security/c/src/xenc/impl/XENCEncryptedTypeImpl.cpp,v
retrieving revision 1.5
retrieving revision 1.6
diff -u -r1.5 -r1.6
--- XENCEncryptedTypeImpl.cpp 17 Sep 2003 10:10:22 -0000 1.5
+++ XENCEncryptedTypeImpl.cpp 3 Oct 2003 09:50:05 -0000 1.6
@@ -74,6 +74,8 @@
#include "XENCEncryptedTypeImpl.hpp"
#include "XENCEncryptionMethodImpl.hpp"
+#include <xsec/xenc/XENCEncryptedKey.hpp>
+
#include <xsec/framework/XSECError.hpp>
#include <xsec/utils/XSECDOMUtils.hpp>
#include <xsec/transformers/TXFMBase64.hpp>
@@ -423,5 +425,12 @@
createKeyInfoElement();
return m_keyInfoList.appendKeyName(name, isDName);
+
+}
+
+void XENCEncryptedTypeImpl::appendEncryptedKey(XENCEncryptedKey *
encryptedKey) {
+
+ createKeyInfoElement();
+ m_keyInfoList.addAndInsertKeyInfo(encryptedKey);
}
1.7 +3 -1 xml-security/c/src/xenc/impl/XENCEncryptedTypeImpl.hpp
Index: XENCEncryptedTypeImpl.hpp
===================================================================
RCS file: /home/cvs/xml-security/c/src/xenc/impl/XENCEncryptedTypeImpl.hpp,v
retrieving revision 1.6
retrieving revision 1.7
diff -u -r1.6 -r1.7
--- XENCEncryptedTypeImpl.hpp 17 Sep 2003 10:10:22 -0000 1.6
+++ XENCEncryptedTypeImpl.hpp 3 Oct 2003 09:50:05 -0000 1.7
@@ -117,6 +117,8 @@
virtual DSIGKeyInfoName * appendKeyName(const XMLCh * name, bool
isDName = false);
virtual XERCES_CPP_NAMESPACE_QUALIFIER DOMNode * getDOMNode(void)
{return mp_encryptedTypeNode;}
+ virtual void appendEncryptedKey(XENCEncryptedKey * encryptedKey);
+
protected: