21951 Commits

Author SHA1 Message Date
Frederic Lecaille
a305bb92b9 MINOR: quic: HyStart++ implementation (RFC 9406)
This is a simple algorithm to replace the classic slow start phase of the
congestion control algorithms. It should reduce the high packet loss during
this step.

Implemented only for Cubic.
2024-04-02 18:47:19 +02:00
Willy Tarreau
e9b774f4b3 BUG/MINOR: backend: properly handle redispatch 0
According to the documentation, "option redispatch 0" is expected to
disable redispatch just like "no option redispatch", but due to the
fact that it keeps PR_O_REDISP set, it doesn't actually work. Let's
make sure value 0 is properly handled and drops PR_O_REDISP. This can
be backported to all versions since it seems it has been broken since
its introduction in 1.6 with commit 726ab7145c ("MEDIUM: backend: Allow
redispatch on retry intervals").

As a workaround, "no option redispatch" does work though.
2024-04-02 15:19:18 +02:00
William Lallemand
4c361a9d8a REGTESTS: ssl: disable ssl/ocsp_auto_update.vtc
Test is broken, keep it disable for now.

  Add test: reg-tests/ssl/ocsp_auto_update.vtc
Testing with haproxy version: 3.0-dev6-9dd928-35
1 tests failed, 0 tests skipped, 0 tests passed
*    diag  0.0 /usr/bin/openssl
*    diag  0.0 /usr/bin/socat
make: *** [Makefile:1177: reg-tests] Error 1
2024-04-02 14:20:39 +02:00
Ilya Shipitsin
9dd9289cec CI: vtest: show coredumps if any
if any coredump	is found, it is	passed to gdb with
'thread apply all bt full'
2024-04-02 07:29:08 +02:00
Tim Duesterhus
ec38e1b39b CLEANUP: Reapply ha_free.cocci
This reapplies ha_free.cocci across the whole src/ tree.
2024-04-02 07:27:33 +02:00
Tim Duesterhus
7c317f4619 CLEANUP: Reapply xalloc_cast.cocci
This reapplies xalloc_cast.cocci across the whole src/ tree.
2024-04-02 07:27:33 +02:00
Tim Duesterhus
f88ea5949c CLEANUP: Reapply strcmp.cocci (2)
This reapplies strcmp.cocci across the whole src/ tree.
2024-04-02 07:27:33 +02:00
Tim Duesterhus
cd5d62249f CLEANUP: Reapply ist.cocci (3)
This reapplies ist.cocci across the whole src/ tree.
2024-04-02 07:27:33 +02:00
Tim Duesterhus
296e9b8de1 REGTESTS: Remove REQUIRE_VERSION=1.9 from all tests (2)
see also:

2a5fb62ad REGTESTS: Remove REQUIRE_VERSION=1.9 from all tests
2024-04-02 07:27:33 +02:00
Tim Duesterhus
34b13378b5 REGTESTS: Do not use REQUIRE_VERSION for HAProxy 2.5+ (4)
Introduced in:

dfb1cea69 REGTESTS: promex: Adapt script to be less verbose
36d936dd1 REGTESTS: write a full reverse regtest
b57f15158 REGTESTS: provide a reverse-server test with name argument
f0bff2947 REGTESTS: provide a reverse-server test

see also:

fbbbc33df REGTESTS: Do not use REQUIRE_VERSION for HAProxy 2.5+
2024-04-02 07:27:33 +02:00
Willy Tarreau
5fc1afb341 BUG/MEDIUM: stick-tables: fix a small remaining race in expiration task
In 2.7 we addressed a race condition in the stick tables expiration task
with commit fbb934d ("BUG/MEDIUM: stick-table: fix a race condition when
updating the expiration task"). The issue was that the task could be
running on another thread which would destroy its expiration timer
while one had just recalculated it and prepares to queue it, causing
a bug due to the attempt to queue an expired task. The fix consisted in
enclosing the change into the stick-table's lock, which had a very low
cost since it's done only after having checked that the date changed,
i.e. no more than once every millisecond.

But as reported by Ricardo and Felipe from Taghos in github issue #2508,
a tiny race remained after the fix: the unlock() was done before the call
to task_queue(), leaving a tiny window for another thread to run between
unlock() and task_queue() and erase the timer. As confirmed, it's
sufficient to also protect the task_queue() call.

But overall this raises a point regarding the task_queue() API on tasks
that may run anywhere. A while ago an attempt was made at removing the
timer for woken up tasks, but something like this would be deserved
with more atomicity on the timer manipulation (e.g. atomically use
task_schedule() instead maybe). This should be backported to all
stable branches.
2024-04-02 07:07:57 +02:00
Anthony Deschamps
faa8c3e024 MEDIUM: lb-chash: Deterministic node hashes based on server address
Motivation: When services are discovered through DNS resolution, the order in
which DNS records get resolved and assigned to servers is arbitrary. Therefore,
even though two HAProxy instances using chash balancing might agree that a
particular request should go to server3, it is likely the case that they have
assigned different IPs and ports to the server in that slot.

This patch adds a server option, "hash-key <key>" which can be set to "id" (the
existing behaviour, default), "addr", or "addr-port". By deriving the keys for
the chash tree nodes from a server's address and port we ensure that independent
HAProxy instances will agree on routing decisions. If an address is not known
then the key is derived from the server's puid as it was previously.

When adjusting a server's weight, we now check whether the server's hash has
changed. If it has, we have to remove all its nodes first, since the node keys
will also have to change.
2024-04-02 07:00:10 +02:00
Amaury Denoyelle
da03396bb3 BUG/BUILD: debug: fix unused variable error
A compilation error occurs when using DEBUG_MEM_STATS due to a variable
now being unused in debug_iohandler_memstats() :

src/debug.c: In function ‘debug_iohandler_memstats’:
src/debug.c:1862:24: error: unused variable ‘sc’ [-Werror=unused-variable]
 1862 |         struct stconn *sc = appctx_sc(appctx);
      |                        ^~

This is caused since the following commit :
  94b8ed446f70a381dde0ea2dc891b62fcc3cc8e1
  MEDIUM: cli/applet: Stop to test opposite SC in I/O handler of CLI commands

This must not be backported.
2024-03-29 17:21:04 +01:00
Aurelien DARRAGON
3c6dfa618a MEDIUM: log/balance: leverage lbprm api for log load-balancing
log load-balancing implementation was not seamlessly integrated within
lbprm API. The consequence is that it could become harder to maintain
over time since it added some specific cases just for the log backend.
Moreover, it resulted in some code duplication since balance algorithms
that are common to logs and regular (tcp, http) backends were specifically
rewritten for log backends.

Thanks to the previous commit, we now have all the prerequisites to make
log load-balancing fully leverage lbprm logic. Thus in this patch we make
__do_send_log_backend() use existing lbprm algorithms, and we no longer
require log-specific lbprm initialization in cfgparse.c and in
postcheck_log_backend().

As a bonus, for log backends this allows weighed algorithms to properly
support weights (ie: roundrobin, random and log-hash) since we now
leverage the same lb algorithms that we use for tcp/http backends
(doc was updated).
2024-03-29 17:08:37 +01:00
Aurelien DARRAGON
9aea6df81f MINOR: lbprm: implement true "sticky" balance algo
As previously mentioned in cd352c0db ("MINOR: log/balance: rename
"log-sticky" to "sticky""), let's define a sticky algorithm that may be
used from any protocol. Sticky algorithm sticks on the same server as
long as it remains available.

The documentation was updated accordingly.
2024-03-29 17:08:37 +01:00
Aurelien DARRAGON
d0692d7019 BUG/MINOR: log/balance: detect if user tries to use unsupported algo
b61147fd ("MEDIUM: log/balance: merge tcp/http algo with log ones")
introduced some ambiguities, because while it shares some algos with the
ones from mode {tcp,http}, we forgot report an error when the user tries
to use an algorithm that is not available in this mode (as per the doc).

Because of that, haproxy would silently drop log messages during runtime.

To fix that, we ensure that algo is one of the supported ones during log
backend postparsing. If the algo is not supported, we raise an error.

This should be backported in 2.9 with b61147fd
2024-03-29 17:08:36 +01:00
Aurelien DARRAGON
d9f42e19f4 DOC: config: balance 'first' not usable in LOG mode
b61147fd ("MEDIUM: log/balance: merge tcp/http algo with log ones")
introduced an ambiguity because 'first' algorithm is not usable in
LOG mode but it was not specified in the doc.

This should be backported in 2.9 with b61147fd.
2024-03-29 17:08:36 +01:00
Christopher Faulet
87426e82ec MAJOR: cli: Use a custom .snd_buf function to only copy the current command
The CLI applet is now using its own snd_buf callback function. Instead of
copying as most output data as possible, only one command is copied at a
time.

To do so, a new state CLI_ST_PARSEREQ is added for the CLI applet. In this
state, the CLI I/O handle knows a full command was copied into its input
buffer and it must parse this command to evaluate it.
2024-03-28 17:32:55 +01:00
Christopher Faulet
838fb54de6 MINOR: stconn: Add a connection flag to notify sending data are the last ones
This flag can be use by endpoints to know the data to send, via .snd_buf
callback function are the last ones. It is useful to know a shutdown is
pending but it cannot be delivered while sedning data are not consumed.
2024-03-28 17:32:55 +01:00
Christopher Faulet
a933569b52 MINOR: applet: Let's applets .snd_buf function deal with full input buffers
It is now the responsbility of applets .snd_buf callback function to notify
the input buffer is full. This will allow the applets to not consume all
data waiting for more data. Of course, it is only useful for applets using a
custom .snd_buf callback function.
2024-03-28 17:32:55 +01:00
Christopher Faulet
f37ddbeb4b MAJOR: cli: Update the CLI applet to handle its own buffers
It is the third applet to be refactored to use its own buffers. In addition to
the CLI applet, some I/O handlers of CLI commands were also updated, especially
the stats ones.

Some command I/O handlers were updated to use applet's buffers instead of
channels ones.
2024-03-28 17:32:51 +01:00
Christopher Faulet
b8ca114031 BUG/MEDIUM: applet: State appctx have more data if its EOI/EOS/ERROR flag is set
It is an harmless bug for now because only stats and cache applets are using
their own buffers and it is not possible to trigger this bug with these
applets. However, it remains important to try a receive if EOI, EOS or ERROR
is reached by the applet while no data was produced. Otherwise, it is not
possible to ack these events at the SE level.

No backport needed.
2024-03-28 17:28:21 +01:00
Christopher Faulet
d2403a412c MINOR: applet: Always use applet API to set appctx flags
Some appctx flags were still set manually while there is a dedicated
function to do so. Be sure to always use applet_fl_set() to set appctx
flags.
2024-03-28 17:28:20 +01:00
Christopher Faulet
94b8ed446f MEDIUM: cli/applet: Stop to test opposite SC in I/O handler of CLI commands
The main CLI I/O handle is responsible to interrupt the processing on
shutdown/abort. It is not the responsibility of the I/O handler of CLI
commands to take care of it.
2024-03-28 17:28:20 +01:00
Christopher Faulet
2c6321842b MEDIUM: applet: Handle applets with their own buffers in put functions
applet_putchk() and other similar functions are now testing the applet's
type to use the applet's outbuf instead of the channel's buffer. This will
ease applets convertion because most of them relies on these functions.
2024-03-28 17:28:20 +01:00
Christopher Faulet
1380b97285 MEDIUM: buf: Add b_getline() and b_getdelim() functions
These functions are very similar to co_getline() and co_getdelim(). The
first one retrieves the longest part of the buffer that is composed
exclusively of characters not in the a delimiter set. The second one stops
on LF only and thus returns a line.
2024-03-28 17:28:20 +01:00
Christopher Faulet
2e6733eb45 MEDIUM: stream: Use generic version to perform sync receives and sends
Instead of using connection versions, we now use generic versions. It means
we will also perfom sync receives and sync sends on applets too, but only
for applets using their own buffers. Old applets are not concerned.
2024-03-28 17:28:20 +01:00
Christopher Faulet
5056cbdb86 MINOR: sc_strm: Add generic version to perform sync receives and sends
sc_sync_recv() and sc_sync_send() were added to use connection or applet
versions, depending on the endpoint type. For now these functions are not
used. But this will be used by process_stream() to replace the connection
version.
2024-03-28 17:28:20 +01:00
Christopher Faulet
498520fdf5 BUG/MINOR: cli: Report an error to user if command or payload is too big
Too big command, larger than a buffer, was silently rejected by the CLI
applet. It was handled as an error and the connection was closed, but no
error message was reported to user to notify him. Now an error is reported
before closing. It is only displayed if the chunk buffer used by the CLI
applet is full and no delimiter (\n or ;) is found to mark the end of the
command. It works for a simple command but also for a command with a huge
payload.

This patch could be backported to all stable versions.
2024-03-28 17:28:20 +01:00
Christopher Faulet
e91da1dd8e REGTESTS: Fix script about OCSP update compatibility tests
There were two occurrences of the seventh test. I don't know really why, but
this triggered a VTC error:

---- h7    Assert error in _assert_VSB_state(), lib/vsb.c line 104:  Condition((s->s_flags & 0x00020000) == state) not true.  Errno=0 Success

Renumbering tests fixes the script.
2024-03-28 17:23:53 +01:00
Amaury Denoyelle
6333e6ec8e MINOR: server: allow cookie for dynamic servers
This commit allows "cookie" keyword for dynamic servers. After code
review, nothing was found which could prevent a dynamic server to use
it. An extra warning is added under cli_parse_add_server() if cookie
value is ignored due to a non HTTP backend.

This patch is not considered a bugfix. However, it may backported if
needed as its impact seems minimal.
2024-03-28 11:54:21 +01:00
Damien Claisse
9a0e0d3a19 BUG/MINOR: server: fix persistence cookie for dynamic servers
When adding a server dynamically, we observe that when a backend has a
dynamic persistence cookie, the new server has no cookie as we receive
the following HTTP header:
set-cookie: test-cookie=; Expires=Thu, 01-Jan-1970 00:00:01 GMT; path=/
Whereas we were expecting to receive something like the following, which
is what we receive for a server added in the config file:
set-cookie: test-cookie=abcdef1234567890; path=/

After investigating code path, srv_set_dyncookie() is never called when
adding a server through CLI, it is only called when parsing config file
or using "set server bkd1/srv1 addr".

To fix this, call srv_set_dyncookie() inside cli_parse_add_server().

This patch must be backported up to 2.4.
2024-03-28 11:54:21 +01:00
Amaury Denoyelle
250c19032f BUG/MINOR: server: reject enabled for dynamic server
Since their first implementation, dynamic servers are created into
maintenance state. This has been done purposely to avoid immediate
activation of a newly inserted server.

However, this principle is incompatible if "enabled" keyword is used on
"add server". The newly created instance will be unreacheable as proxy
load-balancing algorithm is not informed of its presence via
srv_lb_propagate(). The new server could be unblocked by toggling its
state with "disable server" / "enable server" commands, which will
trigger srv_lb_propagate() invocation.

To avoid this unexpected state, simply forbid "enabled" keyword for
dynamic servers. In the long-term, it could be possible to re authorize
it but at least this requires to call srv_lb_propagate() on dynamic
server creation.

This should fix github issue #2497.

This patch should not be backported as-is, to avoid breaking dynamic
servers API on stable versions. "enabled" should instead be ignored for
them. This will be implemented in a dedicated patch on top of 2.9.
2024-03-28 11:51:05 +01:00
Remi Tricot-Le Breton
28dcb7bb64 REGTESTS: ssl: Add functional test for global ocsp-update option
Add tests for the 'tune.ssl.ocsp-update.mode' global option that can be
used to enable ocsp auto update on all certificates.
2024-03-27 11:38:28 +01:00
Remi Tricot-Le Breton
c42132b3d5 REGTESTS: ssl: Add OCSP update compatibility tests
Add tests that focus on the incompatibility checks on ocsp-update mode.
This test will only call "haproxy -c" on multiple configurations that
combine the crt-list 'ocsp-update' option and the global
'tune.ssl.ocsp-update.mode'.
2024-03-27 11:38:28 +01:00
Remi Tricot-Le Breton
7359c0c7f4 MEDIUM: ssl: Add 'tune.ssl.ocsp-update.mode' global option
This option can be used to set a default ocsp-update mode for all
certificates of a given conf file. It allows to activate ocsp-update on
certificates without the need to create separate crt-lists. It can still
be superseded by the crt-list 'ocsp-update' option. It takes either "on"
or "off" as value and defaults to "off".
Since setting this new parameter to "on" would mean that we try to
enable ocsp-update on any certificate, and also certificates that don't
have an OCSP URI, the checks performed in ssl_sock_load_ocsp were
softened. We don't systematically raise an error when trying to enable
ocsp-update on a certificate that does not have an OCSP URI, be it via
the global option or the crt-list one. We will still raise an error when
a user tries to load a certificate that does have an OCSP URI but a
missing issuer certificate (if ocsp-update is enabled).
2024-03-27 11:38:28 +01:00
Remi Tricot-Le Breton
b1d623949c BUG/MINOR: ssl: Detect more 'ocsp-update' incompatibilities
The inconsistencies in 'ocsp-update' parameter were only checked when
parsing a crt-list line so if a certificate was used on a bind line
after being used in a crt-list with 'ocsp-update' set to 'on', then no
error would be raised. This patch helps detect such inconsistencies.

This patch can be backported up to branch 2.8.
2024-03-27 11:38:28 +01:00
Remi Tricot-Le Breton
97c2734f44 BUG/MINOR: ssl: Wrong ocsp-update "incompatibility" error message
In a crt-list such as the following:
    foo.pem [ocsp-update off] foo.com
    foo.pem bar.com
we would get a wrong "Incompatibilities found in OCSP update mode ..."
error message during init when the two lines are actually saying the
same thing since the default for 'ocsp-update' option is 'off'.

This patch can be backported up to branch 2.8.
2024-03-27 11:38:28 +01:00
Willy Tarreau
9cf3d1fcc0 [RELEASE] Released version 3.0-dev6
Released version 3.0-dev6 with the following main changes :
    - MINOR: mux-h2: always use h2c_report_glitch()
    - MEDIUM: mux-h2: allow to set the glitches threshold to kill a connection
    - MINOR: quic: simplify rescheduling for handshake
    - MINOR: quic: remove qc_treat_rx_crypto_frms()
    - DOC: configuration: clarify ciphersuites usage (V2)
    - MINOR: tools: use public interface for FreeBSD get_exec_path()
    - BUG/MINOR: ssl: fix possible ctx memory leak in sample_conv_aes_gcm()
    - BUG/MINOR: ssl: do not set the aead_tag flags in sample_conv_aes_gcm()
    - BUG/MINOR: server: fix first server template not being indexed
    - MEDIUM: ssl: initialize the SSL stack explicitely
    - MEDIUM: ssl: allow to change the OpenSSL security level from global section
    - CLEANUP: ssl: remove useless #ifdef in openssl-compat.h
    - CI: github: add -DDEBUG_LIST to the default builds
    - BUG/MINOR: hlua: segfault when loading the same filter from different contexts
    - BUG/MINOR: hlua: missing lock in hlua_filter_new()
    - BUG/MINOR: hlua: fix missing lock in hlua_filter_delete()
    - DEBUG: lua: precisely identify if stream is stuck inside lua or not
    - MINOR: hlua: use accessors for stream hlua ctx
    - BUG/MEDIUM: hlua: streams don't support mixing lua-load with lua-load-per-thread (2nd try)
    - MINOR: debug: enable insecure fork on the command line
    - CI: github: add -dI to haproxy arguments
    - BUG/MINOR: listener: Wake proxy's mngmt task up if necessary on session release
    - BUG/MINOR: listener: Don't schedule frontend without task in listener_release()
    - MINOR: session: rename private conns elements
    - BUG/MAJOR: server: do not delete srv referenced by session
    - BUG/MEDIUM: spoe: Don't rely on stream's expiration to detect processing timeout
    - BUG/MINOR: spoe: Be sure to be able to quickly close IDLE applets on soft-stop
    - MAJOR: spoe: Deprecate the SPOE filter
    - MINOR: cfgparse: Add a global option to expose deprecated directives
    - MINOR: spoe: Add SPOE filters in the exposed deprecated directives
    - CLEANUP: assorted typo fixes in the code and comments
    - CI: temporarily adjust kernel entropy to work with ASAN/clang
    - BUG/MEDIUM: spoe: Return an invalid frame on recv if size is too small
    - BUG/MINOR: session: ensure conn owner is set after insert into session
    - BUG/MEDIUM: http_ana: ignore NTLM for reuse aggressive/always and no H1
    - BUG/MAJOR: connection: fix server used_conns with H2 + reuse safe
    - BUG/MAJOR: ocsp: Separate refcount per instance and per store
    - REGTESTS: ssl: Add OCSP related tests
    - BUG/MEDIUM: ssl: Fix crash when calling "update ssl ocsp-response" when an update is ongoing
    - BUG/MEDIUM: ssl: Fix crash in ocsp-update log function
    - MEDIUM: ssl: Change output of ocsp-update log
    - MINOR: ssl: Change level of ocsp-update logs
    - CLEANUP: ssl: Remove undocumented ocsp fetches
    - REGTESTS: ssl: Add checks on ocsp-update log format
    - MINOR: connection: implement conn_release()
    - MINOR: connection: extend takeover with release option
    - MEDIUM: server: close idle conn on server deletion
    - MEDIUM: mux: prepare for takeover on private connections
    - MEDIUM: server: close private idle connection before server deletion
    - BUG/MINOR: mux-quic: close all QCS before freeing QCC tasklet
    - BUG/MEDIUM: mux-fcgi: Properly handle EOM flag on end-of-trailers HTX block
    - BUILD: server: fix build regression on old compilers (<= gcc-4.4)
    - OPTIM: http_ext: avoid useless copy in http_7239_extract_{ipv4,ipv6}
    - MINOR: debug: add "debug dev trace" to flood with traces
    - MINOR: atomic: add a read-specific variant of __ha_cpu_relax()
    - MINOR: applet: add new function applet_append_line()
    - MINOR: log/applet: add new function syslog_applet_append_event()
    - MEDIUM: ring/sink: use applet_append_line()/syslog_applet_append_event() for readers
    - REORG: dns/ring: split the ring between the generic one and the DNS one
    - MEDIUM: ring: move the ring reader code to ring_dispatch_messages()
    - MEDIUM: sink: move the generic ring forwarder code use ring_dispatch_messages()
    - MEDIUM: log/sink: make the log forwarder code use ring_dispatch_messages()
    - MINOR: buf: add b_add_ofs() to add a count to an absolute position
    - MINOR: buf: add b_rel_ofs() to turn an absolute offset into a relative one
    - MINOR: buf: add b_putblk_ofs() to copy a block at a specific position
    - MINOR: buf: add b_getblk_ofs() that works relative to area and not head
    - MINOR: ring: make the ring reader use only absolute offsets
    - MINOR: ring: reserve one special value for the readers count
    - MINOR: vecpair: add new vector pair based data manipulation mechanisms
    - MINOR: vecpair: add necessary functions to use vecpairss from/to ring APIs
    - MINOR: ring: rename totlen vs msglen in ring_write()
    - MINOR: ring: add ring_data() to report the amount of data in a ring
    - MINOR: ring: add ring_size() to return the ring's size
    - MINOR: ring: add ring_dup() to copy a ring into another one
    - MINOR: ring: also add ring_area(), ring_head(), ring_tail()
    - MINOR: ring: make callers use ring_data() and ring_size(), not ring->buf
    - MINOR: errors: use ring_dup() to duplicate the startup_logs
    - MINOR: ring: use ring_size(), ring_area(), ring_head() and ring_tail()
    - MINOR: ring: add a flag to indicate a mapped file
    - MAJOR: ring: insert an intermediary ring_storage level
    - MINOR: ring: resize only under thread isolation
    - MINOR: ring: allow to reduce a ring size
    - MEDIUM: ring: replace the buffer API in ring_write() with the vec<->ring API
    - MEDIUM: ring: change the ring reader to use the new vector-based API now
    - MEDIUM: ring: remove the struct buffer from the ring
    - MEDIUM: ring: align the head and tail fields in the ring_storage structure
    - MINOR: ring: make the reader check the readers count before inc/dec
    - MEDIUM: ring: lock the tail's readers counters before proceeding with the changes
    - MEDIUM: ring: protect the reader's positions against writers
    - MEDIUM: ring: use the topmost bit of the tail as a lock
    - MEDIUM: move the ring's lock to only protect the readers list
    - MEDIUM: ring: unlock the ring's tail earlier
    - MINOR: ring: don't take the readers lock if there are no readers
    - MEDIUM: ring/applet: turn the wait_entry list to an mt_list instead
    - MEDIUM: ring: protect the initialization of the initial reader offset
    - MINOR: ring: make sure ring_dispatch waits when facing a changing message
    - MAJOR: ring: drop the now unneeded lock
    - OPTIM: ring: don't even try to update offset when failed to read
    - OPTIM: ring: have only one thread at a time wake up all readers
    - MINOR: ring: keep a few frequently used pointers in the local stack
    - MINOR: ring: add the definition of a ring waiting cell
    - MINOR: ring: make the number of queues configurable
    - MAJOR: ring: implement a waiting queue in front of the ring
    - MEDIUM: ring: significant boost in the loop by checking the ring queue ptr first
    - MEDIUM: ring: improve speed in the queue waiting loop on x86_64
    - MINOR: ring: simplify the write loop a little bit
    - CLEANUP: ring: further simplify the write loop
    - MINOR: ring: it's not x86 but all non-ARMv8.1 which needs the read before OR
    - MINOR: ring: avoid writes to cells during copy
    - OPTIM: ring: use relaxed stores to release the threads
    - CLEANUP: ring: use only curr_cell and not next_cell in the main write loop
    - BUILD: ssl: fix build error on older compilers with openssl-3.2
    - BUG/MINOR: server: 'source' interface ignored from 'default-server' directive
    - BUG/MAJOR: ring: free the ring storage not the ring itself when using maps
2024-03-26 15:36:49 +01:00
Willy Tarreau
40d1c84bf0 BUG/MAJOR: ring: free the ring storage not the ring itself when using maps
A recent issue was uncovered by the CI which started to randomly report
segfaults on a few tests, and more systematically on FreeBSD. It turn
out that it was introduced by recent commit 03816ccfa9 ("MAJOR: ring:
insert an intermediary ring_storage level"), which overlooked the munmap()
path of the sink and startup logs: once the ring and its storage were
split, it was no longer correct to munmap() the ring, only its storage
area needs to be unmapped, and the ring must always be freed separately.

Thanks to Christopher and William for their help at trying to reproduce
it and figure the circumstances that triggers it.

No backport is needed.
2024-03-26 15:15:59 +01:00
Aurelien DARRAGON
bd98db5078 BUG/MINOR: server: 'source' interface ignored from 'default-server' directive
Sebastien Gross reported that 'interface' keyword ('source' subargument)
is silently ignored when used from 'default-server' directive despite the
documentation implicitly stating that the keyword should be supported
there.

When support for 'source' keyword was added to 'default-server' directive
in dba97077 ("MINOR: server: Make 'default-server' support 'source'
keyword."), we properly duplicated the conn iface_name from the default-
server but we forgot to copy the conn iface_len which must be set as well
since it is used as setsockopt()'s 'optlen' argument in
tcp_connect_server().

It should be backported to all stable versions.
2024-03-26 11:09:02 +01:00
Willy Tarreau
2431b20640 BUILD: ssl: fix build error on older compilers with openssl-3.2
OpenSSL 3.2 triggers the code part added by commit 25da217 ("MINOR: ssl:
Update ssl_fc_curve/ssl_bc_curve to use SSL_get0_group_name") which
contains a variable declaration in the for() statement and breaks on
older compilers, as reported in GH issues #2501.

Let's just declare it normally to fix the problem. This must be
backported wherever the commit above is (at least 2.9).
2024-03-25 21:21:47 +01:00
Willy Tarreau
4bc81ec985 CLEANUP: ring: use only curr_cell and not next_cell in the main write loop
It turns out that we can reduce by one variable in the loop and this
clobbers one less register, making it slightly faster on Cortex A72.
2024-03-25 17:34:19 +00:00
Willy Tarreau
0a0a64ef02 OPTIM: ring: use relaxed stores to release the threads
We don't care in what order the threads are released, so we can write
their sent value using relaxed atomic stores. This brings a 3-5% perf
boost on ARM with 80 cores, reaching 7.25M/s, and doesn't change
anything on x86 since it keeps using strict ordering.
2024-03-25 17:34:19 +00:00
Willy Tarreau
cabe945876 MINOR: ring: avoid writes to cells during copy
It has been found that performing a first pass consisting in copying
all messages, and a second one to notify about releases is more efficient
on AMD than updating all of them on the fly using a CAS, despite making
writers wait longer to be released.

Maybe it's related to the ability for the CPU to prefetch the contents
during a simple load while it wouldn't do it for an XCHG, it's unsure
at this point. This will also mater permit to use relaxed stores to
release threads.

On ARM the performance increased to 7.0M/s. If this patch is applied
before the dropping of the intermediary step, instead it drops to
3.9M/s. This shows the dependency between such changes that strive to
limit the number of writes on the fast path.

On x86_64, the EPYC at 3C6T saw a small drop from 4.57M to 4.45M, but
the 24C48T setup saw a nice 33% boost from 3.33M to 4.44M, i.e. we
get stable perf at 3 and 24 cores, despite having 8 CCX involved and
fighting with each other.

Other possibilities are:
  - use of HA_ATOMIC_XCHG() instead of FETCH_OR()
    => slightly faster (4.62/7.37 vs 4.58/7.34). Pb: requires to
       modify the readers to wait much longer since the tail value
       won't be valid in this case during updates, and it will have
       to wait by looping over it.
  - use other conditions to release a cell
    => to be tested
2024-03-25 17:34:19 +00:00
Willy Tarreau
39df8c903d MINOR: ring: it's not x86 but all non-ARMv8.1 which needs the read before OR
Archs relying on CAS benefit from a read prior to FETCH_OR, so it's
not just x86 that benefits from this. Let's just change the condition
to only exclude __ARM_FEATURE_ATOMICS which is the only one faster
without.
2024-03-25 17:34:19 +00:00
Willy Tarreau
e6fc167aec CLEANUP: ring: further simplify the write loop
The loop was cleaned up a little bit so that the inner loops are more
readable and that the ifdef'd parts are whole blocks and not just an
"if" condition. A few conditions were adjusted to benefit from "break"
and "continue".
2024-03-25 17:34:19 +00:00
Willy Tarreau
4b984c5baa MINOR: ring: simplify the write loop a little bit
This is mostly a cleanup in that it turns the two-level loop into a
single one, but it also simplifies the code a little bit and brings
some performance savings again, which are mostly noticeable on ARM,
but don't change anything for x86.
2024-03-25 17:34:19 +00:00
Willy Tarreau
573bbbe127 MEDIUM: ring: improve speed in the queue waiting loop on x86_64
x86_64 doesn't have a native atomic FETCH_OR(), it's implemented using
a CAS, which will always cause a write cycle. Here we know we can just
wait as long as the lock bit is held so better loop on a load, and only
attempt the CAS on success. This requires a tiny ifdef and brings nice
benefits. This brings the performance back from 3.33M to 3.75M at 24C48T
while doing no change at 3C6T.
2024-03-25 17:34:19 +00:00
Willy Tarreau
30a659c355 MEDIUM: ring: significant boost in the loop by checking the ring queue ptr first
By doing that and placing the cpu_relax at the right places, the ARM
reaches 6.0M/s on 80 threads. On x86_64, at 3C6T the EPYC sees a small
increase from 4.45M to 4.57M but at 24C48T it sees a drop from 3.82M
to 3.33M due to the write contention hidden behind the CAS that
implements the FETCH_OR(), that we'll address next.
2024-03-25 17:34:19 +00:00