Skip to content

Openssl

openssl is the name for the whole opensource project and toolkit but also for the commandline tool.

toolkit

Later. For now i only have docs for the command.

command

This will be a little chaotic again but here are just some experiences with openssl.

proxy

Openssl does not have a proxy option but you can use the proxytunnel tool to get it working

proxytunnel
1
2
3
brew install proxytunnel
proxytunnel -p 10.10.1.13:3128 -d www.klopt.org:443 -a 7000 &
openssl s_client -connect localhost:7000

Also this introduces the s_client option, so see next chapter.

s_client

Using openssl as a client, using this command, you could for instance get detailed server information. The command to get server info would be :

s_client
openssl s_client -connect www.klopt.org:443

Of course, when behind a proxy look at the previous chapter. It will dump information like this :

output
CONNECTED(00000003)
depth=3 /C=SE/O=AddTrust AB/OU=AddTrust External TTP Network/CN=AddTrust External CA Root
verify error:num=19:self signed certificate in certificate chain
verify return:0
---
Certificate chain
 0 s:/OU=Domain Control Validated/OU=PositiveSSL Wildcard/CN=*.klopt.org
   i:/C=GB/ST=Greater Manchester/L=Salford/O=COMODO CA Limited/CN=COMODO RSA Domain Validation Secure Server CA
 1 s:/C=GB/ST=Greater Manchester/L=Salford/O=COMODO CA Limited/CN=COMODO RSA Domain Validation Secure Server CA
   i:/C=GB/ST=Greater Manchester/L=Salford/O=COMODO CA Limited/CN=COMODO RSA Certification Authority
 2 s:/C=GB/ST=Greater Manchester/L=Salford/O=COMODO CA Limited/CN=COMODO RSA Certification Authority
   i:/C=SE/O=AddTrust AB/OU=AddTrust External TTP Network/CN=AddTrust External CA Root
 3 s:/C=SE/O=AddTrust AB/OU=AddTrust External TTP Network/CN=AddTrust External CA Root
   i:/C=SE/O=AddTrust AB/OU=AddTrust External TTP Network/CN=AddTrust External CA Root
---
Server certificate
-----BEGIN CERTIFICATE-----
MIIFSTCCBDGgAwIBAgIRANMUcY+/XSQa8N38MsJH8Z4wDQYJKoZIhvcNAQELBQAw
gZAxCzAJBgNVBAYTAkdCMRswGQYDVQQIExJHcmVhdGVyIE1hbmNoZXN0ZXIxEDAO
BgNVBAcTB1NhbGZvcmQxGjAYBgNVBAoTEUNPTU9ETyBDQSBMaW1pdGVkMTYwNAYD
VQQDEy1DT01PRE8gUlNBIERvbWFpbiBWYWxpZGF0aW9uIFNlY3VyZSBTZXJ2ZXIg
Q0EwHhcNMTUwMjE5MDAwMDAwWhcNMTYwMjE5MjM1OTU5WjBYMSEwHwYDVQQLExhE
b21haW4gQ29udHJvbCBWYWxpZGF0ZWQxHTAbBgNVBAsTFFBvc2l0aXZlU1NMIFdp
bGRjYXJkMRQwEgYDVQQDFAsqLmtsb3B0Lm9yZzCCASIwDQYJKoZIhvcNAQEBBQAD
ggEPADCCAQoCggEBALxfmkPaD3ahSeCPrSRf1MIet/tjscrwWWpyjeVTroU0rfRU
GjZG5pTAOvZc/nfZreIAKpLra+QibMzmTVQXpyWCv5s9ljvd+p6n7hGbNHMhdoTP
vNuTgsy7myOepa/LXMYOvLVTW5pzz8frt4kVc8gW/ipDzCCx5yFat8rG6q/u1fS5

….


IILKi5rbG9wdC5vcmeCCWtsb3B0Lm9yZzANBgkqhkiG9w0BAQsFAAOCAQEAbVGI
27qQ6PREeftFlpVT4FKRFfxe18Bx5zlfA80UFRXbhsRs1DPpLLiyPbhP94kdagkm
x3Bk+Bg2Q+X/bhkeezhG/7rBpXaEsfRrxhJS6ZHyFJhrOdr09jgb9ikIphhlU7vN
zOXGcF4lIAIIMFfgKAHP5tFY3isLgrLxgLC08jaBvTjPC4C52s/ZeD3L6zbJrQli
16BIw/PCMiZ8hl8Vxb/L1m5zr5NKnK8D8dIIbl6a2Ua3kyDtROZGRCAdiDZ8j+hd
GrdKYAbYJCpAtr5Ek0Ufsd33b4zL0GsT3M/ejNrv3th6DOe2nNrACkQDI/cdSPGh
AmXEpcw04cZpD2i97w==
-----END CERTIFICATE-----
subject=/OU=Domain Control Validated/OU=PositiveSSL Wildcard/CN=*.klopt.org
issuer=/C=GB/ST=Greater Manchester/L=Salford/O=COMODO CA Limited/CN=COMODO RSA Domain Validation Secure Server CA
---
No client certificate CA names sent
---
SSL handshake has read 6351 bytes and written 456 bytes
---
New, TLSv1/SSLv3, Cipher is DHE-RSA-AES256-SHA
Server public key is 2048 bit
Secure Renegotiation IS supported
Compression: NONE
Expansion: NONE
SSL-Session:
    Protocol  : TLSv1
    Cipher    : DHE-RSA-AES256-SHA
    Session-ID: D529778835446B035C270685E70A806E642D789495B923857437F2ED686D3B7A
    Session-ID-ctx:
    Master-Key: E7A12ED8334E417D9D133006D8A53CF1CA720B838A9AC41AB3F0D381A06A53817D32C7D74F742AF5F1EBA071040069D5
    Key-Arg   : None
    Start Time: 1445250425
    Timeout   : 300 (sec)
    Verify return code: 0 (ok)
---

This is a VERY handy command that works locally for testing your certificate setup.

test certificate
openssl s_client -connect 127.0.0.1:443 -servername poc-services.rinis.nl

s_server

But openssl can also be run in server mode. To demonstrate, open two terminals :

Example terminal 1:

terminal 1
openssl s_server -accept 9090 -state
output
Using default temp DH parameters
Using default temp ECDH parameters
ACCEPT
SSL_accept:before/accept initialization
SSL_accept:SSLv3 read client hello A
SSL_accept:SSLv3 write server hello A
SSL_accept:SSLv3 write certificate A
SSL_accept:SSLv3 write key exchange A
SSL_accept:SSLv3 write server done A
SSL_accept:SSLv3 flush data
SSL_accept:SSLv3 read client key exchange A
SSL_accept:SSLv3 read finished A
SSL_accept:SSLv3 write change cipher spec A
SSL_accept:SSLv3 write finished A
SSL_accept:SSLv3 flush data
-----BEGIN SSL SESSION PARAMETERS-----
MHUCAQECAgMBBAIAOQQgnFIis4dY9EZSZZNw6SbP+RD7g1maNRbWkvd6mGTmsPgE
MG0pv0ufWspXTHVmsCmBF1GMlAfuTmGVc4g+Aglssb3Qgrwc8fCkXtNUJWRVpE/X
zqEGAgRXF3aLogQCAgEspAYEBAEAAAA=
-----END SSL SESSION PARAMETERS-----
Shared ciphers:DHE-RSA-AES256-SHA:DHE-DSS-AES256-SHA:AES256-SHA:EDH-RSA-DES-CBC3-SHA:EDH-DSS-DES-CBC3-SHA:DES-CBC3-SHA:DHE-RSA-AES128-SHA:DHE-DSS-AES128-SHA:AES128-SHA:DHE-RSA-SEED-SHA:DHE-DSS-SEED-SHA:SEED-SHA:RC4-SHA:RC4-MD5:EDH-RSA-DES-CBC-SHA:EDH-DSS-DES-CBC-SHA:DES-CBC-SHA:EXP-EDH-RSA-DES-CBC-SHA:EXP-EDH-DSS-DES-CBC-SHA:EXP-DES-CBC-SHA:EXP-RC2-CBC-MD5:EXP-RC4-MD5
CIPHER is DHE-RSA-AES256-SHA

Example terminal 2:

The client side.

terminal 2
openssl s_client -connect localhost:9090 -state
output
CONNECTED(00000003)
SSL_connect:before/connect initialization
SSL_connect:SSLv2/v3 write client hello A
SSL_connect:SSLv3 read server hello A
depth=0 /CN=localhost/O=Stichting RINIS ROOT CA/C=NL
verify error:num=18:self signed certificate
verify return:1
depth=0 /CN=localhost/O=Stichting RINIS ROOT CA/C=NL
verify return:1
SSL_connect:SSLv3 read server certificate A
SSL_connect:SSLv3 read server key exchange A
SSL_connect:SSLv3 read server done A
SSL_connect:SSLv3 write client key exchange A
SSL_connect:SSLv3 write change cipher spec A
SSL_connect:SSLv3 write finished A
SSL_connect:SSLv3 flush data
SSL_connect:SSLv3 read finished A
---
Certificate chain
 0 s:/CN=localhost/O=Stichting RINIS ROOT CA/C=NL
   i:/CN=localhost/O=Stichting RINIS ROOT CA/C=NL

With more following

So it show all stages in connecting for ssl , very informative as well. So

  • the client and server greet each other
  • the certificate is passed from server to client
  • keys are exchanged
  • a cipher is negotiated

With client certificate verification

On the server :

server side
openssl s_server -accept 9090 -state -Verify 1 -CAfile client.p12
output
SL_accept:before/accept initialization
SSL_accept:SSLv3 read client hello A
SSL_accept:SSLv3 write server hello A
SSL_accept:SSLv3 write certificate A
SSL_accept:SSLv3 write key exchange A
SSL_accept:SSLv3 write certificate request A
SSL_accept:SSLv3 flush data
depth=0 /CN=localhost/O=Stichting RINIS/C=NL
verify error:num=18:self signed certificate
verify return:1
depth=0 /CN=localhost/O=Stichting RINIS/C=NL
verify return:1
SSL_accept:SSLv3 read client certificate A
SSL_accept:SSLv3 read client key exchange A
SSL_accept:SSLv3 read certificate verify A
SSL_accept:SSLv3 read finished A
SSL_accept:SSLv3 write change cipher spec A
SSL_accept:SSLv3 write finished A
SSL_accept:SSLv3 flush data

The highlighted line is extra as opposed to the previous example.

With the client side :

client side
openssl s_client -connect localhost:9090 -state -cert client.pem
output
CONNECTED(00000003)
SSL_connect:before/connect initialization
SSL_connect:SSLv2/v3 write client hello A
SSL_connect:SSLv3 read server hello A
depth=0 /CN=localhost/O=Stichting RINIS ROOT CA/C=NL
verify error:num=18:self signed certificate
verify return:1
depth=0 /CN=localhost/O=Stichting RINIS ROOT CA/C=NL
verify return:1
SSL_connect:SSLv3 read server certificate A
SSL_connect:SSLv3 read server key exchange A
SSL_connect:SSLv3 read server certificate request A
SSL_connect:SSLv3 read server done A
SSL_connect:SSLv3 write client certificate A
SSL_connect:SSLv3 write client key exchange A
SSL_connect:SSLv3 write certificate verify A
SSL_connect:SSLv3 write change cipher spec A
SSL_connect:SSLv3 write finished A
SSL_connect:SSLv3 flush data
SSL_connect:SSLv3 read finished A
---
Certificate chain
 0 s:/CN=localhost/O=Stichting RINIS ROOT CA/C=NL
   i:/CN=localhost/O=Stichting RINIS ROOT CA/C=NL
---

debug option

  • -debug will show a lot more messages, so i put it apart from -state because it will cloud the output for that.

python requests

When querying https requests with python, it seems that python uses a different set of trusted certificates then your browser. An example is digicert, for instance

cyberscanner
https://cyberscanner.nl

This site shows a valid certificate from a browser, but this program fails:

python get
#!/usr/bin/env python3
import requests
import json

url     ="https://cyberscanner.nl/api/batch/v2/requests";
myauth  =("messy", "some-secret")

response = requests.get(url, auth=myauth)
if response.status_code == 200:
    print(response.json())
else:
    print (response.reason)

Caused by SSLError(SSLCertVerificationError(1, '[SSL: CERTIFICATE_VERIFY_FAILED] certificate verify failed: unable to get local issuer certificate (_ssl.c:1056)')))

certifi

This package can be used to debug this, first you can find out where python looks in the first place :

certifi
1
2
3
4
5
6
7
python
Python 3.9.2 (default, Feb 28 2021, 17:03:44) 
[GCC 10.2.1 20210110] on linux
Type "help", "copyright", "credits" or "license" for more information.
>>> import certifi
>>> certifi.where()
'/etc/ssl/certs/ca-certificates.crt'

That is indeed a very standard location, but still it does not contain the digicert CA chain. This oneliner shows all issuer lines :

show issuers
openssl crl2pkcs7 -nocrl -certfile /etc/ssl/certs/ca-certificates.crt | openssl pkcs7 -print_certs -text -noout | grep Issuer

As shown in this output i have added the digicert certificates myself on hoek :

output
1
2
3
4
5
Issuer: C=US, O=DigiCert Inc, OU=www.digicert.com, CN=DigiCert Global Root CA
Issuer: C=US, O=DigiCert Inc, OU=www.digicert.com, CN=DigiCert Global Root CA
Issuer: CN=ACCVRAIZ1, OU=PKIACCV, O=ACCV, C=ES
CA Issuers - URI:http://www.accv.es/fileadmin/Archivos/certificados/raizaccv1.crt
...

However you can also just disable checking by putting verify=False in each request call :

get
response = requests.get(url, auth=myauth, verify=False)

But now we get an InsecureRequestWarning :

warning
1
2
3
4
./test.py 
/usr/lib/python3/dist-packages/urllib3/connectionpool.py:849: InsecureRequestWarning: Unverified HTTPS request is being made. Adding certificate verification is strongly advised. See: https://urllib3.readthedocs.io/en/latest/advanced-usage.html#ssl-warnings
InsecureRequestWarning)
{'requests': [{'name': 'generictest', 'submit_date': '2021-05-06T14:00:02.763077+00:00', 'finished_date': '2021-05-06T14:02:28.988412+00:00', 'request_type': 'web', 'status': 'done', 'request_id': '42e338a589824e83a1cf7222d72108cd'}], 'api_version': '2.0.0'}

These lines can help you get rid of those as well:

silence warning
#!/usr/bin/env python3
import requests
import json

# add two lines to disable InsecureRequestWarning :
from requests.packages.urllib3.exceptions import InsecureRequestWarning
requests.packages.urllib3.disable_warnings(InsecureRequestWarning)

url="https://cyberscanner.nl/api/batch/v2/requests";
myauth=("kees", "aeSagh9zuong")

response = requests.get(url, auth=myauth, verify=False)
if response.status_code == 200:
    print(response.json())
else:
    print (response.reason)