gcc heartbleed.c -o heartbleed -lssl -lssl3 -lcrypto
This looks OK. -lssl
is OpenSSL's SSL/TLS routines. -lcrypto
is OpenSSL's cryptography routines.
But I'm not sure about -lssl3
. What library is that?
heartbleed.c:(.text+0x47d): undefined reference to `SSL_CTX_SRP_CTX_init'
It appears your version of OpenSSL does not support Thomas Wu's Secure Remote Password (SRP). Or it was compiled without support for it.
According to the OpenSSL CHANGELOG, SRP was added at OpenSSL 1.0.1:
*) Add SRP support.
[Tom Wu <[email protected]> and Ben Laurie]
You can verify the OpenSSL library was built without SRP with the following.
First, find the OpenSSL SSL/TLS library:
$ find /usr/ -iname libssl.*
/usr/lib/libssl.0.9.7.dylib
/usr/lib/libssl.0.9.8.dylib
/usr/lib/libssl.dylib
/usr/local/ssl/android-14/lib/libssl.a
/usr/local/ssl/android-14/lib/libssl.so
/usr/local/ssl/android-14/lib/libssl.so.1.0.0
/usr/local/ssl/android-18/lib/libssl.a
/usr/local/ssl/android-18/lib/libssl.so
/usr/local/ssl/android-18/lib/libssl.so.1.0.0
...
Second, see if the symbol is exported:
$ nm /usr/lib/libssl.0.9.7.dylib | grep SSL_CTX_SRP_CTX_init
$
In my case, SRP is not available because Apple's default library is so down level (version 0.9.7).
I have another copy of the library cribbed away (version 1.0.1i):
$ nm /usr/local/ssl/macosx-x64/lib/libssl.dylib | grep SSL_CTX_SRP_CTX_init
0000000000034920 T _SSL_CTX_SRP_CTX_init
My 1.0.1i version has the routine.
Sometimes, you can build without SRP. To check if OpenSSL was configured without SRP:
$ cat /usr/local/ssl/macosx-x64/include/openssl/opensslconf.h | grep -A 1 SRP
$
In the case above, I configured for SRP.
Here's what it looks like when OpenSSL is configured without a feature (I configure without SSLv2):
$ cat /usr//local/ssl/macosx-x64/include/openssl/opensslconf.h | grep -A 1 SSL2
#ifndef OPENSSL_NO_SSL2
# define OPENSSL_NO_SSL2
#endif
--
# if defined(OPENSSL_NO_SSL2) && !defined(NO_SSL2)
# define NO_SSL2
# endif
SSL_CTX_SRP_CTX_init
is used in two places. To fix this, just comment it out.
First, line 355:
/* SSL_CTX_SRP_CTX_init(c->sslContext); */
Second, line 499:
/* SSL_CTX_SRP_CTX_init(c->sslContext); */
Related, the authors of the exploit could probably guard on OpenSSL's version number. The library provides OPENSSL_VERSION_NUMBER(3) just for this sort of thing. Something like:
#if (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRP)
SSL_CTX_SRP_CTX_init(c->sslContext);
#endif