haproxy: Update all patches for HAProxy v1.8.19
authorChristian Lachner <gladiac@gmail.com>
Mon, 1 Apr 2019 08:18:45 +0000 (10:18 +0200)
committerChristian Lachner <gladiac@gmail.com>
Mon, 1 Apr 2019 08:23:00 +0000 (10:23 +0200)
- Add new patches (see https://www.haproxy.org/bugs/bugs-1.8.19.html)
- Raise PKG_RELEASE to 3

Signed-off-by: Christian Lachner <gladiac@gmail.com>
net/haproxy/Makefile
net/haproxy/patches/000-BUG-MAJOR-listener-Make-sure-the-listener-exist-before-using-it.patch [new file with mode: 0644]
net/haproxy/patches/000-deprecated-openssl.patch [deleted file]
net/haproxy/patches/001-BUG-MINOR-listener-keep-accept-rate-counters-accurate-under-saturation.patch [new file with mode: 0644]
net/haproxy/patches/002-BUG-MEDIUM-logs-Only-attempt-to-free-startup_logs-once.patch [new file with mode: 0644]
net/haproxy/patches/003-BUG-MEDIUM-51d-fix-possible-segfault-on-deinit_51degrees.patch [new file with mode: 0644]
net/haproxy/patches/004-BUG-MINOR-ssl-fix-warning-about-ssl-min-max-ver-support.patch [new file with mode: 0644]
net/haproxy/patches/005-MEDIUM-threads-Use-__ATOMIC_SEQ_CST-when-using-the-newer-atomic-API.patch [new file with mode: 0644]
net/haproxy/patches/006-BUG-MEDIUM-threads-fd-do-not-forget-to-take-into-account-epoll_fd-pipes.patch [new file with mode: 0644]
net/haproxy/patches/007-BUG-MAJOR-spoe-Fix-initialization-of-thread-dependent-fields.patch [new file with mode: 0644]
net/haproxy/patches/008-deprecated-openssl.patch [new file with mode: 0644]

index 54e34743efed8f2adfa84f027a8feb9addc4c4fe..e01785a9722ea54e5701a12829fe949d724006b3 100644 (file)
@@ -11,7 +11,7 @@ include $(TOPDIR)/rules.mk
 
 PKG_NAME:=haproxy
 PKG_VERSION:=1.8.19
-PKG_RELEASE:=2
+PKG_RELEASE:=3
 
 PKG_SOURCE:=haproxy-$(PKG_VERSION).tar.gz
 PKG_SOURCE_URL:=https://www.haproxy.org/download/1.8/src/
diff --git a/net/haproxy/patches/000-BUG-MAJOR-listener-Make-sure-the-listener-exist-before-using-it.patch b/net/haproxy/patches/000-BUG-MAJOR-listener-Make-sure-the-listener-exist-before-using-it.patch
new file mode 100644 (file)
index 0000000..7d9708e
--- /dev/null
@@ -0,0 +1,50 @@
+commit 7c3fd37724c58cf09359e0d381a9be305dd7869b
+Author: Olivier Houchard <cognet@ci0.org>
+Date:   Mon Feb 25 16:18:16 2019 +0100
+
+    BUG/MAJOR: listener: Make sure the listener exist before using it.
+    
+    In listener_accept(), make sure we have a listener before attempting to
+    use it.
+    An another thread may have closed the FD meanwhile, and set fdtab[fd].owner
+    to NULL.
+    As the listener is not free'd, it is ok to attempt to accept() a new
+    connection even if the listener was closed. At worst the fd has been
+    reassigned to another connection, and accept() will fail anyway.
+    
+    Many thanks to Richard Russo for reporting the problem, and suggesting the
+    fix.
+    
+    This should be backported to 1.9 and 1.8.
+    
+    (cherry picked from commit d16a9dfed80e75d730754b717370515265698cdd)
+    Signed-off-by: Christopher Faulet <cfaulet@haproxy.com>
+    (cherry picked from commit a2511ed1fcdfa8047dbe2268fc0259f9b06cf891)
+    Signed-off-by: William Lallemand <wlallemand@haproxy.org>
+
+diff --git a/src/listener.c b/src/listener.c
+index a30efe03..5f6fafbc 100644
+--- a/src/listener.c
++++ b/src/listener.c
+@@ -441,8 +441,8 @@ void delete_listener(struct listener *listener)
+ void listener_accept(int fd)
+ {
+       struct listener *l = fdtab[fd].owner;
+-      struct proxy *p = l->bind_conf->frontend;
+-      int max_accept = l->maxaccept ? l->maxaccept : 1;
++      struct proxy *p;
++      int max_accept;
+       int expire;
+       int cfd;
+       int ret;
+@@ -450,6 +450,10 @@ void listener_accept(int fd)
+       static int accept4_broken;
+ #endif
++      if (!l)
++              return;
++      p = l->bind_conf->frontend;
++      max_accept = l->maxaccept ? l->maxaccept : 1;
+       if (HA_SPIN_TRYLOCK(LISTENER_LOCK, &l->lock))
+               return;
diff --git a/net/haproxy/patches/000-deprecated-openssl.patch b/net/haproxy/patches/000-deprecated-openssl.patch
deleted file mode 100644 (file)
index 8dd011e..0000000
+++ /dev/null
@@ -1,107 +0,0 @@
---- a/src/ssl_sock.c
-+++ b/src/ssl_sock.c
-@@ -39,6 +39,7 @@
- #include <netdb.h>
- #include <netinet/tcp.h>
-+#include <openssl/bn.h>
- #include <openssl/crypto.h>
- #include <openssl/ssl.h>
- #include <openssl/x509.h>
-@@ -60,6 +61,17 @@
- #include <openssl/async.h>
- #endif
-+#ifndef OPENSSL_VERSION
-+#define OPENSSL_VERSION               SSLEAY_VERSION
-+#define OpenSSL_version(x)    SSLeay_version(x)
-+#define OpenSSL_version_num   SSLeay
-+#endif
-+
-+#if OPENSSL_VERSION_NUMBER < 0x10100000L
-+#define X509_getm_notBefore X509_get_notBefore
-+#define X509_getm_notAfter X509_get_notAfter
-+#endif
-+
- #include <import/lru.h>
- #include <import/xxhash.h>
-@@ -217,7 +229,7 @@ static struct {
-       .capture_cipherlist = 0,
- };
--#ifdef USE_THREAD
-+#if defined(USE_THREAD) && (OPENSSL_VERSION_NUMBER < 0x10100000L)
- static HA_RWLOCK_T *ssl_rwlocks;
-@@ -1716,8 +1728,8 @@ ssl_sock_do_create_cert(const char *servername, struct bind_conf *bind_conf, SSL
-       ASN1_INTEGER_set(X509_get_serialNumber(newcrt), HA_ATOMIC_ADD(&ssl_ctx_serial, 1));
-       /* Set duration for the certificate */
--      if (!X509_gmtime_adj(X509_get_notBefore(newcrt), (long)-60*60*24) ||
--          !X509_gmtime_adj(X509_get_notAfter(newcrt),(long)60*60*24*365))
-+      if (!X509_gmtime_adj(X509_getm_notBefore(newcrt), (long)-60*60*24) ||
-+          !X509_gmtime_adj(X509_getm_notAfter(newcrt),(long)60*60*24*365))
-               goto mkcert_error;
-       /* set public key in the certificate */
-@@ -6299,7 +6311,7 @@ smp_fetch_ssl_x_notafter(const struct arg *args, struct sample *smp, const char
-               goto out;
-       smp_trash = get_trash_chunk();
--      if (ssl_sock_get_time(X509_get_notAfter(crt), smp_trash) <= 0)
-+      if (ssl_sock_get_time(X509_getm_notAfter(crt), smp_trash) <= 0)
-               goto out;
-       smp->data.u.str = *smp_trash;
-@@ -6399,7 +6411,7 @@ smp_fetch_ssl_x_notbefore(const struct arg *args, struct sample *smp, const char
-               goto out;
-       smp_trash = get_trash_chunk();
--      if (ssl_sock_get_time(X509_get_notBefore(crt), smp_trash) <= 0)
-+      if (ssl_sock_get_time(X509_getm_notBefore(crt), smp_trash) <= 0)
-               goto out;
-       smp->data.u.str = *smp_trash;
-@@ -8976,10 +8988,12 @@ static void __ssl_sock_init(void)
- #endif
-       xprt_register(XPRT_SSL, &ssl_sock);
-+#if OPENSSL_VERSION_NUMBER < 0x10100000L
-       SSL_library_init();
-+#endif
-       cm = SSL_COMP_get_compression_methods();
-       sk_SSL_COMP_zero(cm);
--#ifdef USE_THREAD
-+#if defined(USE_THREAD) && (OPENSSL_VERSION_NUMBER < 0x10100000L)
-       ssl_locking_init();
- #endif
- #if (OPENSSL_VERSION_NUMBER >= 0x1000200fL && !defined OPENSSL_NO_TLSEXT && !defined OPENSSL_IS_BORINGSSL && !defined LIBRESSL_VERSION_NUMBER)
-@@ -9008,8 +9022,8 @@ static void __ssl_sock_init(void)
- #else /* OPENSSL_IS_BORINGSSL */
-               OPENSSL_VERSION_TEXT
-               "\nRunning on OpenSSL version : %s%s",
--             SSLeay_version(SSLEAY_VERSION),
--             ((OPENSSL_VERSION_NUMBER ^ SSLeay()) >> 8) ? " (VERSIONS DIFFER!)" : "");
-+             OpenSSL_version(OPENSSL_VERSION),
-+             ((OPENSSL_VERSION_NUMBER ^ OpenSSL_version_num()) >> 8) ? " (VERSIONS DIFFER!)" : "");
- #endif
-       memprintf(&ptr, "%s\nOpenSSL library supports TLS extensions : "
- #if OPENSSL_VERSION_NUMBER < 0x00907000L
-@@ -9100,12 +9114,14 @@ static void __ssl_sock_deinit(void)
-       }
- #endif
-+#if OPENSSL_VERSION_NUMBER < 0x10100000L
-         ERR_remove_state(0);
-         ERR_free_strings();
-         EVP_cleanup();
-+#endif
--#if OPENSSL_VERSION_NUMBER >= 0x00907000L
-+#if OPENSSL_VERSION_NUMBER >= 0x00907000L && OPENSSL_VERSION_NUMBER < 0x10100000L
-         CRYPTO_cleanup_all_ex_data();
- #endif
- }
diff --git a/net/haproxy/patches/001-BUG-MINOR-listener-keep-accept-rate-counters-accurate-under-saturation.patch b/net/haproxy/patches/001-BUG-MINOR-listener-keep-accept-rate-counters-accurate-under-saturation.patch
new file mode 100644 (file)
index 0000000..1edac3a
--- /dev/null
@@ -0,0 +1,67 @@
+commit 78714ea673cefa83d3dff5aa9aa5e97726cfb5cd
+Author: Willy Tarreau <w@1wt.eu>
+Date:   Mon Feb 25 15:02:04 2019 +0100
+
+    BUG/MINOR: listener: keep accept rate counters accurate under saturation
+    
+    The test on l->nbconn forces to exit the loop before updating the freq
+    counters, so the last session which reaches a listener's limit will not
+    be accounted for in the session rate measurement.
+    
+    Let's move the test at the beginning of the loop and mark the listener
+    as saturated on exit.
+    
+    This may be backported to 1.9 and 1.8.
+    
+    (cherry picked from commit 741b4d6b7aad1e4a66dd8584b5eff729b08fade7)
+    Signed-off-by: William Lallemand <wlallemand@haproxy.org>
+    (cherry picked from commit 5c7c7e447df84a04bda88c40382b652cdb77a079)
+    Signed-off-by: William Lallemand <wlallemand@haproxy.org>
+
+diff --git a/src/listener.c b/src/listener.c
+index 5f6fafbc..b94d823c 100644
+--- a/src/listener.c
++++ b/src/listener.c
+@@ -457,11 +457,6 @@ void listener_accept(int fd)
+       if (HA_SPIN_TRYLOCK(LISTENER_LOCK, &l->lock))
+               return;
+-      if (unlikely(l->nbconn >= l->maxconn)) {
+-              listener_full(l);
+-              goto end;
+-      }
+-
+       if (!(l->options & LI_O_UNLIMITED) && global.sps_lim) {
+               int max = freq_ctr_remain(&global.sess_per_sec, global.sps_lim, 0);
+@@ -520,7 +515,7 @@ void listener_accept(int fd)
+        * worst case. If we fail due to system limits or temporary resource
+        * shortage, we try again 100ms later in the worst case.
+        */
+-      while (max_accept--) {
++      while (l->nbconn < l->maxconn && max_accept--) {
+               struct sockaddr_storage addr;
+               socklen_t laddr = sizeof(addr);
+               unsigned int count;
+@@ -627,11 +622,6 @@ void listener_accept(int fd)
+                       goto transient_error;
+               }
+-              if (l->nbconn >= l->maxconn) {
+-                      listener_full(l);
+-                      goto end;
+-              }
+-
+               /* increase the per-process number of cumulated connections */
+               if (!(l->options & LI_O_UNLIMITED)) {
+                       count = update_freq_ctr(&global.sess_per_sec, 1);
+@@ -659,6 +649,9 @@ void listener_accept(int fd)
+       limit_listener(l, &global_listener_queue);
+       task_schedule(global_listener_queue_task, tick_first(expire, global_listener_queue_task->expire));
+  end:
++      if (l->nbconn >= l->maxconn)
++              listener_full(l);
++
+       HA_SPIN_UNLOCK(LISTENER_LOCK, &l->lock);
+ }
diff --git a/net/haproxy/patches/002-BUG-MEDIUM-logs-Only-attempt-to-free-startup_logs-once.patch b/net/haproxy/patches/002-BUG-MEDIUM-logs-Only-attempt-to-free-startup_logs-once.patch
new file mode 100644 (file)
index 0000000..d726360
--- /dev/null
@@ -0,0 +1,37 @@
+commit 4c82743abd299f0aa8105e98ec92b76375a7f344
+Author: Olivier Houchard <ohouchard@haproxy.com>
+Date:   Thu Mar 7 14:19:24 2019 +0100
+
+    BUG/MEDIUM: logs: Only attempt to free startup_logs once.
+    
+    deinit_log_buffers() can be called once per thread, however startup_logs
+    is common to all threads. So only attempt to free it once.
+    
+    This should be backported to 1.9 and 1.8.
+    
+    (cherry picked from commit 7c49711d6041d1afc42d5b310ddfd7d6f6817c3c)
+    Signed-off-by: William Lallemand <wlallemand@haproxy.org>
+    (cherry picked from commit bc3e21b27849275306a0580488613b7dfd4d8eb5)
+    Signed-off-by: William Lallemand <wlallemand@haproxy.org>
+
+diff --git a/src/log.c b/src/log.c
+index b3f33662..9c112255 100644
+--- a/src/log.c
++++ b/src/log.c
+@@ -1380,11 +1380,15 @@ int init_log_buffers()
+ /* Deinitialize log buffers used for syslog messages */
+ void deinit_log_buffers()
+ {
++      void *tmp_startup_logs;
++
+       free(logheader);
+       free(logheader_rfc5424);
+       free(logline);
+       free(logline_rfc5424);
+-      free(startup_logs);
++      tmp_startup_logs = HA_ATOMIC_XCHG(&startup_logs, NULL);
++      free(tmp_startup_logs);
++
+       logheader         = NULL;
+       logheader_rfc5424 = NULL;
+       logline           = NULL;
diff --git a/net/haproxy/patches/003-BUG-MEDIUM-51d-fix-possible-segfault-on-deinit_51degrees.patch b/net/haproxy/patches/003-BUG-MEDIUM-51d-fix-possible-segfault-on-deinit_51degrees.patch
new file mode 100644 (file)
index 0000000..3c9078f
--- /dev/null
@@ -0,0 +1,35 @@
+commit 63f5dbf1b9fcdc5b10537d733b0e0798905ff1dc
+Author: Dragan Dosen <ddosen@haproxy.com>
+Date:   Thu Mar 7 15:24:23 2019 +0100
+
+    BUG/MEDIUM: 51d: fix possible segfault on deinit_51degrees()
+    
+    When haproxy is built with 51Degrees support, but not configured to use
+    51Degrees database, a segfault can occur when deinit_51degrees()
+    function is called, eg. during soft-stop on SIGUSR1 signal.
+    
+    Only builds that use Pattern algorithm are affected.
+    
+    This fix must be backported to all stable branches where 51Degrees
+    support is available. Additional adjustments are required for some
+    branches due to API and naming changes.
+    
+    (cherry picked from commit bc6218e1b02860c6cdad0d2bb4dc8874557087f8)
+    Signed-off-by: William Lallemand <wlallemand@haproxy.org>
+    (cherry picked from commit 4e0363e84cb3f6ca341e1f83c6fd490c76c9ae6b)
+    Signed-off-by: William Lallemand <wlallemand@haproxy.org>
+
+diff --git a/src/51d.c b/src/51d.c
+index a36333ef..03101136 100644
+--- a/src/51d.c
++++ b/src/51d.c
+@@ -639,7 +639,8 @@ static void deinit_51degrees(void)
+       free(global_51degrees.header_names);
+ #ifdef FIFTYONEDEGREES_H_PATTERN_INCLUDED
+-      fiftyoneDegreesWorksetPoolFree(global_51degrees.pool);
++      if (global_51degrees.pool)
++              fiftyoneDegreesWorksetPoolFree(global_51degrees.pool);
+ #endif
+ #ifdef FIFTYONEDEGREES_H_TRIE_INCLUDED
+       free(global_51degrees.device_offsets.firstOffset);
diff --git a/net/haproxy/patches/004-BUG-MINOR-ssl-fix-warning-about-ssl-min-max-ver-support.patch b/net/haproxy/patches/004-BUG-MINOR-ssl-fix-warning-about-ssl-min-max-ver-support.patch
new file mode 100644 (file)
index 0000000..6c1fac8
--- /dev/null
@@ -0,0 +1,34 @@
+commit 57e2606f70fa8d26fe4b5563ba72a6c7f2a25655
+Author: Lukas Tribus <lukas@ltri.eu>
+Date:   Tue Mar 5 23:14:32 2019 +0100
+
+    BUG/MINOR: ssl: fix warning about ssl-min/max-ver support
+    
+    In 84e417d8 ("MINOR: ssl: support Openssl 1.1.1 early callback for
+    switchctx") the code was extended to also support OpenSSL 1.1.1
+    (code already supported BoringSSL). A configuration check warning
+    was updated but with the wrong logic, the #ifdef needs a && instead
+    of an ||.
+    
+    Reported in #54.
+    
+    Should be backported to 1.8.
+    
+    (cherry picked from commit 1aabc939780d5eab1f88089d01fb077ad9315c65)
+    Signed-off-by: William Lallemand <wlallemand@haproxy.org>
+    (cherry picked from commit f407d16b8f4cf2afb148668a23a1ba1cc4dd942a)
+    Signed-off-by: William Lallemand <wlallemand@haproxy.org>
+
+diff --git a/src/ssl_sock.c b/src/ssl_sock.c
+index 7736c324..afdb1fce 100644
+--- a/src/ssl_sock.c
++++ b/src/ssl_sock.c
+@@ -7418,7 +7418,7 @@ static int parse_tls_method_minmax(char **args, int cur_arg, struct tls_version_
+ static int ssl_bind_parse_tls_method_minmax(char **args, int cur_arg, struct proxy *px, struct ssl_bind_conf *conf, char **err)
+ {
+-#if (OPENSSL_VERSION_NUMBER < 0x10101000L) || !defined(OPENSSL_IS_BORINGSSL)
++#if (OPENSSL_VERSION_NUMBER < 0x10101000L) && !defined(OPENSSL_IS_BORINGSSL)
+       ha_warning("crt-list: ssl-min-ver and ssl-max-ver are not supported with this Openssl version (skipped).\n");
+ #endif
+       return parse_tls_method_minmax(args, cur_arg, &conf->ssl_methods, err);
diff --git a/net/haproxy/patches/005-MEDIUM-threads-Use-__ATOMIC_SEQ_CST-when-using-the-newer-atomic-API.patch b/net/haproxy/patches/005-MEDIUM-threads-Use-__ATOMIC_SEQ_CST-when-using-the-newer-atomic-API.patch
new file mode 100644 (file)
index 0000000..4acae7d
--- /dev/null
@@ -0,0 +1,49 @@
+commit 62aec002ccd6a7129b4f5e2e88be1957a6b2308b
+Author: Olivier Houchard <ohouchard@haproxy.com>
+Date:   Thu Mar 7 18:48:22 2019 +0100
+
+    MEDIUM: threads: Use __ATOMIC_SEQ_CST when using the newer atomic API.
+    
+    When using the new __atomic* API, ask the compiler to generate barriers.
+    A variant of those functions that don't generate barriers will be added later.
+    Before that, using HA_ATOMIC* would not generate any barrier, and some parts
+    of the code should be reviewed and missing barriers should be added.
+    
+    This should probably be backported to 1.8 and 1.9.
+    
+    (cherry picked from commit 113537967c8680f94977473e18c9e14dc09c3356)
+    [wt: this is in fact a real bug fix : all these atomics do not provide
+     the slightest sequential consistency by default as the value 0 is
+     __ATOMIC_RELAXED, which will definitely cause random issues with
+     threads on non-x86 platforms].
+    Signed-off-by: Willy Tarreau <w@1wt.eu>
+    (cherry picked from commit e5d1670f5fa95972fed6391201c0da8982bb9f94)
+    Signed-off-by: Christopher Faulet <cfaulet@haproxy.com>
+
+diff --git a/include/common/hathreads.h b/include/common/hathreads.h
+index 24fb1d1a..8a738aaf 100644
+--- a/include/common/hathreads.h
++++ b/include/common/hathreads.h
+@@ -213,14 +213,14 @@ static inline unsigned long thread_isolated()
+       })
+ #else
+ /* gcc >= 4.7 */
+-#define HA_ATOMIC_CAS(val, old, new) __atomic_compare_exchange_n(val, old, new, 0, 0, 0)
+-#define HA_ATOMIC_ADD(val, i)        __atomic_add_fetch(val, i, 0)
+-#define HA_ATOMIC_XADD(val, i)       __atomic_fetch_add(val, i, 0)
+-#define HA_ATOMIC_SUB(val, i)        __atomic_sub_fetch(val, i, 0)
+-#define HA_ATOMIC_AND(val, flags)    __atomic_and_fetch(val, flags, 0)
+-#define HA_ATOMIC_OR(val, flags)     __atomic_or_fetch(val,  flags, 0)
+-#define HA_ATOMIC_XCHG(val, new)     __atomic_exchange_n(val, new, 0)
+-#define HA_ATOMIC_STORE(val, new)    __atomic_store_n(val, new, 0)
++#define HA_ATOMIC_CAS(val, old, new) __atomic_compare_exchange_n(val, old, new, 0, __ATOMIC_SEQ_CST, __ATOMIC_SEQ_CST)
++#define HA_ATOMIC_ADD(val, i)        __atomic_add_fetch(val, i, __ATOMIC_SEQ_CST)
++#define HA_ATOMIC_XADD(val, i)       __atomic_fetch_add(val, i, __ATOMIC_SEQ_CST)
++#define HA_ATOMIC_SUB(val, i)        __atomic_sub_fetch(val, i, __ATOMIC_SEQ_CST)
++#define HA_ATOMIC_AND(val, flags)    __atomic_and_fetch(val, flags, __ATOMIC_SEQ_CST)
++#define HA_ATOMIC_OR(val, flags)     __atomic_or_fetch(val,  flags, __ATOMIC_SEQ_CST)
++#define HA_ATOMIC_XCHG(val, new)     __atomic_exchange_n(val, new, __ATOMIC_SEQ_CST)
++#define HA_ATOMIC_STORE(val, new)    __atomic_store_n(val, new, __ATOMIC_SEQ_CST)
+ #endif
+ #define HA_ATOMIC_UPDATE_MAX(val, new)                                        \
diff --git a/net/haproxy/patches/006-BUG-MEDIUM-threads-fd-do-not-forget-to-take-into-account-epoll_fd-pipes.patch b/net/haproxy/patches/006-BUG-MEDIUM-threads-fd-do-not-forget-to-take-into-account-epoll_fd-pipes.patch
new file mode 100644 (file)
index 0000000..68cd98a
--- /dev/null
@@ -0,0 +1,34 @@
+commit 1dfa4fd4be313a87f2a4861e81d0ad8ea8214223
+Author: Willy Tarreau <w@1wt.eu>
+Date:   Thu Mar 14 19:10:55 2019 +0100
+
+    BUG/MEDIUM: threads/fd: do not forget to take into account epoll_fd/pipes
+    
+    Each thread uses one epoll_fd or kqueue_fd, and a pipe (thus two FDs).
+    These ones have to be accounted for in the maxsock calculation, otherwise
+    we can reach maxsock before maxconn. This is difficult to observe but it
+    in fact happens when a server connects back to the frontend and has checks
+    enabled : the check uses its FD and serves to fill the loop. In this case
+    all FDs planed for the datapath are used for this.
+    
+    This needs to be backported to 1.9 and 1.8.
+    
+    (cherry picked from commit 2c58b41c96e70f567d0f9ae876a80770630c06ee)
+    Signed-off-by: Willy Tarreau <w@1wt.eu>
+    (cherry picked from commit 26d110ba04cba02b337beff53a83847320e4fcdb)
+    Signed-off-by: Christopher Faulet <cfaulet@haproxy.com>
+
+diff --git a/src/haproxy.c b/src/haproxy.c
+index 68367627..5c3febdd 100644
+--- a/src/haproxy.c
++++ b/src/haproxy.c
+@@ -1828,6 +1828,9 @@ static void init(int argc, char **argv)
+       global.hardmaxconn = global.maxconn;  /* keep this max value */
+       global.maxsock += global.maxconn * 2; /* each connection needs two sockets */
+       global.maxsock += global.maxpipes * 2; /* each pipe needs two FDs */
++      global.maxsock += global.nbthread;     /* one epoll_fd/kqueue_fd per thread */
++      global.maxsock += 2 * global.nbthread; /* one wake-up pipe (2 fd) per thread */
++
+       /* compute fd used by async engines */
+       if (global.ssl_used_async_engines) {
+               int sides = !!global.ssl_used_frontend + !!global.ssl_used_backend;
diff --git a/net/haproxy/patches/007-BUG-MAJOR-spoe-Fix-initialization-of-thread-dependent-fields.patch b/net/haproxy/patches/007-BUG-MAJOR-spoe-Fix-initialization-of-thread-dependent-fields.patch
new file mode 100644 (file)
index 0000000..f4d448c
--- /dev/null
@@ -0,0 +1,54 @@
+commit a3cfe8f4bc2ec98fdbe25c49f2c21699b6d09d2b
+Author: Christopher Faulet <cfaulet@haproxy.com>
+Date:   Mon Mar 18 13:57:42 2019 +0100
+
+    BUG/MAJOR: spoe: Fix initialization of thread-dependent fields
+    
+    A bug was introduced in the commit b0769b ("BUG/MEDIUM: spoe: initialization
+    depending on nbthread must be done last"). The code depending on global.nbthread
+    was moved from cfg_parse_spoe_agent() to spoe_check() but the pointer on the
+    agent configuration was not updated to use the filter's one. The variable
+    curagent is a global variable only valid during the configuration parsing. In
+    spoe_check(), conf->agent must be used instead.
+    
+    This patch must be backported to 1.9 and 1.8.
+    
+    (cherry picked from commit fe261551b9980fe33990eb34d2153bf1de24b20f)
+    Signed-off-by: Christopher Faulet <cfaulet@haproxy.com>
+    (cherry picked from commit 7a93d271d549144a8ed8c816f5694a51ab62b90c)
+    Signed-off-by: Christopher Faulet <cfaulet@haproxy.com>
+
+diff --git a/src/flt_spoe.c b/src/flt_spoe.c
+index e4453882..66d26f34 100644
+--- a/src/flt_spoe.c
++++ b/src/flt_spoe.c
+@@ -2937,20 +2937,20 @@ spoe_check(struct proxy *px, struct flt_conf *fconf)
+       if (global.nbthread == 1)
+               conf->agent->flags |= SPOE_FL_ASYNC;
+-      if ((curagent->rt = calloc(global.nbthread, sizeof(*curagent->rt))) == NULL) {
++      if ((conf->agent->rt = calloc(global.nbthread, sizeof(*conf->agent->rt))) == NULL) {
+               ha_alert("Proxy %s : out of memory initializing SPOE agent '%s' declared at %s:%d.\n",
+                        px->id, conf->agent->id, conf->agent->conf.file, conf->agent->conf.line);
+               return 1;
+       }
+       for (i = 0; i < global.nbthread; ++i) {
+-              curagent->rt[i].frame_size   = curagent->max_frame_size;
+-              curagent->rt[i].applets_act  = 0;
+-              curagent->rt[i].applets_idle = 0;
+-              curagent->rt[i].sending_rate = 0;
+-              LIST_INIT(&curagent->rt[i].applets);
+-              LIST_INIT(&curagent->rt[i].sending_queue);
+-              LIST_INIT(&curagent->rt[i].waiting_queue);
+-              HA_SPIN_INIT(&curagent->rt[i].lock);
++              conf->agent->rt[i].frame_size   = conf->agent->max_frame_size;
++              conf->agent->rt[i].applets_act  = 0;
++              conf->agent->rt[i].applets_idle = 0;
++              conf->agent->rt[i].sending_rate = 0;
++              LIST_INIT(&conf->agent->rt[i].applets);
++              LIST_INIT(&conf->agent->rt[i].sending_queue);
++              LIST_INIT(&conf->agent->rt[i].waiting_queue);
++              HA_SPIN_INIT(&conf->agent->rt[i].lock);
+       }
+       free(conf->agent->b.name);
diff --git a/net/haproxy/patches/008-deprecated-openssl.patch b/net/haproxy/patches/008-deprecated-openssl.patch
new file mode 100644 (file)
index 0000000..8dd011e
--- /dev/null
@@ -0,0 +1,107 @@
+--- a/src/ssl_sock.c
++++ b/src/ssl_sock.c
+@@ -39,6 +39,7 @@
+ #include <netdb.h>
+ #include <netinet/tcp.h>
++#include <openssl/bn.h>
+ #include <openssl/crypto.h>
+ #include <openssl/ssl.h>
+ #include <openssl/x509.h>
+@@ -60,6 +61,17 @@
+ #include <openssl/async.h>
+ #endif
++#ifndef OPENSSL_VERSION
++#define OPENSSL_VERSION               SSLEAY_VERSION
++#define OpenSSL_version(x)    SSLeay_version(x)
++#define OpenSSL_version_num   SSLeay
++#endif
++
++#if OPENSSL_VERSION_NUMBER < 0x10100000L
++#define X509_getm_notBefore X509_get_notBefore
++#define X509_getm_notAfter X509_get_notAfter
++#endif
++
+ #include <import/lru.h>
+ #include <import/xxhash.h>
+@@ -217,7 +229,7 @@ static struct {
+       .capture_cipherlist = 0,
+ };
+-#ifdef USE_THREAD
++#if defined(USE_THREAD) && (OPENSSL_VERSION_NUMBER < 0x10100000L)
+ static HA_RWLOCK_T *ssl_rwlocks;
+@@ -1716,8 +1728,8 @@ ssl_sock_do_create_cert(const char *servername, struct bind_conf *bind_conf, SSL
+       ASN1_INTEGER_set(X509_get_serialNumber(newcrt), HA_ATOMIC_ADD(&ssl_ctx_serial, 1));
+       /* Set duration for the certificate */
+-      if (!X509_gmtime_adj(X509_get_notBefore(newcrt), (long)-60*60*24) ||
+-          !X509_gmtime_adj(X509_get_notAfter(newcrt),(long)60*60*24*365))
++      if (!X509_gmtime_adj(X509_getm_notBefore(newcrt), (long)-60*60*24) ||
++          !X509_gmtime_adj(X509_getm_notAfter(newcrt),(long)60*60*24*365))
+               goto mkcert_error;
+       /* set public key in the certificate */
+@@ -6299,7 +6311,7 @@ smp_fetch_ssl_x_notafter(const struct arg *args, struct sample *smp, const char
+               goto out;
+       smp_trash = get_trash_chunk();
+-      if (ssl_sock_get_time(X509_get_notAfter(crt), smp_trash) <= 0)
++      if (ssl_sock_get_time(X509_getm_notAfter(crt), smp_trash) <= 0)
+               goto out;
+       smp->data.u.str = *smp_trash;
+@@ -6399,7 +6411,7 @@ smp_fetch_ssl_x_notbefore(const struct arg *args, struct sample *smp, const char
+               goto out;
+       smp_trash = get_trash_chunk();
+-      if (ssl_sock_get_time(X509_get_notBefore(crt), smp_trash) <= 0)
++      if (ssl_sock_get_time(X509_getm_notBefore(crt), smp_trash) <= 0)
+               goto out;
+       smp->data.u.str = *smp_trash;
+@@ -8976,10 +8988,12 @@ static void __ssl_sock_init(void)
+ #endif
+       xprt_register(XPRT_SSL, &ssl_sock);
++#if OPENSSL_VERSION_NUMBER < 0x10100000L
+       SSL_library_init();
++#endif
+       cm = SSL_COMP_get_compression_methods();
+       sk_SSL_COMP_zero(cm);
+-#ifdef USE_THREAD
++#if defined(USE_THREAD) && (OPENSSL_VERSION_NUMBER < 0x10100000L)
+       ssl_locking_init();
+ #endif
+ #if (OPENSSL_VERSION_NUMBER >= 0x1000200fL && !defined OPENSSL_NO_TLSEXT && !defined OPENSSL_IS_BORINGSSL && !defined LIBRESSL_VERSION_NUMBER)
+@@ -9008,8 +9022,8 @@ static void __ssl_sock_init(void)
+ #else /* OPENSSL_IS_BORINGSSL */
+               OPENSSL_VERSION_TEXT
+               "\nRunning on OpenSSL version : %s%s",
+-             SSLeay_version(SSLEAY_VERSION),
+-             ((OPENSSL_VERSION_NUMBER ^ SSLeay()) >> 8) ? " (VERSIONS DIFFER!)" : "");
++             OpenSSL_version(OPENSSL_VERSION),
++             ((OPENSSL_VERSION_NUMBER ^ OpenSSL_version_num()) >> 8) ? " (VERSIONS DIFFER!)" : "");
+ #endif
+       memprintf(&ptr, "%s\nOpenSSL library supports TLS extensions : "
+ #if OPENSSL_VERSION_NUMBER < 0x00907000L
+@@ -9100,12 +9114,14 @@ static void __ssl_sock_deinit(void)
+       }
+ #endif
++#if OPENSSL_VERSION_NUMBER < 0x10100000L
+         ERR_remove_state(0);
+         ERR_free_strings();
+         EVP_cleanup();
++#endif
+-#if OPENSSL_VERSION_NUMBER >= 0x00907000L
++#if OPENSSL_VERSION_NUMBER >= 0x00907000L && OPENSSL_VERSION_NUMBER < 0x10100000L
+         CRYPTO_cleanup_all_ex_data();
+ #endif
+ }