For a project I’m working on, I have to read in an XML digital signature – XmlDSig. In this post, I’m going to show how to read an XmlDsig value using SignedXml object from namespace System.Security.Cryptography.Xml.
I add a class to hold my signature data
public class SignedObjectModel
{
public X509Certificate2 Certificate { get; set; }
public DigestModel Digest { get; set; }
public SignatureModel Signature { get; set; }
}
public class DigestModel
{
public string Value { get; set; }
public string Encoding { get; set; }
public string Algorithm { get; set; }
}
public class SignatureModel
{
public string Value { get; set; }
public string Algorithm { get; set; }
public string Encoding { get; set; }
}
The following is the function to read the XmlDsig value
public SignedObjectModel ReadXmlDSigValue(string value)
{
var xmlDoc = new XmlDocument();
xmlDoc.LoadXml(value);
XmlNodeList nodeList = xmlDoc.GetElementsByTagName("Signature", SignedXml.XmlDsigNamespaceUrl);
SignedXml signedXml = new SignedXml((XmlElement)nodeList[0]);
signedXml.LoadXml((XmlElement)nodeList[0]);
var certValue = xmlDoc.GetElementsByTagName("X509Certificate")[0].InnerText;
var cert = new X509Certificate2(Convert.FromBase64String(certValue));
var checkSignature = signedXml.CheckSignature(cert, true);
return new SignedObjectModel
{
Certificate = cert,
Digest = new DigestModel
{
Value = xmlDoc.GetElementsByTagName("DigestValue")[0].InnerText,
Encoding = "Base64",
Algorithm = (signedXml.SignedInfo.References[0] as Reference).DigestMethod
},
Signature = new SignatureModel
{
Value = xmlDoc.GetElementsByTagName("SignatureValue")[0].InnerText,
Algorithm = signedXml.SignatureMethod,
Encoding = "Base64"
}
};
}