24 #include <openssl/err.h>
27 #define UNUSED __attribute__ ((unused))
34 #ifdef PRINT_REQUEST_ERRORS
35 #define print_request_error(fmt, ...)\
36 log_error(fmt, ##__VA_ARGS__);
38 #define print_request_error(...)
46 #ifdef PRINT_REQUEST_ERRORS
47 #define print_ssl_error(ssl, rtn) { \
48 int _err = SSL_get_error(ssl, rtn); \
49 const char* UNUSED error_str = ERR_error_string(_err, NULL); \
51 case SSL_ERROR_ZERO_RETURN: { \
52 print_request_error("SSL_ERROR_ZERO_RETURN (%d): %s\n", _err, error_str); \
55 case SSL_ERROR_WANT_READ: { \
56 print_request_error("SSL_ERROR_WANT_READ (%d): %s\n", _err, error_str);\
59 case SSL_ERROR_WANT_WRITE: {\
60 print_request_error("SSL_ERROR_WANT_WRITE (%d): %s\n", _err, error_str);\
63 case SSL_ERROR_WANT_CONNECT: {\
64 print_request_error("SSL_ERROR_WANT_CONNECT (%d): %s\n", _err, error_str);\
67 case SSL_ERROR_WANT_ACCEPT: {\
68 print_request_error("SSL_ERROR_WANT_ACCEPT (%d): %s\n", _err, error_str);\
71 case SSL_ERROR_WANT_X509_LOOKUP: {\
72 print_request_error("SSL_ERROR_WANT_X509_LOOKUP (%d): %s\n", _err, error_str);\
75 case SSL_ERROR_SYSCALL: {\
76 print_request_error("SSL_ERROR_SYSCALL (%d): %s\n", _err, error_str);\
79 case SSL_ERROR_SSL: {\
80 unsigned long UNUSED err2 = ERR_get_error(); \
81 print_request_error("SSL_ERROR_SSL (%d, %lx): %s\n", _err, err2, error_str);\
89 #define print_ssl_error(ssl, rtn)
96 if (mode & CRYPTO_LOCK) {
104 return (
unsigned long)pthread_self();
108 #if defined(OPENSSL_THREADS)
113 for (
int i=0; i < CRYPTO_num_locks(); i++) {
114 pthread_mutex_init(&(
lockarray[i]), NULL);
123 CRYPTO_set_locking_callback(NULL);
124 for (
int i=0; i<CRYPTO_num_locks(); i++) {
136 log_warn(
"SSL context already initialized. Not initializing again.");
141 OpenSSL_add_all_algorithms();
142 SSL_load_error_strings();
145 const SSL_METHOD *method = TLSv1_2_server_method();
147 SSL_CTX_set_session_cache_mode(
ssl_ctx, SSL_SESS_CACHE_OFF);
149 SSL_OP_NO_SSLv3 | SSL_OP_NO_TICKET | SSL_OP_SINGLE_DH_USE);
151 int rtn = SSL_CTX_set_cipher_list(
ssl_ctx,
"HIGH:!aNULL:!MD5:!RC4");
153 log_error(
"Could not set cipger list for SSL context");
162 if ( SSL_CTX_use_certificate_chain_file(
ssl_ctx, cert_file) <= 0 ) {
166 if ( SSL_CTX_use_PrivateKey_file(
ssl_ctx, cert_file, SSL_FILETYPE_PEM) <= 0 ) {
170 if ( !SSL_CTX_check_private_key(
ssl_ctx) ) {
182 #define CHECK_SSL_WANTS(ssl, rtn) \
184 int err = SSL_get_error(ssl, rtn); \
185 if (err != SSL_ERROR_WANT_READ && err != SSL_ERROR_WANT_WRITE) { \
186 print_ssl_error(ssl, rtn); \
188 } else if ( err == SSL_ERROR_WANT_READ) { \
189 return WS_INCOMPLETE_READ; \
190 } else if ( err == SSL_ERROR_WANT_WRITE) { \
191 return WS_INCOMPLETE_WRITE; \
197 int rtn = SSL_accept(ssl);
199 log_warn(
"The TLS/SSL handshake was not successful "
200 "but was shut down controlled and by the "
201 "specifications of the TLS/SSL protocol");
213 int num_bytes = SSL_read(ssl, buf, *buf_size);
215 *buf_size = num_bytes;
220 log_warn(
"Shouldn't ever get here...");
226 int num_bytes = SSL_write(ssl, buf, *buf_size);
228 if (num_bytes != *buf_size) {
229 log_warn(
"Didn't write the requested amount (written: %d, requested: %d)...",
230 num_bytes, *buf_size);
232 *buf_size = num_bytes;
237 log_warn(
"Shouldn't ever get here...");
243 int rtn = SSL_get_shutdown(ssl);
245 rtn = SSL_shutdown(ssl);
247 log(
WS_ERROR,
"Error shutting down SSL connection");
255 rtn = SSL_shutdown(ssl);
void kill_ssl_locks(void)
void init_ssl_locks(void)
SSL * init_ssl_connection(int fd)
int read_ssl(SSL *ssl, char *buf, int *buf_size)
Logging of status messages to the terminal.
int load_ssl_certificate(char *cert_file, char *key_file)
#define log_error(fmt,...)
#define print_ssl_error(ssl, rtn)
Explains an SSL error.
static unsigned long crypto_id_function(void)
int init_ssl_context(void)
int write_ssl(SSL *ssl, char *buf, int *buf_size)
#define CHECK_SSL_WANTS(ssl, rtn)
#define log(level, fmt,...)
Log at a custom level.
static pthread_mutex_t * lockarray
#define log_warn(fmt,...)
static void crypto_locking_callback(int mode, int n, const char *file, int line)