More sample objects and macros.
authorScott Cantor <cantor.2@osu.edu>
Sun, 2 Apr 2006 02:57:54 +0000 (02:57 +0000)
committerScott Cantor <cantor.2@osu.edu>
Sun, 2 Apr 2006 02:57:54 +0000 (02:57 +0000)
doxyfile
xmltooling/XMLToolingConfig.cpp
xmltooling/base.h
xmltooling/signature/KeyInfo.h
xmltooling/signature/impl/KeyInfoImpl.cpp

index 070f613..f40463b 100644 (file)
--- a/doxyfile
+++ b/doxyfile
@@ -211,7 +211,8 @@ EXPAND_ONLY_PREDEF     = NO
 SEARCH_INCLUDES        = YES
 INCLUDE_PATH           = C:\cvs\cpp-xmltooling
 INCLUDE_FILE_PATTERNS  = 
-PREDEFINED             = _MSC_VER
+PREDEFINED             = _MSC_VER \
+                         DOXYGEN_SKIP
 EXPAND_AS_DEFINED      = 
 SKIP_FUNCTION_MACROS   = YES
 #---------------------------------------------------------------------------
index a9e51b7..5eb291b 100644 (file)
@@ -20,6 +20,8 @@
  * Library configuration 
  */
 
+#define XMLTOOLING_DECLARE_VALIDATORS
+
 #include "internal.h"
 #include "exceptions.h"
 #include "XMLToolingConfig.h"
@@ -168,11 +170,22 @@ bool XMLToolingInternalConfig::init()
         QName q;
         REGISTER_ELEMENT(XMLConstants::XMLSIG_NS,KeyInfo);
         REGISTER_ELEMENT(XMLConstants::XMLSIG_NS,KeyName);
+        REGISTER_ELEMENT(XMLConstants::XMLSIG_NS,KeyValue);
         REGISTER_ELEMENT(XMLConstants::XMLSIG_NS,MgmtData);
+        REGISTER_ELEMENT(XMLConstants::XMLSIG_NS,DSAKeyValue);
         REGISTER_ELEMENT(XMLConstants::XMLSIG_NS,RSAKeyValue);
         REGISTER_ELEMENT(XMLConstants::XMLSIG_NS,Exponent);
         REGISTER_ELEMENT(XMLConstants::XMLSIG_NS,Modulus);
+        REGISTER_ELEMENT(XMLConstants::XMLSIG_NS,P);
+        REGISTER_ELEMENT(XMLConstants::XMLSIG_NS,Q);
+        REGISTER_ELEMENT(XMLConstants::XMLSIG_NS,G);
+        REGISTER_ELEMENT(XMLConstants::XMLSIG_NS,Y);
+        REGISTER_ELEMENT(XMLConstants::XMLSIG_NS,J);
+        REGISTER_ELEMENT(XMLConstants::XMLSIG_NS,Seed);
+        REGISTER_ELEMENT(XMLConstants::XMLSIG_NS,PgenCounter);
         REGISTER_TYPE(XMLConstants::XMLSIG_NS,KeyInfo);
+        REGISTER_TYPE(XMLConstants::XMLSIG_NS,KeyValue);
+        REGISTER_TYPE(XMLConstants::XMLSIG_NS,DSAKeyValue);
         REGISTER_TYPE(XMLConstants::XMLSIG_NS,RSAKeyValue);
 
 #ifndef XMLTOOLING_NO_XMLSEC
index c3e780a..9809d52 100644 (file)
   #define XMLTOOL_EXCEPTIONAPI(api)
 #endif
 
-#ifndef NULL
-#define NULL    0
-#endif
-
 #ifdef _MSC_VER
     #define XMLTOOLING_DOXYGEN(desc) /##** desc */
 #else
         type(const type&); \
         type& operator=(const type&);
 
+#ifndef DOXYGEN_SKIP
+#ifndef NULL
+#define NULL    0
+#endif
 #define UNICODE_LITERAL_1(a) {chLatin_##a, chNull}
 #define UNICODE_LITERAL_2(a,b) {chLatin_##a, chLatin_##b, chNull}
 #define UNICODE_LITERAL_3(a,b,c) {chLatin_##a, chLatin_##b, chLatin_##c, chNull}
     {chLatin_##a, chLatin_##b, chLatin_##c, chLatin_##d, chLatin_##e, chLatin_##f, chLatin_##g, chLatin_##h, chLatin_##i, \
         chLatin_##j, chLatin_##k, chLatin_##l, chLatin_##m, chLatin_##n, chLatin_##o, chLatin_##p, chLatin_##q, chLatin_##r, \
         chLatin_##s, chLatin_##t, chLatin_##u, chLatin_##v, chLatin_##w, chLatin_##x, chLatin_##y, chLatin_##z, chNull}
+#endif /* DOXYGEN_SKIP */
 
 /**
  * Begins the declaration of an XMLObject specialization.
     }
 
 /**
+ * Declares an XMLObject specialization with a simple content model and type,
+ * handling it as string data.
+ * 
+ * @param linkage   linkage specifier for the class
+ * @param cname     the name of the XMLObject specialization
+ * @param proper    the proper name to label the element's content
+ */
+#define DECL_XMLOBJECT_SIMPLE(linkage,cname,proper,desc) \
+    XMLTOOLING_DOXYGEN(desc) \
+    BEGIN_XMLOBJECT(linkage,cname,XMLObject); \
+        DECL_XMLOBJECT_CONTENT(proper); \
+    END_XMLOBJECT
+
+/**
  * Declares and defines an implementation class for an XMLObject with
  * a simple content model and type, handling it as string data.
  * 
         throw ValidationException(#cname" must have "#proper".")
 
 /**
+ * Validator code that checks for one of a pair of
+ * required attributes, content, or singletons.
+ * 
+ * @param cname     the name of the XMLObject specialization
+ * @param proper1   the proper name of the first attribute, content, or singleton member 
+ * @param proper2   the proper name of the second attribute, content, or singleton member 
+ */
+#define XMLOBJECTVALIDATOR_ONEOF(cname,proper1,proper2) \
+    if (!ptr->get##proper1() && !ptr->get##proper2()) \
+        throw ValidationException(#cname" must have "#proper1" or "#proper2".")
+
+/**
+ * Validator code that checks for one of a set of three
+ * required attributes, content, or singletons.
+ * 
+ * @param cname     the name of the XMLObject specialization
+ * @param proper1   the proper name of the first attribute, content, or singleton member
+ * @param proper2   the proper name of the second attribute, content, or singleton member
+ * @param proper3   the proper name of the third attribute, content, or singleton member
+ */
+#define XMLOBJECTVALIDATOR_ONEOF3(cname,proper1,proper2,proper3) \
+    if (!ptr->get##proper1() && !ptr->get##proper2() && !ptr->get##proper3()) \
+        throw ValidationException(#cname" must have "#proper1", "#proper2", or "#proper3".")
+
+/**
+ * Validator code that checks a co-constraint (if one present, the other must be)
+ * between a pair of attributes, content, or singletons.
+ * 
+ * @param cname     the name of the XMLObject specialization
+ * @param proper1   the proper name of the first attribute, content, or singleton member 
+ * @param proper2   the proper name of the second attribute, content, or singleton member 
+ */
+#define XMLOBJECTVALIDATOR_NONEORBOTH(cname,proper1,proper2) \
+    if ((ptr->get##proper1() && !ptr->get##proper2()) || (!ptr->get##proper1() && ptr->get##proper2())) \
+        throw ValidationException(#cname" cannot have "#proper1" without "#proper2".")
+
+/**
  * Validator code that checks for a non-empty collection.
  * 
  * @param cname     the name of the XMLObject specialization
  * @param proper    the proper name of the collection item 
  */
-#define XMLOBJECTVALIDATOR_CHECKEMPTY(cname,proper) \
+#define XMLOBJECTVALIDATOR_NONEMPTY(cname,proper) \
     if (ptr->get##proper##s().empty()) \
         throw ValidationException(#cname" must have at least one "#proper".")
 
+/**
+ * Declares/defines a Validator specialization that checks object type and
+ * a non-empty simple content model.
+ * 
+ * @param linkage   linkage specifier for the class
+ * @param cname     the name of the XMLObject specialization
+ * @param proper    the proper name to label the element's content
+ */
+#define XMLOBJECTVALIDATOR_SIMPLE(linkage,cname,proper) \
+    BEGIN_XMLOBJECTVALIDATOR(linkage,cname); \
+        XMLOBJECTVALIDATOR_REQUIRE(cname,proper); \
+    END_XMLOBJECTVALIDATOR
+
 #include <utility>
 
 namespace xmltooling {
index 50e82cc..786c792 100644 (file)
 
 namespace xmltooling {
 
-    /**
-     * XMLObject representing XML Digital Signature, version 20020212, KeyName element.
-     */
-    BEGIN_XMLOBJECT(XMLTOOL_API,KeyName,XMLObject);
-        DECL_XMLOBJECT_CONTENT(Name);
-    END_XMLOBJECT;
-
-    /**
-     * XMLObject representing XML Digital Signature, version 20020212, MgmtData element.
-     */
-    BEGIN_XMLOBJECT(XMLTOOL_API,MgmtData,XMLObject);
-        DECL_XMLOBJECT_CONTENT(Data);
-    END_XMLOBJECT;
+    DECL_XMLOBJECT_SIMPLE(XMLTOOL_API,KeyName,Name,XML Digital Signature version 20020212 KeyName element);
+    DECL_XMLOBJECT_SIMPLE(XMLTOOL_API,MgmtData,Data,XML Digital Signature version 20020212 MgmtData element);
+    DECL_XMLOBJECT_SIMPLE(XMLTOOL_API,Modulus,Value,XML Digital Signature version 20020212 Modulus element);
+    DECL_XMLOBJECT_SIMPLE(XMLTOOL_API,Exponent,Value,XML Digital Signature version 20020212 Exponent element);
+    DECL_XMLOBJECT_SIMPLE(XMLTOOL_API,Seed,Value,XML Digital Signature version 20020212 Seed element);
+    DECL_XMLOBJECT_SIMPLE(XMLTOOL_API,PgenCounter,Value,XML Digital Signature version 20020212 PgenCounter element);
+    DECL_XMLOBJECT_SIMPLE(XMLTOOL_API,P,Value,XML Digital Signature version 20020212 P element);
+    DECL_XMLOBJECT_SIMPLE(XMLTOOL_API,Q,Value,XML Digital Signature version 20020212 Q element);
+    DECL_XMLOBJECT_SIMPLE(XMLTOOL_API,G,Value,XML Digital Signature version 20020212 G element);
+    DECL_XMLOBJECT_SIMPLE(XMLTOOL_API,Y,Value,XML Digital Signature version 20020212 Y element);
+    DECL_XMLOBJECT_SIMPLE(XMLTOOL_API,J,Value,XML Digital Signature version 20020212 J element);
 
     /**
-     * XMLObject representing XML Digital Signature, version 20020212, Modulus element.
+     * XML Digital Signature version 20020212 DSAKeyValue element.
      */
-    BEGIN_XMLOBJECT(XMLTOOL_API,Modulus,XMLObject);
-        DECL_XMLOBJECT_CONTENT(Value);
-    END_XMLOBJECT;
-
-    /**
-     * XMLObject representing XML Digital Signature, version 20020212, Exponent element.
-     */
-    BEGIN_XMLOBJECT(XMLTOOL_API,Exponent,XMLObject);
-        DECL_XMLOBJECT_CONTENT(Value);
+    BEGIN_XMLOBJECT(XMLTOOL_API,DSAKeyValue,XMLObject);
+        DECL_XMLOBJECT_CHILD(P);
+        DECL_XMLOBJECT_CHILD(Q);
+        DECL_XMLOBJECT_CHILD(G);
+        DECL_XMLOBJECT_CHILD(Y);
+        DECL_XMLOBJECT_CHILD(J);
+        DECL_XMLOBJECT_CHILD(Seed);
+        DECL_XMLOBJECT_CHILD(PgenCounter);
+        /** DSAKeyValueType local name */
+        static const XMLCh TYPE_NAME[];
     END_XMLOBJECT;
 
     /**
-     * XMLObject representing XML Digital Signature, version 20020212, RSAKeyValue element.
+     * XML Digital Signature version 20020212 RSAKeyValue element.
      */
     BEGIN_XMLOBJECT(XMLTOOL_API,RSAKeyValue,XMLObject);
         DECL_XMLOBJECT_CHILD(Modulus);
@@ -76,7 +75,19 @@ namespace xmltooling {
     END_XMLOBJECT;
 
     /**
-     * XMLObject representing XML Digital Signature, version 20020212, KeyInfo element.
+     * XML Digital Signature version 20020212 KeyValue element.
+     */
+    BEGIN_XMLOBJECT(XMLTOOL_API,KeyValue,XMLObject);
+        DECL_XMLOBJECT_CHILD(DSAKeyValue);
+        DECL_XMLOBJECT_CHILD(RSAKeyValue);
+        DECL_XMLOBJECT_CHILD(XMLObject);
+        DECL_XMLOBJECT_CONTENT(TextContent);
+        /** KeyValueType local name */
+        static const XMLCh TYPE_NAME[];
+    END_XMLOBJECT;
+
+    /**
+     * XML Digital Signature version 20020212 KeyInfo element.
      */
     BEGIN_XMLOBJECT(XMLTOOL_API,KeyInfo,ElementProxy);
         DECL_XMLOBJECT_ATTRIB(Id,ID);
@@ -90,33 +101,50 @@ namespace xmltooling {
     DECL_XMLSIGOBJECTBUILDER(MgmtData);
     DECL_XMLSIGOBJECTBUILDER(Modulus);
     DECL_XMLSIGOBJECTBUILDER(Exponent);
+    DECL_XMLSIGOBJECTBUILDER(Seed);
+    DECL_XMLSIGOBJECTBUILDER(PgenCounter);
+    DECL_XMLSIGOBJECTBUILDER(P);
+    DECL_XMLSIGOBJECTBUILDER(Q);
+    DECL_XMLSIGOBJECTBUILDER(G);
+    DECL_XMLSIGOBJECTBUILDER(Y);
+    DECL_XMLSIGOBJECTBUILDER(J);
+    DECL_XMLSIGOBJECTBUILDER(DSAKeyValue);
     DECL_XMLSIGOBJECTBUILDER(RSAKeyValue);
+    DECL_XMLSIGOBJECTBUILDER(KeyValue);
     DECL_XMLSIGOBJECTBUILDER(KeyInfo);
-    
-    BEGIN_XMLOBJECTVALIDATOR(XMLTOOL_DLLLOCAL,KeyName);
-        XMLOBJECTVALIDATOR_REQUIRE(KeyName,Name);
-    END_XMLOBJECTVALIDATOR;
-    
-    BEGIN_XMLOBJECTVALIDATOR(XMLTOOL_DLLLOCAL,MgmtData);
-        XMLOBJECTVALIDATOR_REQUIRE(MgmtData,Data);
-    END_XMLOBJECTVALIDATOR;
 
-    BEGIN_XMLOBJECTVALIDATOR(XMLTOOL_DLLLOCAL,Modulus);
-        XMLOBJECTVALIDATOR_REQUIRE(Modulus,Value);
-    END_XMLOBJECTVALIDATOR;
-
-    BEGIN_XMLOBJECTVALIDATOR(XMLTOOL_DLLLOCAL,Exponent);
-        XMLOBJECTVALIDATOR_REQUIRE(Exponent,Value);
-    END_XMLOBJECTVALIDATOR;
+#ifdef XMLTOOLING_DECLARE_VALIDATORS
+    XMLOBJECTVALIDATOR_SIMPLE(XMLTOOL_DLLLOCAL,KeyName,Name);
+    XMLOBJECTVALIDATOR_SIMPLE(XMLTOOL_DLLLOCAL,MgmtData,Data);
+    XMLOBJECTVALIDATOR_SIMPLE(XMLTOOL_DLLLOCAL,Modulus,Value);
+    XMLOBJECTVALIDATOR_SIMPLE(XMLTOOL_DLLLOCAL,Exponent,Value);
+    XMLOBJECTVALIDATOR_SIMPLE(XMLTOOL_DLLLOCAL,Seed,Value);
+    XMLOBJECTVALIDATOR_SIMPLE(XMLTOOL_DLLLOCAL,PgenCounter,Value);
+    XMLOBJECTVALIDATOR_SIMPLE(XMLTOOL_DLLLOCAL,P,Value);
+    XMLOBJECTVALIDATOR_SIMPLE(XMLTOOL_DLLLOCAL,Q,Value);
+    XMLOBJECTVALIDATOR_SIMPLE(XMLTOOL_DLLLOCAL,G,Value);
+    XMLOBJECTVALIDATOR_SIMPLE(XMLTOOL_DLLLOCAL,Y,Value);
+    XMLOBJECTVALIDATOR_SIMPLE(XMLTOOL_DLLLOCAL,J,Value);
 
     BEGIN_XMLOBJECTVALIDATOR(XMLTOOL_DLLLOCAL,RSAKeyValue);
         XMLOBJECTVALIDATOR_REQUIRE(RSAKeyValue,Modulus);
         XMLOBJECTVALIDATOR_REQUIRE(RSAKeyValue,Exponent);
     END_XMLOBJECTVALIDATOR;
 
+    BEGIN_XMLOBJECTVALIDATOR(XMLTOOL_DLLLOCAL,DSAKeyValue);
+        XMLOBJECTVALIDATOR_REQUIRE(DSAKeyValue,Y);
+        XMLOBJECTVALIDATOR_NONEORBOTH(DSKeyValue,P,Q);
+        XMLOBJECTVALIDATOR_NONEORBOTH(DSKeyValue,Seed,PgenCounter);
+    END_XMLOBJECTVALIDATOR;
+
+    BEGIN_XMLOBJECTVALIDATOR(XMLTOOL_DLLLOCAL,KeyValue);
+        XMLOBJECTVALIDATOR_ONEOF3(KeyValue,DSAKeyValue,RSAKeyValue,XMLObject);
+    END_XMLOBJECTVALIDATOR;
+
     BEGIN_XMLOBJECTVALIDATOR(XMLTOOL_DLLLOCAL,KeyInfo);
-        XMLOBJECTVALIDATOR_CHECKEMPTY(KeyInfo,XMLObject);
+        XMLOBJECTVALIDATOR_NONEMPTY(KeyInfo,XMLObject);
     END_XMLOBJECTVALIDATOR;
+#endif /* XMLTOOLING_DECLARE_VALIDATORS */
 
 };
 
index 8773b04..ee095f6 100644 (file)
@@ -15,9 +15,9 @@
  */
 
 /**
- * XMLSecSignatureImpl.cpp
+ * KeyInfoImpl.cpp
  * 
- * Signature class for XMLSec-based signature-handling
+ * Implementation classes for KeyInfo schema
  */
 
 #include "internal.h"
@@ -41,25 +41,100 @@ using namespace std;
 
 namespace xmltooling {
     
-    class XMLTOOL_DLLLOCAL RSAKeyValueImpl
-        : public RSAKeyValue,
-            public AbstractDOMCachingXMLObject,
-            public AbstractValidatingXMLObject,
-            public AbstractXMLObjectMarshaller,
-            public AbstractXMLObjectUnmarshaller
+    class XMLTOOL_DLLLOCAL DSAKeyValueImpl : public DSAKeyValue,
+        public AbstractDOMCachingXMLObject,
+        public AbstractValidatingXMLObject,
+        public AbstractXMLObjectMarshaller,
+        public AbstractXMLObjectUnmarshaller
+    {
+    public:
+        virtual ~DSAKeyValueImpl() {}
+
+        DSAKeyValueImpl(const XMLCh* nsURI, const XMLCh* localName, const XMLCh* prefix, const QName* schemaType)
+            : AbstractXMLObject(nsURI, localName, prefix, schemaType) {
+            init();
+        }
+            
+        DSAKeyValueImpl(const DSAKeyValueImpl& src)
+                : AbstractXMLObject(src), AbstractDOMCachingXMLObject(src), AbstractValidatingXMLObject(src) {
+            init();
+            setP(src.getP());
+            setQ(src.getQ());
+            setG(src.getG());
+            setY(src.getY());
+            setJ(src.getJ());
+            setSeed(src.getSeed());
+            setPgenCounter(src.getPgenCounter());
+        }
+        
+        void init() {
+            m_P=NULL;
+            m_Q=NULL;
+            m_G=NULL;
+            m_Y=NULL;
+            m_J=NULL;
+            m_Seed=NULL;
+            m_PgenCounter=NULL;
+            m_children.push_back(NULL);
+            m_children.push_back(NULL);
+            m_children.push_back(NULL);
+            m_children.push_back(NULL);
+            m_children.push_back(NULL);
+            m_children.push_back(NULL);
+            m_children.push_back(NULL);
+            m_pos_P=m_children.begin();
+            m_pos_Q=m_pos_P;
+            ++m_pos_Q;
+            m_pos_G=m_pos_Q;
+            ++m_pos_G;
+            m_pos_Y=m_pos_G;
+            ++m_pos_Y;
+            m_pos_J=m_pos_Y;
+            ++m_pos_J;
+            m_pos_Seed=m_pos_J;
+            ++m_pos_Seed;
+            m_pos_PgenCounter=m_pos_Seed;
+            ++m_pos_PgenCounter;
+        }
+        
+        IMPL_XMLOBJECT_CLONE(DSAKeyValue);
+        IMPL_XMLOBJECT_CHILD(P);
+        IMPL_XMLOBJECT_CHILD(Q);
+        IMPL_XMLOBJECT_CHILD(G);
+        IMPL_XMLOBJECT_CHILD(Y);
+        IMPL_XMLOBJECT_CHILD(J);
+        IMPL_XMLOBJECT_CHILD(Seed);
+        IMPL_XMLOBJECT_CHILD(PgenCounter);
+
+    protected:
+        void processChildElement(XMLObject* childXMLObject, const DOMElement* root) {
+            PROC_XMLOBJECT_CHILD(P,XMLConstants::XMLSIG_NS);
+            PROC_XMLOBJECT_CHILD(Q,XMLConstants::XMLSIG_NS);
+            PROC_XMLOBJECT_CHILD(G,XMLConstants::XMLSIG_NS);
+            PROC_XMLOBJECT_CHILD(Y,XMLConstants::XMLSIG_NS);
+            PROC_XMLOBJECT_CHILD(J,XMLConstants::XMLSIG_NS);
+            PROC_XMLOBJECT_CHILD(Seed,XMLConstants::XMLSIG_NS);
+            PROC_XMLOBJECT_CHILD(PgenCounter,XMLConstants::XMLSIG_NS);
+            throw UnmarshallingException("Invalid child element: $1",params(1,childXMLObject->getElementQName().toString().c_str()));
+        }
+    };
+
+    class XMLTOOL_DLLLOCAL RSAKeyValueImpl : public RSAKeyValue,
+        public AbstractDOMCachingXMLObject,
+        public AbstractValidatingXMLObject,
+        public AbstractXMLObjectMarshaller,
+        public AbstractXMLObjectUnmarshaller
     {
     public:
         virtual ~RSAKeyValueImpl() {}
 
         RSAKeyValueImpl(const XMLCh* nsURI, const XMLCh* localName, const XMLCh* prefix, const QName* schemaType)
-            : AbstractXMLObject(nsURI, localName, prefix, schemaType) {
+                : AbstractXMLObject(nsURI, localName, prefix, schemaType) {
             init();
         }
             
         RSAKeyValueImpl(const RSAKeyValueImpl& src)
-            : AbstractXMLObject(src),
-                AbstractDOMCachingXMLObject(src),
-                AbstractValidatingXMLObject(src) {
+                : AbstractXMLObject(src), AbstractDOMCachingXMLObject(src), AbstractValidatingXMLObject(src) {
             init();
             setModulus(src.getModulus());
             setExponent(src.getExponent());
@@ -71,8 +146,8 @@ namespace xmltooling {
             m_children.push_back(NULL);
             m_children.push_back(NULL);
             m_pos_Modulus=m_children.begin();
-            m_pos_Exponent=m_children.begin();
-            m_pos_Exponent++;
+            m_pos_Exponent=m_pos_Modulus;
+            ++m_pos_Exponent;
         }
         
         IMPL_XMLOBJECT_CLONE(RSAKeyValue);
@@ -83,18 +158,74 @@ namespace xmltooling {
         void processChildElement(XMLObject* childXMLObject, const DOMElement* root) {
             PROC_XMLOBJECT_CHILD(Modulus,XMLConstants::XMLSIG_NS);
             PROC_XMLOBJECT_CHILD(Exponent,XMLConstants::XMLSIG_NS);
+            throw UnmarshallingException("Invalid child element: $1",params(1,childXMLObject->getElementQName().toString().c_str()));
+        }
+    };
+
+    class XMLTOOL_DLLLOCAL KeyValueImpl : public KeyValue,
+        public AbstractDOMCachingXMLObject,
+        public AbstractValidatingXMLObject,
+        public AbstractXMLObjectMarshaller,
+        public AbstractXMLObjectUnmarshaller
+    {
+    public:
+        virtual ~KeyValueImpl() {}
+
+        KeyValueImpl(const XMLCh* nsURI, const XMLCh* localName, const XMLCh* prefix, const QName* schemaType)
+                : AbstractXMLObject(nsURI, localName, prefix, schemaType) {
+            init();
+        }
+            
+        KeyValueImpl(const KeyValueImpl& src)
+                : AbstractXMLObject(src), AbstractDOMCachingXMLObject(src), AbstractValidatingXMLObject(src) {
+            init();
+            setDSAKeyValue(src.getDSAKeyValue());
+            setRSAKeyValue(src.getRSAKeyValue());
+            setXMLObject(src.getXMLObject());
+            setTextContent(src.getTextContent());
+        }
+        
+        void init() {
+            m_TextContent=NULL;
+            m_DSAKeyValue=NULL;
+            m_RSAKeyValue=NULL;
+            m_XMLObject=NULL;
+            m_children.push_back(NULL);
+            m_children.push_back(NULL);
+            m_children.push_back(NULL);
+            m_pos_DSAKeyValue=m_children.begin();
+            m_pos_RSAKeyValue=m_pos_DSAKeyValue;
+            ++m_pos_RSAKeyValue;
+            m_pos_XMLObject=m_pos_RSAKeyValue;
+            ++m_pos_XMLObject;
+        }
+        
+        IMPL_XMLOBJECT_CLONE(KeyValue);
+        IMPL_XMLOBJECT_CHILD(DSAKeyValue);
+        IMPL_XMLOBJECT_CHILD(RSAKeyValue);
+        IMPL_XMLOBJECT_CHILD(XMLObject);
+        IMPL_XMLOBJECT_CONTENT(TextContent);
+
+    protected:
+        void processChildElement(XMLObject* childXMLObject, const DOMElement* root) {
+            PROC_XMLOBJECT_CHILD(DSAKeyValue,XMLConstants::XMLSIG_NS);
+            PROC_XMLOBJECT_CHILD(RSAKeyValue,XMLConstants::XMLSIG_NS);
+            
+            // Unknown child.
+            const XMLCh* nsURI=root->getNamespaceURI();
+            if (!XMLString::equals(nsURI,XMLConstants::XMLSIG_NS) && nsURI && *nsURI)
+                setXMLObject(childXMLObject);
             
             throw UnmarshallingException("Invalid child element: $1",params(1,childXMLObject->getElementQName().toString().c_str()));
         }
     };
     
-    class XMLTOOL_DLLLOCAL KeyInfoImpl
-        : public KeyInfo,
-            public AbstractDOMCachingXMLObject,
-            public AbstractElementProxy,
-            public AbstractValidatingXMLObject,
-            public AbstractXMLObjectMarshaller,
-            public AbstractXMLObjectUnmarshaller
+    class XMLTOOL_DLLLOCAL KeyInfoImpl : public KeyInfo,
+        public AbstractDOMCachingXMLObject,
+        public AbstractElementProxy,
+        public AbstractValidatingXMLObject,
+        public AbstractXMLObjectMarshaller,
+        public AbstractXMLObjectUnmarshaller
     {
     public:
         virtual ~KeyInfoImpl() {}
@@ -104,12 +235,8 @@ namespace xmltooling {
         }
             
         KeyInfoImpl(const KeyInfoImpl& src)
-            : AbstractXMLObject(src),
-                AbstractDOMCachingXMLObject(src),
-                AbstractElementProxy(src),
-                AbstractValidatingXMLObject(src),
-                m_Id(XMLString::replicate(src.m_Id)) {
-                    
+                : AbstractXMLObject(src), AbstractDOMCachingXMLObject(src), AbstractElementProxy(src),
+                    AbstractValidatingXMLObject(src), m_Id(XMLString::replicate(src.m_Id)) {
             for (list<XMLObject*>::const_iterator i=src.m_children.begin(); i!=src.m_children.end(); i++) {
                 if (*i) {
                     KeyName* kn=dynamic_cast<KeyName*>(*i);
@@ -117,6 +244,11 @@ namespace xmltooling {
                         getKeyNames().push_back(kn->cloneKeyName());
                         continue;
                     }
+                    KeyValue* kv=dynamic_cast<KeyValue*>(*i);
+                    if (kv) {
+                        getKeyValues().push_back(kv->cloneKeyValue());
+                        continue;
+                    }
                     MgmtData* md=dynamic_cast<MgmtData*>(*i);
                     if (md) {
                         getMgmtDatas().push_back(md->cloneMgmtData());
@@ -130,6 +262,7 @@ namespace xmltooling {
         IMPL_XMLOBJECT_CLONE(KeyInfo);
         IMPL_XMLOBJECT_ATTRIB(Id);
         IMPL_XMLOBJECT_CHILDREN(KeyName,m_children.end());
+        IMPL_XMLOBJECT_CHILDREN(KeyValue,m_children.end());
         IMPL_XMLOBJECT_CHILDREN(MgmtData,m_children.end());
 
     protected:
@@ -152,10 +285,11 @@ namespace xmltooling {
 
         void processChildElement(XMLObject* childXMLObject, const DOMElement* root) {
             PROC_XMLOBJECT_CHILDREN(KeyName,XMLConstants::XMLSIG_NS);
+            PROC_XMLOBJECT_CHILDREN(KeyValue,XMLConstants::XMLSIG_NS);
             PROC_XMLOBJECT_CHILDREN(MgmtData,XMLConstants::XMLSIG_NS);
             
             // Unknown child.
-            const XMLCh* nsURI=childXMLObject->getElementQName().getNamespaceURI();
+            const XMLCh* nsURI=root->getNamespaceURI();
             if (!XMLString::equals(nsURI,XMLConstants::XMLSIG_NS) && nsURI && *nsURI)
                 getXMLObjects().push_back(childXMLObject);
             
@@ -174,6 +308,13 @@ namespace xmltooling {
     DECL_XMLOBJECTIMPL_SIMPLE(XMLTOOL_DLLLOCAL,MgmtData,Data);
     DECL_XMLOBJECTIMPL_SIMPLE(XMLTOOL_DLLLOCAL,Modulus,Value);
     DECL_XMLOBJECTIMPL_SIMPLE(XMLTOOL_DLLLOCAL,Exponent,Value);
+    DECL_XMLOBJECTIMPL_SIMPLE(XMLTOOL_DLLLOCAL,Seed,Value);
+    DECL_XMLOBJECTIMPL_SIMPLE(XMLTOOL_DLLLOCAL,PgenCounter,Value);
+    DECL_XMLOBJECTIMPL_SIMPLE(XMLTOOL_DLLLOCAL,P,Value);
+    DECL_XMLOBJECTIMPL_SIMPLE(XMLTOOL_DLLLOCAL,Q,Value);
+    DECL_XMLOBJECTIMPL_SIMPLE(XMLTOOL_DLLLOCAL,G,Value);
+    DECL_XMLOBJECTIMPL_SIMPLE(XMLTOOL_DLLLOCAL,Y,Value);
+    DECL_XMLOBJECTIMPL_SIMPLE(XMLTOOL_DLLLOCAL,J,Value);
 };
 
 #if defined (_MSC_VER)
@@ -182,19 +323,39 @@ namespace xmltooling {
 
 // Builder Implementations
 
-IMPL_XMLOBJECTBUILDER(KeyInfo);
 IMPL_XMLOBJECTBUILDER(KeyName);
 IMPL_XMLOBJECTBUILDER(MgmtData);
 IMPL_XMLOBJECTBUILDER(Modulus);
 IMPL_XMLOBJECTBUILDER(Exponent);
+IMPL_XMLOBJECTBUILDER(Seed);
+IMPL_XMLOBJECTBUILDER(PgenCounter);
+IMPL_XMLOBJECTBUILDER(P);
+IMPL_XMLOBJECTBUILDER(Q);
+IMPL_XMLOBJECTBUILDER(G);
+IMPL_XMLOBJECTBUILDER(Y);
+IMPL_XMLOBJECTBUILDER(J);
+IMPL_XMLOBJECTBUILDER(DSAKeyValue);
 IMPL_XMLOBJECTBUILDER(RSAKeyValue);
+IMPL_XMLOBJECTBUILDER(KeyValue);
+IMPL_XMLOBJECTBUILDER(KeyInfo);
 
 const XMLCh KeyInfo::LOCAL_NAME[] =         UNICODE_LITERAL_7(K,e,y,I,n,f,o);
 const XMLCh KeyInfo::TYPE_NAME[] =          UNICODE_LITERAL_11(K,e,y,I,n,f,o,T,y,p,e);
 const XMLCh KeyInfo::ID_ATTRIB_NAME[] =     UNICODE_LITERAL_2(I,d);
+const XMLCh KeyValue::LOCAL_NAME[] =        UNICODE_LITERAL_8(K,e,y,V,a,l,u,e);
+const XMLCh KeyValue::TYPE_NAME[] =         UNICODE_LITERAL_12(K,e,y,V,a,l,u,e,T,y,p,e);
+const XMLCh DSAKeyValue::LOCAL_NAME[] =     UNICODE_LITERAL_11(D,S,A,K,e,y,V,a,l,u,e);
+const XMLCh DSAKeyValue::TYPE_NAME[] =      UNICODE_LITERAL_15(D,S,A,K,e,y,V,a,l,u,e,T,y,p,e);
+const XMLCh RSAKeyValue::LOCAL_NAME[] =     UNICODE_LITERAL_11(R,S,A,K,e,y,V,a,l,u,e);
+const XMLCh RSAKeyValue::TYPE_NAME[] =      UNICODE_LITERAL_15(R,S,A,K,e,y,V,a,l,u,e,T,y,p,e);
 const XMLCh MgmtData::LOCAL_NAME[] =        UNICODE_LITERAL_8(M,g,m,t,D,a,t,a);
 const XMLCh KeyName::LOCAL_NAME[] =         UNICODE_LITERAL_7(K,e,y,N,a,m,e);
 const XMLCh Modulus::LOCAL_NAME[] =         UNICODE_LITERAL_7(M,o,d,u,l,u,s);
 const XMLCh Exponent::LOCAL_NAME[] =        UNICODE_LITERAL_8(E,x,p,o,n,e,n,t);
-const XMLCh RSAKeyValue::LOCAL_NAME[] =     UNICODE_LITERAL_11(R,S,A,K,e,y,V,a,l,u,e);
-const XMLCh RSAKeyValue::TYPE_NAME[] =      UNICODE_LITERAL_15(R,S,A,K,e,y,V,a,l,u,e,T,y,p,e);
+const XMLCh Seed::LOCAL_NAME[] =            UNICODE_LITERAL_4(S,e,e,d);
+const XMLCh PgenCounter::LOCAL_NAME[] =     UNICODE_LITERAL_11(P,g,e,n,C,o,u,n,t,e,r);
+const XMLCh P::LOCAL_NAME[] =               UNICODE_LITERAL_1(P);
+const XMLCh Q::LOCAL_NAME[] =               UNICODE_LITERAL_1(Q);
+const XMLCh G::LOCAL_NAME[] =               UNICODE_LITERAL_1(G);
+const XMLCh Y::LOCAL_NAME[] =               UNICODE_LITERAL_1(Y);
+const XMLCh J::LOCAL_NAME[] =               UNICODE_LITERAL_1(J);