From d1cdd4321e0de4ae2c54b41607731d8c5e307249 Mon Sep 17 00:00:00 2001 From: Samo Prelog Date: Wed, 29 Nov 2023 14:57:27 +0000 Subject: [PATCH 1/8] adding failing test case for https://github.com/dotnet/runtime/issues/95390 --- .../tests/SignedXmlTest.cs | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/src/libraries/System.Security.Cryptography.Xml/tests/SignedXmlTest.cs b/src/libraries/System.Security.Cryptography.Xml/tests/SignedXmlTest.cs index 3db8c44aed8270..f6d929929e101e 100644 --- a/src/libraries/System.Security.Cryptography.Xml/tests/SignedXmlTest.cs +++ b/src/libraries/System.Security.Cryptography.Xml/tests/SignedXmlTest.cs @@ -1993,5 +1993,18 @@ public void CheckSignatureHandlesIncorrectOrTamperedReferenceWithMultipleEnvelop Assert.False(subject.CheckSignature()); } + + [Fact] + [ActiveIssue("https://github.com/dotnet/runtime/issues/95390")] + public void CheckSignatureHandlesEnvelopedSignatureWithRootXpointerReference() + { + const string EnvelopedSignatureWithRootXpointerReference = """HiSVaCE5w9iLXTVYTKP1t/yjjmPXvWovMYpgljGgpgz2Y=dqcBmS1ZvDJNhmCEgobpAb+A2XaiuB69dfGIhisZvqoxaWqAqv/0w49jp38+usJ5t3wcq3aMC631QE8iln+lHWrarojDMDWLa00isv3oE3q9UgOIV9e6MUSoRTTvQkmlK/LSYV9T/SKx6h03vLLcIkUMXaTkC/n2kthlJTGkLbU=t6qV1iTlkCPoaIeOTvnDczQv5pytUxMoyNXws5vaMQYxfJMKos47dvmiLtfWUDLYXFX3Yf/JMC14plJw2JA5jLrlHLnZj/vCjRtXckmWW/wGYewXUqrgR1CytStUeQKj9mNsi76erukua10UhzIrWG+H6YQ/qS4AMMJZU6jBvO0=AQAB"""; + XmlDocument xmlDoc = new (); + xmlDoc.LoadXml(EnvelopedSignatureWithRootXpointerReference); + SignedXml signedXml = new (xmlDoc); + signedXml.LoadXml(xmlDoc.GetElementsByTagName("Signature", SignedXml.XmlDsigNamespaceUrl)[0] as XmlElement); + + Assert.True(signedXml.CheckSignature()); + } } } From e5d4e3bd9ce8dea4207dda4d6c3dab5932e13a78 Mon Sep 17 00:00:00 2001 From: Samo Prelog Date: Wed, 29 Nov 2023 20:06:10 +0000 Subject: [PATCH 2/8] adding both positive and negative tests, in-line with recommendations in past PRs --- .../tests/SignedXmlTest.cs | 21 +++++++++++++------ 1 file changed, 15 insertions(+), 6 deletions(-) diff --git a/src/libraries/System.Security.Cryptography.Xml/tests/SignedXmlTest.cs b/src/libraries/System.Security.Cryptography.Xml/tests/SignedXmlTest.cs index f6d929929e101e..32d9fa71641ad6 100644 --- a/src/libraries/System.Security.Cryptography.Xml/tests/SignedXmlTest.cs +++ b/src/libraries/System.Security.Cryptography.Xml/tests/SignedXmlTest.cs @@ -9,6 +9,7 @@ // (C) 2002, 2003 Motus Technologies Inc. (http://www.motus.com) // Copyright (C) 2004-2005, 2008 Novell, Inc (http://www.novell.com) +using System.Collections.Generic; using System.Globalization; using System.IO; using System.Net; @@ -1994,17 +1995,25 @@ public void CheckSignatureHandlesIncorrectOrTamperedReferenceWithMultipleEnvelop Assert.False(subject.CheckSignature()); } - [Fact] - [ActiveIssue("https://github.com/dotnet/runtime/issues/95390")] - public void CheckSignatureHandlesEnvelopedSignatureWithRootXpointerReference() + private static Dictionary EnvelopedSignatureWithRootXpointerReference = new () + { + ["Valid"] = """HiSVaCE5w9iLXTVYTKP1t/yjjmPXvWovMYpgljGgpgz2Y=dqcBmS1ZvDJNhmCEgobpAb+A2XaiuB69dfGIhisZvqoxaWqAqv/0w49jp38+usJ5t3wcq3aMC631QE8iln+lHWrarojDMDWLa00isv3oE3q9UgOIV9e6MUSoRTTvQkmlK/LSYV9T/SKx6h03vLLcIkUMXaTkC/n2kthlJTGkLbU=t6qV1iTlkCPoaIeOTvnDczQv5pytUxMoyNXws5vaMQYxfJMKos47dvmiLtfWUDLYXFX3Yf/JMC14plJw2JA5jLrlHLnZj/vCjRtXckmWW/wGYewXUqrgR1CytStUeQKj9mNsi76erukua10UhzIrWG+H6YQ/qS4AMMJZU6jBvO0=AQAB""", + ["Tampered"] = """Tempered worldSVaCE5w9iLXTVYTKP1t/yjjmPXvWovMYpgljGgpgz2Y=dqcBmS1ZvDJNhmCEgobpAb+A2XaiuB69dfGIhisZvqoxaWqAqv/0w49jp38+usJ5t3wcq3aMC631QE8iln+lHWrarojDMDWLa00isv3oE3q9UgOIV9e6MUSoRTTvQkmlK/LSYV9T/SKx6h03vLLcIkUMXaTkC/n2kthlJTGkLbU=t6qV1iTlkCPoaIeOTvnDczQv5pytUxMoyNXws5vaMQYxfJMKos47dvmiLtfWUDLYXFX3Yf/JMC14plJw2JA5jLrlHLnZj/vCjRtXckmWW/wGYewXUqrgR1CytStUeQKj9mNsi76erukua10UhzIrWG+H6YQ/qS4AMMJZU6jBvO0=AQAB""", + }; + + [Theory] + [InlineData("Valid", true)] + [InlineData("Tampered", false)] + // [ActiveIssue("https://github.com/dotnet/runtime/issues/95390")] + // dotnet test src/libraries/System.Security.Cryptography.Xml/tests/ --framework net9.0 + public void CheckSignatureHandlesEnvelopedSignatureWithRootXpointerReference(string caseName, bool isValid) { - const string EnvelopedSignatureWithRootXpointerReference = """HiSVaCE5w9iLXTVYTKP1t/yjjmPXvWovMYpgljGgpgz2Y=dqcBmS1ZvDJNhmCEgobpAb+A2XaiuB69dfGIhisZvqoxaWqAqv/0w49jp38+usJ5t3wcq3aMC631QE8iln+lHWrarojDMDWLa00isv3oE3q9UgOIV9e6MUSoRTTvQkmlK/LSYV9T/SKx6h03vLLcIkUMXaTkC/n2kthlJTGkLbU=t6qV1iTlkCPoaIeOTvnDczQv5pytUxMoyNXws5vaMQYxfJMKos47dvmiLtfWUDLYXFX3Yf/JMC14plJw2JA5jLrlHLnZj/vCjRtXckmWW/wGYewXUqrgR1CytStUeQKj9mNsi76erukua10UhzIrWG+H6YQ/qS4AMMJZU6jBvO0=AQAB"""; XmlDocument xmlDoc = new (); - xmlDoc.LoadXml(EnvelopedSignatureWithRootXpointerReference); + xmlDoc.LoadXml(EnvelopedSignatureWithRootXpointerReference[caseName]); SignedXml signedXml = new (xmlDoc); signedXml.LoadXml(xmlDoc.GetElementsByTagName("Signature", SignedXml.XmlDsigNamespaceUrl)[0] as XmlElement); - Assert.True(signedXml.CheckSignature()); + Assert.Equal(isValid, signedXml.CheckSignature()); } } } From 9e8c55863c83aca05197fe1335deaad73216589c Mon Sep 17 00:00:00 2001 From: Samo Prelog Date: Wed, 29 Nov 2023 20:45:46 +0000 Subject: [PATCH 3/8] fix implemented --- .../Security/Cryptography/Xml/Reference.cs | 29 +++++++++++++++---- .../tests/SignedXmlTest.cs | 2 -- 2 files changed, 23 insertions(+), 8 deletions(-) diff --git a/src/libraries/System.Security.Cryptography.Xml/src/System/Security/Cryptography/Xml/Reference.cs b/src/libraries/System.Security.Cryptography.Xml/src/System/Security/Cryptography/Xml/Reference.cs index 001aaf26a21aee..962c8037267ded 100644 --- a/src/libraries/System.Security.Cryptography.Xml/src/System/Security/Cryptography/Xml/Reference.cs +++ b/src/libraries/System.Security.Cryptography.Xml/src/System/Security/Cryptography/Xml/Reference.cs @@ -266,18 +266,35 @@ public void LoadXml(XmlElement value) // let the transform read the children of the transformElement for data transform.LoadInnerXml(transformElement.ChildNodes); // Hack! this is done to get around the lack of here() function support in XPath - if (transform is XmlDsigEnvelopedSignatureTransform - && _uri != null && (_uri.Length == 0 || _uri[0] == '#')) + if (transform is XmlDsigEnvelopedSignatureTransform) { // Walk back to the Signature tag. Find the nearest signature ancestor // Signature-->SignedInfo-->Reference-->Transforms-->Transform XmlNode? signatureTag = transformElement.SelectSingleNode("ancestor::ds:Signature[1]", nsm); // Resolve the reference to get starting point for position calculation. - XmlNode? referenceTarget = - _uri.Length == 0 - ? transformElement.OwnerDocument - : SignedXml!.GetIdElement(transformElement.OwnerDocument, Utils.GetIdFromLocalUri(_uri, out bool _)); + // This needs to match the way CalculateSignature resolves URI references. + XmlNode? referenceTarget = null; + if (_uri == null) + { + referenceTarget = transformElement.OwnerDocument; + } + else if (_uri.Length == 0) + { + referenceTarget = transformElement.OwnerDocument; + } + else if (_uri[0] == '#') + { + var idref = Utils.ExtractIdFromLocalUri(_uri); + if (idref == "xpointer(/)") + { + referenceTarget = transformElement.OwnerDocument; + } + else + { + referenceTarget = SignedXml!.GetIdElement(transformElement.OwnerDocument, idref); + } + } XmlNodeList? signatureList = referenceTarget?.SelectNodes(".//ds:Signature", nsm); if (signatureList != null) diff --git a/src/libraries/System.Security.Cryptography.Xml/tests/SignedXmlTest.cs b/src/libraries/System.Security.Cryptography.Xml/tests/SignedXmlTest.cs index 32d9fa71641ad6..7dbe14e4a50d46 100644 --- a/src/libraries/System.Security.Cryptography.Xml/tests/SignedXmlTest.cs +++ b/src/libraries/System.Security.Cryptography.Xml/tests/SignedXmlTest.cs @@ -2004,8 +2004,6 @@ public void CheckSignatureHandlesIncorrectOrTamperedReferenceWithMultipleEnvelop [Theory] [InlineData("Valid", true)] [InlineData("Tampered", false)] - // [ActiveIssue("https://github.com/dotnet/runtime/issues/95390")] - // dotnet test src/libraries/System.Security.Cryptography.Xml/tests/ --framework net9.0 public void CheckSignatureHandlesEnvelopedSignatureWithRootXpointerReference(string caseName, bool isValid) { XmlDocument xmlDoc = new (); From d7542caffebeb6a7032c5e2255b605660d61e146 Mon Sep 17 00:00:00 2001 From: Samo Prelog Date: Wed, 29 Nov 2023 22:45:31 +0100 Subject: [PATCH 4/8] Update src/libraries/System.Security.Cryptography.Xml/src/System/Security/Cryptography/Xml/Reference.cs Co-authored-by: Kevin Jones --- .../src/System/Security/Cryptography/Xml/Reference.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/libraries/System.Security.Cryptography.Xml/src/System/Security/Cryptography/Xml/Reference.cs b/src/libraries/System.Security.Cryptography.Xml/src/System/Security/Cryptography/Xml/Reference.cs index 962c8037267ded..90c4cea4d5f9d2 100644 --- a/src/libraries/System.Security.Cryptography.Xml/src/System/Security/Cryptography/Xml/Reference.cs +++ b/src/libraries/System.Security.Cryptography.Xml/src/System/Security/Cryptography/Xml/Reference.cs @@ -285,7 +285,7 @@ public void LoadXml(XmlElement value) } else if (_uri[0] == '#') { - var idref = Utils.ExtractIdFromLocalUri(_uri); + string idref = Utils.ExtractIdFromLocalUri(_uri); if (idref == "xpointer(/)") { referenceTarget = transformElement.OwnerDocument; From 5f469bb023042a42de382e1152f2db580b67c7a9 Mon Sep 17 00:00:00 2001 From: Samo Prelog Date: Wed, 29 Nov 2023 23:02:39 +0100 Subject: [PATCH 5/8] Update src/libraries/System.Security.Cryptography.Xml/src/System/Security/Cryptography/Xml/Reference.cs Co-authored-by: Kevin Jones --- .../src/System/Security/Cryptography/Xml/Reference.cs | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/src/libraries/System.Security.Cryptography.Xml/src/System/Security/Cryptography/Xml/Reference.cs b/src/libraries/System.Security.Cryptography.Xml/src/System/Security/Cryptography/Xml/Reference.cs index 90c4cea4d5f9d2..ec6e6cabc2cdfa 100644 --- a/src/libraries/System.Security.Cryptography.Xml/src/System/Security/Cryptography/Xml/Reference.cs +++ b/src/libraries/System.Security.Cryptography.Xml/src/System/Security/Cryptography/Xml/Reference.cs @@ -275,11 +275,7 @@ public void LoadXml(XmlElement value) // Resolve the reference to get starting point for position calculation. // This needs to match the way CalculateSignature resolves URI references. XmlNode? referenceTarget = null; - if (_uri == null) - { - referenceTarget = transformElement.OwnerDocument; - } - else if (_uri.Length == 0) + if (_uri == null || _uri.Length == 0) { referenceTarget = transformElement.OwnerDocument; } From ea74198c7072e6ca5e9c260d64b688d805e1e3a4 Mon Sep 17 00:00:00 2001 From: Samo Prelog Date: Sat, 16 Dec 2023 14:13:31 +0000 Subject: [PATCH 6/8] using MemberData for tests --- .../tests/SignedXmlTest.cs | 13 ++++++------- 1 file changed, 6 insertions(+), 7 deletions(-) diff --git a/src/libraries/System.Security.Cryptography.Xml/tests/SignedXmlTest.cs b/src/libraries/System.Security.Cryptography.Xml/tests/SignedXmlTest.cs index 7dbe14e4a50d46..31cec26bfcba01 100644 --- a/src/libraries/System.Security.Cryptography.Xml/tests/SignedXmlTest.cs +++ b/src/libraries/System.Security.Cryptography.Xml/tests/SignedXmlTest.cs @@ -1995,19 +1995,18 @@ public void CheckSignatureHandlesIncorrectOrTamperedReferenceWithMultipleEnvelop Assert.False(subject.CheckSignature()); } - private static Dictionary EnvelopedSignatureWithRootXpointerReference = new () + private static object[][] EnvelopedSignatureWithRootXpointerReference = new object[][] { - ["Valid"] = """HiSVaCE5w9iLXTVYTKP1t/yjjmPXvWovMYpgljGgpgz2Y=dqcBmS1ZvDJNhmCEgobpAb+A2XaiuB69dfGIhisZvqoxaWqAqv/0w49jp38+usJ5t3wcq3aMC631QE8iln+lHWrarojDMDWLa00isv3oE3q9UgOIV9e6MUSoRTTvQkmlK/LSYV9T/SKx6h03vLLcIkUMXaTkC/n2kthlJTGkLbU=t6qV1iTlkCPoaIeOTvnDczQv5pytUxMoyNXws5vaMQYxfJMKos47dvmiLtfWUDLYXFX3Yf/JMC14plJw2JA5jLrlHLnZj/vCjRtXckmWW/wGYewXUqrgR1CytStUeQKj9mNsi76erukua10UhzIrWG+H6YQ/qS4AMMJZU6jBvO0=AQAB""", - ["Tampered"] = """Tempered worldSVaCE5w9iLXTVYTKP1t/yjjmPXvWovMYpgljGgpgz2Y=dqcBmS1ZvDJNhmCEgobpAb+A2XaiuB69dfGIhisZvqoxaWqAqv/0w49jp38+usJ5t3wcq3aMC631QE8iln+lHWrarojDMDWLa00isv3oE3q9UgOIV9e6MUSoRTTvQkmlK/LSYV9T/SKx6h03vLLcIkUMXaTkC/n2kthlJTGkLbU=t6qV1iTlkCPoaIeOTvnDczQv5pytUxMoyNXws5vaMQYxfJMKos47dvmiLtfWUDLYXFX3Yf/JMC14plJw2JA5jLrlHLnZj/vCjRtXckmWW/wGYewXUqrgR1CytStUeQKj9mNsi76erukua10UhzIrWG+H6YQ/qS4AMMJZU6jBvO0=AQAB""", + new object[] { true, """HiSVaCE5w9iLXTVYTKP1t/yjjmPXvWovMYpgljGgpgz2Y=dqcBmS1ZvDJNhmCEgobpAb+A2XaiuB69dfGIhisZvqoxaWqAqv/0w49jp38+usJ5t3wcq3aMC631QE8iln+lHWrarojDMDWLa00isv3oE3q9UgOIV9e6MUSoRTTvQkmlK/LSYV9T/SKx6h03vLLcIkUMXaTkC/n2kthlJTGkLbU=t6qV1iTlkCPoaIeOTvnDczQv5pytUxMoyNXws5vaMQYxfJMKos47dvmiLtfWUDLYXFX3Yf/JMC14plJw2JA5jLrlHLnZj/vCjRtXckmWW/wGYewXUqrgR1CytStUeQKj9mNsi76erukua10UhzIrWG+H6YQ/qS4AMMJZU6jBvO0=AQAB""" }, + new object[] { false, """Tempered worldSVaCE5w9iLXTVYTKP1t/yjjmPXvWovMYpgljGgpgz2Y=dqcBmS1ZvDJNhmCEgobpAb+A2XaiuB69dfGIhisZvqoxaWqAqv/0w49jp38+usJ5t3wcq3aMC631QE8iln+lHWrarojDMDWLa00isv3oE3q9UgOIV9e6MUSoRTTvQkmlK/LSYV9T/SKx6h03vLLcIkUMXaTkC/n2kthlJTGkLbU=t6qV1iTlkCPoaIeOTvnDczQv5pytUxMoyNXws5vaMQYxfJMKos47dvmiLtfWUDLYXFX3Yf/JMC14plJw2JA5jLrlHLnZj/vCjRtXckmWW/wGYewXUqrgR1CytStUeQKj9mNsi76erukua10UhzIrWG+H6YQ/qS4AMMJZU6jBvO0=AQAB""" }, }; [Theory] - [InlineData("Valid", true)] - [InlineData("Tampered", false)] - public void CheckSignatureHandlesEnvelopedSignatureWithRootXpointerReference(string caseName, bool isValid) + [MemberData(nameof(EnvelopedSignatureWithRootXpointerReference))] + public void CheckSignatureHandlesEnvelopedSignatureWithRootXpointerReference(bool isValid, string xml) { XmlDocument xmlDoc = new (); - xmlDoc.LoadXml(EnvelopedSignatureWithRootXpointerReference[caseName]); + xmlDoc.LoadXml(xml); SignedXml signedXml = new (xmlDoc); signedXml.LoadXml(xmlDoc.GetElementsByTagName("Signature", SignedXml.XmlDsigNamespaceUrl)[0] as XmlElement); From f4c2b2761acabf18bb51d2c40dad9f84c5936df9 Mon Sep 17 00:00:00 2001 From: Samo Prelog Date: Sat, 16 Dec 2023 15:31:00 +0000 Subject: [PATCH 7/8] making memberdata target public --- .../System.Security.Cryptography.Xml/tests/SignedXmlTest.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/libraries/System.Security.Cryptography.Xml/tests/SignedXmlTest.cs b/src/libraries/System.Security.Cryptography.Xml/tests/SignedXmlTest.cs index 31cec26bfcba01..a4497eaa5afa8a 100644 --- a/src/libraries/System.Security.Cryptography.Xml/tests/SignedXmlTest.cs +++ b/src/libraries/System.Security.Cryptography.Xml/tests/SignedXmlTest.cs @@ -1995,7 +1995,7 @@ public void CheckSignatureHandlesIncorrectOrTamperedReferenceWithMultipleEnvelop Assert.False(subject.CheckSignature()); } - private static object[][] EnvelopedSignatureWithRootXpointerReference = new object[][] + public static object[][] EnvelopedSignatureWithRootXpointerReference = new object[][] { new object[] { true, """HiSVaCE5w9iLXTVYTKP1t/yjjmPXvWovMYpgljGgpgz2Y=dqcBmS1ZvDJNhmCEgobpAb+A2XaiuB69dfGIhisZvqoxaWqAqv/0w49jp38+usJ5t3wcq3aMC631QE8iln+lHWrarojDMDWLa00isv3oE3q9UgOIV9e6MUSoRTTvQkmlK/LSYV9T/SKx6h03vLLcIkUMXaTkC/n2kthlJTGkLbU=t6qV1iTlkCPoaIeOTvnDczQv5pytUxMoyNXws5vaMQYxfJMKos47dvmiLtfWUDLYXFX3Yf/JMC14plJw2JA5jLrlHLnZj/vCjRtXckmWW/wGYewXUqrgR1CytStUeQKj9mNsi76erukua10UhzIrWG+H6YQ/qS4AMMJZU6jBvO0=AQAB""" }, new object[] { false, """Tempered worldSVaCE5w9iLXTVYTKP1t/yjjmPXvWovMYpgljGgpgz2Y=dqcBmS1ZvDJNhmCEgobpAb+A2XaiuB69dfGIhisZvqoxaWqAqv/0w49jp38+usJ5t3wcq3aMC631QE8iln+lHWrarojDMDWLa00isv3oE3q9UgOIV9e6MUSoRTTvQkmlK/LSYV9T/SKx6h03vLLcIkUMXaTkC/n2kthlJTGkLbU=t6qV1iTlkCPoaIeOTvnDczQv5pytUxMoyNXws5vaMQYxfJMKos47dvmiLtfWUDLYXFX3Yf/JMC14plJw2JA5jLrlHLnZj/vCjRtXckmWW/wGYewXUqrgR1CytStUeQKj9mNsi76erukua10UhzIrWG+H6YQ/qS4AMMJZU6jBvO0=AQAB""" }, From 90f2ff260aba9aafaf420f840370114a5d400959 Mon Sep 17 00:00:00 2001 From: Samo Prelog Date: Wed, 10 Jan 2024 14:47:24 +0000 Subject: [PATCH 8/8] adding test cases for empty --- .../tests/SignedXmlTest.cs | 22 +++++++++++++++++++ 1 file changed, 22 insertions(+) diff --git a/src/libraries/System.Security.Cryptography.Xml/tests/SignedXmlTest.cs b/src/libraries/System.Security.Cryptography.Xml/tests/SignedXmlTest.cs index a4497eaa5afa8a..bd22c5b835eed8 100644 --- a/src/libraries/System.Security.Cryptography.Xml/tests/SignedXmlTest.cs +++ b/src/libraries/System.Security.Cryptography.Xml/tests/SignedXmlTest.cs @@ -2012,5 +2012,27 @@ public void CheckSignatureHandlesEnvelopedSignatureWithRootXpointerReference(boo Assert.Equal(isValid, signedXml.CheckSignature()); } + + + public static object[][] EnvelopedSignatureWithEmptyReference = new object[][] + { + new object[] { true, """HiSVaCE5w9iLXTVYTKP1t/yjjmPXvWovMYpgljGgpgz2Y=CiB9jgIS7+Wq+lpyzCGsBZQcQ2BxqQuEU9VCvb3Li5jMtjwRV1bMO+4Wfnb4VWhEtEUq6NdiVGXhC1xvtVLnnLDX7CD/jG6NvM1Yd0/rf0UUceBhzYLFE9HLsopsBmmm3t8FO6ZtRr1QqKM0XDaQleGK9vYd2m2Jq8OR3r/w4OY=vcM1wQVmLB9DwdnAym8l8nw63/HlTVzgTDhIwNzWPhsPE/qr2wlK4TEQ3rjU+RAdNytfFNCnuuh75ZVMjAWCV9h6VDlp0DOvBhb6GenhymtTAdJJKzBXKJP6mNPga9cPOP31IZ36Ui00G3fjBBPrHa7nStludgL9Wi0dBU28DjU=AQAB""" }, + new object[] { false, """HISVaCE5w9iLXTVYTKP1t/yjjmPXvWovMYpgljGgpgz2Y=CiB9jgIS7+Wq+lpyzCGsBZQcQ2BxqQuEU9VCvb3Li5jMtjwRV1bMO+4Wfnb4VWhEtEUq6NdiVGXhC1xvtVLnnLDX7CD/jG6NvM1Yd0/rf0UUceBhzYLFE9HLsopsBmmm3t8FO6ZtRr1QqKM0XDaQleGK9vYd2m2Jq8OR3r/w4OY=vcM1wQVmLB9DwdnAym8l8nw63/HlTVzgTDhIwNzWPhsPE/qr2wlK4TEQ3rjU+RAdNytfFNCnuuh75ZVMjAWCV9h6VDlp0DOvBhb6GenhymtTAdJJKzBXKJP6mNPga9cPOP31IZ36Ui00G3fjBBPrHa7nStludgL9Wi0dBU28DjU=AQAB""" }, + }; + + [Theory] + [MemberData(nameof(EnvelopedSignatureWithEmptyReference))] + public void CheckSignatureHandlesEnvelopedSignatureWithEmptyReference(bool isValid, string xml) + { + XmlDocument xmlDoc = new (); + xmlDoc.LoadXml(xml); + SignedXml signedXml = new (xmlDoc); + signedXml.LoadXml(xmlDoc.GetElementsByTagName("Signature", SignedXml.XmlDsigNamespaceUrl)[0] as XmlElement); + + // without this, CheckSignature throws + ((Reference)signedXml.SignedInfo.References[0]).TransformChain[0].LoadInput(xmlDoc); + + Assert.Equal(isValid, signedXml.CheckSignature()); + } } }