gpt4 book ai didi

c# - SignedXml checksignature 返回 false

转载 作者:可可西里 更新时间:2023-11-01 09:07:45 26 4
gpt4 key购买 nike

我已经查看了此处关于此问题的其他帖子,但似乎都没有解决我的情况。

上周我一直在尝试验证 SAML 断言,我有 2 个客户向我发送了 SAML,但我无法验证它。

主要过程是我们得到一个 base64 编码的断言,然后我对其进行解码。使用 PreserveWhitespace = true 将其加载到 XmlDocment 中。

验证方法是

  public static bool Verify(X509Certificate2 cert, XmlElement xmlElement, SignedXml signedXml)
{
bool flag;
try
{
KeyInfo keyInfo = new KeyInfo();
var clause = new KeyInfoX509Data(cert);
keyInfo.AddClause(clause);

XmlElement signatureElement = GetSignatureElement(xmlElement);
if (signatureElement == null)
{
string message = "The XML does not contain a signature.";
throw new SAMLSignatureException(message);
}
signedXml.LoadXml(signatureElement);
if (keyInfo != null)
{
signedXml.KeyInfo = keyInfo;
}
SetSigningKeyFromKeyInfo(signedXml);
flag = signedXml.CheckSignature(cert.PublicKey.Key);
}
catch (Exception exception)
{
throw new SAMLSignatureException("Failed to verify the XML signature.", exception);
}
return flag;
}

private static void SetSigningKeyFromKeyInfo(SignedXml signedXml)
{
IEnumerator enumerator = signedXml.KeyInfo.GetEnumerator();
while (enumerator.MoveNext())
{
if (enumerator.Current is KeyInfoX509Data)
{
var current = (KeyInfoX509Data) enumerator.Current;
if (current.Certificates.Count != 0)
{
var certificate = (X509Certificate) current.Certificates[0];
var certificate2 = new X509Certificate2(certificate);
AsymmetricAlgorithm key = certificate2.PublicKey.Key;
signedXml.SigningKey = key;
return;
}
}
else
{
if (enumerator.Current is RSAKeyValue)
{
var value2 = (RSAKeyValue) enumerator.Current;
signedXml.SigningKey = value2.Key;
return;
}
if (enumerator.Current is DSAKeyValue)
{
var value3 = (DSAKeyValue) enumerator.Current;
signedXml.SigningKey = value3.Key;
return;
}
}
}
throw new SAMLSignatureException("No signing key could be found in the key info.");
}

我有从 Web.Config 中读取的客户端证书(它存储为 base64 编码字符串)xmlelement 是签名元素,signedXml 是使用 new SignedXml(xmlElement) 创建的 SignedXml 对象

两个客户端都得到 checksignature 返回的 false,但是当我用我的证书创建自己的签名 saml 时,它将返回 true。

我在这里错过了什么?

编辑:是的,两个客户端都在 Java 上,我发布了 SetSigningKeyFromKeyInfo 方法

最佳答案

我过去经常处理签名的 XML。我只能说这是一场噩梦。基本上,当您签署 XML 时,它会经历一个称为规范化 (C14N) 的过程。它需要将 XML 文本转换为可以签名的字节流。 XML C14N 标准中的空白和 namespace 处理等很难理解,更难正确实现。甚至还有多种类型的 C14N。

.NET 实现对其接受的内容非常有选择性。您的其他实现很可能与 .NET 实现的工作方式不完全相同。这实在是太可悲了。例如,如果您可以在签名之前从源 XML 中消除空格和 namespace ,那可能会有所帮助。此外,如果您可以确保两个实现都使用相同的 C14N 设置。

否则有很多调试等着你。您可以调试框架,或通过反射手动调用其内部方法,以查看它如何计算 XML 片段和签名。并对其他实现执行相同的操作。基本上,您需要查看在这两种情况下签名的确切字节流。这是签名前转换的最后一步。如果这些字节流匹配,那么根据我的经验,RSA 签名部分就没有问题。如果它们不匹配,就像您的情况一样,至少您会看到问题出在哪里。

关于c# - SignedXml checksignature 返回 false,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/3935600/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com