Make it possible to set SSL verify mode
If no SSL certificates are provided, many Redis clients default to disabling SSL peer verification. Previously it was a bit cumbersome to configure this because the client would either have to reimplement `redisCreateSSLContext()` or reach into the internals to set the OpenSSL verify mode. We can improve the SSL API by introducing a `redisCreateSSLContextWithOptions()` call that takes into structured parameters for SSL initialization. This structure contains a verify mode that is used to set the OpenSSL verify mode. Relates to https://github.com/redis/hiredis/issues/646
This commit is contained in:
parent
0865c115ba
commit
71119a71d7
@ -61,6 +61,27 @@ typedef enum {
|
||||
REDIS_SSL_CTX_OS_CERT_ADD_FAILED /* Failed to add CA certificates obtained from system to the SSL context */
|
||||
} redisSSLContextError;
|
||||
|
||||
/* Constants that mirror OpenSSL's verify modes. By default,
|
||||
* REDIS_SSL_VERIFY_PEER is used with redisCreateSSLContext().
|
||||
* Some Redis clients disable peer verification if there are no
|
||||
* certificates specified.
|
||||
*/
|
||||
#define REDIS_SSL_VERIFY_NONE 0x00
|
||||
#define REDIS_SSL_VERIFY_PEER 0x01
|
||||
#define REDIS_SSL_VERIFY_FAIL_IF_NO_PEER_CERT 0x02
|
||||
#define REDIS_SSL_VERIFY_CLIENT_ONCE 0x04
|
||||
#define REDIS_SSL_VERIFY_POST_HANDSHAKE 0x08
|
||||
|
||||
/* Options to create an OpenSSL context. */
|
||||
typedef struct {
|
||||
const char *cacert_filename;
|
||||
const char *capath;
|
||||
const char *cert_filename;
|
||||
const char *private_key_filename;
|
||||
const char *server_name;
|
||||
int verify_mode;
|
||||
} redisSSLOptions;
|
||||
|
||||
/**
|
||||
* Return the error message corresponding with the specified error code.
|
||||
*/
|
||||
@ -101,6 +122,18 @@ redisSSLContext *redisCreateSSLContext(const char *cacert_filename, const char *
|
||||
const char *cert_filename, const char *private_key_filename,
|
||||
const char *server_name, redisSSLContextError *error);
|
||||
|
||||
/**
|
||||
* Helper function to initialize an OpenSSL context that can be used
|
||||
* to initiate SSL connections. This is a more extensible version of redisCreateSSLContext().
|
||||
*
|
||||
* options contains a structure of SSL options to use.
|
||||
*
|
||||
* If error is non-null, it will be populated in case the context creation fails
|
||||
* (returning a NULL).
|
||||
*/
|
||||
redisSSLContext *redisCreateSSLContextWithOptions(redisSSLOptions *options,
|
||||
redisSSLContextError *error);
|
||||
|
||||
/**
|
||||
* Free a previously created OpenSSL context.
|
||||
*/
|
||||
|
21
ssl.c
21
ssl.c
@ -219,6 +219,25 @@ redisSSLContext *redisCreateSSLContext(const char *cacert_filename, const char *
|
||||
const char *cert_filename, const char *private_key_filename,
|
||||
const char *server_name, redisSSLContextError *error)
|
||||
{
|
||||
redisSSLOptions options = {
|
||||
.cacert_filename = cacert_filename,
|
||||
.capath = capath,
|
||||
.cert_filename = cert_filename,
|
||||
.private_key_filename = private_key_filename,
|
||||
.server_name = server_name,
|
||||
.verify_mode = REDIS_SSL_VERIFY_PEER,
|
||||
};
|
||||
|
||||
return redisCreateSSLContextWithOptions(&options, error);
|
||||
}
|
||||
|
||||
redisSSLContext *redisCreateSSLContextWithOptions(redisSSLOptions *options, redisSSLContextError *error) {
|
||||
const char *cacert_filename = options->cacert_filename;
|
||||
const char *capath = options->capath;
|
||||
const char *cert_filename = options->cert_filename;
|
||||
const char *private_key_filename = options->private_key_filename;
|
||||
const char *server_name = options->server_name;
|
||||
|
||||
#ifdef _WIN32
|
||||
HCERTSTORE win_store = NULL;
|
||||
PCCERT_CONTEXT win_ctx = NULL;
|
||||
@ -235,7 +254,7 @@ redisSSLContext *redisCreateSSLContext(const char *cacert_filename, const char *
|
||||
}
|
||||
|
||||
SSL_CTX_set_options(ctx->ssl_ctx, SSL_OP_NO_SSLv2 | SSL_OP_NO_SSLv3);
|
||||
SSL_CTX_set_verify(ctx->ssl_ctx, SSL_VERIFY_PEER, NULL);
|
||||
SSL_CTX_set_verify(ctx->ssl_ctx, options->verify_mode, NULL);
|
||||
|
||||
if ((cert_filename != NULL && private_key_filename == NULL) ||
|
||||
(private_key_filename != NULL && cert_filename == NULL)) {
|
||||
|
Loading…
x
Reference in New Issue
Block a user