Merge pull request #285 from KLuka/master

SSL patches, HTTP timeout patch
This commit is contained in:
Luka Krajger 2015-03-05 18:36:58 +01:00
commit 68b5a487b4
3 changed files with 52 additions and 6 deletions

View file

@ -136,6 +136,9 @@ int (*SSL_write)(SSL *, const void *, int);
SSL_METHOD * (*SSLv23_server_method)(void); SSL_METHOD * (*SSLv23_server_method)(void);
X509 * (*d2i_X509)(X509 **px, const unsigned char **in, int len); X509 * (*d2i_X509)(X509 **px, const unsigned char **in, int len);
void (*X509_free)(X509 *a); void (*X509_free)(X509 *a);
int (*x_SSL_CTX_set_cipher_list)(SSL_CTX *ctx, const char *str);
void (*x_sk_zero)(void *st);
void * (*x_SSL_COMP_get_compression_methods)(void);
#endif #endif
static void sslDestroyCachedContext(void *ssl_, char *context_) { static void sslDestroyCachedContext(void *ssl_, char *context_) {
@ -308,7 +311,9 @@ static void loadSSL(void) {
{ { &SSL_write }, "SSL_write" }, { { &SSL_write }, "SSL_write" },
{ { &SSLv23_server_method }, "SSLv23_server_method" }, { { &SSLv23_server_method }, "SSLv23_server_method" },
{ { &d2i_X509 }, "d2i_X509" }, { { &d2i_X509 }, "d2i_X509" },
{ { &X509_free }, "X509_free" } { { &X509_free }, "X509_free" },
{ { &x_SSL_CTX_set_cipher_list }, "SSL_CTX_set_cipher_list" },
{ { &x_sk_zero }, "sk_zero" }
}; };
for (unsigned i = 0; i < sizeof(symbols)/sizeof(symbols[0]); i++) { for (unsigned i = 0; i < sizeof(symbols)/sizeof(symbols[0]); i++) {
if (!(*symbols[i].var = loadSymbol(path_libssl, symbols[i].fn))) { if (!(*symbols[i].var = loadSymbol(path_libssl, symbols[i].fn))) {
@ -320,6 +325,10 @@ static void loadSSL(void) {
return; return;
} }
} }
// These are optional
x_SSL_COMP_get_compression_methods = loadSymbol(path_libssl, "SSL_COMP_get_compression_methods");
// ends
SSL_library_init(); SSL_library_init();
dcheck(!ERR_peek_error()); dcheck(!ERR_peek_error());
debug("Loaded SSL suppport"); debug("Loaded SSL suppport");
@ -583,6 +592,32 @@ static int sslSetCertificateFromFile(SSL_CTX *context,
} }
#endif #endif
static SSL_CTX *sslMakeContext(void) {
SSL_CTX *context;
check(context = SSL_CTX_new(SSLv23_server_method()));
SSL_CTX_set_options(context, SSL_OP_ALL);
SSL_CTX_set_options(context, SSL_OP_NO_SSLv2 | SSL_OP_NO_SSLv3);
#ifdef SSL_OP_NO_COMPRESSION
SSL_CTX_set_options(context, SSL_OP_NO_COMPRESSION);
#endif
#if defined(HAVE_DLOPEN)
if (SSL_COMP_get_compression_methods) {
sk_SSL_COMP_zero(SSL_COMP_get_compression_methods());
}
#elif OPENSSL_VERSION_NUMBER >= 0x00908000L
sk_SSL_COMP_zero(SSL_COMP_get_compression_methods());
#endif
SSL_CTX_set_options(context, SSL_OP_SINGLE_DH_USE);
#ifdef SSL_OP_SINGLE_ECDH_USE
SSL_CTX_set_options(context, SSL_OP_SINGLE_ECDH_USE);
#endif
#ifdef SSL_OP_NO_SESSION_RESUMPTION_ON_RENEGOTIATION
SSL_CTX_set_options(context, SSL_OP_NO_SESSION_RESUMPTION_ON_RENEGOTIATION);
#endif
check(SSL_CTX_set_cipher_list(context, "HIGH:MEDIUM:!aNULL:!MD5"));
return context;
}
#ifdef HAVE_TLSEXT #ifdef HAVE_TLSEXT
static int sslSNICallback(SSL *sslHndl, int *al ATTR_UNUSED, static int sslSNICallback(SSL *sslHndl, int *al ATTR_UNUSED,
struct SSLSupport *ssl) { struct SSLSupport *ssl) {
@ -619,7 +654,7 @@ static int sslSNICallback(SSL *sslHndl, int *al ATTR_UNUSED,
serverName+1, serverName+1,
NULL); NULL);
if (context == NULL) { if (context == NULL) {
check(context = SSL_CTX_new(SSLv23_server_method())); context = sslMakeContext();
check(ssl->sniCertificatePattern); check(ssl->sniCertificatePattern);
char *certificate = stringPrintfUnchecked(NULL, char *certificate = stringPrintfUnchecked(NULL,
ssl->sniCertificatePattern, ssl->sniCertificatePattern,
@ -697,7 +732,7 @@ void sslSetCertificate(struct SSLSupport *ssl, const char *filename,
} }
// Try to set the default certificate. If necessary, (re-)generate it. // Try to set the default certificate. If necessary, (re-)generate it.
check(ssl->sslContext = SSL_CTX_new(SSLv23_server_method())); ssl->sslContext = sslMakeContext();
if (autoGenerateMissing) { if (autoGenerateMissing) {
if (sslSetCertificateFromFile(ssl->sslContext, defaultCertificate) < 0) { if (sslSetCertificateFromFile(ssl->sslContext, defaultCertificate) < 0) {
char hostname[256], buf[4096]; char hostname[256], buf[4096];
@ -781,7 +816,7 @@ static char *sslFdToFilename(int fd) {
void sslSetCertificateFd(struct SSLSupport *ssl, int fd) { void sslSetCertificateFd(struct SSLSupport *ssl, int fd) {
#ifdef HAVE_OPENSSL #ifdef HAVE_OPENSSL
check(ssl->sslContext = SSL_CTX_new(SSLv23_server_method())); ssl->sslContext = sslMakeContext();
char *filename = sslFdToFilename(fd); char *filename = sslFdToFilename(fd);
if (!sslSetCertificateFromFd(ssl->sslContext, fd)) { if (!sslSetCertificateFromFd(ssl->sslContext, fd)) {
fatal("Cannot read valid certificate from %s. Check file format.", fatal("Cannot read valid certificate from %s. Check file format.",

View file

@ -111,6 +111,9 @@ extern int (*x_SSL_write)(SSL *, const void *, int);
extern SSL_METHOD *(*x_SSLv23_server_method)(void); extern SSL_METHOD *(*x_SSLv23_server_method)(void);
extern X509 * (*x_d2i_X509)(X509 **px, const unsigned char **in, int len); extern X509 * (*x_d2i_X509)(X509 **px, const unsigned char **in, int len);
extern void (*x_X509_free)(X509 *a); extern void (*x_X509_free)(X509 *a);
extern int (*x_SSL_CTX_set_cipher_list)(SSL_CTX *ctx, const char *str);
extern void (*x_sk_zero)(void *st);
extern void *(*x_SSL_COMP_get_compression_methods)(void);
#define BIO_ctrl x_BIO_ctrl #define BIO_ctrl x_BIO_ctrl
#define BIO_f_buffer x_BIO_f_buffer #define BIO_f_buffer x_BIO_f_buffer
@ -151,6 +154,9 @@ extern void (*x_X509_free)(X509 *a);
#define SSLv23_server_method x_SSLv23_server_method #define SSLv23_server_method x_SSLv23_server_method
#define d2i_X509 x_d2i_X509 #define d2i_X509 x_d2i_X509
#define X509_free x_X509_free #define X509_free x_X509_free
#define SSL_CTX_set_cipher_list x_SSL_CTX_set_cipher_list
#define sk_zero x_sk_zero
#define SSL_COMP_get_compression_methods x_SSL_COMP_get_compression_methods
#undef BIO_set_buffer_read_data #undef BIO_set_buffer_read_data
#undef SSL_CTX_set_tlsext_servername_arg #undef SSL_CTX_set_tlsext_servername_arg

View file

@ -164,6 +164,7 @@ ShellInABox.prototype.sendRequest = function(request) {
request = new XMLHttpRequest(); request = new XMLHttpRequest();
} }
request.open('POST', this.url + '?', true); request.open('POST', this.url + '?', true);
request.timeout = 30000; // Don't leave POST pending forever: force 30s timeout to prevent HTTP Proxy thread hijack
request.setRequestHeader('Cache-Control', 'no-cache'); request.setRequestHeader('Cache-Control', 'no-cache');
request.setRequestHeader('Content-Type', request.setRequestHeader('Content-Type',
'application/x-www-form-urlencoded; charset=utf-8'); 'application/x-www-form-urlencoded; charset=utf-8');
@ -202,8 +203,12 @@ ShellInABox.prototype.onReadyStateChange = function(request) {
this.sendRequest(request); this.sendRequest(request);
} }
} else if (request.status == 0) { } else if (request.status == 0) {
// Time Out // Time Out or other connection problems: retry after 1s to prevent release CPU before retry
this.sendRequest(request); setTimeout(function(shellInABox) {
return function() {
shellInABox.sendRequest();
};
}(this), 1000);
} else { } else {
this.sessionClosed(); this.sessionClosed();
} }