secure client/server program in C with OpenSSL - c

I'm trying to write a secure client/server program in C with OpenSSL.
I've found a code sample at http://www.rtfm.com/openssl-examples/ but I get this error:
server: SSL read problem
client: Certificate doesn't verify
I think the problem is with the certificate generation, but I cannot find it.
Any idea?
Thanks

I downloaded the example and verified the error:
"10 X509_V_ERR_CERT_HAS_EXPIRED: certificate has expired"
With this command:
openssl x509 -in client.pem -noout -text
I got this output:
Certificate:
Data:
Version: 1 (0x0)
Serial Number: 258 (0x102)
Signature Algorithm: md5WithRSAEncryption
Issuer: C=US, O=RTFM, Inc., OU=Widgets Division, CN=Test CA20010517
Validity
Not Before: May 17 16:11:36 2001 GMT
Not After : Mar 6 16:11:36 2004 GMT
Subject: C=US, O=RTFM, Inc., OU=Widgets Division, CN=client
Subject Public Key Info:
Public Key Algorithm: rsaEncryption
RSA Public Key: (1024 bit)
Modulus (1024 bit):
00:87:35:64:a8:36:1e:a6:b1:4c:18:18:67:7b:4d:
84:03:b1:d4:86:d1:aa:3a:41:76:98:8e:4f:bb:f1:
9c:8c:41:e6:54:06:ed:9d:64:58:c6:e3:09:f3:90:
ac:2b:0f:8a:e9:fc:9e:4f:2d:1f:40:77:14:7b:da:
56:fd:01:ab:c4:38:a2:f6:50:31:c9:1a:cb:1c:66:
41:95:c3:f6:f3:65:bc:6b:28:5d:ab:bd:da:59:4a:
f2:8f:d4:e8:55:d4:c3:9d:b3:f5:93:a5:19:b5:81:
c9:95:4a:85:79:bc:b3:8c:a9:58:f3:8c:7a:31:43:
ff:b5:ce:98:f3:33:15:8b:d3
Exponent: 65537 (0x10001)
Signature Algorithm: md5WithRSAEncryption
24:c9:85:14:79:b6:ff:00:ed:d7:39:fb:39:8a:47:54:3f:8b:
ca:84:dc:ca:e7:9a:9f:cc:39:71:df:5f:e8:9f:27:fc:3e:b7:
0a:1c:ff:27:78:12:7f:bb:a6:bf:a1:1a:c8:93:a1:f7:2d:d4:
93:99:0d:6f:40:92:af:d9:1a:ed:7e:36:95:51:4f:b0:b0:e7:
71:1d:33:0a:62:ec:0a:f0:64:0b:0b:21:40:6c:28:0e:d0:98:
b4:db:77:08:d4:e5:2e:d6:95:9d:b8:7b:28:19:1f:2a:99:ac:
ae:05:7b:0f:89:bb:39:45:92:4a:08:14:80:c2:7e:29:f2:cf:
6e:26
Not After : Mar 6 16:11:36 2004 GMT
shows that was valid until 2004
You have to create a new certificate to use this example.
You can check those sites:
http://h71000.www7.hp.com/doc/83final/ba554_90007/ch04s02.html#cert2-fig
http://h71000.www7.hp.com/doc/83final/ba554_90007/ch04s03.html
http://blog.taragana.com/index.php/archive/openssl-how-to-create-self-signed-certificate/
http://sandbox.rulemaker.net/ngps/m2/howto.ca.html
http://novosial.org/openssl/ca

Get the value returned by SSL_get_verify_result(ssl) and compare it to the list of results in the Diagnostics section of OpenSSL's verify page. This will tell you the exact error.

Related

what is range of attime in OpenSSL

I need to check the validity of few certificates and am using -attime flag with my OpenSSL command
openssl cms -verify -inform DER *** -attime epochvalue.
I got a doubt here, about the data type of epochvalue, then had a look at the link
https://www.openssl.org/docs/man1.1.1/man1/openssl-s_server.html
in which it is mentioned as [-attime intmax]. I believe intmax mentioned here same as INT_MAX of limits.h
If attime range is only till INT_MAX, which when converts to epoch will be 2147483647 and is nothing but till Tuesday, January 19, 2038 3:14:07, how will the certificates after this date will be validated?

Openssl: SSL_CTX_set_ecdh_auto() return failure

At the moment my openssl version is
OpenSSL 1.0.2h 3 May 2016
I use an example code offered by openssl Simple_TLS_Server to start a server and use s_client to send tls handshake. The server returned error like this:
139629255337616:error:1408A0C1:SSL routines:SSL3_GET_CLIENT_HELLO:no shared cipher:s3_srvr.c:1349
And the s_client returned:
CONNECTED(00000003)
140266915485328:error:14077410:SSL routines:SSL23_GET_SERVER_HELLO:sslv3 alert handshake failure:s23_clnt.c:769:
---
no peer certificate available
---
No client certificate CA names sent
---
SSL handshake has read 7 bytes and written 307 bytes
---
New, (NONE), Cipher is (NONE)
Secure Renegotiation IS NOT supported
Compression: NONE
Expansion: NONE
No ALPN negotiated
SSL-Session:
Protocol : TLSv1.2
Cipher : 0000
Session-ID:
Session-ID-ctx:
Master-Key:
Key-Arg : None
PSK identity: None
PSK identity hint: None
SRP username: None
Start Time: 1471879558
Timeout : 300 (sec)
Verify return code: 0 (ok)
---
After reading this Manual:SSL_CTX_set1_curves(3), i modified some lines of the original:
if(!SSL_CTX_set_ecdh_auto(ctx, 1))
{
fprintf(stderr, "Error: SSL_CTX_set_ecdh_auto(ctx, 1)\n");
}
When i restarted the Simple_TLS_Server, it prints
Error: SSL_CTX_set_ecdh_auto(ctx, 1)
Also tried like this:
if(!SSL_CTX_set_ecdh_auto(ctx, 1))
{
ERR_print_errors_fp(stderr);
}
But there was no available error message.
Does anyone know how could this happen? If you require more information, please just let me know.
PS: i tried certificates and keys with s_server and s_client, that worked fine.
Does anyone know how could this happen?
According to the source code the only cases where SSL_CTX_set_ecdh_auto return 0 is when the openssl library was compiled without support for ECDH (OPENSSL_NO_ECDH) or without support for elliptic curves at all (OPENSSL_NO_EC).

OpenSSL: Fetching SQL Server public certificate

I want to use OpenSSL or any native Linux command to grab the certificate of a SQL Server. I tried the same way as I do with an HTTP server but it doesn't work.
openssl s_client -showcerts -connect MY.MSSQL.SERVER:1433
CONNECTED(00000003)
write:errno=104
---
no peer certificate available
---
No client certificate CA names sent
---
SSL handshake has read 0 bytes and written 249 bytes
---
New, (NONE), Cipher is (NONE)
Secure Renegotiation IS NOT supported
Compression: NONE
Expansion: NONE
---
This gist by github user lnattrass gives a python script that is "A terrible way to connect to MS SQL Server and dump the certificate as a PEM" (his wording) in python. Yes, that's not what you asked about, you asked about OpenSSL. But one of the comments says in part
I was able to get the same results using openssl like this: openssl s_client -showcerts -connect <hostname>:<port> </dev/null 2>/dev/null|openssl x509 -outform PEM >dbcertfile.pem as suggested somewhere.
(no clue where "somewhere" would have been.)
I've tried the openssl method but it failed for me:
rpresser#11MTLDEV-L11626:~$ openssl s_client -showcerts -connect mysqlserver.mydomain.com:1433 </dev/null 2>/dev/null|openssl x509 -outform PEM >dbcertfile.pem
unable to load certificate
140246796931520:error:0909006C:PEM routines:get_name:no start line:../crypto/pem/pem_lib.c:745:Expecting: TRUSTED CERTIFICATE
Perhaps this was because the self-signed cert (see below) was not trusted? I'm really not sure.
After fixing one indentation bug, the python method worked for me:
rpresser#11MTLDEV-L11626:/mnt/c/temp$ python3 get_tds_cert.py redacted.domain.COM 1433
# get_tdspacket: 0, tdspacket len: 43
# Header: {'type': 4, 'status': 1, 'length': 43, 'channel': 0, 'packet': 1, 'window': 0}
# Remaining tdspbuf length: 0
# Starting TLS handshake loop..
# Shaking (0/5)
# get_tdspacket: 0, tdspacket len: 894
# Header: {'type': 18, 'status': 1, 'length': 894, 'channel': 0, 'packet': 0, 'window': 0}
# Remaining tdspbuf length: 0
# Shaking (1/5)
# get_tdspacket: 0, tdspacket len: 67
# Header: {'type': 18, 'status': 1, 'length': 67, 'channel': 0, 'packet': 0, 'window': 0}
# Remaining tdspbuf length: 0
# Handshake completed, dumping certificates
-----BEGIN CERTIFICATE-----
MIIB+zCCAWSgAwIBAgIQYc0YElx/YYFF/Q0PIYETxDANBgkqhkiG9w0BAQUFADA7
MTkwNwYDVQQDHjAAUwBTAEwAXwBTAGUAbABmAF8AUwBpAGcAbgBlAGQAXwBGAGEA
bABsAGIAYQBjAGswIBcNMjAwMjAyMDQ0NzA5WhgPMjA1MDAyMDIwNDQ3MDlaMDsx
OTA3BgNVBAMeMABTAFMATABfAFMAZQBsAGYAXwBTAGkAZwBuAGUAZABfAEYAYQBs
AGwAYgBhAGMAazCBnzANBgkqhkiG9w0BAQEFAAOBjQAwgYkCgYEAohSQbug4qZug
ji16iKuNpX4OzGc9DPAORaho8LB2AGinol+rEmcTGRofeIg9zeXMbiOwWbrCnT3/
RUDLOW6V4papZ7H/qIcmVIKdzNCezWMlfPd0h4S00kVovHDIbC1t2uhcDdfEIsh+
fbgzS34bkXNACurtV5t8kpPWYDsRwqsCAwEAATANBgkqhkiG9w0BAQUFAAOBgQBr
qfAph+/NF6Cgxisp7UHq9kjQ6sYNCIXfq9mJnRqX+I8H6nxSQfpDlljdvKN3GYeg
SL4jowNL11z5xjpJS9/KhLFwodicWKt0Go/CqusPWJKVJo0HgIn9a1hHPipRbR8w
3+QRy50kaPXm5VOoSg83+CjEg9ri7jfgtWLetq+xoQ==
-----END CERTIFICATE-----
I haven't bothered to redact the certificate because it is the SQL Server self-signed fallback, as displayed by SSLShopper Certificate Decoder
Certificate Information:
Common Name: SSL_Self_Signed_Fallback
Valid From: February 1, 2020
Valid To: February 1, 2050
Serial Number: 61cd18125c7f618145fd0d0f218113c4
Inspired by the https://gist.github.com/lnattrass/a4a91dbf439fc1719d69f7865c1b1791 with help from https://learn.microsoft.com/en-us/openspecs/windows_protocols/ms-tds/1ef08b76-1594-40cf-8ce0-d2407133dd3d
Similar implementation in groovy (java 11) which returns certificate chain from sql server:
groovy sqlserver-cert.groovy <host> <port>
After looking for openssl solutions without sucesss and fighting with the python script without success too (both the initial and the fixed versions throwed an error) i resorted to use nmap, in this case it was quite easy:
nmap -v --script=ssl-cert -p 1433 server.example.com
In the output there should be a certificate such as this (selfsigned cert), you should be able to clean the formatting and use it where you need.
| SHA-1: dba1 14a3 d2c7 9410 0a7a bb8d d08e e1a0 d6a1 9e87
| -----BEGIN CERTIFICATE-----
| MIIB+zCCAWSgAwIBAgIQJW6eoEmJJJJDqpOSmq2W6TANBgkqhkiG9w0BAQUFADA7
| MTkwNwYDVQQDHjAAUwBTAEwAXwBTAGUAbABmAF8AUwBpAGcAbgBlAGQAXwBGAGEA
| bABsAGIAYQBjAGswIBcNMjMwMTE4MTEyOTQ5WhgPMjA1MzAxMTgxMTI5NDlaMDsx
| OTA3BgNVBAMeMABTAFMATABfAFMAZQBsAGYAXwBTAGkAZwBuAGUAZABfAEYAYQBs
| AGwAYgBhAGMAazCBnzANBgkqhkiG9w0BAQEFAAOBjQAwgYkCgYEAxKxXDgSq1++4
| yDSOmXDO5F2gDa1cW2x4USQOxXq5ux4RObhteo9pVOIDi2TfmKMUl9OTNUqfxiTl
| YJtHmBKP7aghWK5Z9p5VBDfbzmAG04tdII49piocKvdimy96veGWnPUGFdovx35k
| dEOT7+NpQTVIDscsIIDa8csQJmuwgdsCAwEAATANBgkqhkiG9w0BAQUFAAOBgQBV
| 0KzioJl5tcvpjG2VK/TTpfAdZnz4MZwhg/ThviRtcV3WLVkKbCOh0A1ljCoURgsX
| HIvYXBHn1XdJn4F8HHeh8B53tjwRYkvxg2jGWfKofr0nAu23rbMv3543UroSH6r2
| 3CeLkgsAwFUcXPUfYwae5L48FKlkD5V2TsOhmy8rvg==
|_-----END CERTIFICATE-----

Issue with crypt C API on AIX 7.1

I am writing a password reset utility on AIX (7.1.0.0) and I need to support SMD5, SSHA256, SSHA512 and BLOWFISH password hash algorithms. I have successfully implemented the code for SMD5, SSHA256 and SSHA512. However, for BLOWFISH algorithm the 'crypt' API still returns normal DES hash and not the BLOWFISH hash. I tried different prefixes in salt value - {sblowfish} {sblowfish}08$ {SBLOWFISH} {SBLOWFISH}08$. However, I still don't get blowfish hash. For, AIX 5.3 {sblowfish} prefix in salt value works and I get required hash. However, for AIX 7.1 it doesn't work.
The format for the salt value I am using is as follows -
MD5 - {smd5}<randomly generated 8 characters>$
SHA256 - {ssha256}06$<randomly generated 8 characters>$
SHA512 - {ssha512}06$<randomly generated 8 characters>$
BLOWFISH - {sblowfish}08$<randomly generated 22 characters>$
I then pass the user password and salt value to the 'crypt' API in 'C'.
crypt(password, salt);
For MD5, SHA256 and SHA512 I get the password hash which is compliant to the corresponding algorithm.
However, for BLOWFISH salt, the 'crypt' API rejects the salt and instead returns normal DES hash though i have the blowfish in the system.
Can anybody please help out here? Thanks in advance.

to use RSA_PKCS1_OAEP_PADDING for RSA signature

Previously I was using rsa signature with no padding ,but now I was asked to add PKCS1_OAEP padding ,Initially I tried simple adding this flag "RSA_PKCS1_OAEP_PADDING", but it is giving error code while running like this
error:04066076:rsa routines:RSA_EAY_PRIVATE_ENCRYPT:unknown padding type
Further I googled about the rsa signature with PKCS1_OAEP padding but didn't get anything except it is said that for implementing RSA_PKCS1_OAEP padding you have to use this one
int RSA_padding_add_PKCS1_OAEP(unsigned char *to, int tlen,
unsigned char *f, int fl, unsigned char *p, int pl);
and then do private_encrypt with RSA_NO_padding but still having confusion as they have not explained clearly how to use this padding_add function explictly .can anyone provide help .would really appreciate that .
thanks in advance
According to RFC 3447 OAEP padding scheme can be used only with encryption operation and therefore it cannot be used with signatures. If standard RSASSA-PKCS1-v1_5 scheme is not good enough for you I believe you should use RSASSA-PSS which is recommended for new applications and have characteristics similar to OAEP scheme. See RFC 3447 for more details.
You can easily check out that my answer is correct with command line OpenSSL tool:
Generate private key:
openssl genrsa -out private.key 2048
Generate some input data:
echo "Hello world" > input.data
Try to generate signature with OAEP scheme:
openssl rsautl -sign -oaep -inkey private.key -in input.data -out output.data
RSA operation error
139655304349344:error:04066076:rsa routines:RSA_EAY_PRIVATE_ENCRYPT:unknown padding type:rsa_eay.c:389:
Try to encrypt data with OAEP scheme:
openssl rsautl -encrypt -oaep -inkey private.key -in input.data -out output.data
You can also take a look at "rsautl" module source code if you need more information but remember that RFC 3347 is your friend :)

Resources