SSL_CTX_set_options(srv->ssl_ctx.ctx, options);
SSL_CTX_set_mode(srv->ssl_ctx.ctx, mode);
- SSL_CTX_set_verify(srv->ssl_ctx.ctx, SSL_VERIFY_NONE, NULL);
+ SSL_CTX_set_verify(srv->ssl_ctx.ctx, srv->ssl_ctx.verify ? srv->ssl_ctx.verify : SSL_VERIFY_NONE, NULL);
+ if (srv->ssl_ctx.verify & SSL_VERIFY_PEER) {
+ if (srv->ssl_ctx.ca_file) {
+ /* load CAfile to verify */
+ if (!SSL_CTX_load_verify_locations(srv->ssl_ctx.ctx, srv->ssl_ctx.ca_file, NULL)) {
+ Alert("Proxy '%s', server '%s' |%s:%d] unable to load CA file '%s'.\n",
+ curproxy->id, srv->id,
+ srv->conf.file, srv->conf.line, srv->ssl_ctx.ca_file);
+ cfgerr++;
+ }
+ }
+#ifdef X509_V_FLAG_CRL_CHECK
+ if (srv->ssl_ctx.crl_file) {
+ X509_STORE *store = SSL_CTX_get_cert_store(srv->ssl_ctx.ctx);
+
+ if (!store || !X509_STORE_load_locations(store, srv->ssl_ctx.crl_file, NULL)) {
+ Alert("Proxy '%s', server '%s' |%s:%d] unable to configure CRL file '%s'.\n",
+ curproxy->id, srv->id,
+ srv->conf.file, srv->conf.line, srv->ssl_ctx.crl_file);
+ cfgerr++;
+ }
+ else {
+ X509_STORE_set_flags(store, X509_V_FLAG_CRL_CHECK|X509_V_FLAG_CRL_CHECK_ALL);
+ }
+ }
+#endif
+ }
+
SSL_CTX_set_session_cache_mode(srv->ssl_ctx.ctx, SSL_SESS_CACHE_OFF);
if (srv->ssl_ctx.ciphers &&
!SSL_CTX_set_cipher_list(srv->ssl_ctx.ctx, srv->ssl_ctx.ciphers)) {
return ERR_ALERT | ERR_FATAL;
}
- if ((*args[cur_arg + 1] != '/') && global.ca_base) {
- conf->ca_file = malloc(strlen(global.ca_base) + 1 + strlen(args[cur_arg + 1]) + 1);
- if (conf->ca_file)
- sprintf(conf->ca_file, "%s/%s", global.ca_base, args[cur_arg + 1]);
- return 0;
- }
+ if ((*args[cur_arg + 1] != '/') && global.ca_base)
+ memprintf(&conf->ca_file, "%s/%s", global.ca_base, args[cur_arg + 1]);
+ else
+ memprintf(&conf->ca_file, "%s", args[cur_arg + 1]);
- conf->ca_file = strdup(args[cur_arg + 1]);
return 0;
}
return ERR_ALERT | ERR_FATAL;
}
- if ((*args[cur_arg + 1] != '/') && global.ca_base) {
- conf->crl_file = malloc(strlen(global.ca_base) + 1 + strlen(args[cur_arg + 1]) + 1);
- if (conf->crl_file)
- sprintf(conf->crl_file, "%s/%s", global.ca_base, args[cur_arg + 1]);
- return 0;
- }
+ if ((*args[cur_arg + 1] != '/') && global.ca_base)
+ memprintf(&conf->crl_file, "%s/%s", global.ca_base, args[cur_arg + 1]);
+ else
+ memprintf(&conf->crl_file, "%s", args[cur_arg + 1]);
- conf->crl_file = strdup(args[cur_arg + 1]);
return 0;
#endif
}
/************** "server" keywords ****************/
+/* parse the "ca-file" server keyword */
+static int srv_parse_ca_file(char **args, int *cur_arg, struct proxy *px, struct server *newsrv, char **err)
+{
+ if (!*args[*cur_arg + 1]) {
+ if (err)
+ memprintf(err, "'%s' : missing CAfile path", args[*cur_arg]);
+ return ERR_ALERT | ERR_FATAL;
+ }
+
+ if ((*args[*cur_arg + 1] != '/') && global.ca_base)
+ memprintf(&newsrv->ssl_ctx.ca_file, "%s/%s", global.ca_base, args[*cur_arg + 1]);
+ else
+ memprintf(&newsrv->ssl_ctx.ca_file, "%s", args[*cur_arg + 1]);
+
+ return 0;
+}
+
/* parse the "check-ssl" server keyword */
static int srv_parse_check_ssl(char **args, int *cur_arg, struct proxy *px, struct server *newsrv, char **err)
{
return 0;
}
+/* parse the "crl-file" server keyword */
+static int srv_parse_crl_file(char **args, int *cur_arg, struct proxy *px, struct server *newsrv, char **err)
+{
+#ifndef X509_V_FLAG_CRL_CHECK
+ if (err)
+ memprintf(err, "'%s' : library does not support CRL verify", args[*cur_arg]);
+ return ERR_ALERT | ERR_FATAL;
+#else
+ if (!*args[*cur_arg + 1]) {
+ if (err)
+ memprintf(err, "'%s' : missing CRLfile path", args[*cur_arg]);
+ return ERR_ALERT | ERR_FATAL;
+ }
+
+ if ((*args[*cur_arg + 1] != '/') && global.ca_base)
+ memprintf(&newsrv->ssl_ctx.crl_file, "%s/%s", global.ca_base, args[*cur_arg + 1]);
+ else
+ memprintf(&newsrv->ssl_ctx.crl_file, "%s", args[*cur_arg + 1]);
+
+ return 0;
+#endif
+}
+
+
/* parse the "force-sslv3" server keyword */
static int srv_parse_force_sslv3(char **args, int *cur_arg, struct proxy *px, struct server *newsrv, char **err)
{
return 0;
}
+/* parse the "verify" server keyword */
+static int srv_parse_verify(char **args, int *cur_arg, struct proxy *px, struct server *newsrv, char **err)
+{
+ if (!*args[*cur_arg + 1]) {
+ if (err)
+ memprintf(err, "'%s' : missing verify method", args[*cur_arg]);
+ return ERR_ALERT | ERR_FATAL;
+ }
+
+ if (strcmp(args[*cur_arg + 1], "none") == 0)
+ newsrv->ssl_ctx.verify = SSL_VERIFY_NONE;
+ else if (strcmp(args[*cur_arg + 1], "required") == 0)
+ newsrv->ssl_ctx.verify = SSL_VERIFY_PEER;
+ else {
+ if (err)
+ memprintf(err, "'%s' : unknown verify method '%s', only 'none' and 'required' are supported\n",
+ args[*cur_arg], args[*cur_arg + 1]);
+ return ERR_ALERT | ERR_FATAL;
+ }
+
+ return 0;
+}
+
/* Note: must not be declared <const> as its list will be overwritten.
* Please take care of keeping this list alphabetically sorted.
*/
* not enabled.
*/
static struct srv_kw_list srv_kws = { "SSL", { }, {
+ { "ca-file", srv_parse_ca_file, 1, 0 }, /* set CAfile to process verify server cert */
{ "check-ssl", srv_parse_check_ssl, 0, 0 }, /* enable SSL for health checks */
{ "ciphers", srv_parse_ciphers, 1, 0 }, /* select the cipher suite */
+ { "crl-file", srv_parse_crl_file, 1, 0 }, /* set certificate revocation list file use on server cert verify */
{ "force-sslv3", srv_parse_force_sslv3, 0, 0 }, /* force SSLv3 */
{ "force-tlsv10", srv_parse_force_tlsv10, 0, 0 }, /* force TLSv10 */
{ "force-tlsv11", srv_parse_force_tlsv11, 0, 0 }, /* force TLSv11 */
{ "no-tlsv12", srv_parse_no_tlsv12, 0, 0 }, /* disable TLSv12 */
{ "no-tls-tickets", srv_parse_no_tls_tickets, 0, 0 }, /* disable session resumption tickets */
{ "ssl", srv_parse_ssl, 0, 0 }, /* enable SSL processing */
+ { "verify", srv_parse_verify, 1, 0 }, /* set SSL verify method */
{ NULL, NULL, 0, 0 },
}};