Hello,
I've tried to enable Quic/HTTP3 with HAProxy on Freebsd, but it seems that it is not properly working.
Haproxy daemon doesn't seems to answer to UDP/QUIC packets.
Here are some info of my setup.
The configuration wich allow to enable QUIC/HTTP/3 is there
When started, haproxy listen to UDP properly
The IP binding is a virtual IP (CARP).
But while receiving packet, haproxy does not answer and I can't see any debug log which could explain this behaviour.
At the client side, it is beeing seen as request timeout
I've check firewalling, also try to disable it without success.
Could you give hints to make it work properly ?
Many Thanks
Thomas
I've tried to enable Quic/HTTP3 with HAProxy on Freebsd, but it seems that it is not properly working.
Haproxy daemon doesn't seems to answer to UDP/QUIC packets.
Here are some info of my setup.
Code:
root@www1:~ # uname -a
FreeBSD www1.brozs.net 14.2-RELEASE-p1 FreeBSD 14.2-RELEASE-p1 GENERIC amd64
Code:
[root@www1:~ # pkg info | grep haproxy
haproxy-wolfssl-3.2.1 Reliable, high performance TCP/HTTP load balancer
Code:
root@www1:~ # haproxy -vv
HAProxy version 3.2.1-f4d1a4e 2025/06/11 - https://haproxy.org/
Status: long-term supported branch - will stop receiving fixes around Q2 2030.
Known bugs: http://www.haproxy.org/bugs/bugs-3.2.1.html
Running on: FreeBSD 14.2-RELEASE-p1 FreeBSD 14.2-RELEASE-p1 GENERIC amd64
Build options :
TARGET = freebsd
CC = cc
CFLAGS = -O2 -g -O2 -pipe -I/usr/local/include/wolfssl -fstack-protector-strong -fno-strict-aliasing -fwrapv -DFREEBSD_PORTS
OPTIONS = USE_GETADDRINFO=1 USE_OPENSSL_WOLFSSL=1 USE_ACCEPT4=1 USE_ZLIB=1 USE_CPU_AFFINITY=1 USE_TFO=1 USE_THREAD_DUMP=1 USE_QUIC=1 USE_PROMEX=1 USE_PCRE2=1 USE_PCRE2_JIT=1
DEBUG =
Feature list : -51DEGREES +ACCEPT4 -BACKTRACE +CLOSEFROM +CPU_AFFINITY -CRYPT_H -DEVICEATLAS -DL -ENGINE -EPOLL -EVPORTS +GETADDRINFO +KQUEUE -LIBATOMIC +LIBCRYPT -LINUX_CAP -LINUX_SPLICE -LINUX_TPROXY -LUA -MATH -MEMORY_PROFILING -NETFILTER -NS -OBSOLETE_LINKER +OPENSSL -OPENSSL_AWSLC +OPENSSL_WOLFSSL -OT -PCRE +PCRE2 +PCRE2_JIT -PCRE_JIT +POLL -PRCTL +PROCCTL +PROMEX -PTHREAD_EMULATION +QUIC -QUIC_OPENSSL_COMPAT -RT -SLZ +SSL -STATIC_PCRE -STATIC_PCRE2 +TFO +THREAD +THREAD_DUMP +TPROXY -WURFL +ZLIB
Default settings :
bufsize = 16384, maxrewrite = 1024, maxpollevents = 200
Built with multi-threading support (MAX_TGROUPS=32, MAX_THREADS=1024, default=4).
Built with SSL library version : wolfSSL 5.8.0
Running on SSL library version : wolfSSL 5.8.0
SSL library supports TLS extensions : yes
SSL library supports SNI : yes
SSL library FIPS mode : no
SSL library supports : SSLv3 TLSv1.0 TLSv1.1 TLSv1.2 TLSv1.3
QUIC: connection socket-owner mode support : no
QUIC: GSO emission support : no
Built with the Prometheus exporter as a service
Built with zlib version : 1.3.1
Running on zlib version : 1.3.1
Compression algorithms supported : identity("identity"), deflate("deflate"), raw-deflate("deflate"), gzip("gzip")
Built with transparent proxy support using: IP_BINDANY IPV6_BINDANY
Built with PCRE2 version : 10.45 2025-02-05
PCRE2 library supports JIT : yes
Encrypted password support via crypt(3): yes
Built with clang compiler version 18.1.6 (https://github.com/llvm/llvm-project.git llvmorg-18.1.6-0-g1118c2e05e67)
Available polling systems :
kqueue : pref=300, test result OK
poll : pref=200, test result OK
select : pref=150, test result OK
Total: 3 (3 usable), will use kqueue.
Available multiplexer protocols :
(protocols marked as <default> cannot be specified using 'proto' keyword)
quic : mode=HTTP side=FE mux=QUIC flags=HTX|NO_UPG|FRAMED
h2 : mode=HTTP side=FE|BE mux=H2 flags=HTX|HOL_RISK|NO_UPG
h1 : mode=HTTP side=FE|BE mux=H1 flags=HTX|NO_UPG
<default> : mode=HTTP side=FE|BE mux=H1 flags=HTX
fcgi : mode=HTTP side=BE mux=FCGI flags=HTX|HOL_RISK|NO_UPG
spop : mode=SPOP side=BE mux=SPOP flags=HOL_RISK|NO_UPG
<default> : mode=SPOP side=BE mux=SPOP flags=HOL_RISK|NO_UPG
none : mode=TCP side=FE|BE mux=PASS flags=NO_UPG
<default> : mode=TCP side=FE|BE mux=PASS flags=
Available services : prometheus-exporter
Available filters :
[BWLIM] bwlim-in
[BWLIM] bwlim-out
[CACHE] cache
[COMP] compression
[FCGI] fcgi-app
[SPOE] spoe
[TRACE] trace
The configuration wich allow to enable QUIC/HTTP/3 is there
Code:
frontend fe_main
mode http
capture request header User-Agent len 64
option forwardfor
bind X.Y.Z.W:443 ssl crt /usr/local/etc/ssl/certs/haproxy.pem alpn h2
bind quic4@X.Y.Z.W:443 ssl crt /usr/local/etc/ssl/certs/haproxy.pem alpn h3
.....
use_backend %[req.hdr(Host),lower]
http-after-response add-header alt-svc 'h3=":443"; ma=60'
When started, haproxy listen to UDP properly
Code:
root@www1:~ # sockstat | grep haproxy | grep udp4
www haproxy 54862 5 udp4 X.Y.Z.W:443 *:*
The IP binding is a virtual IP (CARP).
But while receiving packet, haproxy does not answer and I can't see any debug log which could explain this behaviour.
Code:
root@www1:~ # tcpdump -n -i vlan2401 host A.B.C.D and port 443 and proto 17
tcpdump: verbose output suppressed, use -v[v]... for full protocol decode
listening on vlan2401, link-type EN10MB (Ethernet), snapshot length 262144 bytes
08:11:26.159336 IP A.B.C.D.14190 > X.Y.Z.W.443: UDP, length 1200
08:11:27.159528 IP A.B.C.D.14190 > X.Y.Z.W.443: UDP, length 1200
08:11:29.158788 IP A.B.C.D.14190 > X.Y.Z.W.443: UDP, length 1200
08:11:33.156193 IP A.B.C.D.14190 > X.Y.Z.W.443: UDP, length 1200
At the client side, it is beeing seen as request timeout
Code:
tom@vm-debian-3:~$ ./curl -v -sI --http3-only https://www.example.net
* Host www.example.net:443 was resolved.
* IPv6: (none)
* IPv4: X.Y.Z.W
* Trying X.Y.Z.W:443...
* CAfile: /etc/ssl/certs/ca-certificates.crt
* CApath: /etc/ssl/certs
* QUIC connection has been shut down
* QUIC connect to X.Y.Z.W port 443 failed: Could not connect to server
* Failed to connect to www.example.net port 443 after 30016 ms: Could not connect to server
* closing connection #0
I've check firewalling, also try to disable it without success.
Could you give hints to make it work properly ?
Many Thanks
Thomas