open-eid / chrome-token-signing

DEPRECATED Chrome and Firefox extension for signing with your eID on the web
https://github.com/open-eid/chrome-token-signing/wiki
GNU Lesser General Public License v2.1
206 stars 75 forks source link

Two different behaviors with NativeSigner #131

Closed thgramos closed 5 years ago

thgramos commented 5 years ago

We are facing a problem with some users generating an invalid signature, so I started to investigate what is happening and I think the NativeSigner class is the problem. I am not a Windows API expert, so let me know if I misunderstand something.

At line 81 the function CryptAcquireCertificatePrivateKey is used to determine if the key is obtained with CriptoAPI or CNG (flag CRYPT_ACQUIRE_ALLOW_NCRYPT_KEY_FLAG) and the result is stored in spec variable, which is later used within a switch at line 98.

Analyzing the CERT_NCRYPT_KEY_SPEC case (1) some checks of algorithm and size are done and finally called the function NCryptSignHash to sign the informed digest with the user's private key.

But inside the AT_SIGNATURE case (2) there is a call to CryptCreateHash and CryptSetHashParam functions, which calculates a hash from the informed digest to then pass it to CryptSignHashW function.

So, at (1) it is generating a RSA signature from hash and at (2) it is generating a SHA256 RSA signature from hash. Considering that the sign function does not let you select the algorithm I think the behavior of the two cases need to be the same because when the structure of the signature is built, for example a CMS signature, it is necessary to inform the encryption algorithm OID, which will be different: (1) 1.2.840.113549.1.1.1 rsaEncryption and (2) 1.2.840.113549.1.1.11 sha256WithRSAEncryption.

metsma commented 5 years ago

Case 2 will not calculate digest https://github.com/open-eid/chrome-token-signing/blob/master/host-windows/NativeSigner.cpp#L124 It uses HP_HASHVAL param to set digest value https://docs.microsoft.com/en-us/windows/desktop/api/wincrypt/nf-wincrypt-cryptsethashparam

thgramos commented 5 years ago

Oh, sorry for misunderstanding the API (probably because the names used)...

Well, I was able to switch between the Crypto API and CNG and both resulted on the same signature. I verified that both applies a SHA256 with RSA encryption. But my problem persist, I don't no why for some users the signature generated only applies the RSA encryption.

I will dig further more and bring my discoveries here. Thanks!

thgramos commented 5 years ago

The problem was the software/driver of the token. I don't no why it was working but not generating the signature correctly.

Updating the software and checking if the driver is correctly installed and functioning resolved the situation.