wqweto / VbAsyncSocket

Sockets with pure VB6 impl of TLS encryption
MIT License
166 stars 33 forks source link

Http Request Replacement Ax-DLL SetClientCertificate #47

Open Docent24 opened 6 months ago

Docent24 commented 6 months ago

Hi. I've tried to use Http Request dll and faced trouble with SetClientCertificate. Default location for cert is "CURRENT_USER\MY\" and i have valid cert there. I got the error (8009200b): Не удается найти сертификат и закрытый ключ для расшифровки ("Key not found" in eng, i think)

Standard WinHttp.WinHttpRequest.5.1 works fine with that cert. image

When i try to use the wrong cert name - i got different error: 80072f89 - Предоставлен недопустимый сертификат ("certificate invalid"), so i assume i specified the path to the cert correctly.

wqweto commented 6 months ago

This should be a supported use case. Is there some kind of SmartCard device (e.g. YubiKey) involved?

Which URL are you trying to access?

Docent24 commented 6 months ago

Is there some kind of SmartCard device (e.g. YubiKey) involved?

No, only certificate is needed for the connection.

Which URL are you trying to access?

https://mc.api.sberbank.ru/prod/tokens/v3/oauth

wqweto commented 6 months ago

Just pushed some fixes in commit e11373fe9e736deba717967f56f84d29540fd40f -- try downloading latest HttpRequest.zip from Releases section.

Btw, if you only have a single certificate issued by api.sberbank.ru currently registered in your CURRENT_USER\MY certificate store then you don't need the SetClientCertificate call as the class will try to auto-locate it using authorities (root certificates) from server sent certificate request.

Another option to try is using certificate thumbprint instead of common/friendly name like this: SetClientCertificate "68b5220077de8bbeaed8e1c2540fec6c16b418a8"

image

Docent24 commented 6 months ago

Actually, with the last version problem on Win 10 x64 is fixed. Well done!

But, on Windows 7 x64 i got another err message:

cHttpRequest.SetClientCertificate
pvPkiExportRsaPrivateKey.CryptEncodeObjectEx: Automation errorThe system cannot find the file specified. 

Btw, if you only have a single certificate issued

Thanks for the tip, but i have multiple certs =(

Another option to try is using certificate thumbprint

Thumbprint option works in Win 10 x64, on Win 7 i got 80072f89 - Предоставлен недопустимый сертификат ("certificate invalid") error

wqweto commented 6 months ago

Thumbprint option works in Win 10 x64, on Win 7 i got 80072f89

Just fixed finding certificates by hash under Win7 in commit faa131364d99b81b507efb294cebbbfcf8aeecf1 and updated HttpRequest.zip.

The automation error in pvPkiExportRsaPrivateKey should be fixed in the same commit too.

Docent24 commented 6 months ago

Yes, you nailed it! Everything works as expected on both systems. Thanks alot!

Docent24 commented 6 months ago

From time to time i got error: -2147221504 (80040000): The revocation status of the certificate or one of the certificates in the certificate chain is unknown with that server, but not all the time and it seems like only on Win7. Option WinHttpRequestOption_EnableCertificateRevocationCheck fixes that, but with std WinHttp.WinHttpRequest control i don`t have this error if the option is on.

But i think this topic is the case for another issue =)

Once again, thank you for support, quick fix and the whole project. It's incredible!

wqweto commented 6 months ago

From time to time i got error: -2147221504 (80040000): The revocation status of the certificate or one of the certificates in the certificate chain is unknown with that server, but not all the time and it seems like only on Win7

I'll probably have to tweak it to default to not checking revocation on Win7 as it becomes more and more unsupported because OS probably cannot access revocation list servers securely i.e. Schannel is failing to connect to new/upgraded CRL endpoints.

Edit: Just did this in commit 60c578ee6d1f3818e0cd6f6225df28f8dabaf69a and it got a bit faster establishing TLS session under Win7 as a result.

Docent24 commented 6 months ago

Everything works as expected on both systems.

Hm, after further testing i faced another issue, unfortunately. On Windows 10, when i tried to connect to https://mc.api.sberbank.ru/prod/tokens/v3/oauth with cert, i got hang on .Send command. No problem with other connections so far. On Windows 7 - works fine. Version before https://github.com/wqweto/VbAsyncSocket/commit/faa131364d99b81b507efb294cebbbfcf8aeecf1 - works fine on Win10

wqweto commented 6 months ago

There are timeouts you can setup with SetTimeouts. By default will wait 30 seconds on receive before raising timeout error.

Another option is to use the class asynchronously and wait for OnResponseFinished event or call WaitForResponse at any point in time.

Docent24 commented 6 months ago

Let me add some details, I try to use HTTP Request ax dll with VBA-Web solution (mostly for some strong security TLS 1.2 support for Windows 7). So, within VBA-Web, lets say, "framework" - there are timeouts configured. In my case it's 15 sec. Also Openwith Async is used.

Now i got problem only in one case so far: open with cert, provided by SetClientCertificate on Windows 10. I got stuck on .Send and never reach next .WaitForResponse statement.

By the way, with your ax i got many timeouts error with default VBA-Web WaitForResponse setting, so i set it to 1 sec.

Still, i got no propblem with WinHttp.WinHttpRequest.5.1 and version before https://github.com/wqweto/VbAsyncSocket/commit/faa131364d99b81b507efb294cebbbfcf8aeecf1

wqweto commented 6 months ago

Yes, this seems to be a regression in faa131364d99b81b507efb294cebbbfcf8aeecf1 which prevented using CNG containers for certificate private keys (which failed export under Win7 and had to be abandoned) but standard Crypto API keys cannot use PSS padding for signatures so client certificate signatures for your endpoint failed silently which revealed another bug which caused an infinite loop in a code path less travelled -- what an adventure! :-))

Anyway in commit 7fca23a59f80177033ab49861ec8e7192ea0b486 CNG containers are back but this time private keys are not exported at all so this prevents Win7 from choking and allows using PSS padding for client certificates again. HttpRequest.zip updated with latest build.

Docent24 commented 6 months ago

I've done some tests and all seems to work as expected.

Once again, i can't thank you enough for this project. TLS and work with certs is quite complex thing and your knowledge of the entire topic is amazing. Speed of resolving bugs is just out of this world =)

Best wishes. Vladimir, and have a nice weekend!