From: Amaury Denoyelle Date: Fri, 21 May 2021 14:22:11 +0000 (+0200) Subject: MINOR: ssl: render file-access optional on server crt loading X-Git-Tag: v2.5-dev1~74 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=36aa451a4e15c1601b4ef87a45cd0e49bf364beb;p=thirdparty%2Fhaproxy.git MINOR: ssl: render file-access optional on server crt loading The function ssl_sock_load_srv_cert will be used at runtime for dynamic servers. If the cert is not loaded on ckch tree, we try to access it from the file-system. Now this access operation is rendered optional by a new function argument. It is only allowed at parsing time, but will be disabled for dynamic servers at runtime. --- diff --git a/include/haproxy/ssl_sock.h b/include/haproxy/ssl_sock.h index cb9c0b86ca..5593a935e3 100644 --- a/include/haproxy/ssl_sock.h +++ b/include/haproxy/ssl_sock.h @@ -118,7 +118,7 @@ void ssl_async_fd_free(int fd); struct issuer_chain* ssl_get0_issuer_chain(X509 *cert); int ssl_load_global_issuer_from_BIO(BIO *in, char *fp, char **err); int ssl_sock_load_cert(char *path, struct bind_conf *bind_conf, char **err); -int ssl_sock_load_srv_cert(char *path, struct server *server, char **err); +int ssl_sock_load_srv_cert(char *path, struct server *server, int create_if_none, char **err); void ssl_free_global_issuers(void); int ssl_initialize_random(void); int ssl_sock_load_cert_list_file(char *file, int dir, struct bind_conf *bind_conf, struct proxy *curproxy, char **err); diff --git a/src/cfgparse-ssl.c b/src/cfgparse-ssl.c index 11af3aac43..ce84fe3eba 100644 --- a/src/cfgparse-ssl.c +++ b/src/cfgparse-ssl.c @@ -1491,7 +1491,7 @@ static int srv_parse_crt(char **args, int *cur_arg, struct proxy *px, struct ser memprintf(&path, "%s", args[*cur_arg + 1]); if (path) { - retval = ssl_sock_load_srv_cert(path, newsrv, err); + retval = ssl_sock_load_srv_cert(path, newsrv, 1, err); free(path); } diff --git a/src/ssl_sock.c b/src/ssl_sock.c index 4ebf56f2a6..e27611572a 100644 --- a/src/ssl_sock.c +++ b/src/ssl_sock.c @@ -3718,7 +3718,7 @@ int ssl_sock_load_cert(char *path, struct bind_conf *bind_conf, char **err) * backend server (server configuration line). * Returns a set of ERR_* flags possibly with an error in . */ -int ssl_sock_load_srv_cert(char *path, struct server *server, char **err) +int ssl_sock_load_srv_cert(char *path, struct server *server, int create_if_none, char **err) { struct stat buf; int cfgerr = 0; @@ -3729,14 +3729,23 @@ int ssl_sock_load_srv_cert(char *path, struct server *server, char **err) /* we found the ckchs in the tree, we can use it directly */ cfgerr |= ssl_sock_load_srv_ckchs(path, ckchs, server, &server->ssl_ctx.inst, err); found++; - } else if (stat(path, &buf) == 0) { - /* We do not manage directories on backend side. */ - if (S_ISDIR(buf.st_mode) == 0) { - ++found; - ckchs = ckchs_load_cert_file(path, err); - if (!ckchs) - cfgerr |= ERR_ALERT | ERR_FATAL; - cfgerr |= ssl_sock_load_srv_ckchs(path, ckchs, server, &server->ssl_ctx.inst, err); + } else { + if (!create_if_none) { + memprintf(err, "%sunable to stat SSL certificate '%s'.\n", + err && *err ? *err : "", path); + cfgerr |= ERR_ALERT | ERR_FATAL; + goto out; + } + + if (stat(path, &buf) == 0) { + /* We do not manage directories on backend side. */ + if (S_ISDIR(buf.st_mode) == 0) { + ++found; + ckchs = ckchs_load_cert_file(path, err); + if (!ckchs) + cfgerr |= ERR_ALERT | ERR_FATAL; + cfgerr |= ssl_sock_load_srv_ckchs(path, ckchs, server, &server->ssl_ctx.inst, err); + } } } if (!found) { @@ -3745,6 +3754,7 @@ int ssl_sock_load_srv_cert(char *path, struct server *server, char **err) cfgerr |= ERR_ALERT | ERR_FATAL; } +out: return cfgerr; }