Merge pull request #1085 from stanhu/ssl-improve-options-setting

Make it possible to set SSL verify mode
master
Michael Grunder 2022-08-15 17:19:51 -07:00 committed by GitHub
commit 367a82bf02
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 53 additions and 1 deletions

View File

@ -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
View File

@ -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)) {