Forum

RequiredCA and "SSL_accept(): protocol error"

Andrew Lockhart
19 September 2011, 20:58
Hiawatha version: 7.6
Operating System: Ubuntu 10.04.2 LTS (x86_64)

Hiawatha stops responding on peer-verified SSL bindings. Recompiling with CFLAGS="-g -O0" ./configure --enable-debug shows many SSL_accept(): protocol error on the console when running hiawatha -d. Other non-peer-verified bindings that are SSL continue to respond.

I've used the certificates with openssl s_client and s_server without any issue, so I know that everything should verify properly. When running the debug build of hiawatha I did notice that the source of SSL_accept() returning errors seemed to be ssl23_get_client_hello() failing sometimes.

Any help would be appreciated.

Here is my config:
SystemLogfile = /usr/local/var/log/hiawatha/system.log
GarbageLogfile = /usr/local/var/log/hiawatha/garbage.log

Binding {
Port = 443
SSLcertFile = hiawatha.pem
}

Binding {
Port = 40443
SSLcertFile = hiawatha.pem
RequiredCA = cacert.pem
}

CGIhandler = /usr/bin/php-cgi:php
Hostname = 127.0.0.1
WebsiteRoot = /usr/local/var/www/hiawatha
StartFile = index.html
AccessLogfile = /usr/local/var/log/hiawatha/access.log
ErrorLogfile = /usr/local/var/log/hiawatha/error.log
ExecuteCGI = yes


Keys/certificates were generated with the following script/config files:

gen_keypairs.sh:
openssl req -x509 -newkey rsa:2048 -keyout CA.key -out CA.crt -outform PEM -nodes -config CA.cnf
ln -s CA.crt cacert.pem
touch index.txt index.txt.attr
echo 01 > serial

openssl req -newkey rsa:2048 -keyout client.key -keyform PEM -nodes -out client.req -outform PEM -config client.cnf
openssl ca -in client.req -out client.crt -config CA.cnf -batch
openssl pkcs12 -export -inkey client.key -in client.crt -CAfile CA.crt -password pass:password -out client.p12

openssl req -newkey rsa:2048 -keyout server.key -keyform PEM -nodes -out server.req -outform PEM -config server.cnf
openssl ca -in server.req -out server.crt -config CA.cnf -batch
cat server.key server.crt cacert.pem > hiawatha.pem


CA.cnf:
[ ca ]
default_ca = CA_default

[ CA_default ]
dir = .
new_certs_dir = /tmp
#certs = .
#crl_dir = .
database = ./index.txt
default_md = sha1
policy = policy_match
serial = ./serial
default_days = 365

certificate = CA.crt
private_key = CA.key
unique_subject = no


[ req ]
default_bits = 2048
default_keyfile = new.key
default_md = sha1
prompt = no
distinguished_name = root_ca_distinguished_name
x509_extensions = root_ca_extensions

[ root_ca_distinguished_name ]
commonName = CA Root

[ root_ca_extensions ]
basicConstraints = CA:true

[policy_match]
commonName = supplied


client.cnf:
[ req ]
default_bits = 2048
default_keyfile = client.key
default_md = sha1
prompt = no
distinguished_name = distinguished_name
x509_extensions = extensions

[ distinguished_name ]
commonName = client.example.com

[ extensions ]
basicConstraints = CA:false


server.cnf:
[ req ]
default_bits = 2048
default_keyfile = client.key
default_md = sha1
prompt = no
distinguished_name = distinguished_name
x509_extensions = extensions

[ distinguished_name ]
commonName = server.example.com
emailAddress = server@example.com

[ extensions ]
basicConstraints = CA:false
Andrew Lockhart
20 September 2011, 19:17
Hi,

It turns out it was failing in ssl_get_prev_session() in the following chunk of code:
	if((s->verify_mode & SSL_VERIFY_PEER) && s->sid_ctx_length == 0)
{
/* We can't be sure if this session is being used out of
* context, which is especially important for SSL_VERIFY_PEER.
* The application should have used SSL[_CTX]_set_session_id_context.
*
* For this error case, we generate an error instead of treating
* the event like a cache miss (otherwise it would be easy for
* applications to effectively disable the session cache by
* accident without anyone noticing).
*/

SSLerr(SSL_F_SSL_GET_PREV_SESSION,SSL_R_SESSION_ID_CONTEXT_UNINITIALIZED);
fatal = 1;
goto err;
}


Per the comments I've added a call to SSL_CTX_set_session_id_context() after the context is created for the binding. Here is the patch:
--- hiawatha-7.6/hiawatha.c	2011-08-18 08:27:17.000000000 -0700
+++ hiawatha-7.6-SSL_CTX_set_session_id_context-patch/hiawatha.c 2011-09-20 09:58:24.257691766 -0700
@@ -1884,6 +1884,9 @@
perror("bind https");
return -1;
}
+ else {
+ SSL_CTX_set_session_id_context(binding->ssl_context, (unsigned char *)&binding->port, sizeof(binding->port));
+ }
}
binding = binding->next;
}
Hugo Leisink
20 September 2011, 22:48
Hmmm, this used to work. Guess something changed in OpenSSL. Even with your patch, I can't get this working again. I'll have to look at it some more. If you have any hint, please let me know.

Btw, is it now working for you?
This topic has been closed.