.NET SignedXml with a Specific Namespace Prefix ("ds:") and without X509Data

Viewed 1813

I was struggling while trying to digitally sign soap envelope in Microsoft .NET. Webservice was rejecting my .NET signed request, saying “invalid signature”. In this case webservice was written in Java by third party, so i couldn't make any changes in server side.

Server side was expecting signature element with ds prefix. SignedXml class by default was not producing xml with ds prefix for signature element and child elements. Another problem was related to ds:KeyInfo which should have KeyValue and X509IssuerSerial elements - by default in .NET it is X509Data element. So the structure of message should look like this for the server to accept request:

<SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/">
   <SOAP-ENV:Header>
      <wsse:Security SOAP-ENV:mustUnderstand="1" xmlns:wsse="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd">
         <ds:Signature xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
            <ds:SignedInfo>
               <ds:CanonicalizationMethod Algorithm="http://www.w3.org/TR/2001/REC-xml-c14n-20010315#WithComments"/>
               <ds:SignatureMethod Algorithm="http://www.w3.org/2000/09/xmldsig#rsa-sha1"/>
               <ds:Reference URI="#ea43a55321b243c082dadae4f53f32b5">
                  <ds:DigestMethod Algorithm="http://www.w3.org/2000/09/xmldsig#sha1"/>
                  <ds:DigestValue>.........</ds:DigestValue>
               </ds:Reference>
            </ds:SignedInfo>
            <ds:SignatureValue>.......</ds:SignatureValue>
            <ds:KeyInfo>
               <ds:KeyValue>
                  <ds:RSAKeyValue>
                     <ds:Modulus>.......</ds:Modulus>
                     <ds:Exponent>....</ds:Exponent>
                  </ds:RSAKeyValue>
               </ds:KeyValue>
               <ds:X509IssuerSerial>
                  <ds:X509IssuerName>.......</ds:X509IssuerName>
                  <ds:X509SerialNumber>.......</ds:X509SerialNumber>
               </ds:X509IssuerSerial>
            </ds:KeyInfo>
         </ds:Signature>
      </wsse:Security>
   </SOAP-ENV:Header>
   <SOAP-ENV:Body ds:id="ea43a55321b243c082dadae4f53f32b5" xmlns:ds="http://schemas.xmlsoap.org/soap/security/2000-12">
            .................
   </SOAP-ENV:Body>
</SOAP-ENV:Envelope>
2 Answers

You can change directly the XmlElement :

Dim xmlDigitalSignature As XmlElement = SignedXml.GetXml()
xmlDigitalSignature.SetAttribute("xmlns:ds", "http://www.w3.org/2000/09/xmldsig#")
xmlDigitalSignature.Prefix = "ds"
Related