assinar xml

Boa dia a todos, por favor estou tentando fazer uma assinatura digital em um XML, e esta dando super certo com a ajuda do exemples que Chris Glazier e Altair Borges me enviaram, porem esta assinando com o algoritimo RSA-SHA1 mas eu preciso assinar com algoritimo RSA-SHA256, eu achei um exemplo que eu acredite que seja o que eu preciso conforme esta abaixo em C#, mas não estou conseguindo converter o Visual COBOL for Visual Studio, se alguém conseguir me ajudar ficarei muito agradecido.

 

atenciosamente

 

Renato Soares Vieira

 

using System; using System.Security.Cryptography; class RSASample { static void Main() { try { //Create a new instance of RSACryptoServiceProvider. using (RSACryptoServiceProvider rsa = new RSACryptoServiceProvider()) { //The hash to sign. byte[] hash; using (SHA256 sha256 = SHA256.Create()) { byte[] data = new byte[] { 59, 4, 248, 102, 77, 97, 142, 201, 210, 12, 224, 93, 25, 41, 100, 197, 213, 134, 130, 135 }; hash = sha256.ComputeHash(data); } //Create an RSASignatureFormatter object and pass it the //RSACryptoServiceProvider to transfer the key information. RSAPKCS1SignatureFormatter RSAFormatter = new RSAPKCS1SignatureFormatter(rsa); //Set the hash algorithm to SHA256. RSAFormatter.SetHashAlgorithm("SHA256"); //Create a signature for HashValue and return it. byte[] SignedHash = RSAFormatter.CreateSignature(hash); } } catch (CryptographicException e) { Console.WriteLine(e.Message); } } }

  • using System;

    using System.Security.Cryptography;

    class RSASample

    {

    static void Main()

    {

    try

    {

    //Create a new instance of RSACryptoServiceProvider.

    using (RSACryptoServiceProvider rsa = new RSACryptoServiceProvider())

    { //The hash to sign.

    byte[] hash;

    using (SHA256 sha256 = SHA256.Create())

    {

    byte[] data = new byte[] { 59, 4, 248, 102, 77, 97, 142, 201, 210, 12, 224, 93, 25, 41, 100, 197, 213, 134, 130, 135 };

    hash = sha256.ComputeHash(data);

    }

    //Create an RSASignatureFormatter object and pass it the             

    //RSACryptoServiceProvider to transfer the key information.

    RSAPKCS1SignatureFormatter RSAFormatter = new RSAPKCS1SignatureFormatter(rsa);

    //Set the hash algorithm to SHA256.

    RSAFormatter.SetHashAlgorithm("SHA256");

    //Create a signature for HashValue and return it.

    byte[] SignedHash = RSAFormatter.CreateSignature(hash);

    }

    }

    catch (CryptographicException e)

    {

    Console.WriteLine(e.Message);

    }

    }

    }

  • The conversion for this program is as follows:

     

          $set ilusing"System""
          $set ilusing"System.Security.Cryptography" 
           class-id xmldigisign.RSASample.
           working-storage section.
           method-id main static.
           local-storage section.
           procedure division.
    		   try 
                  *> Create a new instance of RSACryptoServiceProvider.
    		      perform using rsa as type RSACryptoServiceProvider = new RSACryptoServiceProvider
    				 *>The hash to sign. 
    				 declare hash as type Byte occurs any 
    		         perform using sha256 as type SHA256 = type SHA256::Create
    					declare #data as type Byte occurs 20 = table of
                          type Byte(59, 4, 248, 102, 77, 97, 142, 201, 210, 12, 224, 93, 25, 41, 100, 197, 213, 134, 130, 135)
    					set hash = sha256::ComputeHash(#data)
    		         end-perform
     
                  *> Create an RSASignatureFormatter object and pass it the               
    			  *> RSACryptoServiceProvider to transfer the key information. 
    				 declare RSAFormatter as type RSAPKCS1SignatureFormatter = new RSAPKCS1SignatureFormatter(rsa) 
    			  *> Set the hash algorithm to SHA256. 
    
                     invoke RSAFormatter::SetHashAlgorithm("SHA256")
    			  *> Create a signature for HashValue and return it. 
    				 declare SignedHash as type Byte occurs any = RSAFormatter::CreateSignature(hash)
    		      end-perform
    		   catch e as type CryptographicException
    		      display e::Message
    		   end-try
    		   goback.
    
           end method.
    
           end class.
    
    
  • Thank you Mr. Glazier, I'm going to test on my project.
  • Bom dia Mr. Glazier

    Infelizmente não deu certo, acho que analisei errado ou estou fazendo alguma coisa errada no programa, no meu XML eu tenho que assinar com algoritmo RSA-SHA256, mas o programa esta assinando com algoritmo RSA-SHA1, por isso pensei que poderia ser aquele método que converteu para mim ontem, mas não deu certo, vou anexar o programa como estou fazendo , e o XML de como assinou e um de como deve assinar, se o Senhor poder me ajudar mais uma vez ficarei muito grato.

    Atenciosamente

    Renato Soares Vieira

          $set ilusing"System"
          *set ilusing"System.Windows.Forms"
          $set ilusing"System.Xml"
          $set ilusing"System.Security.Cryptography"
          $set ilusing"System.Security.Cryptography.Xml"
          $set ilusing"System.Security"
          $set ilusing"System.Security.Cryptography.X509Certificates"
          *class-id xmlsigning.Form1 is partial
          *          inherits type System.Windows.Forms.Form.
           class-id xmlsigning.SignXML.
          
           working-storage section.

           method-id main static.
           procedure division.
          
               declare XMLAssinado as string = "p:\renato\r1000-042018-assinado.xml"
               declare #XML as string = "p:\renato\r1000-042018.xml"
               declare #URI as string = "#ID1507391350000002018041911433600002"
               *>
               declare pCertificado as type X509Certificate2 = null
               try
                  *> Verificar a possibilidade de passar certificado para assinatura, sem a necessidade
                  *> de chamar a lista de certificado
                  declare subject as string = type String::Empty
                  if (pCertificado not = null)
                     set subject to pCertificado::Subject::ToString
                  end-if
                  declare x509Certificate as type X509Certificate2 = new X509Certificate2
                  declare store as type X509Store = new X509Store("MY", type StoreLocation::CurrentUser)
                  invoke store::Open(type OpenFlags::ReadOnly b-or type OpenFlags::OpenExistingOnly)
                  declare collection as type X509Certificate2Collection = store::Certificates
                     as type X509Certificate2Collection
                  declare collection1 as type X509Certificate2Collection
                     = collection::Find(type X509FindType::FindByTimeValid, type DateTime::Now, false)
                       as type X509Certificate2Collection
                  declare collection2 as type X509Certificate2Collection
                     = collection::Find(type X509FindType::FindByKeyUsage,
                       type X509KeyUsageFlags::DigitalSignature, false) as type X509Certificate2Collection
                  declare scollection as type X509Certificate2Collection
                     = type X509Certificate2UI::SelectFromCollection(collection2,
                       "Certificado(s) Digital(is) disponível(is)",
                       "Selecione o certificado digital para uso no aplicativo Perform",
                       type X509SelectionFlag::SingleSelection)
                  if (scollection::Count <> 0)
                *>   invoke type MessageBox::Show("Nenhum certificado digital foi selecionado ou o "
                *>      & "certificado selecionado está com problemas.")
                *>else
                     set pCertificado to scollection[0]
                     declare documento as type XmlDocument = new XmlDocument
                     set documento::PreserveWhitespace to true
                     try
                        *> verificando elemento de referencia
                        invoke documento::Load(#XML)
                        try
                       perform using rsa as type RSACryptoServiceProvider = new RSACryptoServiceProvider
                       *>The hash to sign.
                       declare hash as type Byte occurs any
                             perform using sha256 as type SHA256 = type SHA256::Create
                            declare #data as type Byte occurs 20 = table of
                                                     type Byte(59, 4, 248, 102, 77, 97, 142, 201, 210, 12, 224, 93, 25, 41, 100, 197, 213, 134, 130, 135)
                             set hash = sha256::ComputeHash(#data)
                             end-perform
                              *> Create an RSASignatureFormatter object and pass it the              
                        *> RSACryptoServiceProvider to transfer the key information.
                       declare RSAFormatter as type RSAPKCS1SignatureFormatter = new RSAPKCS1SignatureFormatter(rsa)
                        *> Set the hash algorithm to SHA256.
                              invoke RSAFormatter::SetHashAlgorithm("SHA256")
                        *> Create a signature for HashValue and return it.
                       declare SignedHash as type Byte occurs any = RSAFormatter::CreateSignature(hash)
                       end-perform
                           try
                              *> selecionando certificado digital baseado no subject
                              set x509Certificate to collection1[0]
                              declare docXML as type SignedXml = new SignedXml(documento)
                              set docXML::SigningKey to pCertificado::PrivateKey
                              *> Create a reference to be signed.
                              declare #reference as type Reference = new Reference()
                              set #reference::Uri to #URI
                              *> adicionando EnvelopedSignatureTransform a referencia
                              declare envelopedSigntature as type XmlDsigEnvelopedSignatureTransform
                                 = new XmlDsigEnvelopedSignatureTransform
                              invoke #reference::AddTransform(envelopedSigntature)
                              declare c14Transform as type XmlDsigC14NTransform = new XmlDsigC14NTransform
                              invoke #reference::AddTransform(c14Transform)
                              invoke docXML::AddReference(#reference)
                              *> carrega o certificado em KeyInfoX509Data para adicionar a KeyInfo
                              declare keyInfo as type KeyInfo = new KeyInfo
                              invoke keyInfo::AddClause(new type KeyInfoX509Data(pCertificado))
                              set docXML::KeyInfo to keyInfo
                              invoke docXML::ComputeSignature
                              *> recuperando a representacao do XML assinado
                              declare xmlDigitalSignature as type XmlElement = docXML::GetXml
                              invoke documento::DocumentElement::AppendChild(documento::ImportNode(xmlDigitalSignature,
                                 true))
                              set XMLAssinado to documento::OuterXml
                              invoke documento::Save("p:\renato\r1000-042018-assinado.xml")
                           catch ex as type Exception
                            *>invoke type MessageBox::Show("Erro: " & ex::Message)
                           end-try
                        catch ex as type Exception
                         *>invoke type MessageBox::Show("Erro: " & ex::Message)
                        end-try
                     catch caught as type Exception
                      *>invoke type MessageBox::Show("Erro ao assinar o documento - " & caught::Message)
                     end-try
                  end-if
               catch caught as type Exception
                *>invoke type MessageBox::Show("XML mal formado - " & caught::Message)
               end-try.
               
           end method.
         
           end class.

     

    r1000_2D00_042018_2D00_assinado.xml

    r1000_2D00_042018_2D00_assinado.xml

  • boa tarde, como eu converto o comanda abaixo em c# para o visual cobol?

    CryptoConfig.AddAlgorithm(typeof(RSAPKCS1SHA256SignatureDescription),signatureMethod);

    e

    signer.SignedInfo.CanonicalizationMethod = signatureCanonicalizationMethod;
    signer.SignedInfo.SignatureMethod = signatureMethod;

    obrigado
  • Acho melhor eu colocar o exemplo inteiro para entenderem

     

    obrigado

    exemplo.txt

  • This would look something like the following in COBOL:

     

          $set ilusing"System.Xml"
          $set ilusing"System.Security.Cryptography"
          $set ilusing"System.Security.Cryptography.Xml"
          $set ilusing"System.Security.Cryptography.X509Certificates"
          $set ilusing"System.Deployment.Internal.CodeSigning"
           class-id myclass.
           method-id SignDocument static.
           procedure division using doc as type XmlDocument
    		                  returning retdoc as type XmlDocument.
           
                declare signatureCanonicalizationMethod as string = "www.w3.org/.../xml-exc-c14n
                declare signatureMethod as string = "www.w3.org/.../xmldsig-more
                declare digestMethod as string = "www.w3.org/.../xmlenc
    	    declare signatureReferenceURI as string = "#_73e63a41-156d-4fda-a26c-8d79dcade713"
                invoke type CryptoConfig::AddAlgorithm(type of type RSAPKCS1SHA256SignatureDescription, signatureMethod)
    	    declare signingCertificate = self::GetCertificate
    	    declare signer as type SignedXml = new SignedXml(doc)
                set signer::SigningKey = signingCertificate::PrivateKey
                set signer::KeyInfo = new KeyInfo
                invoke signer::KeyInfo::AddClause(new KeyInfoX509Data(signingCertificate))
    	    set signer::SignedInfo::CanonicalizationMethod = signatureCanonicalizationMethod
                set signer::SignedInfo::SignatureMethod = signatureMethod
    	    declare envelopeTransform as type XmlDsigEnvelopedSignatureTransform = new XmlDsigEnvelopedSignatureTransform
                declare cn14Transform as type XmlDsigExcC14NTransform = new XmlDsigExcC14NTransform
                declare signatureReference as type Reference = new Reference
                set signatureReference::Uri = signatureReferenceURI
                invoke signatureReference::AddTransform(envelopeTransform)
                invoke signatureReference::AddTransform(cn14Transform)
                set signatureReference::DigestMethod = digestMethod
    	    invoke signer::AddReference(signatureReference)
    	    invoke signer::ComputeSignature
                declare signatureElement as type XmlElement = signer::GetXml
    	    invoke doc::DocumentElement::AppendChild(signer::GetXml())
    	    set retdoc to doc
            
    	    goback.
    
           end method.
           method-id GetCertificate private static.
           procedure division returning retcertificate as type X509Certificate2.
           
               declare store as type X509Store = new X509Store(type StoreName::My, type StoreLocation::LocalMachine)
               invoke store::Open(type OpenFlags::ReadOnly)
               declare card as type X509Certificate2 = null
               perform varying cert as type X509Certificate2 thru store::Certificates
                  if not cert::HasPrivateKey
                     exit perform cycle
                  end-if
                  if cert::Thumbprint::Equals("a_certain_thumb_print", type StringComparison::OrdinalIgnoreCase)
                     set card = cert
                     exit perform
    	      end-if
    	   end-perform
               invoke store::Close
    	   set retcertificate to card
               goback.
    
           end method.
           end class.
        	   
    
  • Thank you mr Glazier
     
    Is now just giving an error in the line below, I have to include some method to accept this type?
     
    invoke type CryptoConfig::AddAlgorithm(type of type RSAPKCS1SHA256SignatureDescription, signatureMethod)
     
    erro:
     
    Erro COBCH0845 Unknown type 'type RSAPKCS1SHA256SignatureDescription'
     
    thank you
     
    Renato
     
  • Which version of the .NET Framework are you using?
    I had to change mine to 4.61 and then I added in the References for System.Deployment v4.0.30319 and Microsoft.Build.Tasks.v4.0 v4.0.30319 as well.
  • do not know how to tell you, we are using the visual cobol for visual studio 3.0, and I am running it by itself visual cobol for visual studio.
    How can I see this?