Ir para conteúdo
  • Cadastre-se

dev botao

Validar Assinatura Digital em forma de String


  • Este tópico foi criado há 1798 dias atrás.
  • Talvez seja melhor você criar um NOVO TÓPICO do que postar uma resposta aqui.

Recommended Posts

Prezados amigos:

Tenho a seguinte situação:

Hash original:

  • 1208083C300000046012AA199|300000046012AA000000000000000000|50356286000110|T.d.N.d.C.|201905101600000|3168|9|616|167|217|063|152|5283

Hash em Bytes (variável HashBytes) após parametrização RFC 3986 – UTF-8 (URL Encoding):

  • 3132303830383343333030303030303436303132414131393925374333303030303030343630313241413030303030303030303030303030303030302537433530333536323836303030313130253743542e642e4e2e642e432e253743323031393035313031363030303030253743333136382537433925374336313625374331363725374332313725374330363325374331353225374335323833

Meu sistema VBA envia essa HashBytes para o aplicativo Delphi por intermédio do seguinte comando (via prompt do cmd.exe):

  • Shell "AssinadorDelphi.exe --x-- " & HashBytes

O AssinadorDelphi.exe (que consegui elaborar graças ao inestimável apoio deste maravilhoso fórum), utilizando a minha chave privada (A3 ou A1), assina essa HashBytes em SHA256. Seguem as principais linhas do código (que estão funcionando perfeitamente):  

Citar

                    var HashBytes : pchar;

                    //

                    HashBytes := Pos(' --x-- ', getcommandline);  //  ' --x-- '  => identificador inequívoco do início da HashBytes

                    //

                    FACBrDFe := TACBrDFe.Create(Application);

                    FACBrDFe.Configuracoes.Geral.SSLLib:= libWinCrypt;

                    FACBrDFe.Configuracoes.Certificados.NumeroSerie := '020ad6002a3f0a5ad68b8dce4ab8953a';

                    FACBrDFe.Configuracoes.Certificados.Senha       := 'senha_secreta';

                    AssinaturaDig := FACBrDFe.SSL.CalcHash(HashBytes, dgstSHA256, outBase64, True);

                    FACBrDFe.Free;

                 // mesmo funcionando aparentemente de forma perfeita, aceito críticas e sugestões para melhorar este código. 😉

 

Resultado obtido pelo AssinadorDelphi.exe para a variável AssinaturaDig:

  • ogp3uJQ6oFsdo4sckxQayHGyO+NeBCkamqDfDS3fMDDPChiagxzlbwHPdNMfl7Xa8ZTSZk6/7Rw3SUptBgrO4NkQoQ5LUUDQLvOuGgS0+nUoWqq6QllVC/xYZbX+/qGUZ51CL5vLVBvOdCOMIircuMAlPlThxANEkmpE7T5rODjpFnUhWo1aDFoXJDuc7mbgkoyaKDsV81fMc38q6X9ZWZZmBdrbj5ahafN+iLFWJGsTbc7PHyPI5CGwGdQ+JqGWp2FlLbc3zCTkz3I+KFXs3Rac1fVMOcQz54wj17fLAyPAO02yHDO8+qfEvz6WQk/F165TLCPRHZVeaaip1YKMAA==

Até aí, tudo perfeito! 😀

O que eu preciso agora é o seguinte:

  • uma outra Unit que faça exatamente o inverso, ou seja, de posse dessa AssinaturaDig, preciso obter a HashBytes que a originou, com a utilização da chave pública do emitente, para que o sistema confira a sua integridade.

Ao que me parece, basta substituir umas duas linhas do código.

As pesquisas que fiz neste Fórum e em toda a internet só me retornaram exemplos de "validação de arquivos xml" (obviamente por ser esse o principal uso dos participantes deste fórum). No entanto, para a minha necessidade, o aplicativo terá que conferir a assinatura digital que receberei no formato acima especificado.

Peço a compreensão e paciência de todos, pois não atuo na área de programação (nem sou da área de Exatas) e só soube que Delphi era uma linguagem de programação há pouco mais de 2 meses, quando aqui encontrei a solução acima descrita e que já coloquei em funcionamento. Ou seja, por mais que eu queira encontrar a solução sem atazanar a vida de ninguém, sou obrigado a admitir que não tenho condições técnicas para, no exíguo tempo que me resta para terminar a nova rotina, obter sozinho essa resposta mediante a análise das inúmeras de linhas de código de todas as fontes gentilmente disponibilizadas pela ACBr.

Ficarei feliz diante de qualquer colaboração.

Muito obrigado.

EA

Editado por Eduardo Augusto
Link para o comentário
Compartilhar em outros sites

  • Fundadores

Com um Hash você nunca chegará no conteúdo original...

Trazendo para um mundo maie simples, o Hash se assemelha a um dígito verificador do CNPJ...

Você gerou um Hash sha256 de ums String... esse hash sempre terá o mesmo tamanho...

Qualquer pessoa de posse da String de entrada, poderia gerar um novo Hash... por isso, para garantir que você é o autor do Hash é não houve mudanças na String original, há um outro passo adicional, que é a criptografia do Hash gerado, com a sua chave Pública,.. Isso pode garantir que esse Hash foi gerado por você...

O que é possível de fazer do outro lado, é apenas verificar se o Hash é válido... mas para isso você precisa da String original e da chave privada 

  • Obrigado 1
Consultor SAC ACBr

Daniel Simões de Almeida
O melhor TEF, é com o Projeto ACBr - Clique e Conheça
Ajude o Projeto ACBr crescer - Assine o SAC

Projeto ACBr     Telefone:(15) 2105-0750 WhatsApp(15)99790-2976.

Link para o comentário
Compartilhar em outros sites

Obrigado, Daniel, por sua sempre pronta participação.

Estou meio confuso com esse assunto.

Eis o conteúdo da norma que devo cumprir:

Citar

O Termo de Abertura, assinado criptograficamente pelo TJSP, conterá: 

  • O identificador da Serventia;
  • Data/hora; e
  • Função de hash: SHA256.

O hash do Termo de Abertura deverá ser armazenado como um registro da mesma forma que os registros correspondentes aos atos emitidos pela Serventia.
Exemplo inicial de Termo de Abertura: 

Citar

0000000TA123456061021037F|1SHA256RSA|0|0|201807131810210|0|0|0|0|0|0|0|0|0|Tduw3GPaJkw5bLuwAMmlvQ3fVrwwUuRwxcMVmApxUhVSERlybOhmhzt4GMvMC/UvLVwNCIh+9ª7md2wH3nDXhtlGIamzcZcXTD50H67TD4/HFxk9y7Lvaze+qIU4apdzrPHDtft7mw2AdeSvai+3Vxhe0x231rIk9CXSgxUhc5qA3Fj/eamGcuUU8GyGi6IBJjln1hJqsg8w//XiMMlvkW8gdKzAo+N51osZ2NeK6qxBXEXA25MSsQ59Eaab29Xtp+Z


De posse do registro de abertura, a Serventia: 

  • Passo 1: Calcula o hash usando a função de hash especificada no termo de abertura;
  • Passo 2: Descriptografa o hash do registro de abertura usando a chave pública do TJ;
  • Passo 3: Compara com o hash calculado no passo 1 com o hash obtido no passo 2.

Segue anexa a imagem que ilustra essa operação.

 

O que eu preciso é dos comandos que cumpram os 3 passos acima.

Você poderia me auxiliar?

 

Obrigado.

EA

 

 

 

 

 

 

CA22B764-8BFF-464B-8A57-43C71FD49980.jpeg

Link para o comentário
Compartilhar em outros sites

  • Fundadores

Creio que você possa usar o método abaixo:

   function ValidarHash( const AStringList : TStringList;
       const Digest: TSSLDgst;
       const Hash: AnsiString;
       const Assinado: Boolean =  False): Boolean; overload;  

Exemplo:

   if ValidarHash( StringOriginal, dgstSHA256, HashCalculado, True) then
      ShowMessage('Hash OK');

 

  • Curtir 2
Consultor SAC ACBr

Daniel Simões de Almeida
O melhor TEF, é com o Projeto ACBr - Clique e Conheça
Ajude o Projeto ACBr crescer - Assine o SAC

Projeto ACBr     Telefone:(15) 2105-0750 WhatsApp(15)99790-2976.

Link para o comentário
Compartilhar em outros sites

Em 13/05/2019 at 10:49, Daniel Simoes disse:

Creio que você possa usar o método abaixo:


   function ValidarHash( const AStringList : TStringList;
       const Digest: TSSLDgst;
       const Hash: AnsiString;
       const Assinado: Boolean =  False): Boolean; overload;  

Exemplo:


   if ValidarHash( StringOriginal, dgstSHA256, HashCalculado, True) then
      ShowMessage('Hash OK');

 

Olá, Daniel.

Não obtive êxito nos testes.

A linha << If ValidarHash(StrOriginal, dgstSHA256, HashCalculado, True) then >> está acusando o seguinte erro  "F2066 MIssing operator or semicolon".

Na tentativa de encontrar uma solução, tentei usar a analogia com o método CalcHash e alterei a chamada da função ValidarHash com a inclusão de FACBrDFe.SSL.ValidarHash.

FACBrDFe := TACBrDFe.Create(Application);
FACBrDFe.Configuracoes.Geral.SSLLib:= libWinCrypt;
FACBrDFe.Configuracoes.Certificados.NumeroSerie := '0a520aadce0d6002a3f4bab8d983568a';
        
If not FACBrDFe.SSL.ValidarHash(StrOriginal, dgstSHA256, HashCalculado, True) then
   showmessage('Ainda não estoui no caminho certo...') ;
if FACBrDFe.SSL.ValidarHash(StrOriginal, dgstSHA256, HashCalculado, True) then
   showmessage('Deu Certo!!!! Yuuupiiii!!!!');

O código não acusou nenhum erro, mas como ainda não entendi muito bem qual deve ser o conteúdo das constantes StrOriginal e HashCalculado, só obtive o resultado "Ainda não estou no caminho certo...".

Por favor, corrijam-me se eu estiver enganado:

Com a função FACBrDFe.SSL.CalcHash, direcionada ao meu certificado digital A1, eu transformo uma hash composta de bytes na AssinaturaDig :

  • INPUT/HashBytes: 3132303830383343333030303030303436303132414131393925374333303030303030343630313241413030303030303030303030303030303030302537433530333536323836303030313130253743542e642e4e2e642e432e253743323031393035313031363030303030253743333136382537433925374336313625374331363725374332313725374330363325374331353225374335323833
  • OUTPUT/AssinaturaDigogp3uJQ6oFsdo4sckxQayHGyO+NeBCkamqDfDS3fMDDPChiagxzlbwHPdNMfl7Xa8ZTSZk6/7Rw3SUptBgrO4NkQoQ5LUUDQLvOuGgS0+nUoWqq6QllVC/xYZbX+/qGUZ51CL5vLVBvOdCOMIircuMAlPlThxANEkmpE7T5rODjpFnUhWo1aDFoXJDuc7mbgkoyaKDsV81fMc38q6X9ZWZZmBdrbj5ahafN+iLFWJGsTbc7PHyPI5CGwGdQ+JqGWp2FlLbc3zCTkz3I+KFXs3Rac1fVMOcQz54wj17fLAyPAO02yHDO8+qfEvz6WQk/F165TLCPRHZVeaaip1YKMAA==

Eu estou deduzindo que a função ValidarHash serve para comparar as duas strings, a de entrada (Hashbytes) com o resultado (AssinaturaDig).

Ou seja, nos teste que estou fazendo (e falhando) eu estou atribuindo os seguintes valores  às constantes  da função ValidarHash:

  • StrOriginal: o valor da  HashBytes: 313230383038334333303030303...
  • HashCalculado: o valor da AssinaturaDigogp3uJQ6oFsdo4sckxQayHGyO+...

Estaria eu equivocado nesse raciocínio?

E quanto ao erro que o código está acusando e ao meu abuso de alterar sua grafia?

Mais uma vez agradeço pela paciência de todos.

EA

 

 

 

 

 

Link para o comentário
Compartilhar em outros sites

  • 2 semanas depois ...
  • Fundadores

Sua abordagem parece correta... mas esse assunto é realmente complexo...

Infelizmente eu não tenho como ajudar mais, sem debugar no código...

Consultor SAC ACBr

Daniel Simões de Almeida
O melhor TEF, é com o Projeto ACBr - Clique e Conheça
Ajude o Projeto ACBr crescer - Assine o SAC

Projeto ACBr     Telefone:(15) 2105-0750 WhatsApp(15)99790-2976.

Link para o comentário
Compartilhar em outros sites

  • Este tópico foi criado há 1798 dias atrás.
  • Talvez seja melhor você criar um NOVO TÓPICO do que postar uma resposta aqui.

Crie uma conta ou entre para comentar

Você precisar ser um membro para fazer um comentário

Criar uma conta

Crie uma nova conta em nossa comunidade. É fácil!

Crie uma nova conta

Entrar

Já tem uma conta? Faça o login.

Entrar Agora
×
×
  • Criar Novo...

Informação Importante

Colocamos cookies em seu dispositivo para ajudar a tornar este site melhor. Você pode ajustar suas configurações de cookies, caso contrário, assumiremos que você está bem para continuar.

The popup will be closed in 10 segundos...