Hi,

HAProxy 1.9-dev2 was released on 2018/09/12. It added 199 new commits
after version 1.9-dev1.

Let's be clear about this one : it's mostly aimed at developers to resync
their ongoing work. We've changed a number of pretty sensitive stuff and
definitely expect to spot some interesting bugs starting with "this is
impossible" and ending with "I didn't remember we supported this". Warning
given :-)

Since 1.9-dev1, a number of additional changes were merged. This is always
a good sign, it indicates that the developers do not intend to significantly
modify their design anymore. We're still not close to a release though, but
the steady efforts are paying off.

Among the recent changes (forgive me if I forget anyone) that should be
user-visible, I can list :
  - removal of the synchronization point for a thinner rendez-vous point.
    This is used to propagate server status changes. It used to induce a
    huge CPU consumption on all threads when servers were changing very
    often. Now we don't need to wake the sleeping threads up anymore so
    the health checks are much less noticeable.

  - added support for the new keyword "proto" on "bind" and "server" lines.
    This permits to force the application level protocol (which normally is
    negociated via ALPN). We temporarily use it to develop the new HTTP/1
    mux and it is also useful to process clear-text HTTP/2. For example it
    is possible to strip TLS using front servers then forward this to a
    unique listener for HTTP processing.

  - the server queues used to be only ordered on request arrival time. Now
    they also support time priority offsets and classes. This means it is
    possible to decide among all the requests pending in a server queue
    which one will be picked first based on its priority. The classes are
    always considered first, which means that all requests in a low number
    class will be processed before any request in a high number class. Then
    the offsets can be enforced based on time, for example it's possible to
    enforce that requests matching this criterion will experience 250ms
    less queuing time than other requests. It can be useful to deliver
    javascript/CSS before images for example, or to boost premium level
    users compared to other ones.

  - a few new sample fetch functions were added to determine the number
    of available connections on a server or on a backend.

The rest is mostly infrastructure changes which are not (well should not
be) user-visible :
  - the logs can now be emitted without a stream. This will be required to
    emit logs from the muxes. The HTTP/2 mux now emits a few logs on some
    rare error cases.

  - make error captures work outside of a stream. The purpose is to be able
    to continue to capture bad messages at various protocol layers. Soon we
    should get the ability to capture invalid H2 frames and invalid HPACK
    sequences just like we used to do at the HTTP level. This will be needed
    to preserve this functionnality when HTTP/1 processing moves down to the
    mux. It could possibly even be used in other contexts (peers or SPOE
    maybe ?).

  - the error captures are now dynamically allocated. For now it remains
    simple but the purpose is to have the ability to keep only a limited
    number of captures (total and per proxy) in order to significantly
    reduce the memory usage for those with tens of thousands of backends,
    and at the same time to maintain several logs per proxy, and not just
    the last one for each direction.

  - the master-worker model has improve quite a bit. Now instead of using
    pipes between the master and the workers, it uses socket pairs. The
    goal here is to allow the master to better communicate with workers.
    More specifically, a second patch set introducing the support for
    communicating via socket pairs over UNIX sockets will be usable in
    conjunction with this, allowing the CLI to bounce from the master to
    the workers (not finished yet).

  - the HTTP definitions and semantics code were moved to a new file,
    http.c, which is version-agnostic. Thanks to this, proto_http.c now
    mostly deals with the analysers and sample processing. This is aimed
    at simplifying the porting of the existing code to the new model.

  - the new HTTP/1 parser that was implemented to convert HTTP/1 responses
    to HTTP/2 was completed so that it will be reusable by the upcoming
    HTTP/1 mux.

  - the connection scheduling was reworked to feature true async-I/O at
    every level : till now, when an upper layer wanted to send some data
    (let's say a response to a client), it had to enable data polling on
    the underlying conn_stream which itself requested polling of the FD
    in the fd_cache from the mux, resulting in this FD being seen as
    active and the send() callback to be called, and in turn the snd_buf()
    function of the data layer to be called to deliver the data to the
    lower level. It was an insane amount of round trips, especially for
    some protocols like H2 where the connection state is irrelevant to
    this. Now a direct snd_buf() attempt is performed, and if it fails,
    the caller is subscribed to the lower layer to be called when it
    becomes possible. This way only the required number of layers are
    crossed and woken up. It also allows to deliver more fine-grained
    information between them (e.g. use flags to filter on certain events).
    Due to the very long history of working in the previous way (since
    version 1.0), it would not be surprising if this change wakes up some
    long-burried zombie bugs. So any CLOSE_WAIT or CPU loop report would
    be welcome in this case.

There's also one initially announced feature which will probably not make
it in 1.9, it's the SSL certificate update from the CLI. After looking at
the impacts deeply with Emeric and William, we figured that the only way
to make it reliable and future-proof requires some non-trivial changes to
the way the certificates are currently indexed. It's not an enormous change
but one significant enough to require a full-time person for a few weeks,
so unless someone steps up and is autonomous enough on this one we'll have
to postpone. Likewise, the changes that William made to load certificates
and private keys from distinct files are supposedly mergeable but we have
to double-check before putting us into a dead-end.

Now the good news for those who have made the effort to read me till here
is that we'll increase the release rate to two releases per year. The
observation is that while the current model works reasonably fine, it's
extremely challenging to try to complete all the foundation changes before
starting to work on the promised features which entirely depend on them,
and once the release date approaches, we see pressure build up and heavy
conflicts starting to appear between various branches. Additionnally, we
all know that the vast majority of users test only after a release, causing
massive reports of issues at different layers just after the release. Last
but not least, distros which ship with a version tend to ship with an early
one which is not yet very stable, and this complicates their ability to
follow fixes.

So in order to improve the situation, we'll proceed differently : we'll
release a version around October-November like nowadays, and this version
will be focused on mostly technical stuff. Very often it will in fact
include some optmizations that were developed in the context of the
previous release but which were not dry enough to be merged. An example
of this could be the lockless fd_cache changes that were merged very early
in 1.9. And another release will happen around May for mostly functional
changes. These ones will be much more user-visible and will present a much
lower risk of regression. The May version will continue to be maintained
for a long time while the November version will be short-lived (around 1
year, mostly for advanced users).

As such, we'll release 1.9 as planned, around October-November depending
on how things go, and we'll emit a 2.0 around May with more user-visible
changes. 1.9 will stop getting fixes once 2.1 is released in November 2019,
but 2.0 will continue to be maintained. This means that distros should
definitely avoid to package odd releases (including 1.9) and should only
focus on even ones (starting with 2.0).

I also predict that with this improved model we'll start to see the
emergence of topic branches, which are merged once ready. It's will be less
problematic to skip a release because it will postpone a feature for only 6
months and not one year like now. This will cause less last-minute conflicts
between the various activities and should result in a better overall
stability in even versions, and a much smoother distributed development
cycle where it's even likely that different maintainers will be able to
emit development releases (specifically the technical ones which nobody
thinks about doing).

Now... back to the code ;-)

Willy

Please find the usual URLs below :
   Site index       : http://www.haproxy.org/
   Discourse        : http://discourse.haproxy.org/
   Sources          : http://www.haproxy.org/download/1.9/src/
   Git repository   : http://git.haproxy.org/git/haproxy.git/
   Git Web browsing : http://git.haproxy.org/?p=haproxy.git
   Changelog        : http://www.haproxy.org/download/1.9/src/CHANGELOG
   Cyril's HTML doc : http://cbonte.github.io/haproxy-dconv/

Willy
---
Complete changelog :
Baptiste Assmann (2):
      BUG/MEDIUM: dns/server: fix incomatibility between SRV resolution and 
server state file
      BUG/MINOR: dns: check and link servers' resolvers right after config 
parsing

Bertrand Jacquin (1):
      DOC: ssl: Use consistent naming for TLS protocols

Christopher Faulet (17):
      BUG/MINOR: buffers: Fix b_slow_realign when a buffer is realign without 
output
      MEDIUM: mux: Remove const on the buffer in mux->snd_buf()
      CLEANUP: backend: Move mux install to call it at only one place
      MINOR: conn_stream: add an tx buffer to the conn_stream
      MINOR: conn_stream: add cs_send() as a default snd_buf() function
      MINOR: backend: Try to find the best mux for outgoing connections
      MEDIUM: backend: don't rely on mux_pt_ops in connect_server()
      MINOR: mux: Add info about the supported side in alpn_mux_list structure
      MINOR: mux: Unlink ALPN and multiplexers to rather speak of mux protocols
      MINOR: mux: Print the list of existing mux protocols during HA startup
      BUG/MINOR: threads: Remove the unexisting lock label 
"UPDATED_SERVERS_LOCK"
      BUG/MEDIUM: stream_int: Don't check CO_FL_SOCK_RD_SH flag to trigger cs 
receive
      MINOR: mux: Change get_mux_proto to get an ist as parameter
      MINOR: mux: Improve the message with the list of existing mux protocols
      MINOR: mux/frontend: Add 'proto' keyword to force the mux protocol
      MINOR: mux/server: Add 'proto' keyword to force the multiplexer's protocol
      MEDIUM: mux: Use the mux protocol specified on bind/server lines

Cyril Bonté (2):
      BUG/MEDIUM: lua: socket timeouts are not applied
      BUG/MINOR: lua: fix extra 500ms added to socket timeouts

Emeric Brun (4):
      BUG/MINOR: ssl: empty connections reported as errors.
      BUG/MEDIUM: ssl: fix missing error loading a keytype cert from a bundle.
      BUG/MEDIUM: ssl: loading dh param from certifile causes unpredictable 
error.
      BUG/MINOR: map: fix map_regm with backref

Emmanuel Hocdet (1):
      BUG/MEDIUM: ECC cert should work with TLS < v1.2 and openssl >= 1.1.1

Frédéric Lécaille (9):
      REGTEST/MINOR: Missing mandatory "ignore_unknown_macro".
      REGTEST/MINOR: Add a new class of regression testing files.
      BUG/MINOR: lua: Bad HTTP client request duration.
      REGEST/MINOR: Add reg testing files.
      REGTEST/MINOR: Add a reg testing file for b406b87 commit.
      BUG/MAJOR: thread: lua: Wrong SSL context initialization.
      REGTEST/MINOR: Add a reg testing file for 3e60b11.
      REGTEST/MINOR: lua: Add reg testing files for 70d318c.
      BUG/MINOR: server: Crash when setting FQDN via CLI.

Jens Bissinger (1):
      DOC: Fix spelling error in configuration doc

Lukas Tribus (1):
      DOC: dns: explain set server ... fqdn requires resolver

Olivier Houchard (39):
      MINOR: connections: Make rcv_buf mandatory and nuke cs_recv().
      MINOR: connections: Move rxbuf from the conn_stream to the h2s.
      MINOR: connections: Get rid of txbuf.
      MINOR: tasks: Allow tasklet_wakeup() to wakeup a task.
      MINOR: connections/mux: Add the wait reason(s) to wait_list.
      MINOR: stream_interface: Don't use si_cs_send() as a task handler.
      MINOR: stream_interface: Give stream_interface its own wait_list.
      MINOR: mux_h2: Don't use h2_send() as a callback.
      MINOR: checks: Add event_srv_chk_io().
      BUG/MEDIUM: tasks: Don't insert in the global rqueue if nbthread == 1
      BUG/MEDIUM: sessions: Don't use t->state.
      MINOR: tasks: Don't special-case when nbthreads == 1
      MINOR: fd cache: And the thread_mask with all_threads_mask.
      BUG/MEDIUM: streams: Don't forget to remove the si from the wait list.
      BUG/MEDIUM: tasklets: Add the thread as active when waking a tasklet.
      BUG/MEDIUM: stream-int: Check if the conn_stream exist in si_cs_io_cb.
      BUG/MEDIUM: H2: Activate polling after successful h2_snd_buf().
      BUG/MEDIUM: stream_interface: Call the wake callback after sending.
      BUG/MEDIUM: hlua: Make sure we drain the output buffer when done.
      MINOR: checks: Call wake_srv_chk() when we can finally send data.
      BUG/MEDIUM: stream_interface: try to call si_cs_send() earlier.
      BUG/MEDIUM: hlua: Don't call RESET_SAFE_LJMP if SET_SAFE_LJMP returns 0.
      MINOR: log: One const should be enough.
      BUG/MAJOR: kqueue: Don't reset the changes number by accident.
      BUG/MEDIUM: tasks: Don't forget to decrement task_list_size in 
tasklet_free().
      MEDIUM: connections: Don't reset the polling flags in conn_fd_handler().
      MEDIUM: connections/mux: Add a recv and a send+recv wait list.
      MEDIUM: connections: Get rid of the recv() method.
      MINOR: h2: Let user of h2_recv() and h2_send() know xfer has been done.
      MEDIUM: h2: always subscribe to receive if allowed.
      MEDIUM: h2: Don't use a wake() method anymore.
      MEDIUM: stream_interface: Make recv() subscribe when more data is needed.
      MINOR: connections: Add a "handle" field to wait_list.
      MEDIUM: mux_h2: Revamp the send path when blocking.
      MEDIUM: stream_interfaces: Starts receiving from the upper layers.
      MINOR: checks: Give checks their own wait_list.
      MINOR: conn_streams: Remove wait_list from conn_streams.
      BUG/MEDIUM: h2: Don't forget to empty the wait lists on destroy.
      BUG/MEDIUM: h2: Don't forget to set recv_wait_list to NULL in h2_detach.

Patrick Hemmer (9):
      MINOR: stream: rename {srv,prx}_queue_size to *_queue_pos
      MINOR: queue: store the queue index in the stream when enqueuing
      MINOR: queue: replace the linked list with a tree
      MEDIUM: add set-priority-class and set-priority-offset
      MEDIUM: queue: adjust position based on priority-class and priority-offset
      DOC: add documentation for prio_class and prio_offset sample fetches.
      BUG/MEDIUM: lua: reset lua transaction between http requests
      MINOR: add be_conn_free sample fetch
      MINOR: Add srv_conn_free sample fetch

William Lallemand (17):
      MEDIUM: mworker: remove register/unregister signal functions
      MEDIUM: mworker: use the haproxy poll loop
      BUG/MINOR: mworker: no need to stop peers for each proxy
      MINOR: mworker: mworker_cleanlisteners() delete the listeners
      MEDIUM: mworker: block SIGCHLD until the master is ready
      MEDIUM: mworker: never block SIG{TERM,INT} during reload
      MEDIUM: startup: unify signal init between daemon and mworker mode
      MINOR: mworker: don't deinit the poller fd when in wait mode
      MEDIUM: mworker: master wait mode use its own initialization
      MEDIUM: mworker: replace the master pipe by socketpairs
      MINOR: mworker: keep and clean the listeners
      MEDIUM: threads: close the thread-waker pipe during deinit
      MEDIUM: mworker: call per_thread deinit in mworker_reload()
      MEDIUM: protocol: use a custom AF_MAX to help protocol parser
      MEDIUM: protocol: sockpair protocol
      TESTS: add a python wrapper for sockpair@
      BUILD: fix build without thread

Willy Tarreau (96):
      BUG/MEDIUM: threads: fix the no-thread case after the change to the sync 
point
      BUG/MEDIUM: servers: check the queues once enabling a server
      BUG/MEDIUM: queue: prevent a backup server from draining the proxy's 
connections
      MEDIUM: checks: use the new rendez-vous point to spread check result
      MEDIUM: haproxy: don't use sync_poll_loop() anymore in the main loop
      MINOR: threads: remove the previous synchronization point
      MAJOR: server: make server state changes synchronous again
      CLEANUP: server: remove the update list and the update lock
      BUG/MEDIUM: connection/mux: take care of serverless proxies
      MINOR: queue: make sure the pendconn is released before logging
      DOC: update the roadmap about priority queues
      DOC: update the layering design notes
      BUG/MEDIUM: server: update our local state before propagating changes
      BUG/MEDIUM: cli/threads: protect all "proxy" commands against concurrent 
updates
      DOC: server/threads: document which functions need to be called 
with/without locks
      BUG/MEDIUM: cli/threads: protect some server commands against concurrent 
operations
      BUG/MAJOR: queue/threads: make pendconn_redistribute not lock the server
      BUG/MEDIUM: connection: don't forget to always delete the list's head
      BUG/MEDIUM: lb/threads: always properly lock LB algorithms on maintenance 
operations
      BUG/MEDIUM: check/threads: do not involve the rendez-vous point for 
status updates
      BUG/MINOR: chunks: do not store -1 into chunk_printf() in case of error
      BUG/MEDIUM: http: don't store exp_replace() result in the trash's length
      BUG/MEDIUM: http: don't store url_decode() result in the samples's length
      BUG/MEDIUM: dns: don't store dns_build_query() result in the trash's 
length
      BUG/MEDIUM: map: don't store exp_replace() result in the trash's length
      BUG/MEDIUM: connection: don't store recv() result into trash.data
      BUG/MEDIUM: cli/ssl: don't store base64dec() result in the trash's length
      MINOR: chunk: remove impossible tests on negative chunk->data
      MINOR: sample: remove impossible tests on negative smp->data.u.str.data
      BUG/MEDIUM: unix: provide a ->drain() function
      MINOR: connection: make conn_sock_drain() work for all socket families
      BUG/MEDIUM: mux_pt: dereference the connection with care in mux_pt_wake()
      MINOR: tools: make date2str_log() take some consts
      MINOR: thread: implement HA_ATOMIC_XADD()
      BUG/MINOR: stream: use atomic increments for the request counter
      BUG/MEDIUM: session: fix reporting of handshake processing time in the 
logs
      BUG/MEDIUM: h2: fix risk of memory leak on malformated wrapped frames
      BUG/MAJOR: buffer: fix incorrect check in __b_putblk()
      MINOR: log: move the log code to sess_build_logline() to add extra 
arguments
      MINOR: log: make the backend fall back to the frontend when there's no 
stream
      MINOR: log: make sess_build_logline() not dereference a NULL stream for 
txn
      MINOR: log: don't unconditionally pick log info from s->logs
      CLEANUP: log: make the low_level lf_{ip,port,text,text_len} functions 
take consts
      MINOR: log: keep a copy of the backend connection early in 
sess_build_logline()
      MINOR: log: do not dereference a null stream to access captures
      MINOR: log: be sure not to dereference a null stream for a target
      MINOR: log: don't check the stream-int's conn_retries if the stream is 
NULL
      MINOR: log: use NULL for the unique_id if there is no stream
      MINOR: log: keep a copy of s->flags early to avoid a dereference
      MINOR: log: use zero as the request counter if there is no stream
      MEDIUM: log: make sess_build_logline() support being called with no stream
      MINOR: log: provide a function to emit a log for a session
      MEDIUM: h2: produce some logs on early errors that prevent streams from 
being created
      BUG/MINOR: h1: fix buffer shift after realignment
      MINOR: connection: make the initialization more consistent
      MINOR: connection: add new function conn_get_proxy()
      MINOR: connection: add new function conn_is_back()
      BUG/MINOR: http/threads: atomically increment the error snapshot ID
      MINOR: snapshot: restart on the event ID and not the stream ID
      MINOR: snapshot: split the error snapshots into common and proto-specific 
parts
      MEDIUM: snapshot: start to reorder the HTTP snapshot output a little bit
      MEDIUM: snapshot: implement a show() callback and use it for HTTP
      MINOR: proxy: add a new generic proxy_capture_error()
      MINOR: http: make the HTTP error capture rely on the generic proxy code
      MINOR: http: remove the pointer to the error snapshot in 
http_capture_bad_message()
      REORG: cli: move the "show errors" handler from http to proxy
      BUG/MEDIUM: snapshot: take the proxy's lock while dumping errors
      MEDIUM: snapshots: dynamically allocate the snapshots
      MEDIUM: snapshot: merge the captured data after the descriptor
      REORG: http: move the HTTP semantics definitions to http.h/http.c
      REORG: http: move http_get_path() to http.c
      REORG: http: move error codes production and processing to http.c
      REORG: http: move the log encoding tables to log.c
      REORG: http: move some header value processing functions to http.c
      BUG/MINOR: h2: report asynchronous end of stream on closed connections
      REORG: h1: create a new h1m_state
      MINOR: h1: add the restart offsets into struct h1m
      MINOR: h1: remove the unused states from h1m_state
      MINOR: h1: provide a distinct init() function for request and response
      MINOR: h1: add a message flag to indicate that a message carries a 
response
      MINOR: h2: make sure h1m->err_pos field is correct on chunk error
      MINOR: h1: properly pre-initialize err_pos to -2
      MINOR: mux_h2: replace the req,res h1 messages with a single h1 message
      MINOR: h2: pre-initialize h1m->err_pos to -1 on the output path
      MEDIUM: h1: consider err_pos before deciding to accept a header name or 
not
      MEDIUM: h1: make the parser support a pointer to a start line
      MEDIUM: h1: let the caller pass the initial parser's state
      MINOR: h1: make the message parser support a null <hdr> argument
      MEDIUM: h1: support partial message parsing
      MEDIUM: h1: remove the useless H1_MSG_BODY state
      MINOR: h2: store the HTTP status into the H2S, not the H1M
      MINOR: h1: remove the HTTP status from the H1M struct
      MEDIUM: h1: implement the request parser as well
      MINOR: h1: add H1_MF_TOLOWER to decide when to turn header names to lower 
case
      MINOR: connection: pass the proxy when creating a connection
      BUG/MAJOR: h2: reset the parser's state on mux buffer full

---

Reply via email to