Esempio n. 1
0
        /// <summary>
        /// Reads XML conforming to https://www.w3.org/TR/2001/PR-xmldsig-core-20010820/#sec-KeyInfo
        /// </summary>
        /// <param name="reader"><see cref="XmlReader"/> pointing positioned on a &lt;KeyInfo> element.</param>
        /// <exception cref="ArgumentNullException">if <paramref name="reader"/> is null.</exception>
        /// <exception cref="XmlReadException">if there is a problem reading the XML.</exception>
        /// <remarks>Only handles IssuerSerial, Ski, SubjectName, Certificate. Unsupported types are skipped. Only a X509 data element is supported.</remarks>
        public virtual KeyInfo ReadKeyInfo(XmlReader reader)
        {
            XmlUtil.CheckReaderOnEntry(reader, XmlSignatureConstants.Elements.KeyInfo, XmlSignatureConstants.Namespace);

            var keyInfo = new KeyInfo
            {
                Prefix = reader.Prefix
            };

            try
            {
                bool isEmptyElement = reader.IsEmptyElement;

                // <KeyInfo>
                reader.ReadStartElement();
                while (reader.IsStartElement())
                {
                    // <X509Data>
                    if (reader.IsStartElement(XmlSignatureConstants.Elements.X509Data, XmlSignatureConstants.Namespace))
                    {
                        keyInfo.X509Data.Add(ReadX509Data(reader));
                    }
                    // <RetrievalMethod>
                    else if (reader.IsStartElement(XmlSignatureConstants.Elements.RetrievalMethod, XmlSignatureConstants.Namespace))
                    {
                        keyInfo.RetrievalMethodUri = reader.GetAttribute(XmlSignatureConstants.Attributes.URI);
                        reader.ReadOuterXml();
                    }
                    // <KeyName>
                    else if (reader.IsStartElement(XmlSignatureConstants.Elements.KeyName, XmlSignatureConstants.Namespace))
                    {
                        keyInfo.KeyName = reader.ReadElementContentAsString(XmlSignatureConstants.Elements.KeyName, XmlSignatureConstants.Namespace);
                    }
                    // <KeyValue>
                    else if (reader.IsStartElement(XmlSignatureConstants.Elements.KeyValue, XmlSignatureConstants.Namespace))
                    {
                        reader.ReadStartElement(XmlSignatureConstants.Elements.KeyValue, XmlSignatureConstants.Namespace);
                        if (reader.IsStartElement(XmlSignatureConstants.Elements.RSAKeyValue, XmlSignatureConstants.Namespace))
                        {
                            // Multiple RSAKeyValues were found
                            if (keyInfo.RSAKeyValue != null)
                            {
                                throw XmlUtil.LogReadException(LogMessages.IDX30015, XmlSignatureConstants.Elements.RSAKeyValue);
                            }

                            keyInfo.RSAKeyValue = ReadRSAKeyValue(reader);
                        }
                        else
                        {
                            // Skip the element since it is not an <RSAKeyValue>
                            LogHelper.LogWarning(LogMessages.IDX30300, reader.ReadOuterXml());
                        }

                        // </KeyValue>
                        reader.ReadEndElement();
                    }
                    else
                    {
                        // Skip the element since it is not one of  <RetrievalMethod>, <X509Data>, <KeyValue>
                        LogHelper.LogWarning(LogMessages.IDX30300, reader.ReadOuterXml());
                    }
                }

                // </KeyInfo>
                if (!isEmptyElement)
                {
                    reader.ReadEndElement();
                }
            }
            catch (Exception ex)
            {
                if (ex is XmlReadException)
                {
                    throw;
                }

                throw XmlUtil.LogReadException(LogMessages.IDX30017, ex, XmlSignatureConstants.Elements.KeyInfo, ex);
            }

            return(keyInfo);
        }
Esempio n. 2
0
        /// <summary>
        /// Writes the contents of a <see cref="KeyInfo"/> as XML conforming to https://www.w3.org/TR/2001/PR-xmldsig-core-20010820/#sec-KeyInfo.
        /// </summary>
        /// <param name="writer">the <see cref="XmlWriter"/> to use.</param>
        /// <param name="keyInfo">the <see cref="KeyInfo"/>to write.</param>
        /// <exception cref="ArgumentNullException">if <paramref name="writer"/> is null.</exception>
        /// <exception cref="ArgumentNullException">if <paramref name="keyInfo"/> is null.</exception>
        /// <exception cref="XmlWriteException">if there is a problem writing the XML.</exception>
        public virtual void WriteKeyInfo(XmlWriter writer, KeyInfo keyInfo)
        {
            if (writer == null)
            {
                throw LogArgumentNullException(nameof(writer));
            }

            if (keyInfo == null)
            {
                throw LogArgumentNullException(nameof(keyInfo));
            }

            // <KeyInfo>
            writer.WriteStartElement(XmlSignatureConstants.Elements.KeyInfo, XmlSignatureConstants.Namespace);

            if (keyInfo.KeyName != null)
            {
                writer.WriteElementString(Prefix, XmlSignatureConstants.Elements.KeyName, XmlSignatureConstants.Namespace, keyInfo.KeyName);
            }

            if (keyInfo.RSAKeyValue != null)
            {
                // <KeyValue>
                writer.WriteStartElement(Prefix, XmlSignatureConstants.Elements.KeyValue, XmlSignatureConstants.Namespace);

                // <RSAKeyValue>
                writer.WriteStartElement(Prefix, XmlSignatureConstants.Elements.RSAKeyValue, XmlSignatureConstants.Namespace);

                // <Modulus>...</Modulus>
                writer.WriteElementString(Prefix, XmlSignatureConstants.Elements.Modulus, XmlSignatureConstants.Namespace, keyInfo.RSAKeyValue.Modulus);

                // <Exponent>...</Exponent>
                writer.WriteElementString(Prefix, XmlSignatureConstants.Elements.Exponent, XmlSignatureConstants.Namespace, keyInfo.RSAKeyValue.Exponent);

                // </RSAKeyValue>
                writer.WriteEndElement();

                // </KeyValue>
                writer.WriteEndElement();
            }

            if (keyInfo.RetrievalMethodUri != null)
            {
                writer.WriteStartElement(keyInfo.Prefix, XmlSignatureConstants.Elements.RetrievalMethod, XmlSignatureConstants.Namespace);
                writer.WriteAttributeString(XmlSignatureConstants.Attributes.URI, null, keyInfo.RetrievalMethodUri);
                writer.WriteEndElement();
            }

            foreach (var data in keyInfo.X509Data)
            {
                // <X509Data>
                writer.WriteStartElement(keyInfo.Prefix, XmlSignatureConstants.Elements.X509Data, XmlSignatureConstants.Namespace);

                if (data.IssuerSerial != null)
                {
                    writer.WriteStartElement(keyInfo.Prefix, XmlSignatureConstants.Elements.X509IssuerSerial, XmlSignatureConstants.Namespace);

                    writer.WriteElementString(keyInfo.Prefix, XmlSignatureConstants.Elements.X509IssuerName, XmlSignatureConstants.Namespace, data.IssuerSerial.IssuerName);

                    writer.WriteElementString(keyInfo.Prefix, XmlSignatureConstants.Elements.X509SerialNumber, XmlSignatureConstants.Namespace, data.IssuerSerial.SerialNumber);

                    writer.WriteEndElement();
                }

                if (data.SKI != null)
                {
                    writer.WriteElementString(keyInfo.Prefix, XmlSignatureConstants.Elements.X509SKI, XmlSignatureConstants.Namespace, data.SKI);
                }

                if (data.SubjectName != null)
                {
                    writer.WriteElementString(keyInfo.Prefix, XmlSignatureConstants.Elements.X509SubjectName, XmlSignatureConstants.Namespace, data.SubjectName);
                }

                foreach (var certificate in data.Certificates)
                {
                    // <X509Certificate>...</X509Certificate>
                    writer.WriteElementString(keyInfo.Prefix, XmlSignatureConstants.Elements.X509Certificate, XmlSignatureConstants.Namespace, certificate);
                }

                if (data.CRL != null)
                {
                    writer.WriteElementString(keyInfo.Prefix, XmlSignatureConstants.Elements.X509CRL, XmlSignatureConstants.Namespace, data.CRL);
                }

                // </X509Data>
                writer.WriteEndElement();
            }

            // </KeyInfo>
            writer.WriteEndElement();
        }