Ir para conteúdo
  • Cadastre-se

dev botao

Falha ao definir PIN do Certificado. Erro: 80100004


Jakson
Ver Solução Respondido por Controla,
  • Este tópico foi criado há 2513 dias atrás.
  • Talvez seja melhor você criar um NOVO TÓPICO do que postar uma resposta aqui.

Recommended Posts

  • Fundadores

Tente debugar a Unit ACBrDFeWinCrypt.pas e veja onde o problema ocorre...

provavelmente é algo no metodo:

procedure SetCertContextPassword(ACertContext: PCCERT_CONTEXT; APass: AnsiString);

 

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

  • Membros Pro

Obrigado Daniel, vou debugar e posto aqui o resultado, mas o estranho que isso aconteceu depois que atualizei o acbr, inclusive no projeto AcbrNfe acontece o mesmo, dai quando eu clico novamente pra assinar ele aceita.

Link para o comentário
Compartilhar em outros sites

  • Fundadores

Por favor sejam mais específicos, e sempre usando apenas o Demo do ACBrNFe...

Como devo configura-lo?

Quais botões ou operações devo fazer para obter o erro?

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

Boa tarde Daniel, assim que eu atualizei os fontes, vou gerar uma nota fiscal, ao assinar ele ja aparece a mensagem que o Jakson mencionou, logo em seguida aperto para assinar novamente ai ele assina normal e continua sem dar erro.

Mesmo sem montar a nota apertando o status do servico ele aparece a mensagem, logo apos voce aperta de novo ele nao aparece mais o erro e retorna o status.

wga.png.c9fa592cd046fc87a239c5c1b373c1a4.png

Willians O. Tonelotto
[email protected]

Cordeirópolis/SP - www.wgainformatica.com.br

Link para o comentário
Compartilhar em outros sites

  • Fundadores

Vou tentar ser mais específico.
1 - Abra o Demo do ACBrNFe
2 - Configure com libCapicom e WebService XYZ
3 - Clique no botão "bla bla bla"
4 - Carregue o XML, xyz
5 - clique no botão "tal tal"... observe o erro...

ISSO É UM PASSO A PASSO

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

  • Fundadores

O erro é diferente do citado no tópico:  3F0 hex = 1008 decimal = ERROR_NO_TOKEN      

- Esse Certificado, já funcionava antes, com o ACBr ?

- Se deixar a Senha em branco, o Windows pergunta a senha e tudo funciona ?

- Vá com o Debug no método "procedure SetCertContextPassword(ACertContext: PCCERT_CONTEXT; APass: AnsiString);" e veja qual é a linha exata, onde o erro é disparado...

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

Sim, esse certificado ja funcionava com o ACBr, como voce cito sobre a senha em branco na primeira vez ele da a mensagem de erro, na segunda vez que voce clica em status do servico o windows pergunta a senha, uma coisa que notei e se voce abrir a tela normal e aperta a primeira vez aparece o erro, na segunda ele pedi a senha e nao acontece mais o erro, somente se fechar e abrir de novo acontece o erro novamente.

Daniel, o erro era apresentado na linha em que esta comentada, apenas mudei como linha de comentário no comando e não ocorreu mais o erro citado acima, funcionou normal o status do serviço na primeira vez em que foi solicitado o status.

procedure SetCertContextPassword(ACertContext: PCCERT_CONTEXT; APass: AnsiString);
var
  dwKeySpec: DWORD;
  pfCallerFreeProv: LongBool;
  Ret: Longint;
  ProviderOrKeyHandle: HCRYPTPROV_OR_NCRYPT_KEY_HANDLE;

  procedure CheckPINError(WinErro: DWORD = 0);
  begin
    if WinErro = 0 then
      WinErro := GetLastError;

    if WinErro = 0 then
      Exit;

    if WinErro = SCARD_W_WRONG_CHV then
      raise EACBrDFeWrongPINException.Create('O cartão não pode ser acessado porque o PIN errado foi apresentado.')
    else if WinErro = SCARD_W_CHV_BLOCKED then
      raise EACBrDFeWrongPINException.Create('O cartão não pode ser acessado porque o número máximo de tentativas de entrada de PIN foi atingido');
  //  else
  //    raise EACBrDFeException.Create('Falha ao Definir PIN do Certificado. Erro: '+GetLastErrorAsHexaStr(WinErro));                  <------------ erro ocorria nessa linha.
  end;

wga.png.c9fa592cd046fc87a239c5c1b373c1a4.png

Willians O. Tonelotto
[email protected]

Cordeirópolis/SP - www.wgainformatica.com.br

Link para o comentário
Compartilhar em outros sites

  • Fundadores

Notei que você comentou o linha que dispara o erro genérico...

Você diz que: Informado o Certificado A3, com a Senha pré-definida na configuração. Se não disparar o Exception, quando o erro for " 3F0", o certificado é acessado normalmente ?  Isso parece correto ?

Testou a assinatura de XML ?

 

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

Boa tarde Daniel, sim após eu comentar essa linha fiz o teste funcionou normalmente, acessa o certificado A3 sem o erro do pin, assina, valida e transmiti a NFe normalmente sem erro, se eu volto a linha de comando a mensagem retorna sempre na primeira vez que tenta assinar ou consultar o status do serviço, depois na segunda tentativa faz a consulta normalmente. Ex: se eu abrir o demo e fazer uma consulta ele aparece a mensagem, se eu clicar novamente não da mais a mensagem consulta normal todas as vezes, se eu fechar e abrir de novo , na primeira chamada ele mostra a mensagem de novo.

wga.png.c9fa592cd046fc87a239c5c1b373c1a4.png

Willians O. Tonelotto
[email protected]

Cordeirópolis/SP - www.wgainformatica.com.br

Link para o comentário
Compartilhar em outros sites

  • Fundadores

No SVN...
 

Citar

-- ACBrDFeWinCrypt --
[*] Método "SetCertContextPassword", ajuste para que não seja disparado Exception,
    quando o retorno for (000003F0 hex = 1008 decimal = ERROR_NO_TOKEN)

 

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

  • Fundadores
3 horas atrás, Jakson disse:

Bom dia, Atualizei meu Acbr e mesmo assim continua o erro.

De fato.. pois não há tratamento para o erro "80100004"..

Não posso simplesmente, comentar a Linha, como sugerido... isso faria o ACBr ignorar todos os erros...

Os erros precisam ser compreendidos e tratados...

Por favor seja mais específico... Observe que essa sub-procedure "CheckPINError", é chamada em 3 locais. Qual é exatamente a chamada, que originou o problema...

    if dwKeySpec = CERT_NCRYPT_KEY_SPEC then
    begin
      if not GetCNGProviderIsHardware(ProviderOrKeyHandle) then
        Exit;

      Ret := NCryptSetProperty( ProviderOrKeyHandle,    // Não testado...
                                NCRYPT_PIN_PROPERTY,
                                PBYTE(APass),
                                Length(APass)+1, 0);
      CheckPINError(Ret);    // AQUI ?
    end
    else
    begin
      if not GetCSPProviderIsHardware(ProviderOrKeyHandle) then
        Exit;

      if CryptSetProvParam(ProviderOrKeyHandle, PP_KEYEXCHANGE_PIN, PBYTE(APass), 0) then
        CheckPINError();      // AQUI ?

      if not CryptSetProvParam(ProviderOrKeyHandle, PP_SIGNATURE_PIN, PBYTE(APass), 0) then
        CheckPINError();       // OU AQUI ?
    end;  

 

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

Daniel boa tarde

eu também estou passando pelo mesmo problema

como você sugeriu verificar onde ocorre o erro eu debuguei aqui e o erro é chamado nesta linha

if not CryptSetProvParam(ProviderOrKeyHandle, PP_SIGNATURE_PIN, PBYTE(APass), 0) then
        CheckPINError();

da mesma maneira como disse o BILLI579 o erro acontece uma vez, se chamar o código novamente funciona normal.

Link para o comentário
Compartilhar em outros sites

  • Fundadores

Não foi isso que perguntei... eu preciso saber se a mensagem de erro é exatamente igual a do título desse tópico "Falha ao definir PIN do Certificado. Erro: 80100004"

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

Acho que vou fazer um RTA "Recurso Tecnológico Alternativo" até termos uma solução definitiva.

Vou deixar o código assim:


procedure SetCertContextPassword(ACertContext: PCCERT_CONTEXT; APass: AnsiString);
var
  dwKeySpec: DWORD;
  pfCallerFreeProv: LongBool;
  Ret: Longint;
  ProviderOrKeyHandle: HCRYPTPROV_OR_NCRYPT_KEY_HANDLE;

  procedure CheckPINError(WinErro: DWORD = 0);
  begin
    if WinErro = 0 then
      WinErro := GetLastError;

    if (WinErro = 0) or (WinErro = ERROR_NO_TOKEN) then
      Exit;

    if WinErro = SCARD_W_WRONG_CHV then
      raise EACBrDFeWrongPINException.Create('O cartão não pode ser acessado porque o PIN errado foi apresentado.')
    else if WinErro = SCARD_W_CHV_BLOCKED then
      raise EACBrDFeWrongPINException.Create('O cartão não pode ser acessado porque o número máximo de tentativas de entrada de PIN foi atingido')
    else
      raise EACBrDFeException.Create('Falha ao Definir PIN do Certificado. Erro: '+GetLastErrorAsHexaStr(WinErro));
  end;

begin
  ProviderOrKeyHandle := 0;
  dwKeySpec := 0;
  pfCallerFreeProv := False;

  // Obtendo o Contexto do Provedor de Criptografia do Certificado //
  if not CryptAcquireCertificatePrivateKey( ACertContext,
                                            CRYPT_ACQUIRE_ALLOW_NCRYPT_KEY_FLAG,
                                            Nil,
                                            ProviderOrKeyHandle,
                                            dwKeySpec,
                                            pfCallerFreeProv) then
    raise EACBrDFeException.Create( MsgErroGetCryptProvider );

  try
    if dwKeySpec = CERT_NCRYPT_KEY_SPEC then
    begin
      if not GetCNGProviderIsHardware(ProviderOrKeyHandle) then
        Exit;

      Ret := NCryptSetProperty( ProviderOrKeyHandle,    // Não testado...
                                NCRYPT_PIN_PROPERTY,
                                PBYTE(APass),
                                Length(APass)+1, 0);
      CheckPINError(Ret);
    end
    else
    begin
      if not GetCSPProviderIsHardware(ProviderOrKeyHandle) then
        Exit;

      if CryptSetProvParam(ProviderOrKeyHandle, PP_KEYEXCHANGE_PIN, PBYTE(APass), 0) then
        CheckPINError();

      CryptSetProvParam(ProviderOrKeyHandle, PP_SIGNATURE_PIN, PBYTE(APass), 0);                 // <- DEIXEI A LINHA DESTE JEITO SEM TESTES DE ERRO
//      if not CryptSetProvParam(ProviderOrKeyHandle, PP_SIGNATURE_PIN, PBYTE(APass), 0) then    // <- ANTES ERA ASSIM
//        CheckPINError();

    end;
  finally
    if pfCallerFreeProv then
      CryptReleaseContext(ProviderOrKeyHandle, 0);
  end;
end;


Desta forma o comportamento obtido está sendo o seguinte:
Se o certificado não for encontrado mostra a mensagem: Certificado "xxxxxx" não encontrado!
Se o PIN informado estiver incorreto ele abre a tela de digitação do PIN, lembrando que já foi utilizada uma tentativa.

Sei que desta forma estou ignorando erros que possam ocorer, mas nos teste aqui dá pra funcionar legal.

Este comportamento acontece com o certificado que usa o Oberthur, já com o certificado que usa o SafeSing o problema não acontece.

Não gosto de remendos no código, mas por hora acho que será o jeito.
O que vocês acham ?

Link para o comentário
Compartilhar em outros sites

  • Fundadores

Apliquei as seguintes modificações, no SVN...

Citar

-- ACBrDFeWinCrypt --
[*] Ajuste em "SetCertContextPassword", para não disparar erros desconhecidos na
    atribuição de senha para "PP_SIGNATURE_PIN"
    (por: DSA)

 

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á 2513 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.