Ejemplo n.º 1
0
        public void DecryptData_CipherReference_IdUri()
        {
            XmlDocument doc = new XmlDocument();

            doc.PreserveWhitespace = true;
            string xml = "<root>  <child>sample</child>   </root>";

            doc.LoadXml(xml);

            using (Aes aes = Aes.Create())
            {
                EncryptedXml exml        = new EncryptedXml(doc);
                string       cipherValue = Convert.ToBase64String(exml.EncryptData(Encoding.UTF8.GetBytes(xml), aes));

                EncryptedData ed = new EncryptedData();
                ed.Type             = EncryptedXml.XmlEncElementUrl;
                ed.EncryptionMethod = new EncryptionMethod(EncryptedXml.XmlEncAES256Url);
                ed.CipherData       = new CipherData();
                // Create CipherReference: first extract node value, then convert from base64 using Transforms
                ed.CipherData.CipherReference = new CipherReference("#ID_0");
                string xslt = "<xsl:stylesheet version=\"1.0\" xmlns:xsl=\"http://www.w3.org/1999/XSL/Transform\"><xsl:template match = \"/\"><xsl:value-of select=\".\" /></xsl:template></xsl:stylesheet>";
                XmlDsigXsltTransform xsltTransform = new XmlDsigXsltTransform();
                XmlDocument          xsltDoc       = new XmlDocument();
                xsltDoc.LoadXml(xslt);
                xsltTransform.LoadInnerXml(xsltDoc.ChildNodes);
                ed.CipherData.CipherReference.AddTransform(xsltTransform);
                ed.CipherData.CipherReference.AddTransform(new XmlDsigBase64Transform());

                // Create a document with EncryptedData and node with the actual cipher data (with the ID)
                doc.LoadXml("<root></root>");
                XmlNode encryptedDataNode = doc.ImportNode(ed.GetXml(), true);
                doc.DocumentElement.AppendChild(encryptedDataNode);
                XmlElement cipherDataByReference = doc.CreateElement("CipherData");
                cipherDataByReference.SetAttribute("ID", "ID_0");
                cipherDataByReference.InnerText = cipherValue;
                doc.DocumentElement.AppendChild(cipherDataByReference);

                string decryptedXmlString = Encoding.UTF8.GetString(exml.DecryptData(ed, aes));
                Assert.Equal(xml, decryptedXmlString);
            }
        }
Ejemplo n.º 2
0
        // Probably it is a bug in .NET, but sometimes it does not contain
        // proper padding bytes. For such cases, use PaddingMode.None
        // instead. It must not be done in EncryptedXml class as it
        // correctly rejects improper ISO10126 padding.
        byte [] DecryptData(EncryptedXml encXml, EncryptedData ed, SymmetricAlgorithm symAlg)
        {
            PaddingMode bak = symAlg.Padding;

            try
            {
                byte [] bytes = ed.CipherData.CipherValue;

                if (encXml.Padding != PaddingMode.None &&
                    encXml.Padding != PaddingMode.Zeros &&
                    bytes [bytes.Length - 1] > symAlg.BlockSize / 8)
                {
                    symAlg.Padding = PaddingMode.None;
                }
                return(encXml.DecryptData(ed, symAlg));
            }
            finally
            {
                symAlg.Padding = bak;
            }
        }
Ejemplo n.º 3
0
        public void ReplaceData2NonDocumentElementTest()
        {
            XmlDocument doc = new XmlDocument();

            doc.PreserveWhitespace = true;
            doc.LoadXml(InputXml);

            using (Rijndael aes = new RijndaelManaged())
            {
                aes.GenerateKey();
                aes.GenerateIV();

                // Encrypt the XML document
                EncryptedXml encryptedXml = new EncryptedXml(doc);
                encryptedXml.AddKeyNameMapping("key", aes);

                XmlElement    secretElement = doc.GetElementsByTagName("child")[0] as XmlElement;
                EncryptedData encrypted     = encryptedXml.Encrypt(secretElement, "key");
                EncryptedXml.ReplaceElement(secretElement, encrypted, false);

                // Decrypt it back
                XmlElement encryptedElement = doc.GetElementsByTagName("EncryptedData", EncryptedXml.XmlEncNamespaceUrl)[0] as XmlElement;

                EncryptedData encryptedData = new EncryptedData();
                encryptedData.LoadXml(encryptedElement);

                EncryptedXml decryptXml = new EncryptedXml(doc);
                decryptXml.AddKeyNameMapping("key", aes);

                byte[] decryptedData = decryptXml.DecryptData(encryptedData,
                                                              decryptXml.GetDecryptionKey(encryptedData, null));
                decryptXml.ReplaceData2(encryptedElement, decryptedData);
            }

            // Now that we've encrypted and decrypted the data, ensure that we have both the XML
            // declaration, and the root node in place.
            Assert.IsTrue(doc.FirstChild.NodeType == XmlNodeType.XmlDeclaration);
            Assert.AreEqual("root", doc.FirstChild.NextSibling.Name);
            Assert.AreEqual(InputXml, doc.OuterXml);
        }
        public string Decrypt(XmlDocument cxDoc)
        {
            var Doc = cxDoc;
            SymmetricAlgorithm Alg = rijndaelManaged_;

            // Check the arguments.
            if (Doc == null)
            {
                throw new ArgumentNullException("Doc");
            }
            if (Alg == null)
            {
                throw new ArgumentNullException("Alg");
            }

            // Find the EncryptedData element in the XmlDocument.
            XmlElement encryptedElement = Doc.GetElementsByTagName("EncryptedData")[0] as XmlElement;

            // If the EncryptedData element was not found, throw an exception.
            if (encryptedElement == null)
            {
                throw new XmlException("The EncryptedData element was not found.");
            }

            // Create an EncryptedData object and populate it.
            EncryptedData edElement = new EncryptedData();

            edElement.LoadXml(encryptedElement);

            // Create a new EncryptedXml object.
            EncryptedXml exml = new EncryptedXml();

            // Decrypt the element using the symmetric key.
            byte[] rgbOutput = exml.DecryptData(edElement, Alg);

            // Replace the encryptedData element with the plaintext XML element.
            exml.ReplaceData(encryptedElement, rgbOutput);

            return(Doc.InnerXml);
        }
Ejemplo n.º 5
0
        // Расшифрование узла XML документа на симметричном ключе
        private static void Decrypt(string srcName, string destName, SymmetricAlgorithm Alg)
        {
            // Создаем новый объект xml документа.
            XmlDocument xmlDoc = new XmlDocument();

            // Пробельные символы участвуют в вычислении подписи и должны быть сохранены для совместимости с другими реализациями.
            xmlDoc.PreserveWhitespace = true;

            // Загружаем в объект созданный XML документ.
            xmlDoc.Load(srcName);

            // Ищем узел для расшифрования.
            XmlElement encryptedElement = xmlDoc.GetElementsByTagName(
                "EncryptedData")[0] as XmlElement;

            if (encryptedElement == null)
            {
                throw new XmlException("Узел EncryptedData не найден");
            }

            // Создаем объект EncryptedData.
            EncryptedData edElement = new EncryptedData();

            // и загружаем в него зашифрованный узел
            edElement.LoadXml(encryptedElement);

            // Создаем объект EncryptedXml
            EncryptedXml exml = new EncryptedXml();

            // Расшифровываем элемент используя
            // симметричный ключ.
            byte[] rgbOutput = exml.DecryptData(edElement, Alg);

            // Заменяем зашифрованный узел расшифрованным
            exml.ReplaceData(encryptedElement, rgbOutput);

            // Сохраняем расшифрованный документ.
            xmlDoc.Save(destName);
        }
Ejemplo n.º 6
0
        public static String DecryptXML(String xml, SymmetricAlgorithm key = null)
        {
            if (String.IsNullOrEmpty(xml))
            {
                throw new ArgumentNullException("xml");
            }

            if (key == null)
            {
                key = DefaultCryptographyKey;
            }

            var xmlDoc    = default(XmlDocument);
            var element   = default(XmlElement);
            var edElement = default(EncryptedData);
            var exml      = default(EncryptedXml);
            var rgbOutput = default(Byte[]);

            xmlDoc = new XmlDocument();
            xmlDoc.LoadXml(xml);

            element = xmlDoc.DocumentElement;

            // Create an EncryptedData object and populate it.
            edElement = new EncryptedData();

            Contract.Assert(element != null, "element != null");
            edElement.LoadXml(element);
            // Create a new EncryptedXml object.
            exml = new EncryptedXml();

            // Decrypt the element using the symmetric key.
            rgbOutput = exml.DecryptData(edElement, key);
            // Replace the encryptedData element with the plaintext XML element.
            exml.ReplaceData(element, rgbOutput);

            return(xmlDoc.OuterXml);
        }
Ejemplo n.º 7
0
        public void DecryptIfNeeded(X509Certificate2 spCert)
        {
            if (spCert == null)
            {
                throw new ArgumentNullException(nameof(spCert));
            }

            var responseNode           = SelectSingleNode("/samlp:Response");
            var encryptedAssertionNode = SelectSingleNode("/samlp:Response/saml:EncryptedAssertion");

            if (encryptedAssertionNode != null)
            {
                var encryptedDataNode            = SelectSingleNode("/samlp:Response/saml:EncryptedAssertion/xenc:EncryptedData");
                var encryptionMethodAlgorithm    = SelectSingleNode("/samlp:Response/saml:EncryptedAssertion/xenc:EncryptedData/xenc:EncryptionMethod")?.Attributes["Algorithm"]?.Value;
                var encryptionMethodKeyAlgorithm = SelectSingleNode("/samlp:Response/saml:EncryptedAssertion/xenc:EncryptedData/ds:KeyInfo/e:EncryptedKey/e:EncryptionMethod")?.Attributes["Algorithm"]?.Value;
                var cypherText = SelectSingleNode("/samlp:Response/saml:EncryptedAssertion/xenc:EncryptedData/ds:KeyInfo/e:EncryptedKey/e:CipherData/e:CipherValue")?.InnerText;

                var key = Rijndael.Create(encryptionMethodAlgorithm);
                key.Key = EncryptedXml.DecryptKey(
                    Convert.FromBase64String(cypherText),
                    (RSA)spCert.PrivateKey,
                    useOAEP: encryptionMethodKeyAlgorithm == EncryptedXml.XmlEncRSAOAEPUrl
                    );

                var encryptedXml  = new EncryptedXml();
                var encryptedData = new EncryptedData();
                encryptedData.LoadXml((XmlElement)encryptedDataNode);

                var plaintext = encryptedXml.DecryptData(encryptedData, key);
                var xmlString = Encoding.UTF8.GetString(plaintext);

                var tempDoc = new XmlDocument();
                tempDoc.LoadXml(xmlString);

                var importNode = responseNode.OwnerDocument.ImportNode(tempDoc.DocumentElement, true);
                responseNode.ReplaceChild(importNode, encryptedAssertionNode);
            }
        }
Ejemplo n.º 8
0
        void AssertDecryption1(string resourceName)
        {
            XmlDocument doc = new XmlDocument();

            doc.PreserveWhitespace = true;
            doc.Load(LoadResourceStream(resourceName));
            EncryptedXml encxml = new EncryptedXml(doc);

            using (RSA rsa = new X509Certificate2(Convert.FromBase64String(SamplePfx), "mono").PrivateKey as RSA)
            {
                Assert.NotNull(rsa);

                XmlNamespaceManager nm = new XmlNamespaceManager(doc.NameTable);
                nm.AddNamespace("s", "http://www.w3.org/2003/05/soap-envelope");
                nm.AddNamespace("o", "http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd");
                nm.AddNamespace("e", EncryptedXml.XmlEncNamespaceUrl);
                XmlElement   el   = doc.SelectSingleNode("/s:Envelope/s:Header/o:Security/e:EncryptedKey", nm) as XmlElement;
                EncryptedKey ekey = new EncryptedKey();
                ekey.LoadXml(el);
                byte[] key = rsa.Decrypt(ekey.CipherData.CipherValue, RSAEncryptionPadding.OaepSHA1);
                using (Aes aes = Aes.Create())
                {
                    aes.Key  = key;
                    aes.Mode = CipherMode.CBC;
                    ArrayList al = new ArrayList();
                    foreach (XmlElement ed in doc.SelectNodes("//e:EncryptedData", nm))
                    {
                        al.Add(ed);
                    }
                    foreach (XmlElement ed in al)
                    {
                        EncryptedData edata = new EncryptedData();
                        edata.LoadXml(ed);
                        encxml.ReplaceData(ed, encxml.DecryptData(edata, aes));
                    }
                }
            }
        }
Ejemplo n.º 9
0
        public static XmlDocument DecryptAssertion(XmlDocument responseWithEncryptedAssertion)
        {
            XmlElement    encryptedDataElement = (XmlElement)responseWithEncryptedAssertion.GetElementsByTagName("EncryptedData", "http://www.w3.org/2001/04/xmlenc#")[0];
            EncryptedData encryptedData        = new EncryptedData();

            encryptedData.LoadXml(encryptedDataElement);

            var sessionKey = ExtractSessionKey(encryptedDataElement, encryptedData?.EncryptionMethod?.KeyAlgorithm ?? String.Empty);

            EncryptedXml encryptedXml = new EncryptedXml();

            byte[] assertionBytes = encryptedXml.DecryptData(encryptedData, sessionKey);

            XmlDocument assertionXml = new XmlDocument
            {
                XmlResolver        = null,
                PreserveWhitespace = true
            };

            assertionXml.Load(new StringReader(Encoding.UTF8.GetString(assertionBytes)));

            return(assertionXml);
        }
Ejemplo n.º 10
0
        public static void Decrypt(XmlDocument Doc, SymmetricAlgorithm Alg)
        {
            XmlElement encryptedElement = Doc.GetElementsByTagName("EncryptedData")[0] as XmlElement;

            // If the EncryptedData element was not found, throw an exception.
            if (encryptedElement == null)
            {
                throw new XmlException("The EncryptedData element was not found.");
            }

            // Create an EncryptedData object and populate it.
            EncryptedData edElement = new EncryptedData();

            edElement.LoadXml(encryptedElement);

            // Create a new EncryptedXml object.
            EncryptedXml exml = new EncryptedXml();

            // Decrypt the element using the symmetric key.
            byte[] rgbOutput = exml.DecryptData(edElement, Alg);

            // Replace the encryptedData element with the plaintext XML element.
            exml.ReplaceData(encryptedElement, rgbOutput);
        }
Ejemplo n.º 11
0
 public void Decrypt(string xmlFileName)
 {
     TripleDESCryptoServiceProvider encryptionKey = new TripleDESCryptoServiceProvider();
     encryptionKey.Key = UTF8Encoding.UTF8.GetBytes("");  // your salt value
     XmlDocument document = new XmlDocument();
     document.Load(xmlFileName);
     XmlElement encOrderElem = document.GetElementsByTagName("EncryptedData")[0] as XmlElement;
     EncryptedData encData = new EncryptedData();
     encData.LoadXml(encOrderElem);
     EncryptedXml encryptedXml = new EncryptedXml();
     byte[] decryptedOrder = encryptedXml.DecryptData(encData, encryptionKey);
     encryptedXml.ReplaceData(encOrderElem, decryptedOrder);
     document.Save(xmlFileName);
 }
Ejemplo n.º 12
0
        public void DecryptData_SymmetricAlgorithmNull()
        {
            EncryptedXml ex = new EncryptedXml();

            ex.DecryptData(new EncryptedData(), null);
        }
Ejemplo n.º 13
0
        public void DecryptData_EncryptedDataNull()
        {
            EncryptedXml ex = new EncryptedXml();

            ex.DecryptData(null, Rijndael.Create());
        }
Ejemplo n.º 14
0
        XmlElement VerifyInput2(MessageBuffer buf)
        {
            Message      msg2 = buf.CreateMessage();
            StringWriter sw   = new StringWriter();

            using (XmlDictionaryWriter w = XmlDictionaryWriter.CreateDictionaryWriter(XmlWriter.Create(sw))) {
                msg2.WriteMessage(w);
            }
            XmlDocument doc = new XmlDocument();

            doc.PreserveWhitespace = true;
            doc.LoadXml(sw.ToString());

            // decrypt the key with service certificate privkey
            PaddingMode  mode   = PaddingMode.PKCS7;          // not sure which is correct ... ANSIX923, ISO10126, PKCS7, Zeros, None.
            EncryptedXml encXml = new EncryptedXml(doc);

            encXml.Padding = mode;
            X509Certificate2    cert2 = new X509Certificate2("Test/Resources/test.pfx", "mono");
            XmlNamespaceManager nsmgr = new XmlNamespaceManager(doc.NameTable);

            nsmgr.AddNamespace("s", "http://www.w3.org/2003/05/soap-envelope");
            nsmgr.AddNamespace("c", "http://schemas.xmlsoap.org/ws/2005/02/sc");
            nsmgr.AddNamespace("o", "http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd");
            nsmgr.AddNamespace("e", "http://www.w3.org/2001/04/xmlenc#");
            nsmgr.AddNamespace("dsig", "http://www.w3.org/2000/09/xmldsig#");
            XmlNode n = doc.SelectSingleNode("//o:Security/e:EncryptedKey/e:CipherData/e:CipherValue", nsmgr);

            Assert.IsNotNull(n, "premise: enckey does not exist");
            string raw = n.InnerText;

            byte [] rawbytes             = Convert.FromBase64String(raw);
            RSACryptoServiceProvider rsa = (RSACryptoServiceProvider)cert2.PrivateKey;

            byte [] decryptedKey = EncryptedXml.DecryptKey(rawbytes, rsa, true);             //rsa.Decrypt (rawbytes, true);

#if false
            // create derived keys
            Dictionary <string, byte[]>  keys = new Dictionary <string, byte[]> ();
            InMemorySymmetricSecurityKey skey =
                new InMemorySymmetricSecurityKey(decryptedKey);
            foreach (XmlElement el in doc.SelectNodes("//o:Security/c:DerivedKeyToken", nsmgr))
            {
                n = el.SelectSingleNode("c:Offset", nsmgr);
                int offset = (n == null) ? 0 :
                             int.Parse(n.InnerText, CultureInfo.InvariantCulture);
                n = el.SelectSingleNode("c:Length", nsmgr);
                int length = (n == null) ? 32 :
                             int.Parse(n.InnerText, CultureInfo.InvariantCulture);
                n = el.SelectSingleNode("c:Label", nsmgr);
                byte [] label = (n == null) ? decryptedKey :
                                Convert.FromBase64String(n.InnerText);
                n = el.SelectSingleNode("c:Nonce", nsmgr);
                byte [] nonce = (n == null) ? new byte [0] :
                                Convert.FromBase64String(n.InnerText);
                byte [] derkey = skey.GenerateDerivedKey(
                    //SecurityAlgorithms.Psha1KeyDerivation,
                    "http://schemas.xmlsoap.org/ws/2005/02/sc/dk/p_sha1",
// FIXME: maybe due to the label, this key resolution somehow does not seem to work.
                    label,
                    nonce,
                    length * 8,
                    offset);

                keys [el.GetAttribute("Id", "http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd")] = derkey;
            }
#endif

            // decrypt the signature with the decrypted key
#if true
            n = doc.SelectSingleNode("//o:Security/e:EncryptedData/e:CipherData/e:CipherValue", nsmgr);
            Assert.IsNotNull(n, "premise: encdata does not exist");
            raw      = n.InnerText;
            rawbytes = Convert.FromBase64String(raw);
            Rijndael aes = RijndaelManaged.Create();
//			aes.Key = keys [n.SelectSingleNode ("../../dsig:KeyInfo/o:SecurityTokenReference/o:Reference/@URI", nsmgr).InnerText.Substring (1)];
            aes.Key     = decryptedKey;
            aes.Mode    = CipherMode.CBC;
            aes.Padding = mode;
            MemoryStream ms = new MemoryStream();
            CryptoStream cs = new CryptoStream(ms, aes.CreateDecryptor(), CryptoStreamMode.Write);
            cs.Write(rawbytes, 0, rawbytes.Length);
            cs.Close();
            byte [] decryptedSignature = ms.ToArray();
#else
            Rijndael aes = RijndaelManaged.Create();
//			aes.Key = keys [n.SelectSingleNode ("../../dsig:KeyInfo/o:SecurityTokenReference/o:Reference/@URI", nsmgr).InnerText.Substring (1)];
            aes.Key     = decryptedKey;
            aes.Mode    = CipherMode.CBC;
            aes.Padding = mode;

            EncryptedData ed = new EncryptedData();
            n = doc.SelectSingleNode("//o:Security/e:EncryptedData", nsmgr);
            Assert.IsNotNull(n, "premise: encdata does not exist");
            ed.LoadXml(n as XmlElement);
            byte [] decryptedSignature = encXml.DecryptData(ed, aes);
#endif
//Console.Error.WriteLine (Encoding.UTF8.GetString (decryptedSignature));
//Console.Error.WriteLine ("============= Decrypted Signature End ===========");

            // decrypt the body with the decrypted key
#if true
            n = doc.SelectSingleNode("//s:Body/e:EncryptedData/e:CipherData/e:CipherValue", nsmgr);
            Assert.IsNotNull(n, "premise: encdata does not exist");
            raw      = n.InnerText;
            rawbytes = Convert.FromBase64String(raw);
//			aes.Key = keys [n.SelectSingleNode ("../../dsig:KeyInfo/o:SecurityTokenReference/o:Reference/@URI", nsmgr).InnerText.Substring (1)];
            aes.Key = decryptedKey;
            ms      = new MemoryStream();
            cs      = new CryptoStream(ms, aes.CreateDecryptor(), CryptoStreamMode.Write);
            cs.Write(rawbytes, 0, rawbytes.Length);
            cs.Close();
            byte [] decryptedBody = ms.ToArray();
#else
            // decrypt the body with the decrypted key
            EncryptedData ed2 = new EncryptedData();
            XmlElement    el  = doc.SelectSingleNode("/s:Envelope/s:Body/e:EncryptedData", nsmgr) as XmlElement;
            ed2.LoadXml(el);
//			aes.Key = keys [n.SelectSingleNode ("../../dsig:KeyInfo/o:SecurityTokenReference/o:Reference/@URI", nsmgr).InnerText.Substring (1)];
            aes.Key = decryptedKey;
            byte [] decryptedBody = encXml.DecryptData(ed2, aes);
#endif
//foreach (byte b in decryptedBody) Console.Error.Write ("{0:X02} ", b);
            Console.Error.WriteLine(Encoding.UTF8.GetString(decryptedBody));
            Console.Error.WriteLine("============= Decrypted Body End ===========");

            // FIXME: find out what first 16 bytes mean.
            for (int mmm = 0; mmm < 16; mmm++)
            {
                decryptedBody [mmm] = 0x20;
            }
            doc.LoadXml(Encoding.UTF8.GetString(decryptedBody));
            Assert.AreEqual("RequestSecurityToken", doc.DocumentElement.LocalName, "#b-1");
            Assert.AreEqual("http://schemas.xmlsoap.org/ws/2005/02/trust", doc.DocumentElement.NamespaceURI, "#b-2");

            return(doc.DocumentElement);
        }
Ejemplo n.º 15
0
        public void DecryptData_SymmetricAlgorithmNull()
        {
            EncryptedXml ex = new EncryptedXml();

            Assert.Throws <ArgumentNullException>(() => ex.DecryptData(new EncryptedData(), null));
        }
Ejemplo n.º 16
0
        public void DecryptData_EncryptedDataNull()
        {
            EncryptedXml ex = new EncryptedXml();

            Assert.Throws <ArgumentNullException>(() => ex.DecryptData(null, Aes.Create()));
        }
        internal static ICollection <SamlAttributesEncryptionKey> DecryptXml(RSA asymmetricAlgorithm, XmlDocument xmlDoc, string[] xmlElementsXPaths)
        {
            if (asymmetricAlgorithm == null)
            {
                throw new ArgumentNullException("asymmetricAlgorithm");
            }
            if (xmlDoc == null)
            {
                throw new ArgumentNullException("xmlDoc");
            }
            if (xmlElementsXPaths == null)
            {
                throw new ArgumentNullException("xmlElementsXPaths");
            }

            // create the symmetric algorithm which was used for encryption
            var symmetricAlgorithm = new AesManaged();

            symmetricAlgorithm.Padding = PaddingMode.ISO10126;
            ICollection <SamlAttributesEncryptionKey> attributesEncryptionKeys = new Collection <SamlAttributesEncryptionKey>();

            foreach (var xPath in xmlElementsXPaths)
            {
                // select all encrypted attribute elements
                var encryptedElements = xmlDoc.SelectNodes(xPath);

                Debug.Assert(encryptedElements != null, "encryptedElements != null");
                foreach (XmlNode encryptedElement in encryptedElements)
                {
                    // load the encrypted data element
                    var encryptedDataElement = encryptedElement.SelectSingleNode("//*[local-name() = 'EncryptedData']") as XmlElement;
                    var encryptedData        = new EncryptedData();
                    Debug.Assert(encryptedDataElement != null, "encryptedDataElement != null");
                    encryptedData.LoadXml(encryptedDataElement);

                    // load the encrypted key element
                    var encryptedKeyElement = encryptedDataElement.SelectSingleNode("//*[local-name() = 'EncryptedKey']") as XmlElement;
                    var encryptedKey        = new EncryptedKey();
                    Debug.Assert(encryptedKeyElement != null, "encryptedKeyElement != null");
                    encryptedKey.LoadXml(encryptedKeyElement);

                    // decrypt the key using the specifief asymmetric algorithm
                    var symetricKey = asymmetricAlgorithm.Decrypt(encryptedKey.CipherData.CipherValue, RSAEncryptionPadding.OaepSHA1);

                    // use the asymmetric decrypted key to decrypt the encrypted data using the specified symmetric algorithm
                    symmetricAlgorithm.Key = symetricKey;

                    var output = new EncryptedXml {
                        Mode = CipherMode.CBC, Padding = PaddingMode.ISO10126
                    };
                    var data = output.DecryptData(encryptedData, symmetricAlgorithm);

                    var previousSibling = (XmlElement)encryptedElement.PreviousSibling;
                    var nextSibling     = (XmlElement)encryptedElement.NextSibling;
                    var parentElement   = (XmlElement)encryptedElement.ParentNode;

                    // replace the encrypted element with its decrypted form
                    output.ReplaceData((XmlElement)encryptedElement, data); var currentNode = previousSibling?.NextSibling
                                                                                              ?? nextSibling?.PreviousSibling
                                                                                              ?? parentElement?.FirstChild;

                    if (currentNode == null)
                    {
                        continue;
                    }

                    var attributesEncryptionKey = GetAttributesEncryptionKey(currentNode, symetricKey);

                    if (attributesEncryptionKey != null)
                    {
                        attributesEncryptionKeys.Add(attributesEncryptionKey);
                    }
                }
            }
            return(attributesEncryptionKeys);
        }
Ejemplo n.º 18
0
        /// <summary>
        /// Gets the assertion.
        /// </summary>
        /// <param name="idpSamlResponseToken">The idp saml response token.</param>
        /// <param name="options">The options.</param>
        /// <returns></returns>
        /// <exception cref="Exception">Missing assertion
        /// or
        /// Unable to parse the decrypted assertion.</exception>
        /// <exception cref="System.Exception">Missing assertion
        /// or
        /// Unable to parse the decrypted assertion.</exception>
        public string GetAssertion(ResponseType idpSamlResponseToken, Saml2Options options)
        {
            string token;
            string xmlTemplate;
            var    assertion = idpSamlResponseToken.Items[0];

            if (assertion == null)
            {
                throw new Exception("Missing assertion");
            }

            //check if its a decrypted assertion
            if (assertion.GetType() == typeof(EncryptedElementType))
            {
                EncryptedElementType encryptedElement = (EncryptedElementType)assertion;
                SymmetricAlgorithm   sessionKey;

                if (encryptedElement.EncryptedData.EncryptionMethod != null)
                {
                    sessionKey = ExtractSessionKey(encryptedElement, options.ServiceProvider.X509Certificate2.PrivateKey);

                    var           encryptedXml  = new EncryptedXml();
                    XmlSerializer xmlSerializer = new XmlSerializer(typeof(EncryptedDataType));
                    using (MemoryStream memStm = new MemoryStream())
                    {
                        xmlSerializer.Serialize(memStm, encryptedElement.EncryptedData);
                        memStm.Position = 0;
                        xmlTemplate     = new StreamReader(memStm).ReadToEnd();
                    }

                    var doc = new XmlDocument();
                    doc.PreserveWhitespace = true;
                    doc.LoadXml(xmlTemplate);
                    var t             = doc.GetElementsByTagName("EncryptedData");
                    var encryptedData = new EncryptedData();
                    encryptedData.LoadXml((XmlElement)t[0]);

                    byte[] plaintext = encryptedXml.DecryptData(encryptedData, sessionKey);
                    token = Encoding.UTF8.GetString(plaintext);
                    return(token);
                }
            }
            else
            {
                XmlSerializer xmlSerializer = new XmlSerializer(typeof(AssertionType));
                using (MemoryStream memStm = new MemoryStream())
                {
                    xmlSerializer.Serialize(memStm, assertion);
                    memStm.Position = 0;
                    xmlTemplate     = new StreamReader(memStm).ReadToEnd();
                }

                var doc = new XmlDocument();
                doc.PreserveWhitespace = false;
                doc.LoadXml(xmlTemplate);

                string request = doc.OuterXml;
                return(request);
            }
            throw new Exception("Unable to parse the decrypted assertion.");
        }
Ejemplo n.º 19
0
        /// <summary>
        /// An example on how to decrypt an encrypted assertion.
        /// </summary>
        /// <param name="file">The file.</param>
        public static void DecryptAssertion(string file)
        {
            var doc = new XmlDocument();

            doc.Load(file);
            var encryptedDataElement = GetElement(Schema.XEnc.EncryptedData.ElementName, Saml20Constants.Xenc, doc);

            var encryptedData = new EncryptedData();

            encryptedData.LoadXml(encryptedDataElement);

            var nodelist = doc.GetElementsByTagName(Schema.XmlDSig.KeyInfo.ElementName, Saml20Constants.Xmldsig);

            Assert.True(nodelist.Count > 0);

            var key = new KeyInfo();

            key.LoadXml((XmlElement)nodelist[0]);

            // Review: Is it possible to figure out which certificate to load based on the Token?

            /*
             * Comment:
             * It would be possible to provide a key/certificate identifier in the EncryptedKey element, which contains the "recipient" attribute.
             * The implementation (Safewhere.Tokens.Saml20.Saml20EncryptedAssertion) currently just expects an appropriate asymmetric key to be provided,
             * and is not not concerned about its origin.
             * If the need arises, we can easily extend the Saml20EncryptedAssertion class with a property that allows extraction key info, eg. the "recipient"
             * attribute.
             */
            var cert = Certificates.InMemoryResourceUtility.GetInMemoryCertificate("sts_dev_certificate.pfx", "test1234");

            // ms-help://MS.MSDNQTR.v80.en/MS.MSDN.v80/MS.NETDEVFX.v20.en/CPref18/html/T_System_Security_Cryptography_Xml_KeyInfoClause_DerivedTypes.htm
            // Look through the list of KeyInfo elements to find the encrypted key.
            SymmetricAlgorithm symmetricKey = null;

            foreach (KeyInfoClause keyInfoClause in key)
            {
                if (keyInfoClause is KeyInfoEncryptedKey)
                {
                    var keyInfoEncryptedKey = (KeyInfoEncryptedKey)keyInfoClause;
                    var encryptedKey        = keyInfoEncryptedKey.EncryptedKey;
                    symmetricKey = new RijndaelManaged
                    {
                        Key = EncryptedXml.DecryptKey(encryptedKey.CipherData.CipherValue, (RSA)cert.PrivateKey, false)
                    };
                }
            }

            // Explode if we didn't manage to find a viable key.
            Assert.NotNull(symmetricKey);
            var encryptedXml = new EncryptedXml();
            var plaintext    = encryptedXml.DecryptData(encryptedData, symmetricKey);

            var assertion = new XmlDocument();

            assertion.Load(new StringReader(System.Text.Encoding.UTF8.GetString(plaintext)));

            // A very simple test to ensure that there is indeed an assertion in the plaintext.
            Assert.Equal(Assertion.ElementName, assertion.DocumentElement.LocalName);
            Assert.Equal(Saml20Constants.Assertion, assertion.DocumentElement.NamespaceURI);

            // At this point, assertion will contain a decrypted assertion.
        }
Ejemplo n.º 20
0
        /// <summary>
        /// Расшифровывает ответ ФСС по пути
        /// </summary>
        /// <param name="filename">Путь к зашифрованному файлу</param>
        /// <returns>Путь к расшифрованному файлу</returns>
        public string decryptResponse(string filename)
        {
            if (!File.Exists(filename))
            {
                throw new Exception("Шаг 5. Файл не найден!\r\nПуть:" + filename);
            }

            string filename5 = filename + ".decrypted.xml";

            // Создаем объект XmlDocument.
            XmlDocument xmlDoc = new XmlDocument();

            // Загружаем XML файл в объект XmlDocument.
            xmlDoc.PreserveWhitespace = true;
            xmlDoc.Load(filename);

            // Ищем все зашифрованные данные.
            XmlNamespaceManager nsmgr = new XmlNamespaceManager(xmlDoc.NameTable);

            nsmgr.AddNamespace("xenc", "http://www.w3.org/2001/04/xmlenc#");
            XmlNodeList list = xmlDoc.SelectNodes("//xenc:EncryptedData", nsmgr);

            // Создаем объект EncryptedXml.
            EncryptedXml exml = new EncryptedXml(xmlDoc);

            if (list != null)
            {
                // Для всех зашифрованных данных.
                foreach (XmlNode node in list)
                {
                    XmlElement    element       = node as XmlElement;
                    EncryptedData encryptedData = new EncryptedData();
                    encryptedData.LoadXml(element);

                    // Находим подходящий ключ для расшифрования.
                    SymmetricAlgorithm decryptionKey = GetDecryptionKey(exml, encryptedData);
                    if (decryptionKey == null)
                    {
                        throw new Exception("Ключ для расшифрования сообщения не найден");
                    }

                    // И на нем расшифровываем данные.
                    byte[] decryptedData = exml.DecryptData(encryptedData, decryptionKey);
                    exml.ReplaceData(element, decryptedData);
                }
            }

            xmlDoc.Save(filename5);


            // Отображаем файл если требуется для дебага
            if (DEBUG_STEP < 5)
            {
                foView view = new foView();
                view.Text        = filename5;
                view.xmlFileName = filename5;
                view.Show();
            }

            return(filename5);
        }
Ejemplo n.º 21
0
        private bool TryDecrypt(EncryptedType encryptedType, out byte[] plainText)
        {
            var xml       = new EncryptedXml();
            var keys      = GetSecurityKeys(encryptedType);
            var algorithm = encryptedType.EncryptionMethod.KeyAlgorithm;

            foreach (var key in keys)
            {
                var crypto = GetCrypto(key);
                if (!crypto.IsSupportedAlgorithm(algorithm, key))
                {
                    continue;
                }
                var symmetric = null as SymmetricAlgorithm;
                try
                {
                    if (encryptedType is EncryptedData encryptedData)
                    {
                        if (!(key is SymmetricSecurityKey symmetricKey))
                        {
                            continue;
                        }
                        symmetric    = crypto.CreateSymmetricAlgorithm(symmetricKey, algorithm);
                        symmetric.IV = xml.GetDecryptionIV(encryptedData, algorithm);
                        var pt = xml.DecryptData(encryptedData, symmetric);
                        plainText = pt;
                        return(true);
                    }

                    if (encryptedType is EncryptedKey encryptedKey)
                    {
                        var pt = null as byte[];
                        var keyWrapAlgorithm = encryptedKey.EncryptionMethod.KeyAlgorithm;
                        if (crypto.IsSupportedAlgorithm(algorithm, key))
                        {
                            var keyWrap = crypto.CreateKeyWrapProviderForUnwrap(key, encryptedKey.EncryptionMethod.KeyAlgorithm);
                            try
                            {
                                pt        = keyWrap.UnwrapKey(encryptedKey.CipherData.CipherValue);
                                plainText = pt;
                                return(true);
                            }
                            finally
                            {
                                crypto.ReleaseKeyWrapProvider(keyWrap);
                            }
                        }
                    }
                }
                catch (Exception ex)
                {
                }
                finally
                {
                    if (symmetric != null)
                    {
                        crypto.ReleaseSymmetricAlgorithm(symmetric);
                        symmetric = null;
                    }
                }
            }
            return(Out.False(out plainText));
        }
Ejemplo n.º 22
0
        protected override void DecryptElement(XmlElement element, string password)
        {
            var saltXmlAttribute = XmlHelpers.GetAttributeNode(element, "Salt");

            if (string.IsNullOrEmpty(saltXmlAttribute?.Value))
            {
                throw new InvalidXmlException($"Encrypted node {element.Name} does not contain required Attribute \"Salt\"", element);
            }
            byte[] rgbSalt;
            try
            {
                rgbSalt = Convert.FromBase64String(saltXmlAttribute.Value);
            }
            catch (FormatException)
            {
                throw new InvalidXmlException($"Invalid value of Attribute \"Salt\" ({saltXmlAttribute.Value}) in encrypted node {element.Name} ", element);
            }
            var ivXmlAttribute = XmlHelpers.GetAttributeNode(element, "IV");

            if (string.IsNullOrEmpty(ivXmlAttribute?.Value))
            {
                throw new InvalidXmlException($"Encrypted node {element.Name} does not contain required Attribute \"IV\"", element);
            }
            byte[] numArray;
            try
            {
                numArray = Convert.FromBase64String(ivXmlAttribute.Value);
            }
            catch (FormatException)
            {
                throw new InvalidXmlException($"Invalid value of Attribute \"IV\" ({ivXmlAttribute.Value}) in encrypted node {element.Name} ", element);
            }
            var cryptoServiceProvider = new TripleDESCryptoServiceProvider {
                IV = numArray
            };

            var passwordDeriveBytes = new PasswordDeriveBytes(password, rgbSalt);

            var encryptedData = new EncryptedData();

            encryptedData.LoadXml(element);


            cryptoServiceProvider.Key = passwordDeriveBytes.CryptDeriveKey("TripleDES", "SHA1", 192,
                                                                           cryptoServiceProvider.IV);

            // weird edge case - if this is a parameter value, then it must replace one more parent level up
            var elementToReplace = element.ParentNode?.Name == "DTS:Property" && (element.ParentNode as XmlElement) != null && element.ParentNode?.ParentNode?.Name == "DTS:PackageParameter"
                ? (XmlElement)element.ParentNode
                : element;

            var exml = new EncryptedXml();

            try
            {
                var output = exml.DecryptData(encryptedData, cryptoServiceProvider);
                exml.ReplaceData(elementToReplace, output);
            }
            catch (CryptographicException)
            {
                throw new InvalidPaswordException();
            }
        }
Ejemplo n.º 23
0
        public static (OuterContainer ContainerOuter, InnerContainer ContainerInner, byte[] Key) DecryptOuterContainer(byte[] fileBytes, string password)
        {
            byte[] outerContainerBytes;

            try
            {
                outerContainerBytes = Shared.Utility.Decompress(fileBytes);
            }
            catch (Exception ex)
            {
                throw new Exception(string.Format("failed to decompress (corrupted or not a valid container file): {0}", ex.Message));
            }

            XmlDocument outerContainerXml = new XmlDocument();

            outerContainerXml.LoadXml(Encoding.UTF8.GetString(outerContainerBytes));

            string version;

            try
            {
                version = outerContainerXml.SelectSingleNode("/OuterContainer/@version").Value;
            }
            catch (Exception ex)
            {
                throw new Exception(string.Format("unable to read /OuterContainer/@version: {0}", ex.Message));
            }

            Version parsedVersion = new Version(version);

            if (parsedVersion.Major != 1)
            {
                throw new Exception(string.Format("outer container version too new (this container was written on a newer software version) - expected 1, got {0}", parsedVersion.Major));
            }

            OuterContainer outerContainer = new OuterContainer();

            string outerVersion = "1.0";

            outerContainer.Version       = outerVersion;
            outerContainer.KeyDerivation = new KeyDerivation();

            byte[] key;

            string derivationAlgorithm;

            try
            {
                derivationAlgorithm = outerContainerXml.SelectSingleNode("/OuterContainer/KeyDerivation/DerivationAlgorithm").InnerText;
            }
            catch (Exception ex)
            {
                throw new Exception(string.Format("invalid KeyDerivation DerivationAlgorithm: {0}", ex.Message));
            }

            outerContainer.KeyDerivation.DerivationAlgorithm = derivationAlgorithm;

            if (derivationAlgorithm == "PBKDF2")
            {
                string hashAlgorithm;

                try
                {
                    hashAlgorithm = outerContainerXml.SelectSingleNode("/OuterContainer/KeyDerivation/HashAlgorithm").InnerText;
                }
                catch (Exception ex)
                {
                    throw new Exception(string.Format("invalid KeyDerivation HashAlgorithm: {0}", ex.Message));
                }

                outerContainer.KeyDerivation.HashAlgorithm = hashAlgorithm;

                byte[] salt;

                try
                {
                    salt = Convert.FromBase64String(outerContainerXml.SelectSingleNode("/OuterContainer/KeyDerivation/Salt").InnerText);
                }
                catch (Exception ex)
                {
                    throw new Exception(string.Format("invalid KeyDerivation Salt: {0}", ex.Message));
                }

                outerContainer.KeyDerivation.Salt = salt;

                int iterationCount;

                try
                {
                    iterationCount = Convert.ToInt32(outerContainerXml.SelectSingleNode("/OuterContainer/KeyDerivation/IterationCount").InnerText);
                }
                catch (Exception ex)
                {
                    throw new Exception(string.Format("invalid KeyDerivation IterationCount: {0}", ex.Message));
                }

                outerContainer.KeyDerivation.IterationCount = iterationCount;

                int keyLength;

                try
                {
                    keyLength = Convert.ToInt32(outerContainerXml.SelectSingleNode("/OuterContainer/KeyDerivation/KeyLength").InnerText);
                }
                catch (Exception ex)
                {
                    throw new Exception(string.Format("invalid KeyDerivation KeyLength: {0}", ex.Message));
                }

                outerContainer.KeyDerivation.KeyLength = keyLength;

                key = Pbkdf2DeriveKeyFromPassword(password, salt, iterationCount, hashAlgorithm, keyLength);
            }
            else
            {
                throw new Exception(string.Format("unsupported KeyDerivation DerivationAlgorithm: {0}", derivationAlgorithm));
            }

            outerContainer.EncryptedDataPlaceholder = "placeholder";

            XmlElement encryptedDataElement = outerContainerXml.GetElementsByTagName("EncryptedData")[0] as XmlElement;

            if (encryptedDataElement == null)
            {
                throw new Exception("unable to find EncryptedData");
            }

            EncryptedData encryptedData = new EncryptedData();

            encryptedData.LoadXml(encryptedDataElement);

            EncryptedXml encryptedXml = new EncryptedXml();

            byte[] innerContainerBytes;

            using (AesCryptoServiceProvider aesCsp = new AesCryptoServiceProvider())
            {
                aesCsp.KeySize = 256;            // critical security parameter
                aesCsp.Key     = key;            // critical security parameter
                aesCsp.Mode    = CipherMode.CBC; // critical security parameter
                aesCsp.GenerateIV();             // critical security parameter

                try
                {
                    innerContainerBytes = encryptedXml.DecryptData(encryptedData, aesCsp);
                }
                catch (Exception ex)
                {
                    throw new Exception(string.Format("unable to decrypt InnerContainer (check password): {0}", ex.Message));
                }
            }

            XmlDocument innerContainerXml = new XmlDocument();

            try
            {
                innerContainerXml.LoadXml(Encoding.UTF8.GetString(innerContainerBytes));
            }
            catch (Exception ex)
            {
                throw new Exception(string.Format("unable to parse InnerContainer (check password): {0}", ex.Message));
            }

            string innerReadVersion;

            try
            {
                innerReadVersion = innerContainerXml.SelectSingleNode("/InnerContainer/@version").Value;
            }
            catch (Exception ex)
            {
                throw new Exception(string.Format("unable to read /InnerContainer/@version: {0}", ex.Message));
            }

            Version innerReadVersionParsed = new Version(innerReadVersion);

            if (innerReadVersionParsed.Major != 1)
            {
                throw new Exception(string.Format("inner container version too new (this container was written on a newer software version) - expected 1, got {0}", innerReadVersionParsed.Major));
            }

            InnerContainer innerContainer;

            using (XmlReader xmlReader = new XmlNodeReader(innerContainerXml))
            {
                try
                {
                    innerContainer = (InnerContainer) new XmlSerializer(typeof(InnerContainer)).Deserialize(xmlReader);
                }
                catch (Exception ex)
                {
                    throw new Exception(string.Format("unable to deserialize InnerContainer: {0}", ex.Message));
                }
            }

            return(outerContainer, innerContainer, key);
        }
Ejemplo n.º 24
0
        public void RoundtripSample1()
        {
            using (StringWriter sw = new StringWriter())
            {
                // Encryption
                {
                    XmlDocument doc = new XmlDocument();
                    doc.PreserveWhitespace = true;
                    doc.LoadXml("<root>  <child>sample</child>   </root>");

                    XmlElement body = doc.DocumentElement;

                    using (Aes aes = Aes.Create())
                    {
                        aes.Mode    = CipherMode.CBC;
                        aes.KeySize = 256;
                        aes.IV      = Convert.FromBase64String("pBUM5P03rZ6AE4ZK5EyBrw==");
                        aes.Key     = Convert.FromBase64String("o/ilseZu+keLBBWGGPlUHweqxIPc4gzZEFWr2nBt640=");
                        aes.Padding = PaddingMode.Zeros;

                        EncryptedXml  exml      = new EncryptedXml();
                        byte[]        encrypted = exml.EncryptData(body, aes, false);
                        EncryptedData edata     = new EncryptedData();
                        edata.Type             = EncryptedXml.XmlEncElementUrl;
                        edata.EncryptionMethod = new EncryptionMethod(EncryptedXml.XmlEncAES256Url);
                        EncryptedKey ekey = new EncryptedKey();
                        // omit key encryption, here for testing
                        byte[] encKeyBytes = aes.Key;
                        ekey.CipherData       = new CipherData(encKeyBytes);
                        ekey.EncryptionMethod = new EncryptionMethod(EncryptedXml.XmlEncRSA15Url);
                        DataReference dr = new DataReference();
                        dr.Uri = "_0";
                        ekey.AddReference(dr);
                        edata.KeyInfo.AddClause(new KeyInfoEncryptedKey(ekey));
                        edata.KeyInfo = new KeyInfo();
                        ekey.KeyInfo.AddClause(new RSAKeyValue(RSA.Create()));
                        edata.CipherData.CipherValue = encrypted;
                        EncryptedXml.ReplaceElement(doc.DocumentElement, edata, false);
                        doc.Save(new XmlTextWriter(sw));
                    }
                }

                // Decryption
                {
                    using (Aes aes = Aes.Create())
                    {
                        aes.Mode    = CipherMode.CBC;
                        aes.KeySize = 256;
                        aes.Key     = Convert.FromBase64String(
                            "o/ilseZu+keLBBWGGPlUHweqxIPc4gzZEFWr2nBt640=");
                        aes.Padding = PaddingMode.Zeros;

                        XmlDocument doc = new XmlDocument();
                        doc.PreserveWhitespace = true;
                        doc.LoadXml(sw.ToString());
                        EncryptedXml  encxml = new EncryptedXml(doc);
                        EncryptedData edata  = new EncryptedData();
                        edata.LoadXml(doc.DocumentElement);
                        encxml.ReplaceData(doc.DocumentElement, encxml.DecryptData(edata, aes));
                    }
                }
            }
        }