haproxy: Update all patches for HAProxy v1.8.14

- Add new patches (see https://www.haproxy.org/bugs/bugs-1.8.14.html)
- Raise PKG_RELEASE to 2

Signed-off-by: Christian Lachner <gladiac@gmail.com>
This commit is contained in:
Christian Lachner 2018-10-17 09:18:37 +02:00
parent bcd482a194
commit 6e309cd99e
29 changed files with 1818 additions and 1 deletions

View File

@ -11,7 +11,7 @@ include $(TOPDIR)/rules.mk
PKG_NAME:=haproxy
PKG_VERSION:=1.8.14
PKG_RELEASE:=1
PKG_RELEASE:=2
PKG_SOURCE:=haproxy-$(PKG_VERSION).tar.gz
PKG_SOURCE_URL:=https://www.haproxy.org/download/1.8/src/

View File

@ -0,0 +1,38 @@
commit 14844e448b637fea2770bcb03a43a010c4c8176d
Author: Olivier Houchard <ohouchard@haproxy.com>
Date: Thu Sep 27 14:55:34 2018 +0200
MINOR: threads: Make sure threads_sync_pipe is initialized before using it.
thread_want_sync() might be called before thread_sync_init() was called,
at least when reading the server state file, as apply_server_state() is called
before thread_sync_init(). So make sure the threads_sync_pipe was initialized
before writing to it, if it was not, there's no thread, so no need to sync
anything anyway, and if we don't check it we'll end up writing a 'S' on
stdin.
this only applies to 1.8.
diff --git a/src/hathreads.c b/src/hathreads.c
index 97ed31c5..9dba4356 100644
--- a/src/hathreads.c
+++ b/src/hathreads.c
@@ -28,7 +28,7 @@ void thread_sync_io_handler(int fd)
#ifdef USE_THREAD
static HA_SPINLOCK_T sync_lock;
-static int threads_sync_pipe[2];
+static int threads_sync_pipe[2] = {-1, -1};
static unsigned long threads_want_sync = 0;
volatile unsigned long threads_want_rdv_mask = 0;
volatile unsigned long threads_harmless_mask = 0;
@@ -76,7 +76,8 @@ void thread_want_sync()
if (all_threads_mask & (all_threads_mask - 1)) {
if (threads_want_sync & tid_bit)
return;
- if (HA_ATOMIC_OR(&threads_want_sync, tid_bit) == tid_bit)
+ if (HA_ATOMIC_OR(&threads_want_sync, tid_bit) == tid_bit &&
+ threads_sync_pipe[1] != -1)
shut_your_big_mouth_gcc(write(threads_sync_pipe[1], "S", 1));
}
else {

View File

@ -0,0 +1,39 @@
commit 18aff2297ce844362f28ea5317c289ba154bd33d
Author: Lukas Tribus <lukas@ltri.eu>
Date: Mon Oct 1 02:00:16 2018 +0200
DOC: clarify force-private-cache is an option
"boolean" may confuse users into thinking they need to provide
additional arguments, like false or true. This is a simple option
like many others, so lets not confuse the users with internals.
Also fixes an additional typo.
Should be backported to 1.8 and 1.7.
(cherry picked from commit 2793578eaf934bbf28f742a35f3a1ae656280324)
Signed-off-by: Christopher Faulet <cfaulet@haproxy.com>
diff --git a/doc/configuration.txt b/doc/configuration.txt
index c69033b1..580194ec 100644
--- a/doc/configuration.txt
+++ b/doc/configuration.txt
@@ -1651,7 +1651,7 @@ tune.ssl.cachesize <number>
this value to 0 disables the SSL session cache.
tune.ssl.force-private-cache
- This boolean disables SSL session cache sharing between all processes. It
+ This option disables SSL session cache sharing between all processes. It
should normally not be used since it will force many renegotiations due to
clients hitting a random process. But it may be required on some operating
systems where none of the SSL cache synchronization method may be used. In
@@ -6535,7 +6535,7 @@ option smtpchk <hello> <domain>
yes | no | yes | yes
Arguments :
<hello> is an optional argument. It is the "hello" command to use. It can
- be either "HELO" (for SMTP) or "EHLO" (for ESTMP). All other
+ be either "HELO" (for SMTP) or "EHLO" (for ESMTP). All other
values will be turned into the default command ("HELO").
<domain> is the domain name to present to the server. It may only be

View File

@ -0,0 +1,47 @@
commit f6d20e718131aa2b468ff0a6c42e20c0b900e58b
Author: Ilya Shipitsin <chipitsine@gmail.com>
Date: Sat Sep 15 00:50:05 2018 +0500
BUG/MINOR: connection: avoid null pointer dereference in send-proxy-v2
found by coverity.
[wt: this bug was introduced by commit 404d978 ("MINOR: add ALPN
information to send-proxy-v2"). It might be triggered by a health
check on a server using ppv2 or by an applet making use of such a
server, if at all configurable].
This needs to be backported to 1.8.
(cherry picked from commit ca56fce8bd271928b18d38b439bd35bd273fe8d4)
Signed-off-by: Christopher Faulet <cfaulet@haproxy.com>
diff --git a/src/connection.c b/src/connection.c
index 8c5af156..7403e8ae 100644
--- a/src/connection.c
+++ b/src/connection.c
@@ -874,6 +874,7 @@ int conn_recv_netscaler_cip(struct connection *conn, int flag)
return 0;
}
+/* Note: <remote> is explicitly allowed to be NULL */
int make_proxy_line(char *buf, int buf_len, struct server *srv, struct connection *remote)
{
int ret = 0;
@@ -985,6 +986,7 @@ static int make_tlv(char *dest, int dest_len, char type, uint16_t length, const
return length + sizeof(*tlv);
}
+/* Note: <remote> is explicitly allowed to be NULL */
int make_proxy_line_v2(char *buf, int buf_len, struct server *srv, struct connection *remote)
{
const char pp2_signature[] = PP2_SIGNATURE;
@@ -1060,7 +1062,7 @@ int make_proxy_line_v2(char *buf, int buf_len, struct server *srv, struct connec
}
}
- if (conn_get_alpn(remote, &value, &value_len)) {
+ if (remote && conn_get_alpn(remote, &value, &value_len)) {
if ((buf_len - ret) < sizeof(struct tlv))
return 0;
ret += make_tlv(&buf[ret], (buf_len - ret), PP2_TYPE_ALPN, value_len, value);

View File

@ -0,0 +1,43 @@
commit e725a7f9bfd8b7fe2e74c62c7c6bf2b9ebf83772
Author: Willy Tarreau <w@1wt.eu>
Date: Wed Oct 3 10:20:19 2018 +0200
BUG/MINOR: backend: check that the mux installed properly
The return value from conn_install_mux() was not checked, so if an
inconsistency happens in the code, or a memory allocation fails while
initializing the mux, we can crash while using an uninitialized mux.
In practice the code inconsistency does not really happen since we
cannot configure such a situation, except during development, but
the out of memory condition could definitely happen.
This should be backported to 1.8 (the code is a bit different there,
there are two calls to conn_install_mux()).
(cherry picked from commit 33dd4ef81245bb868b22f99b9be45d0791131eec)
Signed-off-by: Christopher Faulet <cfaulet@haproxy.com>
diff --git a/src/backend.c b/src/backend.c
index 2b6167dc..fc1eac0d 100644
--- a/src/backend.c
+++ b/src/backend.c
@@ -1163,7 +1163,8 @@ int connect_server(struct stream *s)
if (srv) {
conn_prepare(srv_conn, protocol_by_family(srv_conn->addr.to.ss_family), srv->xprt);
/* XXX: Pick the right mux, when we finally have one */
- conn_install_mux(srv_conn, &mux_pt_ops, srv_cs);
+ if (conn_install_mux(srv_conn, &mux_pt_ops, srv_cs) < 0)
+ return SF_ERR_INTERNAL;
}
else if (obj_type(s->target) == OBJ_TYPE_PROXY) {
/* proxies exclusively run on raw_sock right now */
@@ -1171,7 +1172,8 @@ int connect_server(struct stream *s)
if (!objt_cs(s->si[1].end) || !objt_cs(s->si[1].end)->conn->ctrl)
return SF_ERR_INTERNAL;
/* XXX: Pick the right mux, when we finally have one */
- conn_install_mux(srv_conn, &mux_pt_ops, srv_cs);
+ if (conn_install_mux(srv_conn, &mux_pt_ops, srv_cs) < 0)
+ return SF_ERR_INTERNAL;
}
else
return SF_ERR_INTERNAL; /* how did we get there ? */

View File

@ -0,0 +1,40 @@
commit 45e9f3c660c872e93588cf1c0b74c192f2c8c3d5
Author: Olivier Houchard <ohouchard@haproxy.com>
Date: Wed Sep 26 15:09:58 2018 +0200
BUG/MEDIUM: buffers: Make sure we don't wrap in buffer_insert_line2/replace2.
In buffer_insert_line2() and buffer_replace2(), we can't afford to wrap,
so don't use b_tail to check if we do, directly use b->p + b->i instead.
This should be backported to previous versions.
(cherry picked from commit 363c745569b6ffd8f095d2b7758131d08aa27219)
Signed-off-by: Christopher Faulet <cfaulet@haproxy.com>
[cf: This patch was adapted and its commit message too. Because of the
refactoring of the buffer's API in 1.9, the original patch fixes same bug in
ci_insert_line2/b_rep_blk.]
diff --git a/src/buffer.c b/src/buffer.c
index 167b75ae..6ad38a02 100644
--- a/src/buffer.c
+++ b/src/buffer.c
@@ -107,7 +107,7 @@ int buffer_replace2(struct buffer *b, char *pos, char *end, const char *str, int
delta = len - (end - pos);
- if (bi_end(b) + delta > b->data + b->size)
+ if (b->p + b->i + delta > b->data + b->size)
return 0; /* no space left */
if (buffer_not_empty(b) &&
@@ -146,7 +146,7 @@ int buffer_insert_line2(struct buffer *b, char *pos, const char *str, int len)
delta = len + 2;
- if (bi_end(b) + delta >= b->data + b->size)
+ if (b->p + b->i + delta >= b->data + b->size)
return 0; /* no space left */
if (buffer_not_empty(b) &&

View File

@ -0,0 +1,473 @@
commit 4be76416751aa22992a44f2f5cfdba506809fd89
Author: Dirkjan Bussink <d.bussink@gmail.com>
Date: Fri Sep 14 11:14:21 2018 +0200
MEDIUM: ssl: add support for ciphersuites option for TLSv1.3
OpenSSL released support for TLSv1.3. It also added a separate function
SSL_CTX_set_ciphersuites that is used to set the ciphers used in the
TLS 1.3 handshake. This change adds support for that new configuration
option by adding a ciphersuites configuration variable that works
essentially the same as the existing ciphers setting.
Note that it should likely be backported to 1.8 in order to ease usage
of the now released openssl-1.1.1.
(cherry picked from commit 415150f7640b06740fa832363d186c5c6565338e)
Signed-off-by: Willy Tarreau <w@1wt.eu>
diff --git a/doc/configuration.txt b/doc/configuration.txt
index 580194ec..7a268386 100644
--- a/doc/configuration.txt
+++ b/doc/configuration.txt
@@ -580,8 +580,10 @@ The following keywords are supported in the "global" section :
- setenv
- stats
- ssl-default-bind-ciphers
+ - ssl-default-bind-ciphersuites
- ssl-default-bind-options
- ssl-default-server-ciphers
+ - ssl-default-server-ciphersuites
- ssl-default-server-options
- ssl-dh-param-file
- ssl-server-verify
@@ -984,11 +986,25 @@ setenv <name> <value>
ssl-default-bind-ciphers <ciphers>
This setting is only available when support for OpenSSL was built in. It sets
the default string describing the list of cipher algorithms ("cipher suite")
- that are negotiated during the SSL/TLS handshake for all "bind" lines which
- do not explicitly define theirs. The format of the string is defined in
- "man 1 ciphers" from OpenSSL man pages, and can be for instance a string such
- as "AES:ALL:!aNULL:!eNULL:+RC4:@STRENGTH" (without quotes). Please check the
- "bind" keyword for more information.
+ that are negotiated during the SSL/TLS handshake except for TLSv1.3 for all
+ "bind" lines which do not explicitly define theirs. The format of the string
+ is defined in "man 1 ciphers" from OpenSSL man pages, and can be for instance
+ a string such as "AES:ALL:!aNULL:!eNULL:+RC4:@STRENGTH" (without quotes). For
+ TLSv1.3 cipher configuration, please check the "ssl-default-bind-ciphersuites"
+ keyword. Please check the "bind" keyword for more information.
+
+ssl-default-bind-ciphersuites <ciphersuites>
+ This setting is only available when support for OpenSSL was built in and
+ OpenSSL 1.1.1 or later was used to build HAProxy. It sets the default string
+ describing the list of cipher algorithms ("cipher suite") that are negotiated
+ during the TLSv1.3 handshake for all "bind" lines which do not explicitly define
+ theirs. The format of the string is defined in
+ "man 1 ciphers" from OpenSSL man pages under the section "ciphersuites", and can
+ be for instance a string such as
+ "TLS_AES_256_GCM_SHA384:TLS_CHACHA20_POLY1305_SHA256:TLS_AES_128_GCM_SHA256"
+ (without quotes). For cipher configuration for TLSv1.2 and earlier, please check
+ the "ssl-default-bind-ciphers" keyword. Please check the "bind" keyword for more
+ information.
ssl-default-bind-options [<option>]...
This setting is only available when support for OpenSSL was built in. It sets
@@ -1002,10 +1018,21 @@ ssl-default-bind-options [<option>]...
ssl-default-server-ciphers <ciphers>
This setting is only available when support for OpenSSL was built in. It
sets the default string describing the list of cipher algorithms that are
- negotiated during the SSL/TLS handshake with the server, for all "server"
- lines which do not explicitly define theirs. The format of the string is
- defined in "man 1 ciphers". Please check the "server" keyword for more
- information.
+ negotiated during the SSL/TLS handshake except for TLSv1.3 with the server,
+ for all "server" lines which do not explicitly define theirs. The format of
+ the string is defined in "man 1 ciphers". For TLSv1.3 cipher configuration,
+ please check the "ssl-default-server-ciphersuites" keyword. Please check the
+ "server" keyword for more information.
+
+ssl-default-server-ciphersuites <ciphersuites>
+ This setting is only available when support for OpenSSL was built in and
+ OpenSSL 1.1.1 or later was used to build HAProxy. It sets the default
+ string describing the list of cipher algorithms that are negotiated during
+ the TLSv1.3 handshake with the server, for all "server" lines which do not
+ explicitly define theirs. The format of the string is defined in
+ "man 1 ciphers" under the "ciphersuites" section. For cipher configuration for
+ TLSv1.2 and earlier, please check the "ssl-default-server-ciphers" keyword.
+ Please check the "server" keyword for more information.
ssl-default-server-options [<option>]...
This setting is only available when support for OpenSSL was built in. It sets
@@ -10510,13 +10537,26 @@ ca-sign-pass <passphrase>
ciphers <ciphers>
This setting is only available when support for OpenSSL was built in. It sets
the string describing the list of cipher algorithms ("cipher suite") that are
- negotiated during the SSL/TLS handshake. The format of the string is defined
- in "man 1 ciphers" from OpenSSL man pages, and can be for instance a string
- such as "AES:ALL:!aNULL:!eNULL:+RC4:@STRENGTH" (without quotes).
- Depending on the compatibility and security requirements, the list of suitable
- ciphers depends on a variety of variables. For background information and
- recommendations see e. g. (https://wiki.mozilla.org/Security/Server_Side_TLS)
- and (https://mozilla.github.io/server-side-tls/ssl-config-generator/).
+ negotiated during the SSL/TLS handshake except for TLSv1.3. The format of the
+ string is defined in "man 1 ciphers" from OpenSSL man pages, and can be for
+ instance a string such as "AES:ALL:!aNULL:!eNULL:+RC4:@STRENGTH" (without
+ quotes). Depending on the compatibility and security requirements, the list
+ of suitable ciphers depends on a variety of variables. For background
+ information and recommendations see e.g.
+ (https://wiki.mozilla.org/Security/Server_Side_TLS) and
+ (https://mozilla.github.io/server-side-tls/ssl-config-generator/). For TLSv1.3
+ cipher configuration, please check the "ciphersuites" keyword.
+
+ciphersuites <ciphersuites>
+ This setting is only available when support for OpenSSL was built in and
+ OpenSSL 1.1.1 or later was used to build HAProxy. It sets the string describing
+ the list of cipher algorithms ("cipher suite") that are negotiated during the
+ TLSv1.3 handshake. The format of the string is defined in "man 1 ciphers" from
+ OpenSSL man pages under the "ciphersuites" section, and can be for instance a
+ string such as
+ "TLS_AES_256_GCM_SHA384:TLS_CHACHA20_POLY1305_SHA256:TLS_AES_128_GCM_SHA256"
+ (without quotes). For cipher configuration for TLSv1.2 and earlier, please check
+ the "ciphers" keyword.
crl-file <crlfile>
This setting is only available when support for OpenSSL was built in. It
@@ -11226,8 +11266,9 @@ check-ssl
this option.
ciphers <ciphers>
- This option sets the string describing the list of cipher algorithms that is
- is negotiated during the SSL/TLS handshake with the server. The format of the
+ This setting is only available when support for OpenSSL was built in. This
+ option sets the string describing the list of cipher algorithms that is
+ negotiated during the SSL/TLS handshake with the server. The format of the
string is defined in "man 1 ciphers". When SSL is used to communicate with
servers on the local network, it is common to see a weaker set of algorithms
than what is used over the internet. Doing so reduces CPU usage on both the
@@ -11235,6 +11276,13 @@ ciphers <ciphers>
Some algorithms such as RC4-SHA1 are reasonably cheap. If no security at all
is needed and just connectivity, using DES can be appropriate.
+ciphersuites <ciphersuites>
+ This setting is only available when support for OpenSSL was built in and
+ OpenSSL 1.1.1 or later was used to build HAProxy. This option sets the string
+ describing the list of cipher algorithms that is negotiated during the TLS
+ 1.3 handshake with the server. The format of the string is defined in
+ "man 1 ciphers" under the "ciphersuites" section.
+
cookie <value>
The "cookie" parameter sets the cookie value assigned to the server to
<value>. This value will be checked in incoming requests, and the first
diff --git a/include/common/defaults.h b/include/common/defaults.h
index f53c611e..a45ab0da 100644
--- a/include/common/defaults.h
+++ b/include/common/defaults.h
@@ -234,11 +234,21 @@
#define CONNECT_DEFAULT_CIPHERS NULL
#endif
+/* ciphers used as defaults on TLS 1.3 connect */
+#ifndef CONNECT_DEFAULT_CIPHERSUITES
+#define CONNECT_DEFAULT_CIPHERSUITES NULL
+#endif
+
/* ciphers used as defaults on listeners */
#ifndef LISTEN_DEFAULT_CIPHERS
#define LISTEN_DEFAULT_CIPHERS NULL
#endif
+/* cipher suites used as defaults on TLS 1.3 listeners */
+#ifndef LISTEN_DEFAULT_CIPHERSUITES
+#define LISTEN_DEFAULT_CIPHERSUITES NULL
+#endif
+
/* named curve used as defaults for ECDHE ciphers */
#ifndef ECDHE_DEFAULT_CURVE
#define ECDHE_DEFAULT_CURVE "prime256v1"
diff --git a/include/types/listener.h b/include/types/listener.h
index c55569cd..ea2eadb5 100644
--- a/include/types/listener.h
+++ b/include/types/listener.h
@@ -128,6 +128,9 @@ struct ssl_bind_conf {
char *ca_file; /* CAfile to use on verify */
char *crl_file; /* CRLfile to use on verify */
char *ciphers; /* cipher suite to use if non-null */
+#if (OPENSSL_VERSION_NUMBER >= 0x10101000L && !defined OPENSSL_IS_BORINGSSL && !defined LIBRESSL_VERSION_NUMBER)
+ char *ciphersuites; /* TLS 1.3 cipher suite to use if non-null */
+#endif
char *curves; /* curves suite to use for ECDHE */
char *ecdhe; /* named curve to use for ECDHE */
struct tls_version_filter ssl_methods; /* ssl methods */
diff --git a/include/types/server.h b/include/types/server.h
index fd3c8bad..79ae7b72 100644
--- a/include/types/server.h
+++ b/include/types/server.h
@@ -281,6 +281,9 @@ struct server {
int allocated_size;
} * reused_sess;
char *ciphers; /* cipher suite to use if non-null */
+#if (OPENSSL_VERSION_NUMBER >= 0x10101000L && !defined OPENSSL_IS_BORINGSSL && !defined LIBRESSL_VERSION_NUMBER)
+ char *ciphersuites; /* TLS 1.3 cipher suite to use if non-null */
+#endif
int options; /* ssl options */
int verify; /* verify method (set of SSL_VERIFY_* flags) */
struct tls_version_filter methods; /* ssl methods */
diff --git a/src/server.c b/src/server.c
index 842e4149..4941bd03 100644
--- a/src/server.c
+++ b/src/server.c
@@ -1380,6 +1380,10 @@ static void srv_ssl_settings_cpy(struct server *srv, struct server *src)
srv->ssl_ctx.verify_host = strdup(src->ssl_ctx.verify_host);
if (src->ssl_ctx.ciphers != NULL)
srv->ssl_ctx.ciphers = strdup(src->ssl_ctx.ciphers);
+#if (OPENSSL_VERSION_NUMBER >= 0x10101000L && !defined OPENSSL_IS_BORINGSSL && !defined LIBRESSL_VERSION_NUMBER)
+ if (src->ssl_ctx.ciphersuites != NULL)
+ srv->ssl_ctx.ciphersuites = strdup(src->ssl_ctx.ciphersuites);
+#endif
if (src->sni_expr != NULL)
srv->sni_expr = strdup(src->sni_expr);
}
diff --git a/src/ssl_sock.c b/src/ssl_sock.c
index 08fdffab..2da0df68 100644
--- a/src/ssl_sock.c
+++ b/src/ssl_sock.c
@@ -169,6 +169,10 @@ static struct {
char *listen_default_ciphers;
char *connect_default_ciphers;
+#if (OPENSSL_VERSION_NUMBER >= 0x10101000L && !defined OPENSSL_IS_BORINGSSL && !defined LIBRESSL_VERSION_NUMBER)
+ char *listen_default_ciphersuites;
+ char *connect_default_ciphersuites;
+#endif
int listen_default_ssloptions;
int connect_default_ssloptions;
struct tls_version_filter listen_default_sslmethods;
@@ -186,6 +190,14 @@ static struct {
#endif
#ifdef CONNECT_DEFAULT_CIPHERS
.connect_default_ciphers = CONNECT_DEFAULT_CIPHERS,
+#endif
+#if (OPENSSL_VERSION_NUMBER >= 0x10101000L && !defined OPENSSL_IS_BORINGSSL && !defined LIBRESSL_VERSION_NUMBER)
+#ifdef LISTEN_DEFAULT_CIPHERSUITES
+ .listen_default_ciphersuites = LISTEN_DEFAULT_CIPHERSUITES,
+#endif
+#ifdef CONNECT_DEFAULT_CIPHERSUITES
+ .connect_default_ciphersuites = CONNECT_DEFAULT_CIPHERSUITES,
+#endif
#endif
.listen_default_ssloptions = BC_SSL_O_NONE,
.connect_default_ssloptions = SRV_SSL_O_NONE,
@@ -3528,6 +3540,10 @@ void ssl_sock_free_ssl_conf(struct ssl_bind_conf *conf)
conf->crl_file = NULL;
free(conf->ciphers);
conf->ciphers = NULL;
+#if (OPENSSL_VERSION_NUMBER >= 0x10101000L && !defined OPENSSL_IS_BORINGSSL && !defined LIBRESSL_VERSION_NUMBER)
+ free(conf->ciphersuites);
+ conf->ciphersuites = NULL;
+#endif
free(conf->curves);
conf->curves = NULL;
free(conf->ecdhe);
@@ -4061,6 +4077,9 @@ int ssl_sock_prepare_ctx(struct bind_conf *bind_conf, struct ssl_bind_conf *ssl_
int verify = SSL_VERIFY_NONE;
struct ssl_bind_conf __maybe_unused *ssl_conf_cur;
const char *conf_ciphers;
+#if (OPENSSL_VERSION_NUMBER >= 0x10101000L && !defined OPENSSL_IS_BORINGSSL && !defined LIBRESSL_VERSION_NUMBER)
+ const char *conf_ciphersuites;
+#endif
const char *conf_curves = NULL;
if (ssl_conf) {
@@ -4160,6 +4179,16 @@ int ssl_sock_prepare_ctx(struct bind_conf *bind_conf, struct ssl_bind_conf *ssl_
cfgerr++;
}
+#if (OPENSSL_VERSION_NUMBER >= 0x10101000L && !defined OPENSSL_IS_BORINGSSL && !defined LIBRESSL_VERSION_NUMBER)
+ conf_ciphersuites = (ssl_conf && ssl_conf->ciphersuites) ? ssl_conf->ciphersuites : bind_conf->ssl_conf.ciphersuites;
+ if (conf_ciphersuites &&
+ !SSL_CTX_set_ciphersuites(ctx, conf_ciphersuites)) {
+ ha_alert("Proxy '%s': unable to set TLS 1.3 cipher suites to '%s' for bind '%s' at [%s:%d].\n",
+ curproxy->id, conf_ciphersuites, bind_conf->arg, bind_conf->file, bind_conf->line);
+ cfgerr++;
+ }
+#endif
+
#ifndef OPENSSL_NO_DH
/* If tune.ssl.default-dh-param has not been set,
neither has ssl-default-dh-file and no static DH
@@ -4642,6 +4671,16 @@ int ssl_sock_prepare_srv_ctx(struct server *srv)
cfgerr++;
}
+#if (OPENSSL_VERSION_NUMBER >= 0x10101000L && !defined OPENSSL_IS_BORINGSSL && !defined LIBRESSL_VERSION_NUMBER)
+ if (srv->ssl_ctx.ciphersuites &&
+ !SSL_CTX_set_cipher_list(srv->ssl_ctx.ctx, srv->ssl_ctx.ciphersuites)) {
+ ha_alert("Proxy '%s', server '%s' [%s:%d] : unable to set TLS 1.3 cipher suites to '%s'.\n",
+ curproxy->id, srv->id,
+ srv->conf.file, srv->conf.line, srv->ssl_ctx.ciphersuites);
+ cfgerr++;
+ }
+#endif
+
return cfgerr;
}
@@ -7101,6 +7140,26 @@ static int bind_parse_ciphers(char **args, int cur_arg, struct proxy *px, struct
{
return ssl_bind_parse_ciphers(args, cur_arg, px, &conf->ssl_conf, err);
}
+
+#if (OPENSSL_VERSION_NUMBER >= 0x10101000L && !defined OPENSSL_IS_BORINGSSL && !defined LIBRESSL_VERSION_NUMBER)
+/* parse the "ciphersuites" bind keyword */
+static int ssl_bind_parse_ciphersuites(char **args, int cur_arg, struct proxy *px, struct ssl_bind_conf *conf, char **err)
+{
+ if (!*args[cur_arg + 1]) {
+ memprintf(err, "'%s' : missing cipher suite", args[cur_arg]);
+ return ERR_ALERT | ERR_FATAL;
+ }
+
+ free(conf->ciphersuites);
+ conf->ciphersuites = strdup(args[cur_arg + 1]);
+ return 0;
+}
+static int bind_parse_ciphersuites(char **args, int cur_arg, struct proxy *px, struct bind_conf *conf, char **err)
+{
+ return ssl_bind_parse_ciphersuites(args, cur_arg, px, &conf->ssl_conf, err);
+}
+#endif
+
/* parse the "crt" bind keyword */
static int bind_parse_crt(char **args, int cur_arg, struct proxy *px, struct bind_conf *conf, char **err)
{
@@ -7492,6 +7551,10 @@ static int bind_parse_ssl(char **args, int cur_arg, struct proxy *px, struct bin
if (global_ssl.listen_default_ciphers && !conf->ssl_conf.ciphers)
conf->ssl_conf.ciphers = strdup(global_ssl.listen_default_ciphers);
+#if (OPENSSL_VERSION_NUMBER >= 0x10101000L && !defined OPENSSL_IS_BORINGSSL && !defined LIBRESSL_VERSION_NUMBER)
+ if (global_ssl.listen_default_ciphersuites && !conf->ssl_conf.ciphersuites)
+ conf->ssl_conf.ciphersuites = strdup(global_ssl.listen_default_ciphersuites);
+#endif
conf->ssl_options |= global_ssl.listen_default_ssloptions;
conf->ssl_conf.ssl_methods.flags |= global_ssl.listen_default_sslmethods.flags;
if (!conf->ssl_conf.ssl_methods.min)
@@ -7689,6 +7752,10 @@ static int srv_parse_check_ssl(char **args, int *cur_arg, struct proxy *px, stru
newsrv->check.use_ssl = 1;
if (global_ssl.connect_default_ciphers && !newsrv->ssl_ctx.ciphers)
newsrv->ssl_ctx.ciphers = strdup(global_ssl.connect_default_ciphers);
+#if (OPENSSL_VERSION_NUMBER >= 0x10101000L && !defined OPENSSL_IS_BORINGSSL && !defined LIBRESSL_VERSION_NUMBER)
+ if (global_ssl.connect_default_ciphersuites && !newsrv->ssl_ctx.ciphersuites)
+ newsrv->ssl_ctx.ciphersuites = strdup(global_ssl.connect_default_ciphersuites);
+#endif
newsrv->ssl_ctx.options |= global_ssl.connect_default_ssloptions;
newsrv->ssl_ctx.methods.flags |= global_ssl.connect_default_sslmethods.flags;
if (!newsrv->ssl_ctx.methods.min)
@@ -7712,6 +7779,21 @@ static int srv_parse_ciphers(char **args, int *cur_arg, struct proxy *px, struct
return 0;
}
+#if (OPENSSL_VERSION_NUMBER >= 0x10101000L && !defined OPENSSL_IS_BORINGSSL && !defined LIBRESSL_VERSION_NUMBER)
+/* parse the "ciphersuites" server keyword */
+static int srv_parse_ciphersuites(char **args, int *cur_arg, struct proxy *px, struct server *newsrv, char **err)
+{
+ if (!*args[*cur_arg + 1]) {
+ memprintf(err, "'%s' : missing cipher suite", args[*cur_arg]);
+ return ERR_ALERT | ERR_FATAL;
+ }
+
+ free(newsrv->ssl_ctx.ciphersuites);
+ newsrv->ssl_ctx.ciphersuites = strdup(args[*cur_arg + 1]);
+ return 0;
+}
+#endif
+
/* 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)
{
@@ -7853,6 +7935,10 @@ static int srv_parse_ssl(char **args, int *cur_arg, struct proxy *px, struct ser
newsrv->use_ssl = 1;
if (global_ssl.connect_default_ciphers && !newsrv->ssl_ctx.ciphers)
newsrv->ssl_ctx.ciphers = strdup(global_ssl.connect_default_ciphers);
+#if (OPENSSL_VERSION_NUMBER >= 0x10101000L && !defined OPENSSL_IS_BORINGSSL && !defined LIBRESSL_VERSION_NUMBER)
+ if (global_ssl.connect_default_ciphersuites && !newsrv->ssl_ctx.ciphersuites)
+ newsrv->ssl_ctx.ciphersuites = strdup(global_ssl.connect_default_ciphersuites);
+#endif
return 0;
}
@@ -8092,6 +8178,32 @@ static int ssl_parse_global_ciphers(char **args, int section_type, struct proxy
return 0;
}
+#if (OPENSSL_VERSION_NUMBER >= 0x10101000L && !defined OPENSSL_IS_BORINGSSL && !defined LIBRESSL_VERSION_NUMBER)
+/* parse the "ssl-default-bind-ciphersuites" / "ssl-default-server-ciphersuites" keywords
+ * in global section. Returns <0 on alert, >0 on warning, 0 on success.
+ */
+static int ssl_parse_global_ciphersuites(char **args, int section_type, struct proxy *curpx,
+ struct proxy *defpx, const char *file, int line,
+ char **err)
+{
+ char **target;
+
+ target = (args[0][12] == 'b') ? &global_ssl.listen_default_ciphersuites : &global_ssl.connect_default_ciphersuites;
+
+ if (too_many_args(1, args, err, NULL))
+ return -1;
+
+ if (*(args[1]) == 0) {
+ memprintf(err, "global statement '%s' expects a cipher suite as an argument.", args[0]);
+ return -1;
+ }
+
+ free(*target);
+ *target = strdup(args[1]);
+ return 0;
+}
+#endif
+
/* parse various global tune.ssl settings consisting in positive integers.
* Returns <0 on alert, >0 on warning, 0 on success.
*/
@@ -8599,6 +8711,9 @@ static struct ssl_bind_kw ssl_bind_kws[] = {
{ "alpn", ssl_bind_parse_alpn, 1 }, /* set ALPN supported protocols */
{ "ca-file", ssl_bind_parse_ca_file, 1 }, /* set CAfile to process verify on client cert */
{ "ciphers", ssl_bind_parse_ciphers, 1 }, /* set SSL cipher suite */
+#if (OPENSSL_VERSION_NUMBER >= 0x10101000L && !defined OPENSSL_IS_BORINGSSL && !defined LIBRESSL_VERSION_NUMBER)
+ { "ciphersuites", ssl_bind_parse_ciphersuites, 1 }, /* set TLS 1.3 cipher suite */
+#endif
{ "crl-file", ssl_bind_parse_crl_file, 1 }, /* set certificat revocation list file use on client cert verify */
{ "curves", ssl_bind_parse_curves, 1 }, /* set SSL curve suite */
{ "ecdhe", ssl_bind_parse_ecdhe, 1 }, /* defines named curve for elliptic curve Diffie-Hellman */
@@ -8618,6 +8733,9 @@ static struct bind_kw_list bind_kws = { "SSL", { }, {
{ "ca-sign-file", bind_parse_ca_sign_file, 1 }, /* set CAFile used to generate and sign server certs */
{ "ca-sign-pass", bind_parse_ca_sign_pass, 1 }, /* set CAKey passphrase */
{ "ciphers", bind_parse_ciphers, 1 }, /* set SSL cipher suite */
+#if (OPENSSL_VERSION_NUMBER >= 0x10101000L && !defined OPENSSL_IS_BORINGSSL && !defined LIBRESSL_VERSION_NUMBER)
+ { "ciphersuites", bind_parse_ciphersuites, 1 }, /* set TLS 1.3 cipher suite */
+#endif
{ "crl-file", bind_parse_crl_file, 1 }, /* set certificat revocation list file use on client cert verify */
{ "crt", bind_parse_crt, 1 }, /* load SSL certificates from this location */
{ "crt-ignore-err", bind_parse_ignore_err, 1 }, /* set error IDs to ingore on verify depth == 0 */
@@ -8661,6 +8779,9 @@ static struct srv_kw_list srv_kws = { "SSL", { }, {
{ "check-sni", srv_parse_check_sni, 1, 1 }, /* set SNI */
{ "check-ssl", srv_parse_check_ssl, 0, 1 }, /* enable SSL for health checks */
{ "ciphers", srv_parse_ciphers, 1, 1 }, /* select the cipher suite */
+#if (OPENSSL_VERSION_NUMBER >= 0x10101000L && !defined OPENSSL_IS_BORINGSSL && !defined LIBRESSL_VERSION_NUMBER)
+ { "ciphersuites", srv_parse_ciphersuites, 1, 1 }, /* select the cipher suite */
+#endif
{ "crl-file", srv_parse_crl_file, 1, 1 }, /* set certificate revocation list file use on server cert verify */
{ "crt", srv_parse_crt, 1, 1 }, /* set client certificate */
{ "force-sslv3", srv_parse_tls_method_options, 0, 1 }, /* force SSLv3 */
@@ -8716,6 +8837,10 @@ static struct cfg_kw_list cfg_kws = {ILH, {
{ CFG_GLOBAL, "tune.ssl.capture-cipherlist-size", ssl_parse_global_capture_cipherlist },
{ CFG_GLOBAL, "ssl-default-bind-ciphers", ssl_parse_global_ciphers },
{ CFG_GLOBAL, "ssl-default-server-ciphers", ssl_parse_global_ciphers },
+#if (OPENSSL_VERSION_NUMBER >= 0x10101000L && !defined OPENSSL_IS_BORINGSSL && !defined LIBRESSL_VERSION_NUMBER)
+ { CFG_GLOBAL, "ssl-default-bind-ciphersuites", ssl_parse_global_ciphersuites },
+ { CFG_GLOBAL, "ssl-default-server-ciphersuites", ssl_parse_global_ciphersuites },
+#endif
{ 0, NULL, NULL },
}};
@@ -8793,6 +8918,12 @@ static void __ssl_sock_init(void)
global_ssl.listen_default_ciphers = strdup(global_ssl.listen_default_ciphers);
if (global_ssl.connect_default_ciphers)
global_ssl.connect_default_ciphers = strdup(global_ssl.connect_default_ciphers);
+#if (OPENSSL_VERSION_NUMBER >= 0x10101000L && !defined OPENSSL_IS_BORINGSSL && !defined LIBRESSL_VERSION_NUMBER)
+ if (global_ssl.listen_default_ciphersuites)
+ global_ssl.listen_default_ciphersuites = strdup(global_ssl.listen_default_ciphersuites);
+ if (global_ssl.connect_default_ciphersuites)
+ global_ssl.connect_default_ciphersuites = strdup(global_ssl.connect_default_ciphersuites);
+#endif
xprt_register(XPRT_SSL, &ssl_sock);
SSL_library_init();

View File

@ -0,0 +1,62 @@
commit 30ba96df349ace825749a57490defeb50001a550
Author: Emeric Brun <ebrun@haproxy.com>
Date: Wed Oct 10 14:51:02 2018 +0200
BUG/MEDIUM: Cur/CumSslConns counters not threadsafe.
CurSslConns inc/dec operations are not threadsafe. The unsigned CurSslConns
counter can wrap to a negative value. So we could notice connection rejects
because of MaxSslConns limit artificially exceeded.
CumSslConns inc operation are also not threadsafe so we could miss
some connections and show inconsistenties values compared to CumConns.
This fix should be backported to v1.8.
(cherry picked from commit 7ad43e7928c9a61b40332e4d5e9a7ccc33e6b65b)
Signed-off-by: Willy Tarreau <w@1wt.eu>
diff --git a/src/ssl_sock.c b/src/ssl_sock.c
index 2da0df68..6eed8022 100644
--- a/src/ssl_sock.c
+++ b/src/ssl_sock.c
@@ -491,7 +491,7 @@ static void ssl_async_fd_free(int fd)
/* Now we can safely call SSL_free, no more pending job in engines */
SSL_free(ssl);
- sslconns--;
+ HA_ATOMIC_SUB(&sslconns, 1);
HA_ATOMIC_SUB(&jobs, 1);
}
/*
@@ -5011,8 +5011,8 @@ static int ssl_sock_init(struct connection *conn)
/* leave init state and start handshake */
conn->flags |= CO_FL_SSL_WAIT_HS | CO_FL_WAIT_L6_CONN;
- sslconns++;
- totalsslconns++;
+ HA_ATOMIC_ADD(&sslconns, 1);
+ HA_ATOMIC_ADD(&totalsslconns, 1);
return 0;
}
else if (objt_listener(conn->target)) {
@@ -5062,8 +5062,8 @@ static int ssl_sock_init(struct connection *conn)
conn->flags |= CO_FL_EARLY_SSL_HS;
#endif
- sslconns++;
- totalsslconns++;
+ HA_ATOMIC_ADD(&sslconns, 1);
+ HA_ATOMIC_ADD(&totalsslconns, 1);
return 0;
}
/* don't know how to handle such a target */
@@ -5713,7 +5713,7 @@ static void ssl_sock_close(struct connection *conn) {
#endif
SSL_free(conn->xprt_ctx);
conn->xprt_ctx = NULL;
- sslconns--;
+ HA_ATOMIC_SUB(&sslconns, 1);
}
}

View File

@ -0,0 +1,33 @@
commit 8a6c4ff3f407b916bc08da4e76ed7813768ac937
Author: mildis <me@mildis.org>
Date: Tue Oct 2 16:46:34 2018 +0200
BUG/MINOR: checks: queues null-deref
queues can be null if calloc() failed.
Bypass free* calls when calloc did fail.
(cherry picked from commit 5ab01cb01114065a3573570a48e84815e751bf14)
Signed-off-by: Willy Tarreau <w@1wt.eu>
diff --git a/src/checks.c b/src/checks.c
index 098ddecf..74958b2d 100644
--- a/src/checks.c
+++ b/src/checks.c
@@ -3182,7 +3182,7 @@ int init_email_alert(struct mailers *mls, struct proxy *p, char **err)
if ((queues = calloc(mls->count, sizeof(*queues))) == NULL) {
memprintf(err, "out of memory while allocating mailer alerts queues");
- goto error;
+ goto fail_no_queue;
}
for (mailer = mls->mailer_list; mailer; i++, mailer = mailer->next) {
@@ -3239,6 +3239,7 @@ int init_email_alert(struct mailers *mls, struct proxy *p, char **err)
free_check(check);
}
free(queues);
+ fail_no_queue:
return 1;
}

View File

@ -0,0 +1,52 @@
commit df4822ea169adc5c7c987fa077438f0ded1ac39b
Author: Emeric Brun <ebrun@haproxy.com>
Date: Thu Oct 11 15:27:07 2018 +0200
BUG/MEDIUM: mworker: segfault receiving SIGUSR1 followed by SIGTERM.
This bug appeared only if nbthread > 1. Handling the pipe with the
master, multiple threads of the same worker could process the deinit().
In addition, deinit() was called while some other threads were still
performing some tasks.
This patch assign the handler of the pipe with master to only the first
thread and removes the call to deinit() before exiting with an error.
This patch should be backported in v1.8.
(cherry picked from commit c8c0ed91cb4436491efd2ce2c4b4b1694aeeccca)
[wt: adjusted context]
Signed-off-by: Willy Tarreau <w@1wt.eu>
diff --git a/src/haproxy.c b/src/haproxy.c
index e0186ff9..1959dd0f 100644
--- a/src/haproxy.c
+++ b/src/haproxy.c
@@ -2349,7 +2349,13 @@ void mworker_pipe_handler(int fd)
break;
}
- deinit();
+ /* At this step the master is down before
+ * this worker perform a 'normal' exit.
+ * So we want to exit with an error but
+ * other threads could currently process
+ * some stuff so we can't perform a clean
+ * deinit().
+ */
exit(EXIT_FAILURE);
return;
}
@@ -2364,7 +2370,10 @@ void mworker_pipe_register()
fcntl(mworker_pipe[0], F_SETFL, O_NONBLOCK);
fdtab[mworker_pipe[0]].owner = mworker_pipe;
fdtab[mworker_pipe[0]].iocb = mworker_pipe_handler;
- fd_insert(mworker_pipe[0], MAX_THREADS_MASK);
+ /* In multi-tread, we need only one thread to process
+ * events on the pipe with master
+ */
+ fd_insert(mworker_pipe[0], 1);
fd_want_recv(mworker_pipe[0]);
}

View File

@ -0,0 +1,29 @@
commit 4bf6d76a22b9b601fd57df4aa0f4fba62733cb07
Author: Willy Tarreau <w@1wt.eu>
Date: Mon Oct 15 11:08:55 2018 +0200
BUG/MEDIUM: stream: don't crash on out-of-memory
In case pool_alloc() fails in stream_new(), we try to detach the stream
from the list before it has been added, dereferencing a NULL. In order
to fix it, simply move the LIST_DEL call upwards.
This must be backported to 1.8.
(cherry picked from commit e5f229e6392fd54aaba7fe58f457723c16b9d15f)
Signed-off-by: Willy Tarreau <w@1wt.eu>
diff --git a/src/stream.c b/src/stream.c
index 11c9dbf3..ef7cff5c 100644
--- a/src/stream.c
+++ b/src/stream.c
@@ -282,8 +282,8 @@ struct stream *stream_new(struct session *sess, enum obj_type *origin)
out_fail_accept:
flt_stream_release(s, 0);
task_free(t);
- out_fail_alloc:
LIST_DEL(&s->list);
+ out_fail_alloc:
pool_free(pool_head_stream, s);
return NULL;
}

View File

@ -0,0 +1,29 @@
commit d332b12b262ad7df1c8bdda52dad100f40399d24
Author: Willy Tarreau <w@1wt.eu>
Date: Mon Oct 15 11:01:59 2018 +0200
BUILD: ssl: fix null-deref warning in ssl_fc_cipherlist_str sample fetch
Gcc 6.4 detects a potential null-deref warning in smp_fetch_ssl_fc_cl_str().
This one is not real since already addressed a few lines above. Let's use
__objt_conn() instead of objt_conn() to avoid the extra test that confuses
it.
This could be backported to 1.8.
(cherry picked from commit b729077710b14c75936909409e27a4fa0badcb54)
Signed-off-by: Willy Tarreau <w@1wt.eu>
diff --git a/src/ssl_sock.c b/src/ssl_sock.c
index 6eed8022..4577fef4 100644
--- a/src/ssl_sock.c
+++ b/src/ssl_sock.c
@@ -6929,7 +6929,7 @@ smp_fetch_ssl_fc_cl_str(const struct arg *args, struct sample *smp, const char *
#if defined(OPENSSL_IS_BORINGSSL)
cipher = SSL_get_cipher_by_value(id);
#else
- struct connection *conn = objt_conn(smp->sess->origin);
+ struct connection *conn = __objt_conn(smp->sess->origin);
cipher = SSL_CIPHER_find(conn->xprt_ctx, bin);
#endif
str = SSL_CIPHER_get_name(cipher);

View File

@ -0,0 +1,28 @@
commit 892c21240adb9ac230d4bd27cc8be4767b4902aa
Author: Willy Tarreau <w@1wt.eu>
Date: Mon Oct 15 13:20:07 2018 +0200
BUILD: ssl: fix another null-deref warning in ssl_sock_switchctx_cbk()
This null-deref cannot happen either as there necesarily is a listener
where this function is called. Let's use __objt_listener() to address
this.
This may be backported to 1.8.
(cherry picked from commit a8825520b785d592467c45e183ad8213cb7bf891)
Signed-off-by: Willy Tarreau <w@1wt.eu>
diff --git a/src/ssl_sock.c b/src/ssl_sock.c
index 4577fef4..cfbc38b7 100644
--- a/src/ssl_sock.c
+++ b/src/ssl_sock.c
@@ -2113,7 +2113,7 @@ static int ssl_sock_switchctx_cbk(SSL *ssl, int *al, void *arg)
int i;
conn = SSL_get_ex_data(ssl, ssl_app_data_index);
- s = objt_listener(conn->target)->bind_conf;
+ s = __objt_listener(conn->target)->bind_conf;
if (s->ssl_conf.early_data)
allow_early = 1;

View File

@ -0,0 +1,26 @@
commit eb72c1faedc39c68fb1246ea8a97d1f96831756c
Author: Willy Tarreau <w@1wt.eu>
Date: Mon Oct 15 11:12:15 2018 +0200
BUILD: stick-table: make sure not to fail on task_new() during initialization
Gcc reports a potential null-deref error in the stick-table init code.
While not critical there, it's trivial to fix. This check has been
missing since 1.4 so this fix can be backported to all supported versions.
(cherry picked from commit 848522f05df9e60eea9274e11f1e9fcd19594a5c)
Signed-off-by: Willy Tarreau <w@1wt.eu>
diff --git a/src/stick_table.c b/src/stick_table.c
index 5a2f1295..653a1ffb 100644
--- a/src/stick_table.c
+++ b/src/stick_table.c
@@ -602,6 +602,8 @@ int stktable_init(struct stktable *t)
t->exp_next = TICK_ETERNITY;
if ( t->expire ) {
t->exp_task = task_new(MAX_THREADS_MASK);
+ if (!t->exp_task)
+ return 0;
t->exp_task->process = process_table_expire;
t->exp_task->context = (void *)t;
}

View File

@ -0,0 +1,77 @@
commit d28afe3631e20a9fcca47efde031d62e501eff48
Author: Willy Tarreau <w@1wt.eu>
Date: Mon Oct 15 11:18:03 2018 +0200
BUILD: peers: check allocation error during peers_init_sync()
peers_init_sync() doesn't check task_new()'s return value and doesn't
return any result to indicate success or failure. Let's make it return
an int and check it from the caller.
This can be backported as far as 1.6.
(cherry picked from commit d944344f01d9ea914d94c45f6ac7c224c6143fc9)
Signed-off-by: Willy Tarreau <w@1wt.eu>
diff --git a/include/proto/peers.h b/include/proto/peers.h
index 782b66e4..9d4aaff2 100644
--- a/include/proto/peers.h
+++ b/include/proto/peers.h
@@ -28,7 +28,7 @@
#include <types/stream.h>
#include <types/peers.h>
-void peers_init_sync(struct peers *peers);
+int peers_init_sync(struct peers *peers);
void peers_register_table(struct peers *, struct stktable *table);
void peers_setup_frontend(struct proxy *fe);
diff --git a/src/cfgparse.c b/src/cfgparse.c
index d1474d4b..7414b60d 100644
--- a/src/cfgparse.c
+++ b/src/cfgparse.c
@@ -9111,7 +9111,12 @@ out_uri_auth_compat:
curpeers->peers_fe = NULL;
}
else {
- peers_init_sync(curpeers);
+ if (!peers_init_sync(curpeers)) {
+ ha_alert("Peers section '%s': out of memory, giving up on peers.\n",
+ curpeers->id);
+ cfgerr++;
+ break;
+ }
last = &curpeers->next;
continue;
}
diff --git a/src/peers.c b/src/peers.c
index c56ed3af..0cd56da3 100644
--- a/src/peers.c
+++ b/src/peers.c
@@ -2159,9 +2159,9 @@ static struct task *process_peer_sync(struct task * task)
/*
- *
+ * returns 0 in case of error.
*/
-void peers_init_sync(struct peers *peers)
+int peers_init_sync(struct peers *peers)
{
struct peer * curpeer;
struct listener *listener;
@@ -2173,10 +2173,14 @@ void peers_init_sync(struct peers *peers)
list_for_each_entry(listener, &peers->peers_fe->conf.listeners, by_fe)
listener->maxconn = peers->peers_fe->maxconn;
peers->sync_task = task_new(MAX_THREADS_MASK);
+ if (!peers->sync_task)
+ return 0;
+
peers->sync_task->process = process_peer_sync;
peers->sync_task->context = (void *)peers;
peers->sighandler = signal_register_task(0, peers->sync_task, 0);
task_wakeup(peers->sync_task, TASK_WOKEN_INIT);
+ return 1;
}

View File

@ -0,0 +1,56 @@
commit c6eb147201c1d05afaadc5fd248b17be91f97331
Author: Bertrand Jacquin <bertrand@jacquin.bzh>
Date: Sat Oct 13 16:06:18 2018 +0100
DOC: Fix a few typos
these are mostly spelling mistakes, some of them might be candidate for
backporting as well.
(cherry picked from commit d5e4de8e5f99108e31dc7a23a0e91c4231e37974)
Signed-off-by: Willy Tarreau <w@1wt.eu>
diff --git a/CONTRIBUTING b/CONTRIBUTING
index b2c2b493..cd97e69b 100644
--- a/CONTRIBUTING
+++ b/CONTRIBUTING
@@ -309,7 +309,7 @@ do not think about them anymore after a few patches.
A good rule of thumb is that if your identifiers start to contain more than
3 words or more than 15 characters, they can become confusing. For function
names it's less important especially if these functions are rarely used or
- are used in a complex context where it is important to differenciate between
+ are used in a complex context where it is important to differentiate between
their multiple variants.
9) Unified diff only
@@ -318,7 +318,7 @@ do not think about them anymore after a few patches.
that you have committed your patch to a local branch, with an appropriate
subject line and a useful commit message explaining what the patch attempts
to do. It is not strictly required to use git, but what is strictly required
- is to have all these elements in the same mail, easily distinguishible, and
+ is to have all these elements in the same mail, easily distinguishable, and
a patch in "diff -up" format (which is also the format used by Git). This
means the "unified" diff format must be used exclusively, and with the
function name printed in the diff header of each block. That significantly
@@ -761,7 +761,7 @@ sent to the mailing list : haproxy@formilux.org and CCed to relevant subsystem
maintainers or authors of the modified files if their address appears at the
top of the file.
-Please don't send pull-requests, they are really unconvenient. First, a pull
+Please don't send pull-requests, they are really inconvenient. First, a pull
implies a merge operation and the code doesn't move fast enough to justify the
use of merges. Second, pull requests are not easily commented on by the
project's participants, contrary to e-mails where anyone is allowed to have an
diff --git a/include/types/connection.h b/include/types/connection.h
index 5e8af3e7..b9e46048 100644
--- a/include/types/connection.h
+++ b/include/types/connection.h
@@ -45,7 +45,7 @@ struct server;
struct pipe;
-/* A connection handle is how we differenciate two connections on the lower
+/* A connection handle is how we differentiate two connections on the lower
* layers. It usually is a file descriptor but can be a connection id.
*/
union conn_handle {

View File

@ -0,0 +1,36 @@
commit 75795017480da0f0a1157e945043249fe625f92f
Author: Willy Tarreau <w@1wt.eu>
Date: Tue Oct 16 16:11:56 2018 +0200
BUG/MEDIUM: threads: fix thread_release() at the end of the rendez-vous point
There is a bug in this function used to release other threads. It leaves
the current thread marked as harmless. If after this another thread does
a thread_isolate(), but before the first one reaches poll(), the second
thread will believe it's alone while it's not.
This must be backported to 1.8 since the rendez-vous point was merged
into 1.8.14.
(cherry picked from commit a9c0252b2e8ff7bb728b84d977ac6e9581ea12f8)
Signed-off-by: Willy Tarreau <w@1wt.eu>
diff --git a/src/hathreads.c b/src/hathreads.c
index 9dba4356..0a7c12f7 100644
--- a/src/hathreads.c
+++ b/src/hathreads.c
@@ -221,12 +221,8 @@ void thread_isolate()
*/
void thread_release()
{
- while (1) {
- HA_ATOMIC_AND(&threads_want_rdv_mask, ~tid_bit);
- if (!(threads_want_rdv_mask & all_threads_mask))
- break;
- thread_harmless_till_end();
- }
+ HA_ATOMIC_AND(&threads_want_rdv_mask, ~tid_bit);
+ thread_harmless_end();
}
__attribute__((constructor))

View File

@ -0,0 +1,29 @@
commit 4805c249aabc45cd59386694f962e19ab50e8ca9
Author: Willy Tarreau <w@1wt.eu>
Date: Tue Oct 16 16:57:40 2018 +0200
BUG/MEDIUM: threads: make sure threads_want_sync is marked volatile
The threads_want_sync variable is not volatile, which allows the compiler
to cache old copies of it for long parts of code and possibly optimize
some tests away. This could result in deadlocks when using heavy queue
activity or health check state changes.
There is no upstream commit for this fix because the sync point was
completely removed from 1.9. This fix is exclusively for 1.8.
Signed-off-by: Willy Tarreau <w@1wt.eu>
diff --git a/src/hathreads.c b/src/hathreads.c
index 0a7c12f7..730ebee4 100644
--- a/src/hathreads.c
+++ b/src/hathreads.c
@@ -29,7 +29,7 @@ void thread_sync_io_handler(int fd)
static HA_SPINLOCK_T sync_lock;
static int threads_sync_pipe[2] = {-1, -1};
-static unsigned long threads_want_sync = 0;
+volatile static unsigned long threads_want_sync = 0;
volatile unsigned long threads_want_rdv_mask = 0;
volatile unsigned long threads_harmless_mask = 0;
volatile unsigned long all_threads_mask = 1; // nbthread 1 assumed by default

View File

@ -0,0 +1,38 @@
commit d26a40412197ba61a72368c71e8a8582d686d28c
Author: Willy Tarreau <w@1wt.eu>
Date: Mon Oct 15 11:53:34 2018 +0200
BUILD: compiler: add a new statement "__unreachable()"
This statement is used as a hint for the compiler so that it knows that
the location where it's placed cannot be reached. It will mostly be used
after longjmp() or equivalent statements that deal with error processing
and that the compiler doesn't know will not return on certain conditions,
so that it doesn't complain about null dereferences on error paths.
(cherry picked from commit 8d26f02e693121764bfa0cb48c9a7ab31e17225d)
Signed-off-by: Willy Tarreau <w@1wt.eu>
diff --git a/include/common/compiler.h b/include/common/compiler.h
index a13aad5c..6f4f5a67 100644
--- a/include/common/compiler.h
+++ b/include/common/compiler.h
@@ -82,6 +82,18 @@
*/
#define __maybe_unused __attribute__((unused))
+/* This allows gcc to know that some locations are never reached, for example
+ * after a longjmp() in the Lua code, hence that some errors caught by such
+ * methods cannot propagate further. This is important with gcc versions 6 and
+ * above which can more aggressively detect null dereferences. The builtin
+ * below was introduced in gcc 4.5, and before it we didn't care.
+ */
+#if __GNUC__ >= 5 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 5)
+#define __unreachable() __builtin_unreachable()
+#else
+#define __unreachable()
+#endif
+
/*
* Gcc >= 3 provides the ability for the programme to give hints to the
* compiler about what branch of an if is most likely to be taken. This

View File

@ -0,0 +1,304 @@
commit 330e08dfc588dc9b0ad42203123fab6c191ca2f8
Author: Willy Tarreau <w@1wt.eu>
Date: Tue Oct 16 17:52:55 2018 +0200
MINOR: lua: all functions calling lua_yieldk() may return
There was a mistake when tagging functions which always use longjmp and
those which may use it in that all those supposed to call lua_yieldk()
may return without calling longjmp. Thus they must not use WILL_LJMP()
but MAY_LJMP(). It has zero impact on the code emitted as such, but
prevents other fixes from being properly implemented : this was the
cause of the previous failure with the __unreachable() calls.
This may be backported to older versions. It may or may not apply
well depending on the context, though the change simply consists in
replacing "WILL_LJMP(hlua_yieldk" with "MAY_LJMP(hlua_yieldk", and
same with the single call to lua_yieldk() in hlua_yieldk().
(cherry picked from commit 9635e03c41e95dff38731f67cc9d8b00e3731d2a)
Signed-off-by: Willy Tarreau <w@1wt.eu>
diff --git a/src/hlua.c b/src/hlua.c
index 60ba94ea..64102e8a 100644
--- a/src/hlua.c
+++ b/src/hlua.c
@@ -852,7 +852,7 @@ __LJMP void hlua_yieldk(lua_State *L, int nresults, int ctx,
hlua->flags |= flags;
/* Process the yield. */
- WILL_LJMP(lua_yieldk(L, nresults, ctx, k));
+ MAY_LJMP(lua_yieldk(L, nresults, ctx, k));
}
/* This function initialises the Lua environment stored in the stream.
@@ -1003,7 +1003,7 @@ void hlua_hook(lua_State *L, lua_Debug *ar)
* If the state is not yieldable, trying yield causes an error.
*/
if (lua_isyieldable(L))
- WILL_LJMP(hlua_yieldk(L, 0, 0, NULL, TICK_ETERNITY, HLUA_CTRLYIELD));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, NULL, TICK_ETERNITY, HLUA_CTRLYIELD));
/* If we cannot yield, update the clock and check the timeout. */
tv_update_date(0, 1);
@@ -1883,7 +1883,7 @@ connection_empty:
WILL_LJMP(luaL_error(L, "out of memory"));
}
xref_unlock(&socket->xref, peer);
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_socket_receive_yield, TICK_ETERNITY, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_socket_receive_yield, TICK_ETERNITY, 0));
return 0;
}
@@ -2082,7 +2082,7 @@ hlua_socket_write_yield_return:
WILL_LJMP(luaL_error(L, "out of memory"));
}
xref_unlock(&socket->xref, peer);
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_socket_write_yield, TICK_ETERNITY, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_socket_write_yield, TICK_ETERNITY, 0));
return 0;
}
@@ -2375,7 +2375,7 @@ __LJMP static int hlua_socket_connect_yield(struct lua_State *L, int status, lua
WILL_LJMP(luaL_error(L, "out of memory error"));
}
xref_unlock(&socket->xref, peer);
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_socket_connect_yield, TICK_ETERNITY, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_socket_connect_yield, TICK_ETERNITY, 0));
return 0;
}
@@ -2493,7 +2493,7 @@ __LJMP static int hlua_socket_connect(struct lua_State *L)
task_wakeup(s->task, TASK_WOKEN_INIT);
/* Return yield waiting for connection. */
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_socket_connect_yield, TICK_ETERNITY, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_socket_connect_yield, TICK_ETERNITY, 0));
return 0;
}
@@ -2819,7 +2819,7 @@ __LJMP static int hlua_channel_dup_yield(lua_State *L, int status, lua_KContext
chn = MAY_LJMP(hlua_checkchannel(L, 1));
if (_hlua_channel_dup(chn, L) == 0)
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_channel_dup_yield, TICK_ETERNITY, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_channel_dup_yield, TICK_ETERNITY, 0));
return 1;
}
@@ -2845,7 +2845,7 @@ __LJMP static int hlua_channel_get_yield(lua_State *L, int status, lua_KContext
ret = _hlua_channel_dup(chn, L);
if (unlikely(ret == 0))
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_channel_get_yield, TICK_ETERNITY, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_channel_get_yield, TICK_ETERNITY, 0));
if (unlikely(ret == -1))
return 1;
@@ -2883,7 +2883,7 @@ __LJMP static int hlua_channel_getline_yield(lua_State *L, int status, lua_KCont
ret = ci_getline_nc(chn, &blk1, &len1, &blk2, &len2);
if (ret == 0)
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_channel_getline_yield, TICK_ETERNITY, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_channel_getline_yield, TICK_ETERNITY, 0));
if (ret == -1) {
lua_pushnil(L);
@@ -2932,7 +2932,7 @@ __LJMP static int hlua_channel_append_yield(lua_State *L, int status, lua_KConte
*/
if (chn->buf->size == 0) {
si_applet_cant_put(chn_prod(chn));
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_channel_append_yield, TICK_ETERNITY, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_channel_append_yield, TICK_ETERNITY, 0));
}
max = channel_recv_limit(chn) - buffer_len(chn->buf);
@@ -2946,7 +2946,7 @@ __LJMP static int hlua_channel_append_yield(lua_State *L, int status, lua_KConte
}
if (ret == -1) {
chn->flags |= CF_WAKE_WRITE;
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_channel_append_yield, TICK_ETERNITY, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_channel_append_yield, TICK_ETERNITY, 0));
}
l += ret;
lua_pop(L, 1);
@@ -2962,7 +2962,7 @@ __LJMP static int hlua_channel_append_yield(lua_State *L, int status, lua_KConte
return 1;
}
if (l < len)
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_channel_append_yield, TICK_ETERNITY, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_channel_append_yield, TICK_ETERNITY, 0));
return 1;
}
@@ -3026,7 +3026,7 @@ __LJMP static int hlua_channel_send_yield(lua_State *L, int status, lua_KContext
*/
if (chn->buf->size == 0) {
si_applet_cant_put(chn_prod(chn));
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_channel_send_yield, TICK_ETERNITY, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_channel_send_yield, TICK_ETERNITY, 0));
}
/* the writed data will be immediatly sent, so we can check
@@ -3082,7 +3082,7 @@ __LJMP static int hlua_channel_send_yield(lua_State *L, int status, lua_KContext
HLUA_SET_WAKERESWR(hlua);
else
HLUA_SET_WAKEREQWR(hlua);
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_channel_send_yield, TICK_ETERNITY, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_channel_send_yield, TICK_ETERNITY, 0));
}
return 1;
@@ -3146,7 +3146,7 @@ __LJMP static int hlua_channel_forward_yield(lua_State *L, int status, lua_KCont
HLUA_SET_WAKEREQWR(hlua);
/* Otherwise, we can yield waiting for new data in the inpout side. */
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_channel_forward_yield, TICK_ETERNITY, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_channel_forward_yield, TICK_ETERNITY, 0));
}
return 1;
@@ -3654,7 +3654,7 @@ __LJMP static int hlua_applet_tcp_getline_yield(lua_State *L, int status, lua_KC
/* Data not yet avalaible. return yield. */
if (ret == 0) {
si_applet_cant_get(si);
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_applet_tcp_getline_yield, TICK_ETERNITY, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_applet_tcp_getline_yield, TICK_ETERNITY, 0));
}
/* End of data: commit the total strings and return. */
@@ -3709,7 +3709,7 @@ __LJMP static int hlua_applet_tcp_recv_yield(lua_State *L, int status, lua_KCont
/* Data not yet avalaible. return yield. */
if (ret == 0) {
si_applet_cant_get(si);
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_applet_tcp_recv_yield, TICK_ETERNITY, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_applet_tcp_recv_yield, TICK_ETERNITY, 0));
}
/* End of data: commit the total strings and return. */
@@ -3732,7 +3732,7 @@ __LJMP static int hlua_applet_tcp_recv_yield(lua_State *L, int status, lua_KCont
luaL_addlstring(&appctx->b, blk2, len2);
co_skip(si_oc(si), len1 + len2);
si_applet_cant_get(si);
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_applet_tcp_recv_yield, TICK_ETERNITY, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_applet_tcp_recv_yield, TICK_ETERNITY, 0));
} else {
@@ -3756,7 +3756,7 @@ __LJMP static int hlua_applet_tcp_recv_yield(lua_State *L, int status, lua_KCont
lua_pushinteger(L, len);
lua_replace(L, 2);
si_applet_cant_get(si);
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_applet_tcp_recv_yield, TICK_ETERNITY, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_applet_tcp_recv_yield, TICK_ETERNITY, 0));
}
/* return the result. */
@@ -3825,7 +3825,7 @@ __LJMP static int hlua_applet_tcp_send_yield(lua_State *L, int status, lua_KCont
*/
if (l < len) {
si_applet_cant_put(si);
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_applet_tcp_send_yield, TICK_ETERNITY, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_applet_tcp_send_yield, TICK_ETERNITY, 0));
}
return 1;
@@ -4122,7 +4122,7 @@ __LJMP static int hlua_applet_http_getline_yield(lua_State *L, int status, lua_K
*/
if (ret == -1) {
si_applet_cant_put(si);
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_applet_http_getline_yield, TICK_ETERNITY, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_applet_http_getline_yield, TICK_ETERNITY, 0));
}
appctx->appctx->ctx.hlua_apphttp.flags &= ~APPLET_100C;
}
@@ -4139,7 +4139,7 @@ __LJMP static int hlua_applet_http_getline_yield(lua_State *L, int status, lua_K
/* Data not yet avalaible. return yield. */
if (ret == 0) {
si_applet_cant_get(si);
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_applet_http_getline_yield, TICK_ETERNITY, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_applet_http_getline_yield, TICK_ETERNITY, 0));
}
/* End of data: commit the total strings and return. */
@@ -4208,7 +4208,7 @@ __LJMP static int hlua_applet_http_recv_yield(lua_State *L, int status, lua_KCon
*/
if (ret == -1) {
si_applet_cant_put(si);
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_applet_http_recv_yield, TICK_ETERNITY, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_applet_http_recv_yield, TICK_ETERNITY, 0));
}
appctx->appctx->ctx.hlua_apphttp.flags &= ~APPLET_100C;
}
@@ -4219,7 +4219,7 @@ __LJMP static int hlua_applet_http_recv_yield(lua_State *L, int status, lua_KCon
/* Data not yet avalaible. return yield. */
if (ret == 0) {
si_applet_cant_get(si);
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_applet_http_recv_yield, TICK_ETERNITY, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_applet_http_recv_yield, TICK_ETERNITY, 0));
}
/* End of data: commit the total strings and return. */
@@ -4254,7 +4254,7 @@ __LJMP static int hlua_applet_http_recv_yield(lua_State *L, int status, lua_KCon
lua_pushinteger(L, len);
lua_replace(L, 2);
si_applet_cant_get(si);
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_applet_http_recv_yield, TICK_ETERNITY, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_applet_http_recv_yield, TICK_ETERNITY, 0));
}
/* return the result. */
@@ -4320,7 +4320,7 @@ __LJMP static int hlua_applet_http_send_yield(lua_State *L, int status, lua_KCon
*/
if (l < len) {
si_applet_cant_put(si);
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_applet_http_send_yield, TICK_ETERNITY, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_applet_http_send_yield, TICK_ETERNITY, 0));
}
return 1;
@@ -4460,7 +4460,7 @@ __LJMP static int hlua_applet_http_start_response_yield(lua_State *L, int status
/* If ret is -1, we dont have room in the buffer, so we yield. */
if (ret == -1) {
si_applet_cant_put(si);
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_applet_http_start_response_yield, TICK_ETERNITY, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_applet_http_start_response_yield, TICK_ETERNITY, 0));
}
/* Headers sent, set the flag. */
@@ -5510,7 +5510,7 @@ __LJMP static int hlua_sleep_yield(lua_State *L, int status, lua_KContext ctx)
{
int wakeup_ms = lua_tointeger(L, -1);
if (now_ms < wakeup_ms)
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_sleep_yield, wakeup_ms, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_sleep_yield, wakeup_ms, 0));
return 0;
}
@@ -5525,7 +5525,7 @@ __LJMP static int hlua_sleep(lua_State *L)
wakeup_ms = tick_add(now_ms, delay);
lua_pushinteger(L, wakeup_ms);
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_sleep_yield, wakeup_ms, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_sleep_yield, wakeup_ms, 0));
return 0;
}
@@ -5540,7 +5540,7 @@ __LJMP static int hlua_msleep(lua_State *L)
wakeup_ms = tick_add(now_ms, delay);
lua_pushinteger(L, wakeup_ms);
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_sleep_yield, wakeup_ms, 0));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_sleep_yield, wakeup_ms, 0));
return 0;
}
@@ -5555,7 +5555,7 @@ __LJMP static int hlua_yield_yield(lua_State *L, int status, lua_KContext ctx)
__LJMP static int hlua_yield(lua_State *L)
{
- WILL_LJMP(hlua_yieldk(L, 0, 0, hlua_yield_yield, TICK_ETERNITY, HLUA_CTRLYIELD));
+ MAY_LJMP(hlua_yieldk(L, 0, 0, hlua_yield_yield, TICK_ETERNITY, HLUA_CTRLYIELD));
return 0;
}

View File

@ -0,0 +1,48 @@
commit 8019e88dd1ac73a3baa71e9acfbc1b7a3fbc7442
Author: Willy Tarreau <w@1wt.eu>
Date: Tue Oct 16 17:37:12 2018 +0200
BUILD: lua: silence some compiler warnings about potential null derefs (#2)
Here we make sure that appctx is always taken from the unchecked value
since we know it's an appctx, which explains why it's immediately
dereferenced. A missing test was added to ensure that task_new() does
not return a NULL.
This may be backported to 1.8.
(cherry picked from commit e09101e8d92b0c0ef8674fbc791e309112ab7f1c)
Signed-off-by: Willy Tarreau <w@1wt.eu>
diff --git a/src/hlua.c b/src/hlua.c
index 64102e8a..ad9238ef 100644
--- a/src/hlua.c
+++ b/src/hlua.c
@@ -2361,7 +2361,7 @@ __LJMP static int hlua_socket_connect_yield(struct lua_State *L, int status, lua
return 2;
}
- appctx = objt_appctx(s->si[0].end);
+ appctx = __objt_appctx(s->si[0].end);
/* Check for connection established. */
if (appctx->ctx.hlua_cosocket.connected) {
@@ -2473,7 +2473,7 @@ __LJMP static int hlua_socket_connect(struct lua_State *L)
}
hlua = hlua_gethlua(L);
- appctx = objt_appctx(s->si[0].end);
+ appctx = __objt_appctx(s->si[0].end);
/* inform the stream that we want to be notified whenever the
* connection completes.
@@ -5693,6 +5693,9 @@ static int hlua_register_task(lua_State *L)
WILL_LJMP(luaL_error(L, "lua out of memory error."));
task = task_new(MAX_THREADS_MASK);
+ if (!task)
+ WILL_LJMP(luaL_error(L, "Lua out of memory error."));
+
task->context = hlua;
task->process = hlua_process_task;

View File

@ -0,0 +1,39 @@
commit 3f39e1d4b5ca37e57247034421c69bc301d996b2
Author: Willy Tarreau <w@1wt.eu>
Date: Tue Oct 16 17:57:36 2018 +0200
BUILD: lua: silence some compiler warnings after WILL_LJMP
These ones are on error paths that are properly handled by luaL_error()
which does a longjmp() but the compiler cannot know it. By adding an
__unreachable() statement in WILL_LJMP(), there is no ambiguity anymore.
This may be backported to 1.8 but these previous patches are needed first :
- BUILD: compiler: add a new statement "__unreachable()"
- MINOR: lua: all functions calling lua_yieldk() may return
- BUILD: lua: silence some compiler warnings about potential null derefs (#2)
(cherry picked from commit b059b894cdf795f134b6e53ff95ea7f907feb846)
Signed-off-by: Willy Tarreau <w@1wt.eu>
diff --git a/src/hlua.c b/src/hlua.c
index ad9238ef..c3bb269a 100644
--- a/src/hlua.c
+++ b/src/hlua.c
@@ -24,6 +24,7 @@
#include <ebpttree.h>
#include <common/cfgparse.h>
+#include <common/compiler.h>
#include <common/xref.h>
#include <common/hathreads.h>
@@ -63,7 +64,7 @@
* MAY_LJMP() marks an lua function that may use longjmp.
*/
#define __LJMP
-#define WILL_LJMP(func) func
+#define WILL_LJMP(func) do { func; __unreachable(); } while(0)
#define MAY_LJMP(func) func
/* This couple of function executes securely some Lua calls outside of

View File

@ -0,0 +1,27 @@
commit b884ba5222a765b395e8ac93971639a0452d6422
Author: Dirkjan Bussink <d.bussink@gmail.com>
Date: Fri Sep 14 14:31:22 2018 +0200
CLEANUP: stick-tables: Remove unneeded double (()) around conditional clause
In the past this conditional had multiple conditionals which is why the
additional parentheses were needed. The conditional was simplified but
the duplicate parentheses were not cleaned up.
(cherry picked from commit ff57f1bbcf8af1e6389520aa845df5aa97ef55b6)
[wt: fixes build warnings with clang]
Signed-off-by: Willy Tarreau <w@1wt.eu>
diff --git a/src/stick_table.c b/src/stick_table.c
index 653a1ffb..f1442603 100644
--- a/src/stick_table.c
+++ b/src/stick_table.c
@@ -1860,7 +1860,7 @@ smp_fetch_sc_tracked(const struct arg *args, struct sample *smp, const char *kw,
smp->data.u.sint = !!stkctr;
/* release the ref count */
- if ((stkctr == &tmpstkctr))
+ if (stkctr == &tmpstkctr)
stktable_release(stkctr->table, stkctr_entry(stkctr));
return 1;

View File

@ -0,0 +1,41 @@
commit 0820ab24974cd2bad84c8ec5a90f7ce0e1681cf0
Author: Willy Tarreau <w@1wt.eu>
Date: Wed Oct 3 09:40:22 2018 +0200
BUILD: Makefile: add a "make opts" target to simply show the build options
We're often missing an easy way to map input variables to output ones.
The "opts" build target will simply show the input variables and the ones
passed to the compiler and linker. This way it's easier to quickly see
what a given build script or package will use, or the detected warnings
supported by the compiler.
(cherry picked from commit a8b12c6bb73b924f6429c3ae4d20b96992e92c2e)
[wt: this is not needed but significantly helps for packaging]
Signed-off-by: Willy Tarreau <w@1wt.eu>
diff --git a/Makefile b/Makefile
index 5d170041..d3615060 100644
--- a/Makefile
+++ b/Makefile
@@ -996,3 +996,20 @@ update-version:
echo "$(VERSION)" > VERSION
echo "$(SUBVERS)" > SUBVERS
echo "$(VERDATE)" > VERDATE
+
+# just display the build options
+opts:
+ @echo -n 'Using: '
+ @echo -n 'TARGET="$(strip $(TARGET))" '
+ @echo -n 'ARCH="$(strip $(ARCH))" '
+ @echo -n 'CPU="$(strip $(CPU))" '
+ @echo -n 'CC="$(strip $(CC))" '
+ @echo -n 'ARCH_FLAGS="$(strip $(ARCH_FLAGS))" '
+ @echo -n 'CPU_CFLAGS="$(strip $(CPU_CFLAGS))" '
+ @echo -n 'DEBUG_CFLAGS="$(strip $(DEBUG_CFLAGS))" '
+ @echo "$(strip $(BUILD_OPTIONS))"
+ @echo 'COPTS="$(strip $(COPTS))"'
+ @echo 'LDFLAGS="$(strip $(LDFLAGS))"'
+ @echo 'LDOPTS="$(strip $(LDOPTS))"'
+ @echo 'OPTIONS_OBJS="$(strip $(OPTIONS_OBJS))"'
+ @echo 'OBJS="$(strip $(OBJS))"'

View File

@ -0,0 +1,38 @@
commit 5df1480da4c4e58830d108f4f0f3347598c55ab3
Author: Willy Tarreau <w@1wt.eu>
Date: Wed Oct 3 09:52:51 2018 +0200
BUILD: Makefile: speed up compiler options detection
Commits b78016649 and d3a7f4035 brought the ability to detect the build
options and warnings that the compiler supports. However, they're detected
using "$(CC) -c", which is 50% slower than "$(CC) -E" for the same result,
just because it starts the assembler at the end. Given that we're starting
to check for a number of warnings, this detection alone starts to become
visible, taking a bit more than 300 ms on the build time. Let's switch to
-E instead to shrink this incompressible time by roughly 100 ms.
(cherry picked from commit f11ca5e7a43c772637018ec2ad981a9fd7d3816f)
[wt: only backported for context and consistency with next patch]
Signed-off-by: Willy Tarreau <w@1wt.eu>
diff --git a/Makefile b/Makefile
index d3615060..1a971f92 100644
--- a/Makefile
+++ b/Makefile
@@ -96,13 +96,13 @@
# Usage: CFLAGS += $(call cc-opt,option). Eg: $(call cc-opt,-fwrapv)
# Note: ensure the referencing variable is assigned using ":=" and not "=" to
# call it only once.
-cc-opt = $(shell set -e; if $(CC) $(1) -c -xc - -o /dev/null </dev/null >&0 2>&0; then echo "$(1)"; fi;)
+cc-opt = $(shell set -e; if $(CC) $(1) -E -xc - -o /dev/null </dev/null >&0 2>&0; then echo "$(1)"; fi;)
# Disable a warning when supported by the compiler. Don't put spaces around the
# warning! And don't use cc-opt which doesn't always report an error until
# another one is also returned.
# Usage: CFLAGS += $(call cc-nowarn,warning). Eg: $(call cc-opt,format-truncation)
-cc-nowarn = $(shell set -e; if $(CC) -W$(1) -c -xc - -o /dev/null </dev/null >&0 2>&0; then echo "-Wno-$(1)"; fi;)
+cc-nowarn = $(shell set -e; if $(CC) -W$(1) -E -xc - -o /dev/null </dev/null >&0 2>&0; then echo "-Wno-$(1)"; fi;)
#### Installation options.
DESTDIR =

View File

@ -0,0 +1,38 @@
commit a7e9853db925b12b1d040be8b04bafc11d84d685
Author: Willy Tarreau <w@1wt.eu>
Date: Tue Oct 16 18:11:34 2018 +0200
BUILD: Makefile: silence an option conflict warning with clang
clang complains that -fno-strict-overflow is not used when -fwrapv is
used, which breaks the build when -Werror is used. Let's introduce a
cc-opt-alt function to emit the former only then the latter is not
supported (since it implies the former).
(cherry picked from commit 0d7a2ae4f5199ec37ead6914fa24d40ec0989a4d)
Signed-off-by: Willy Tarreau <w@1wt.eu>
diff --git a/Makefile b/Makefile
index 1a971f92..6ffc1b06 100644
--- a/Makefile
+++ b/Makefile
@@ -98,6 +98,9 @@
# call it only once.
cc-opt = $(shell set -e; if $(CC) $(1) -E -xc - -o /dev/null </dev/null >&0 2>&0; then echo "$(1)"; fi;)
+# same but emits $2 if $1 is not supported
+cc-opt-alt = $(shell set -e; if $(CC) $(1) -E -xc - -o /dev/null </dev/null >&0 2>&0; then echo "$(1)"; else echo "$(2)"; fi;)
+
# Disable a warning when supported by the compiler. Don't put spaces around the
# warning! And don't use cc-opt which doesn't always report an error until
# another one is also returned.
@@ -147,8 +150,7 @@ DEBUG_CFLAGS = -g
# can do whatever it wants since it's an undefined behavior, so use -fwrapv
# to be sure we get the intended behavior.
SPEC_CFLAGS := -fno-strict-aliasing -Wdeclaration-after-statement
-SPEC_CFLAGS += $(call cc-opt,-fwrapv)
-SPEC_CFLAGS += $(call cc-opt,-fno-strict-overflow)
+SPEC_CFLAGS += $(call cc-opt-alt,-fwrapv,$(call cc-opt,-fno-strict-overflow))
SPEC_CFLAGS += $(call cc-nowarn,format-truncation)
SPEC_CFLAGS += $(call cc-nowarn,address-of-packed-member)
SPEC_CFLAGS += $(call cc-nowarn,null-dereference)

View File

@ -0,0 +1,34 @@
commit 541e3b40b394fb6bde563ff8ce4c882dafca4eb1
Author: Olivier Houchard <ohouchard@haproxy.com>
Date: Tue Oct 16 18:35:01 2018 +0200
MINOR: server: Use memcpy() instead of strncpy().
Use memcpy instead of strncpy, strncpy buys us nothing, and gcc is being
annoying.
(cherry picked from commit 17f8b90736d811ac9a04af198a3aee34e9935cec)
Signed-off-by: Willy Tarreau <w@1wt.eu>
diff --git a/src/server.c b/src/server.c
index 4941bd03..208f21da 100644
--- a/src/server.c
+++ b/src/server.c
@@ -3078,7 +3078,7 @@ void apply_server_state(void)
globalfilepathlen = 0;
goto globalfileerror;
}
- strncpy(globalfilepath, global.server_state_base, len);
+ memcpy(globalfilepath, global.server_state_base, len);
globalfilepath[globalfilepathlen] = 0;
/* append a slash if needed */
@@ -3147,7 +3147,7 @@ void apply_server_state(void)
localfilepathlen = 0;
goto localfileerror;
}
- strncpy(localfilepath, global.server_state_base, len);
+ memcpy(localfilepath, global.server_state_base, len);
localfilepath[localfilepathlen] = 0;
/* append a slash if needed */

View File

@ -0,0 +1,34 @@
commit 1993e23d59e37ee7befbc64bf1535640a16354bc
Author: Olivier Houchard <ohouchard@haproxy.com>
Date: Tue Oct 16 18:39:38 2018 +0200
MINOR: cfgparse: Write 130 as 128 as 0x82 and 0x80.
Write 130 and 128 as 8x82 and 0x80, to avoid warnings about casting from
int to size. "check_req" should probably be unsigned, but it's hard to do so.
(cherry picked from commit 3332090a2d3e9e84bac67af79fb03be111359429)
Signed-off-by: Willy Tarreau <w@1wt.eu>
diff --git a/src/cfgparse.c b/src/cfgparse.c
index 7414b60d..87a4d803 100644
--- a/src/cfgparse.c
+++ b/src/cfgparse.c
@@ -5082,7 +5082,7 @@ stats_error_parsing:
((unsigned char) (packetlen >> 16) & 0xff));
curproxy->check_req[3] = 1;
- curproxy->check_req[5] = 130;
+ curproxy->check_req[5] = 0x82; // 130
curproxy->check_req[11] = 1;
curproxy->check_req[12] = 33;
memcpy(&curproxy->check_req[36], mysqluser, userlen);
@@ -5108,7 +5108,7 @@ stats_error_parsing:
((unsigned char) (packetlen >> 16) & 0xff));
curproxy->check_req[3] = 1;
- curproxy->check_req[5] = 128;
+ curproxy->check_req[5] = 0x80;
curproxy->check_req[8] = 1;
memcpy(&curproxy->check_req[9], mysqluser, userlen);
curproxy->check_req[9 + userlen + 1 + 1] = 1;

View File

@ -0,0 +1,39 @@
commit 0d31b8e1dae2bd0ad73c90748a03f9cfeed837d8
Author: Olivier Houchard <ohouchard@haproxy.com>
Date: Tue Oct 16 18:49:26 2018 +0200
MINOR: peers: use defines instead of enums to appease clang.
Clang (rightfully) warns that we're trying to set chars to values >= 128.
Use defines with hex values instead of an enum to address this.
(cherry picked from commit 33992267aac00d7e8ae67e0703bf7fffc9cf9b54)
Signed-off-by: Willy Tarreau <w@1wt.eu>
diff --git a/src/peers.c b/src/peers.c
index 0cd56da3..465ffe85 100644
--- a/src/peers.c
+++ b/src/peers.c
@@ -122,15 +122,13 @@ enum {
/* Note: ids >= 128 contains */
/* id message cotains data */
/*******************************/
-enum {
- PEER_MSG_STKT_UPDATE = 128,
- PEER_MSG_STKT_INCUPDATE,
- PEER_MSG_STKT_DEFINE,
- PEER_MSG_STKT_SWITCH,
- PEER_MSG_STKT_ACK,
- PEER_MSG_STKT_UPDATE_TIMED,
- PEER_MSG_STKT_INCUPDATE_TIMED,
-};
+#define PEER_MSG_STKT_UPDATE 0x80
+#define PEER_MSG_STKT_INCUPDATE 0x81
+#define PEER_MSG_STKT_DEFINE 0x82
+#define PEER_MSG_STKT_SWITCH 0x83
+#define PEER_MSG_STKT_ACK 0x84
+#define PEER_MSG_STKT_UPDATE_TIMED 0x85
+#define PEER_MSG_STKT_INCUPDATE_TIMED 0x86
/**********************************/
/* Peer Session IO handler states */