summaryrefslogtreecommitdiffstats
path: root/reg-tests
diff options
context:
space:
mode:
Diffstat (limited to '')
-rw-r--r--reg-tests/cache/vary.vtc51
-rw-r--r--reg-tests/connection/h2_glitches.vtc8
-rw-r--r--reg-tests/connection/http_reuse_conn_hash.vtc67
-rw-r--r--reg-tests/connection/reverse_connect_full.vtc2
-rw-r--r--reg-tests/connection/reverse_server.vtc2
-rw-r--r--reg-tests/connection/reverse_server_name.vtc2
-rw-r--r--reg-tests/contrib/prometheus.vtc27
-rw-r--r--reg-tests/http-messaging/h1_host_normalization.vtc152
-rw-r--r--reg-tests/http-messaging/h1_request_target_validation.vtc111
-rw-r--r--reg-tests/http-messaging/truncated.vtc1
-rw-r--r--reg-tests/http-rules/acl_cli_spaces.vtc2
-rw-r--r--reg-tests/http-rules/http-err-fail.vtc84
-rw-r--r--reg-tests/http-rules/map_ordering.map2
-rw-r--r--reg-tests/http-rules/map_ordering.vtc18
-rw-r--r--reg-tests/sample_fetches/acl.vtc35
-rw-r--r--reg-tests/ssl/crt_store.vtc31
-rw-r--r--reg-tests/ssl/ocsp_auto_update.vtc468
-rw-r--r--reg-tests/ssl/ocsp_compat_check.vtc401
-rw-r--r--reg-tests/ssl/ocsp_update/multicert_both_certs.crt-list2
-rw-r--r--reg-tests/stats/sample-stats-file26
-rw-r--r--reg-tests/stats/stats-file.vtc35
-rw-r--r--reg-tests/webstats/missing-stats-fields.vtc2
22 files changed, 1376 insertions, 153 deletions
diff --git a/reg-tests/cache/vary.vtc b/reg-tests/cache/vary.vtc
index 6c8cedf..782a76c 100644
--- a/reg-tests/cache/vary.vtc
+++ b/reg-tests/cache/vary.vtc
@@ -91,6 +91,20 @@ server s1 {
-hdr "Content-Encoding: gzip" \
-bodylen 59
+ rxreq
+ expect req.url == "/origin-referer"
+ txresp -hdr "Vary: origin,referer" \
+ -hdr "Cache-Control: max-age=5" \
+ -hdr "Content-Encoding: gzip" \
+ -bodylen 60
+
+ rxreq
+ expect req.url == "/origin-referer"
+ txresp -hdr "Vary: origin,referer" \
+ -hdr "Cache-Control: max-age=5" \
+ -hdr "Content-Encoding: gzip" \
+ -bodylen 61
+
# Multiple Accept-Encoding headers
rxreq
expect req.url == "/multiple_headers"
@@ -366,6 +380,43 @@ client c1 -connect ${h1_fe_sock} {
expect resp.bodylen == 59
expect resp.http.X-Cache-Hit == 1
+ # Mixed Vary (origin + Referer)
+ txreq -url "/origin-referer" \
+ -hdr "Accept-Encoding: br, gzip" \
+ -hdr "Referer: referer" \
+ -hdr "Origin: origin"
+ rxresp
+ expect resp.status == 200
+ expect resp.bodylen == 60
+ expect resp.http.X-Cache-Hit == 0
+
+ txreq -url "/origin-referer" \
+ -hdr "Accept-Encoding: br, gzip" \
+ -hdr "Referer: referer" \
+ -hdr "Origin: origin"
+ rxresp
+ expect resp.status == 200
+ expect resp.bodylen == 60
+ expect resp.http.X-Cache-Hit == 1
+
+ txreq -url "/origin-referer" \
+ -hdr "Accept-Encoding: br, gzip" \
+ -hdr "Referer: other-referer" \
+ -hdr "Origin: other-origin"
+ rxresp
+ expect resp.status == 200
+ expect resp.bodylen == 61
+ expect resp.http.X-Cache-Hit == 0
+
+ txreq -url "/origin-referer" \
+ -hdr "Accept-Encoding: br, gzip" \
+ -hdr "Referer: other-referer" \
+ -hdr "Origin: other-origin"
+ rxresp
+ expect resp.status == 200
+ expect resp.bodylen == 61
+ expect resp.http.X-Cache-Hit == 1
+
# Multiple Accept-encoding headers
txreq -url "/multiple_headers" \
-hdr "Accept-Encoding: gzip" \
diff --git a/reg-tests/connection/h2_glitches.vtc b/reg-tests/connection/h2_glitches.vtc
index 39ec4d6..4f25164 100644
--- a/reg-tests/connection/h2_glitches.vtc
+++ b/reg-tests/connection/h2_glitches.vtc
@@ -11,7 +11,9 @@ haproxy hap -conf {
listen fe1
bind "fd@${fe1}" proto h2
- http-request return status 200 hdr x-glitches %[fc_glitches]
+ tcp-request session track-sc0 src
+ http-request return status 200 hdr x-glitches %[fc_glitches] hdr x-glitch-cnt %[sc0_glitch_cnt] hdr x-glitch-rate %[sc0_glitch_rate]
+ stick-table type ip size 10 store glitch_cnt,glitch_rate(1m)
} -start
# valid request: no glitch
@@ -73,6 +75,8 @@ client c2-path -connect ${hap_fe1_sock} {
rxresp
expect resp.status == 200
expect resp.http.x-glitches == 1
+ expect resp.http.x-glitch-cnt == 1
+ expect resp.http.x-glitch-rate == 1
} -run
} -run
@@ -104,5 +108,7 @@ client c3-scheme -connect ${hap_fe1_sock} {
rxresp
expect resp.status == 200
expect resp.http.x-glitches == 0
+ expect resp.http.x-glitch-cnt == 1
+ expect resp.http.x-glitch-rate == 1
} -run
} -run
diff --git a/reg-tests/connection/http_reuse_conn_hash.vtc b/reg-tests/connection/http_reuse_conn_hash.vtc
index 991e86f..d77f759 100644
--- a/reg-tests/connection/http_reuse_conn_hash.vtc
+++ b/reg-tests/connection/http_reuse_conn_hash.vtc
@@ -13,6 +13,16 @@ haproxy h1 -conf {
bind "fd@${feS_sni}"
server srv2 ${h1_feR_ssl_addr}:${h1_feR_ssl_port} ssl sni "req.hdr(x-sni)" verify none pool-low-conn 2
+ # pool-conn-name
+ listen sender-name
+ bind "fd@${feS_name}"
+ server srv2 ${h1_feR_addr}:${h1_feR_port} pool-conn-name "req.hdr(x-name)" pool-low-conn 2
+
+ # sni + pool-conn-name
+ listen sender-sni-name
+ bind "fd@${feS_sni_name}"
+ server srv2 ${h1_feR_ssl_addr}:${h1_feR_ssl_port} ssl sni "req.hdr(x-sni)" verify none pool-conn-name "req.hdr(x-name)" pool-low-conn 2
+
# set-dst
# specify dst1_addr for server, which should be identical to dst2_addr
# port is specified by the client in header x-dst-port
@@ -29,6 +39,7 @@ haproxy h1 -conf {
server srv2 ${h1_feR_proxy_addr}:${h1_feR_proxy_port} send-proxy pool-low-conn 2
listen receiver
+ bind "fd@${feR}"
bind "fd@${feR_ssl}" ssl crt ${testdir}/common.pem
bind "fd@${feR_proxy}" accept-proxy
http-request return status 200
@@ -72,6 +83,62 @@ client c_sni -connect ${h1_feS_sni_sock} {
expect resp.http.http_first_request == "0"
} -run
+client c_name -connect ${h1_feS_name_sock} {
+ # first request
+ txreq \
+ -hdr "x-name: www.custom.com"
+ rxresp
+ expect resp.http.http_first_request == "1"
+
+ # second request with same name, connection must be reused
+ txreq \
+ -hdr "x-name: www.custom.com"
+ rxresp
+ expect resp.http.http_first_request == "0"
+
+ # third request with a different name, a new connection must be used
+ txreq \
+ -hdr "x-name: www.custom2.com"
+ rxresp
+ expect resp.http.http_first_request == "1"
+
+ # fourth request, reuse name2
+ txreq \
+ -hdr "x-name: www.custom2.com"
+ rxresp
+ expect resp.http.http_first_request == "0"
+} -run
+
+client c_sni_name -connect ${h1_feS_sni_name_sock} {
+ # first request
+ txreq \
+ -hdr "x-sni: www.custom.com" \
+ -hdr "x-name: www.custom.com"
+ rxresp
+ expect resp.http.http_first_request == "1"
+
+ # second request with same name but different sni, connection must be reused
+ txreq \
+ -hdr "x-sni: www.custom2.com" \
+ -hdr "x-name: www.custom.com"
+ rxresp
+ expect resp.http.http_first_request == "0"
+
+ # third request with a different name, a new connection must be used
+ txreq \
+ -hdr "x-sni: www.custom2.com" \
+ -hdr "x-name: www.custom2.com"
+ rxresp
+ expect resp.http.http_first_request == "1"
+
+ # fourth request, reuse name2 with a new sni
+ txreq \
+ -hdr "x-sni: www.custom3.com" \
+ -hdr "x-name: www.custom2.com"
+ rxresp
+ expect resp.http.http_first_request == "0"
+} -run
+
# http-reuse with destination address
client c_dst1 -connect ${h1_feS_dst_sock} {
txreq \
diff --git a/reg-tests/connection/reverse_connect_full.vtc b/reg-tests/connection/reverse_connect_full.vtc
index 238831f..cc88382 100644
--- a/reg-tests/connection/reverse_connect_full.vtc
+++ b/reg-tests/connection/reverse_connect_full.vtc
@@ -1,7 +1,7 @@
varnishtest "Reverse connect full test"
feature ignore_unknown_macro
-#REQUIRE_VERSION=2.9
+feature cmd "$HAPROXY_PROGRAM -cc 'version_atleast(2.9-dev0)'"
server s1 {
rxreq
diff --git a/reg-tests/connection/reverse_server.vtc b/reg-tests/connection/reverse_server.vtc
index 50fe8ce..5cd77ca 100644
--- a/reg-tests/connection/reverse_server.vtc
+++ b/reg-tests/connection/reverse_server.vtc
@@ -1,7 +1,7 @@
varnishtest "Reverse server test"
feature ignore_unknown_macro
-#REQUIRE_VERSION=2.9
+feature cmd "$HAPROXY_PROGRAM -cc 'version_atleast(2.9-dev0)'"
barrier b1 cond 2
diff --git a/reg-tests/connection/reverse_server_name.vtc b/reg-tests/connection/reverse_server_name.vtc
index 0fd850f..3a24601 100644
--- a/reg-tests/connection/reverse_server_name.vtc
+++ b/reg-tests/connection/reverse_server_name.vtc
@@ -2,7 +2,7 @@ varnishtest "Reverse server with a name parameter test"
feature cmd "$HAPROXY_PROGRAM -cc 'feature(OPENSSL)'"
feature ignore_unknown_macro
-#REQUIRE_VERSION=2.9
+feature cmd "$HAPROXY_PROGRAM -cc 'version_atleast(2.9-dev0)'"
barrier b1 cond 2
diff --git a/reg-tests/contrib/prometheus.vtc b/reg-tests/contrib/prometheus.vtc
index a481240..89d65d7 100644
--- a/reg-tests/contrib/prometheus.vtc
+++ b/reg-tests/contrib/prometheus.vtc
@@ -1,6 +1,6 @@
varnishtest "prometheus exporter test"
-#REQUIRE_VERSION=2.4
+feature cmd "$HAPROXY_PROGRAM -cc 'version_atleast(3.0-dev0)'"
#REQUIRE_SERVICES=prometheus-exporter
feature ignore_unknown_macro
@@ -39,9 +39,9 @@ haproxy h1 -conf {
} -start
client c1 -connect ${h1_stats_sock} {
+ # test general metrics
txreq -url "/metrics"
rxresp
- # test general metrics
expect resp.status == 200
expect resp.body ~ ".*haproxy_process.*"
expect resp.body ~ ".*haproxy_frontend.*"
@@ -49,8 +49,20 @@ client c1 -connect ${h1_stats_sock} {
expect resp.body ~ ".*haproxy_backend.*"
expect resp.body ~ ".*haproxy_server.*"
expect resp.body ~ ".*haproxy_sticktable.*"
+ expect resp.body ~ ".*haproxy_resolver.*"
+
+ # test well known labels presence
+ expect resp.body ~ ".*haproxy_process_build_info{version=\".*\"} 1.*"
+ expect resp.body ~ ".*haproxy_frontend_http_responses_total{proxy=\"stats\",code=\"4xx\"} 0.*"
+ expect resp.body ~ ".*haproxy_frontend_status{proxy=\"fe\",state=\"UP\"} 1.*"
+ expect resp.body ~ ".*haproxy_listener_status{proxy=\"stats\",listener=\"sock-1\",state=\"WAITING\"} 0.*"
+ expect resp.body ~ ".*haproxy_backend_status{proxy=\"be\",state=\"UP\"} 1.*"
+ expect resp.body ~ ".*haproxy_server_status{proxy=\"be\",server=\"s1\",state=\"DOWN\"} 0.*"
+ expect resp.body ~ ".*haproxy_server_check_status{proxy=\"be\",server=\"s2\",state=\"HANA\"} 0.*"
# test expected NaN values
+ txreq -url "/metrics?scope=backend&scope=server"
+ rxresp
expect resp.body ~ ".*haproxy_server_check_failures_total{proxy=\"be\",server=\"s1\"} NaN.*"
expect resp.body ~ ".*haproxy_server_check_up_down_total{proxy=\"be\",server=\"s1\"} NaN.*"
expect resp.body ~ ".*haproxy_server_check_failures_total{proxy=\"be\",server=\"s2\"} 0.*"
@@ -72,15 +84,6 @@ client c1 -connect ${h1_stats_sock} {
expect resp.body ~ ".*haproxy_server_idle_connections_limit{proxy=\"be\",server=\"s1\"} NaN.*"
expect resp.body ~ ".*haproxy_server_idle_connections_limit{proxy=\"be\",server=\"s2\"} 42.*"
- # test well known labels presence
- expect resp.body ~ ".*haproxy_process_build_info{version=\".*\"} 1.*"
- expect resp.body ~ ".*haproxy_frontend_http_responses_total{proxy=\"stats\",code=\"4xx\"} 0.*"
- expect resp.body ~ ".*haproxy_frontend_status{proxy=\"fe\",state=\"UP\"} 1.*"
- expect resp.body ~ ".*haproxy_listener_status{proxy=\"stats\",listener=\"sock-1\",state=\"WAITING\"} 0.*"
- expect resp.body ~ ".*haproxy_backend_status{proxy=\"be\",state=\"UP\"} 1.*"
- expect resp.body ~ ".*haproxy_server_status{proxy=\"be\",server=\"s1\",state=\"DOWN\"} 0.*"
- expect resp.body ~ ".*haproxy_server_check_status{proxy=\"be\",server=\"s2\",state=\"HANA\"} 0.*"
-
# test scope
txreq -url "/metrics?scope="
rxresp
@@ -96,6 +99,7 @@ client c1 -connect ${h1_stats_sock} {
expect resp.body !~ ".*haproxy_backend.*"
expect resp.body ~ ".*haproxy_server.*"
expect resp.body !~ ".*haproxy_sticktable.*"
+ expect resp.body !~ ".*haproxy_resolver.*"
txreq -url "/metrics?scope=frontend&scope=backend"
rxresp
@@ -106,6 +110,7 @@ client c1 -connect ${h1_stats_sock} {
expect resp.body ~ ".*haproxy_backend.*"
expect resp.body !~ ".*haproxy_server.*"
expect resp.body !~ ".*haproxy_sticktable.*"
+ expect resp.body !~ ".*haproxy_resolver.*"
txreq -url "/metrics?scope"
rxresp
diff --git a/reg-tests/http-messaging/h1_host_normalization.vtc b/reg-tests/http-messaging/h1_host_normalization.vtc
index 48174b8..909d525 100644
--- a/reg-tests/http-messaging/h1_host_normalization.vtc
+++ b/reg-tests/http-messaging/h1_host_normalization.vtc
@@ -175,22 +175,62 @@ syslog S1 -level info {
# C32
recv
- expect ~ "^.* uri: GET http:// HTTP/1.1; host: {}$"
+ expect ~ "^.* uri: GET http:/// HTTP/1.1; host: {}$"
barrier b1 sync
# C33
recv
- expect ~ "^.* uri: GET https:// HTTP/1.1; host: {}$"
+ expect ~ "^.* uri: GET https:/// HTTP/1.1; host: {}$"
barrier b1 sync
# C34
recv
- expect ~ "^.* uri: GET http:// HTTP/1.1; host: {}$"
+ expect ~ "^.* uri: GET http:/// HTTP/1.1; host: {}$"
barrier b1 sync
# C35
recv
- expect ~ "^.* uri: GET https:// HTTP/1.1; host: {}$"
+ expect ~ "^.* uri: GET https:/// HTTP/1.1; host: {}$"
+ barrier b1 sync
+
+ # C36
+ recv
+ expect ~ "^.* uri: GET http://hostname/ HTTP/1.1; host: {hostname}$"
+ barrier b1 sync
+
+ # C37
+ recv
+ expect ~ "^.* uri: GET http://hostname/ HTTP/1.1; host: {hostname}$"
+ barrier b1 sync
+
+ # C38
+ recv
+ expect ~ "^.* uri: GET http://hostname/ HTTP/1.1; host: {hostname}$"
+ barrier b1 sync
+
+ # C39
+ recv
+ expect ~ "^.* uri: GET https://hostname/ HTTP/1.1; host: {hostname}$"
+ barrier b1 sync
+
+ # C40
+ recv
+ expect ~ "^.* uri: GET https://hostname/ HTTP/1.1; host: {hostname}$"
+ barrier b1 sync
+
+ # C41
+ recv
+ expect ~ "^.* uri: GET https://hostname/ HTTP/1.1; host: {hostname}$"
+ barrier b1 sync
+
+ # C42
+ recv
+ expect ~ "^.* uri: GET http://hostname:81/ HTTP/1.1; host: {hostname:81}$"
+ barrier b1 sync
+
+ # C43
+ recv
+ expect ~ "^.* uri: GET https://hostname:444/ HTTP/1.1; host: {hostname:444}$"
} -start
@@ -759,4 +799,108 @@ client c35 -connect ${h1_fe_sock} {
expect resp.status == 200
} -run
+# Wait matching on log message
+barrier b1 sync
+
+client c36 -connect ${h1_fe_sock} {
+ txreq \
+ -req "GET" \
+ -url "http://hostname" \
+ -hdr "host: hostname"
+
+ rxresp
+ expect resp.status == 200
+} -run
+
+# Wait matching on log message
+barrier b1 sync
+
+client c37 -connect ${h1_fe_sock} {
+ txreq \
+ -req "GET" \
+ -url "http://hostname:80" \
+ -hdr "host: hostname"
+
+ rxresp
+ expect resp.status == 200
+} -run
+
+# Wait matching on log message
+barrier b1 sync
+
+client c38 -connect ${h1_fe_sock} {
+ txreq \
+ -req "GET" \
+ -url "http://hostname:" \
+ -hdr "host: hostname"
+
+ rxresp
+ expect resp.status == 200
+} -run
+
+# Wait matching on log message
+barrier b1 sync
+
+client c39 -connect ${h1_fe_sock} {
+ txreq \
+ -req "GET" \
+ -url "https://hostname" \
+ -hdr "host: hostname"
+
+ rxresp
+ expect resp.status == 200
+} -run
+
+# Wait matching on log message
+barrier b1 sync
+
+client c40 -connect ${h1_fe_sock} {
+ txreq \
+ -req "GET" \
+ -url "https://hostname:443" \
+ -hdr "host: hostname"
+
+ rxresp
+ expect resp.status == 200
+} -run
+
+# Wait matching on log message
+barrier b1 sync
+
+client c41 -connect ${h1_fe_sock} {
+ txreq \
+ -req "GET" \
+ -url "https://hostname:" \
+ -hdr "host: hostname"
+
+ rxresp
+ expect resp.status == 200
+} -run
+
+# Wait matching on log message
+barrier b1 sync
+
+client c42 -connect ${h1_fe_sock} {
+ txreq \
+ -req "GET" \
+ -url "http://hostname:81" \
+ -hdr "host: hostname:81"
+
+ rxresp
+ expect resp.status == 200
+} -run
+
+# Wait matching on log message
+barrier b1 sync
+
+client c43 -connect ${h1_fe_sock} {
+ txreq \
+ -req "GET" \
+ -url "https://hostname:444" \
+ -hdr "host: hostname:444"
+
+ rxresp
+ expect resp.status == 200
+} -run
+
syslog S1 -wait
diff --git a/reg-tests/http-messaging/h1_request_target_validation.vtc b/reg-tests/http-messaging/h1_request_target_validation.vtc
new file mode 100644
index 0000000..63e194a
--- /dev/null
+++ b/reg-tests/http-messaging/h1_request_target_validation.vtc
@@ -0,0 +1,111 @@
+varnishtest "HTTP request tests: H1 request target parsing"
+
+feature ignore_unknown_macro
+
+#REQUIRE_VERSION=3.0
+
+haproxy h1 -conf {
+ global
+ # WT: limit false-positives causing "HTTP header incomplete" due to
+ # idle server connections being randomly used and randomly expiring
+ # under us.
+ tune.idle-pool.shared off
+
+ defaults
+ mode http
+ timeout connect "${HAPROXY_TEST_TIMEOUT-5s}"
+ timeout client "${HAPROXY_TEST_TIMEOUT-5s}"
+ timeout server "${HAPROXY_TEST_TIMEOUT-5s}"
+
+ listen li1
+ bind "fd@${li1}"
+ http-request return status 200
+} -start
+
+client c1 -connect ${h1_li1_sock} {
+ txreq -req "OPTIONS" -url "*"
+ rxresp
+ expect resp.status == 200
+
+} -run
+
+client c2 -connect ${h1_li1_sock} {
+ txreq -req "OPTIONS" -url "/"
+ rxresp
+ expect resp.status == 200
+
+} -run
+
+client c3 -connect ${h1_li1_sock} {
+ txreq -req "OPTIONS" -url "http://haproxy.org" \
+ -hdr "Host: haproxy.org"
+ rxresp
+ expect resp.status == 200
+
+} -run
+
+client c4 -connect ${h1_li1_sock} {
+ txreq -req "OPTIONS" -url "*/test"
+ rxresp
+ expect resp.status == 400
+} -run
+
+client c5 -connect ${h1_li1_sock} {
+ txreq -req "GET" -url "*"
+ rxresp
+ expect resp.status == 400
+} -run
+
+client c6 -connect ${h1_li1_sock} {
+ txreq -req "CONNECT" -url "haproxy.org:80" \
+ -hdr "Host: haproxy.org"
+ rxresp
+ expect resp.status == 200
+
+} -run
+
+client c7 -connect ${h1_li1_sock} {
+ txreq -req "CONNECT" -url "haproxy.org" \
+ -hdr "Host: haproxy.org"
+ rxresp
+ expect resp.status == 400
+} -run
+
+client c8 -connect ${h1_li1_sock} {
+ txreq -req "CONNECT" -url "/"
+ rxresp
+ expect resp.status == 400
+} -run
+
+client c9 -connect ${h1_li1_sock} {
+ txreq -req "CONNECT" -url "http://haproxy.org:80" \
+ -hdr "Host: haproxy.org"
+ rxresp
+ expect resp.status == 400
+} -run
+
+client c11 -connect ${h1_li1_sock} {
+ txreq -req "GET" -url "/" \
+ -hdr "Host: haproxy.org"
+ rxresp
+ expect resp.status == 200
+} -run
+
+client c12 -connect ${h1_li1_sock} {
+ txreq -req "GET" -url "haproxy.org:80" \
+ -hdr "Host: haproxy.org"
+ rxresp
+ expect resp.status == 400
+} -run
+
+client c13 -connect ${h1_li1_sock} {
+ txreq -req "GET" -url "admin"
+ rxresp
+ expect resp.status == 400
+} -run
+
+client c14 -connect ${h1_li1_sock} {
+ txreq -req "GET" -url "admin/a/b"
+ rxresp
+ expect resp.status == 400
+} -run
diff --git a/reg-tests/http-messaging/truncated.vtc b/reg-tests/http-messaging/truncated.vtc
index 7579f6d..7f262d7 100644
--- a/reg-tests/http-messaging/truncated.vtc
+++ b/reg-tests/http-messaging/truncated.vtc
@@ -1,5 +1,4 @@
varnishtest "HTTP response size tests: H2->H1 (HTX and legacy mode)"
-#REQUIRE_VERSION=1.9
feature ignore_unknown_macro
diff --git a/reg-tests/http-rules/acl_cli_spaces.vtc b/reg-tests/http-rules/acl_cli_spaces.vtc
index a554977..334133d 100644
--- a/reg-tests/http-rules/acl_cli_spaces.vtc
+++ b/reg-tests/http-rules/acl_cli_spaces.vtc
@@ -10,8 +10,6 @@ server s1 {
haproxy h1 -W -S -conf {
defaults
mode http
- log global
- option httplog
timeout connect "${HAPROXY_TEST_TIMEOUT-5s}"
timeout client "${HAPROXY_TEST_TIMEOUT-5s}"
timeout server "${HAPROXY_TEST_TIMEOUT-5s}"
diff --git a/reg-tests/http-rules/http-err-fail.vtc b/reg-tests/http-rules/http-err-fail.vtc
new file mode 100644
index 0000000..6d8f9ea
--- /dev/null
+++ b/reg-tests/http-rules/http-err-fail.vtc
@@ -0,0 +1,84 @@
+varnishtest "test for http-err-codes/http-fail-codes redefinitions"
+
+feature cmd "$HAPROXY_PROGRAM -cc 'version_atleast(3.0-dev1)'"
+feature ignore_unknown_macro
+
+server s2 {
+ rxreq
+ txresp -status 220
+} -start
+
+server s3 {
+ rxreq
+ txresp -status 300
+} -start
+
+server s4 {
+ rxreq
+ txresp -status 400
+} -start
+
+server s5 {
+ rxreq
+ txresp -status 555
+} -start
+
+
+haproxy h1 -conf {
+ global
+ http-err-codes 220 +300-499 -300-399 # only 220, 400-499 remain
+ http-fail-codes -550-580 +555,599,556-566
+
+ defaults
+ mode http
+ timeout connect "${HAPROXY_TEST_TIMEOUT-5s}"
+ timeout client "${HAPROXY_TEST_TIMEOUT-5s}"
+ timeout server "${HAPROXY_TEST_TIMEOUT-5s}"
+ option socket-stats
+
+ frontend fe
+ bind "fd@${fe}"
+ http-request track-sc0 path
+ http-after-response add-header x-table err=%[sc0_http_err_cnt],fail=%[sc0_http_fail_cnt]
+ stick-table type string size 100 store http_err_cnt,http_fail_cnt
+ default_backend be
+
+ backend be
+ use-server s2 if { path -m beg /2 }
+ use-server s3 if { path -m beg /3 }
+ use-server s4 if { path -m beg /4 }
+ use-server s5 if { path -m beg /5 }
+
+ server s2 ${s2_addr}:${s2_port}
+ server s3 ${s3_addr}:${s3_port}
+ server s4 ${s4_addr}:${s4_port}
+ server s5 ${s5_addr}:${s5_port}
+} -start
+
+client c2 -connect ${h1_fe_sock} {
+ txreq -url "/2"
+ rxresp
+ expect resp.status == 220
+ expect resp.http.x-table ~ "err=1,fail=0"
+} -run
+
+client c3 -connect ${h1_fe_sock} {
+ txreq -url "/3"
+ rxresp
+ expect resp.status == 300
+ expect resp.http.x-table ~ "err=0,fail=0"
+} -run
+
+client c4 -connect ${h1_fe_sock} {
+ txreq -url "/4"
+ rxresp
+ expect resp.status == 400
+ expect resp.http.x-table ~ "err=1,fail=0"
+} -run
+
+client c5 -connect ${h1_fe_sock} {
+ txreq -url "/5"
+ rxresp
+ expect resp.status == 555
+ expect resp.http.x-table ~ "err=0,fail=1"
+} -run
diff --git a/reg-tests/http-rules/map_ordering.map b/reg-tests/http-rules/map_ordering.map
index dcd9529..dc9ac71 100644
--- a/reg-tests/http-rules/map_ordering.map
+++ b/reg-tests/http-rules/map_ordering.map
@@ -2,3 +2,5 @@
first.domain.tld first
domain.tld domain
second.domain.tld second
+# This entry is used to test duplicate behavior (ie: tree-based match)
+first.domain.tld first_dup
diff --git a/reg-tests/http-rules/map_ordering.vtc b/reg-tests/http-rules/map_ordering.vtc
index 40da465..923d19f 100644
--- a/reg-tests/http-rules/map_ordering.vtc
+++ b/reg-tests/http-rules/map_ordering.vtc
@@ -1,4 +1,4 @@
-varnishtest "Test list-based matching types ordering"
+varnishtest "Ensure mapfile ordering is preserved when loading the file"
feature cmd "$HAPROXY_PROGRAM -cc 'version_atleast(2.5-dev0)'"
feature ignore_unknown_macro
@@ -14,9 +14,13 @@ haproxy h1 -conf {
# check list ordering using map_dom (list-based match)
http-request return hdr dom %[req.hdr(Host),lower,map_dom(${testdir}/map_ordering.map)] if { url_beg /dom }
+
+ # check tree ordering using map_str (tree-based match) and duplicated keys
+ http-request return hdr str %[req.hdr(Host),lower,map_str(${testdir}/map_ordering.map)] if { url_beg /str }
+
} -start
-# Check map ordering
+# Check map ordering for list-based matching types
client c1 -connect ${h1_fe1_sock} {
# first.domain.tld is above domain.tld so it should match first
txreq -url "/dom" -hdr "Host: first.domain.tld"
@@ -30,3 +34,13 @@ client c1 -connect ${h1_fe1_sock} {
expect resp.status == 200
expect resp.http.dom == "domain"
} -run
+
+# Check map ordering for tree-based matching types (check that the matching
+# key is the first one seen in the file)
+client c2 -connect ${h1_fe1_sock} {
+ # first.domain.tld is first mapped to "first" in the mapfile
+ txreq -url "/str" -hdr "Host: first.domain.tld"
+ rxresp
+ expect resp.status == 200
+ expect resp.http.str == "first"
+} -run
diff --git a/reg-tests/sample_fetches/acl.vtc b/reg-tests/sample_fetches/acl.vtc
new file mode 100644
index 0000000..905ae3e
--- /dev/null
+++ b/reg-tests/sample_fetches/acl.vtc
@@ -0,0 +1,35 @@
+varnishtest "Test acl() sample fetch"
+feature cmd "$HAPROXY_PROGRAM -cc 'version_atleast(2.9-dev2)'"
+
+feature ignore_unknown_macro
+
+haproxy h1 -conf {
+ defaults
+ mode http
+ timeout connect "${HAPROXY_TEST_TIMEOUT-5s}"
+ timeout client "${HAPROXY_TEST_TIMEOUT-5s}"
+ timeout server "${HAPROXY_TEST_TIMEOUT-5s}"
+
+ frontend fe1
+ bind "fd@${fe1}"
+
+ acl ACL1 always_true
+ acl ACL2 acl(ACL1)
+ acl ACL3 acl(!ACL2)
+ acl ACL4 acl(ACL2,!ACL3)
+
+ http-request return status 200 hdr x-acl "ACL1=%[acl(ACL1)] ACL2=%[acl(ACL2)] ACL3=%[acl(ACL3)] ACL4=%[acl(ACL4)] TRUE=%[acl(TRUE)]"
+
+ log-format ACL1=%[acl(ACL1)]
+} -start
+
+client c1 -connect ${h1_fe1_sock} {
+ txreq -req GET -url /
+ rxresp
+ expect resp.status == 200
+ expect resp.http.x-acl ~ "ACL1=1"
+ expect resp.http.x-acl ~ "ACL2=1"
+ expect resp.http.x-acl ~ "ACL3=0"
+ expect resp.http.x-acl ~ "ACL4=1"
+ expect resp.http.x-acl ~ "TRUE=1"
+} -run
diff --git a/reg-tests/ssl/crt_store.vtc b/reg-tests/ssl/crt_store.vtc
new file mode 100644
index 0000000..685183e
--- /dev/null
+++ b/reg-tests/ssl/crt_store.vtc
@@ -0,0 +1,31 @@
+#REGTEST_TYPE=devel
+varnishtest "Test the crt-store section"
+feature cmd "$HAPROXY_PROGRAM -cc 'version_atleast(3.0-dev7)'"
+feature cmd "$HAPROXY_PROGRAM -cc 'feature(OPENSSL)'"
+feature ignore_unknown_macro
+
+#
+# Basic check for the crt-store, ensure that loading works and that we can't
+# load a crt which was used before
+#
+
+
+haproxy h1 -arg -V -conf-OK {
+ crt-store
+ load crt "${testdir}/common.crt" key "${testdir}/common.key"
+
+ listen ssl-lst
+ bind "${tmpdir}/ssl.sock" ssl crt ${testdir}/common.crt strict-sni
+
+}
+
+haproxy h2 -arg -V -conf-BAD {} {
+
+ listen ssl-lst
+ bind "${tmpdir}/ssl.sock" ssl crt ${testdir}/common.pem strict-sni
+
+ crt-store
+ load crt "${testdir}/common.pem" key "${testdir}/common.key"
+
+}
+
diff --git a/reg-tests/ssl/ocsp_auto_update.vtc b/reg-tests/ssl/ocsp_auto_update.vtc
index a1d9a3c..0193953 100644
--- a/reg-tests/ssl/ocsp_auto_update.vtc
+++ b/reg-tests/ssl/ocsp_auto_update.vtc
@@ -1,4 +1,5 @@
#REGTEST_TYPE=slow
+# reg-test is around ~2.5s
# broken with BoringSSL.
@@ -14,29 +15,20 @@
# soon as possible by the update task.
#
# The ocsp responder used in all the tests will be an openssl using the
-# certificate database in ocsp_update/index.txt. It will listen on port 12346
-# which is not the same as the one specified in the certificates' OCSP URI
-# which point to port 12345. The link from port 12345 to port 12346 will be
-# ensured through HAProxy instances that will enable logs, later used as a
-# synchronization mean.
-#
-# Unfortunately some arbitrary "sleep" calls are still needed to leave some
-# time for the ocsp update task to actually process the ocsp responses and
-# reinsert them into the tree. This explains why the test's mode is set to
-# "slow".
-#
-# The fourth test case focuses on the "update ssl ocsp-response" CLI command
-# and tests two certificates that have a known OCSP response loaded during init
-# but no OCSP auto update. The only difference between the two certificates is
-# that one has a separate .issuer file while the other one has the issuer
-# certificate directly in the main .pem file.
+# certificate database in ocsp_update/index.txt. It will listen on port 12345
+# which was specified explicitly in the certificates used in the tests.
+# The synchronization will be based on the logs emitted by the OCSP update task
+# directly. When this log is created, we will know that the update was
+# effective and the updated OCSP response is loaded in the tree. So any
+# following call to "show ssl ocsp-response" will display the latest response
+# information.
#
# If this test does not work anymore:
# - Check that you have openssl and socat
varnishtest "Test the OCSP auto update feature"
-feature cmd "$HAPROXY_PROGRAM -cc 'version_atleast(2.7-dev0)'"
-feature cmd "$HAPROXY_PROGRAM -cc 'feature(OPENSSL) && !ssllib_name_startswith(BoringSSL) && openssl_version_atleast(1.1.1)'"
+feature cmd "$HAPROXY_PROGRAM -cc 'version_atleast(3.0-dev0)'"
+feature cmd "$HAPROXY_PROGRAM -cc 'feature(OPENSSL) && !ssllib_name_startswith(BoringSSL) && !ssllib_name_startswith(LibreSSL) && openssl_version_atleast(1.1.1)'"
feature cmd "command -v openssl && command -v socat"
feature ignore_unknown_macro
@@ -102,26 +94,23 @@ haproxy h1 -wait
# This test will focus on two separate certificates that have the same OCSP uri
# (http://ocsp.haproxy.com:12345) but no OCSP response loaded at build time.
# The update mode is set to 'on' in the two crt-lists used. The two ocsp
-# responses should then be fetched automatically after init. We use an http
-# listener as a rebound on which http log is enabled towards Syslog_http. This
-# ensures that two requests are sent by the ocsp auto update task and it
-# enables to use a barrier to synchronize the ocsp task and the subsequent cli
-# calls. Thanks to the barrier we know that when calling "show ssl
-# ocsp-response" on the cli, the two answers should already have been received
-# and processed.
+# responses should then be fetched automatically after init.
+# We rely on the OCSP logs to ensure that the two updates are over before
+# calling "show ssl ocsp-response". This is done through the Syslog_ocsp
+# listener and a dedicated barrier.
-process p1 "openssl ocsp -index ${testdir}/ocsp_update/index.txt -rsigner ${testdir}/ocsp_update/ocsp.haproxy.com.pem -CA ${testdir}/ocsp_update/ocsp_update_rootca.crt -nrequest 2 -ndays 1 -port 12346 -timeout 5" -start
+process p2 "openssl ocsp -index ${testdir}/ocsp_update/index.txt -rsigner ${testdir}/ocsp_update/ocsp.haproxy.com.pem -CA ${testdir}/ocsp_update/ocsp_update_rootca.crt -nrequest 2 -ndays 1 -port 12345 -timeout 5" -start
-barrier b1 cond 2 -cyclic
+barrier b2 cond 2 -cyclic
-syslog Syslog_http -level info {
+syslog Syslog_ocsp -level notice {
recv
- expect ~ "GET /MEMwQTA%2FMD0wOzAJBgUrDgMCGgUABBSKg%2BAGD6%2F3Ccp%2Bm5VSKi6BY1%2FaCgQU9lKw5DXV6pI4UVCPCtvpLYXeAHoCAhAV HTTP/1.1"
+ expect ~ "<OCSP-UPDATE> ${testdir}/ocsp_update/multicert_no_ocsp/server_ocsp_rsa.pem 1 \"Update successful\" 0 1"
recv
- expect ~ "GET /MEMwQTA%2FMD0wOzAJBgUrDgMCGgUABBSKg%2BAGD6%2F3Ccp%2Bm5VSKi6BY1%2FaCgQU9lKw5DXV6pI4UVCPCtvpLYXeAHoCAhAW HTTP/1.1"
+ expect ~ "<OCSP-UPDATE> ${testdir}/ocsp_update/multicert_no_ocsp/server_ocsp_ecdsa.pem 1 \"Update successful\" 0 1"
- barrier b1 sync
+ barrier b2 sync
} -start
haproxy h2 -conf {
@@ -130,6 +119,7 @@ haproxy h2 -conf {
tune.ssl.capture-buffer-size 1
stats socket "${tmpdir}/h2/stats" level admin
crt-base ${testdir}/ocsp_update
+ log ${Syslog_ocsp_addr}:${Syslog_ocsp_port} local0 notice notice
defaults
mode http
@@ -146,18 +136,9 @@ haproxy h2 -conf {
frontend ssl-ecdsa-fe
bind "${tmpdir}/ssl3.sock" ssl crt-list ${testdir}/ocsp_update/multicert_ecdsa.crt-list ca-file ${testdir}/set_cafile_rootCA.crt verify none crt-ignore-err all
http-request return status 200
-
- listen http_rebound_lst
- mode http
- option httplog
- log ${Syslog_http_addr}:${Syslog_http_port} local0
- bind "127.0.0.1:12345"
- server s1 "127.0.0.1:12346"
} -start
-barrier b1 sync
-
-shell "sleep 1"
+barrier b2 sync
# We should have two distinct ocsp IDs known that were loaded at build time and
# the responses' contents should have been filled automatically by the ocsp
@@ -176,7 +157,7 @@ haproxy h2 -cli {
}
haproxy h2 -wait
-process p1 -wait -expect-exit 0
+process p2 -wait -expect-exit 0
###################
@@ -189,15 +170,14 @@ process p1 -wait -expect-exit 0
# will not enable ocsp-update on its certificate. Only one request should then
# be sent.
-process p2 "openssl ocsp -index ${testdir}/ocsp_update/index.txt -rsigner ${testdir}/ocsp_update/ocsp.haproxy.com.pem -CA ${testdir}/ocsp_update/ocsp_update_rootca.crt -nrequest 1 -ndays 1 -port 12346 -timeout 5" -start
+process p3 "openssl ocsp -index ${testdir}/ocsp_update/index.txt -rsigner ${testdir}/ocsp_update/ocsp.haproxy.com.pem -CA ${testdir}/ocsp_update/ocsp_update_rootca.crt -nrequest 1 -ndays 1 -port 12345 -timeout 5" -start
-barrier b2 cond 2 -cyclic
+barrier b3 cond 2 -cyclic
-syslog Syslog_http2 -level info {
+syslog Syslog_ocsp3 -level notice {
recv
- expect ~ "GET /MEMwQTA%2FMD0wOzAJBgUrDgMCGgUABBSKg%2BAGD6%2F3Ccp%2Bm5VSKi6BY1%2FaCgQU9lKw5DXV6pI4UVCPCtvpLYXeAHoCAhAV HTTP/1.1"
-
- barrier b2 sync
+ expect ~ "<OCSP-UPDATE> ${testdir}/ocsp_update/multicert_no_ocsp/server_ocsp_rsa.pem 1 \"Update successful\" 0 1"
+ barrier b3 sync
} -start
haproxy h3 -conf {
@@ -206,6 +186,7 @@ haproxy h3 -conf {
tune.ssl.capture-buffer-size 1
stats socket "${tmpdir}/h3/stats" level admin
crt-base ${testdir}/ocsp_update
+ log ${Syslog_ocsp3_addr}:${Syslog_ocsp3_port} local0 notice notice
defaults
mode http
@@ -222,18 +203,9 @@ haproxy h3 -conf {
frontend ssl-ecdsa-fe
bind "${tmpdir}/ssl5.sock" ssl crt-list ${testdir}/ocsp_update/multicert_ecdsa_no_update.crt-list ca-file ${testdir}/set_cafile_rootCA.crt verify none crt-ignore-err all
http-request return status 200
-
- listen http_rebound_lst
- mode http
- option httplog
- log ${Syslog_http2_addr}:${Syslog_http2_port} local0
- bind "127.0.0.1:12345"
- server s1 "127.0.0.1:12346"
} -start
-barrier b2 sync
-
-shell "sleep 1"
+barrier b3 sync
# We should have a single ocsp ID known that was loaded at build time and the
# response should be filled
@@ -248,7 +220,7 @@ haproxy h3 -cli {
}
haproxy h3 -wait
-process p2 -wait
+process p3 -wait
@@ -258,8 +230,27 @@ process p2 -wait
# (CLI COMMAND) #
# #
####################
+# This test focuses on the "update ssl ocsp-response" CLI command and tests two
+# certificates that have a known OCSP response loaded during init but no OCSP
+# auto update. The only difference between the two certificates is that one has
+# a separate .issuer file while the other one has the issuer certificate
+# directly in the main .pem file.
+# We store the original "Produced At" date of the responses loaded during init
+# in haproxy proc variables in order to compare them to their new value after
+# the update is performed.
+
+process p4 "openssl ocsp -index ${testdir}/ocsp_update/index.txt -rsigner ${testdir}/ocsp_update/ocsp.haproxy.com.pem -CA ${testdir}/ocsp_update/ocsp_update_rootca.crt -nrequest 2 -ndays 1 -port 12345 -timeout 5" -start
-process p3 "openssl ocsp -index ${testdir}/ocsp_update/index.txt -rsigner ${testdir}/ocsp_update/ocsp.haproxy.com.pem -CA ${testdir}/ocsp_update/ocsp_update_rootca.crt -nrequest 2 -ndays 1 -port 12346 -timeout 5" -start
+barrier b4 cond 2 -cyclic
+
+syslog Syslog_ocsp4 -level notice {
+ recv
+ expect ~ "<OCSP-UPDATE> ${testdir}/ocsp_update/multicert/server_ocsp.pem.rsa 1 \"Update successful\" 0 1"
+
+ recv
+ expect ~ "<OCSP-UPDATE> ${testdir}/ocsp_update/multicert/server_ocsp_ecdsa.pem 1 \"Update successful\" 0 1"
+ barrier b4 sync
+} -start
haproxy h4 -conf {
global
@@ -267,6 +258,7 @@ haproxy h4 -conf {
tune.ssl.capture-buffer-size 1
stats socket "${tmpdir}/h4/stats" level admin
crt-base ${testdir}/ocsp_update
+ log ${Syslog_ocsp4_addr}:${Syslog_ocsp4_port} local0 notice notice
defaults
mode http
@@ -283,19 +275,12 @@ haproxy h4 -conf {
frontend ssl-ecdsa-ocsp
bind "${tmpdir}/ssl6.sock" ssl crt ${testdir}/ocsp_update/multicert/server_ocsp_ecdsa.pem ca-file ${testdir}/set_cafile_rootCA.crt verify none crt-ignore-err all
http-request return status 200
-
- listen http_rebound_lst
- mode http
- option httplog
- bind "127.0.0.1:12345"
- http-response set-var(proc.processed) int(1)
- server s1 "127.0.0.1:12346"
} -start
# We need to "enable" the cli with a first cli call before using it only through socats
haproxy h4 -cli {
- send "show ssl ocsp-response"
- expect ~ "Certificate ID key : 303b300906052b0e03021a050004148a83e0060faff709ca7e9b95522a2e81635fda0a0414f652b0e435d5ea923851508f0adbe92d85de007a02021016"
+ send "show ssl cert"
+ expect ~ ""
}
# We should have two OCSP responses loaded during init
@@ -307,62 +292,53 @@ shell {
echo "$responses" | grep "Serial Number: 1015"
}
-shell {
- echo "show ssl ocsp-response 303b300906052b0e03021a050004148a83e0060faff709ca7e9b95522a2e81635fda0a0414f652b0e435d5ea923851508f0adbe92d85de007a02021015" | socat "${tmpdir}/h4/stats" - | grep "Cert Status: revoked"
-}
+haproxy h4 -cli {
+ send "show ssl ocsp-response 303b300906052b0e03021a050004148a83e0060faff709ca7e9b95522a2e81635fda0a0414f652b0e435d5ea923851508f0adbe92d85de007a02021015"
+ expect ~ "Cert Status: revoked"
-shell {
- echo "show ssl ocsp-response 303b300906052b0e03021a050004148a83e0060faff709ca7e9b95522a2e81635fda0a0414f652b0e435d5ea923851508f0adbe92d85de007a02021016" | socat "${tmpdir}/h4/stats" - | grep "Cert Status: good"
+ send "show ssl ocsp-response 303b300906052b0e03021a050004148a83e0060faff709ca7e9b95522a2e81635fda0a0414f652b0e435d5ea923851508f0adbe92d85de007a02021016"
+ expect ~ "Cert Status: good"
}
# Update the first ocsp response (ckch_data has a non-NULL ocsp_issuer pointer)
shell {
# Store the current "Produced At" in order to ensure that after the update
# the OCSP response actually changed
- produced_at=$(echo "show ssl ocsp-response 303b300906052b0e03021a050004148a83e0060faff709ca7e9b95522a2e81635fda0a0414f652b0e435d5ea923851508f0adbe92d85de007a02021015" | socat "${tmpdir}/h4/stats" - | grep "Produced At")
+ produced_at1=$(echo "show ssl ocsp-response 303b300906052b0e03021a050004148a83e0060faff709ca7e9b95522a2e81635fda0a0414f652b0e435d5ea923851508f0adbe92d85de007a02021015" | socat "${tmpdir}/h4/stats" - | grep "Produced At" | tr -d ' ')
echo "update ssl ocsp-response ${testdir}/ocsp_update/multicert/server_ocsp.pem.rsa" | socat "${tmpdir}/h4/stats" -
- while ! echo "get var proc.processed" | socat "${tmpdir}/h4/stats" - | grep 'proc.processed: type=sint value=<1>'
- do
- echo "get var proc.processed" | socat "${tmpdir}/h4/stats" - >> /tmp/toto
- sleep 0.5
- done
- echo "experimental-mode on;set var proc.processed int(0)" | socat "${tmpdir}/h4/stats" -
+ # Update the second ocsp response (ckch_data has a NULL ocsp_issuer pointer)
+ # Store the current "Produced At" in order to ensure that after the update
+ # the OCSP response actually changed
+ produced_at2=$(echo "show ssl ocsp-response 303b300906052b0e03021a050004148a83e0060faff709ca7e9b95522a2e81635fda0a0414f652b0e435d5ea923851508f0adbe92d85de007a02021016" | socat "${tmpdir}/h4/stats" - | grep "Produced At" | tr -d ' ')
- ocsp_response=$(echo "show ssl ocsp-response 303b300906052b0e03021a050004148a83e0060faff709ca7e9b95522a2e81635fda0a0414f652b0e435d5ea923851508f0adbe92d85de007a02021015" | socat "${tmpdir}/h4/stats" -)
- new_produced_at=$(echo "$ocsp_response" | grep "Produced At")
+ echo "update ssl ocsp-response ${testdir}/ocsp_update/multicert/server_ocsp_ecdsa.pem" | socat "${tmpdir}/h4/stats" -
- echo "$ocsp_response" | grep -q "Serial Number: 1015" && \
- echo "$ocsp_response" | grep -q "Cert Status: revoked" && \
- [ "$new_produced_at" != "$produced_at" ]
+ echo "experimental-mode on;set var proc.produced_at1 str($produced_at1)" | socat "${tmpdir}/h4/stats" -
+ echo "experimental-mode on;set var proc.produced_at2 str($produced_at2)" | socat "${tmpdir}/h4/stats" -
}
-# Update the second ocsp response (ckch_data has a NULL ocsp_issuer pointer)
-shell {
- # Store the current "Produced At" in order to ensure that after the update
- # the OCSP response actually changed
- produced_at=$(echo "show ssl ocsp-response 303b300906052b0e03021a050004148a83e0060faff709ca7e9b95522a2e81635fda0a0414f652b0e435d5ea923851508f0adbe92d85de007a02021016" | socat "${tmpdir}/h4/stats" - | grep "Produced At")
+barrier b4 sync
- echo "update ssl ocsp-response ${testdir}/ocsp_update/multicert/server_ocsp_ecdsa.pem" | socat "${tmpdir}/h4/stats" -
- while ! echo "get var proc.processed" | socat "${tmpdir}/h4/stats" - | grep 'proc.processed: type=sint value=<1>'
- do
- echo "get var proc.processed" | socat "${tmpdir}/h4/stats" - >> /tmp/toto
- sleep 0.5
- done
+shell {
+ produced_at1_after=$(echo "show ssl ocsp-response 303b300906052b0e03021a050004148a83e0060faff709ca7e9b95522a2e81635fda0a0414f652b0e435d5ea923851508f0adbe92d85de007a02021015" | socat "${tmpdir}/h4/stats" - | grep "Produced At" | tr -d ' ')
+ produced_at2_after=$(echo "show ssl ocsp-response 303b300906052b0e03021a050004148a83e0060faff709ca7e9b95522a2e81635fda0a0414f652b0e435d5ea923851508f0adbe92d85de007a02021016" | socat "${tmpdir}/h4/stats" - | grep "Produced At" | tr -d ' ')
- echo "experimental-mode on;set var proc.processed int(0)" | socat "${tmpdir}/h4/stats" -
+ ocsp_response1=$(echo "show ssl ocsp-response 303b300906052b0e03021a050004148a83e0060faff709ca7e9b95522a2e81635fda0a0414f652b0e435d5ea923851508f0adbe92d85de007a02021015" | socat "${tmpdir}/h4/stats" -)
+ ocsp_response2=$(echo "show ssl ocsp-response 303b300906052b0e03021a050004148a83e0060faff709ca7e9b95522a2e81635fda0a0414f652b0e435d5ea923851508f0adbe92d85de007a02021016" | socat "${tmpdir}/h4/stats" -)
- ocsp_response=$(echo "show ssl ocsp-response 303b300906052b0e03021a050004148a83e0060faff709ca7e9b95522a2e81635fda0a0414f652b0e435d5ea923851508f0adbe92d85de007a02021016" | socat "${tmpdir}/h4/stats" -)
- new_produced_at=$(echo "$ocsp_response" | grep "Produced At")
+ echo "$ocsp_response1" | grep -q "Serial Number: 1015" && \
+ echo "$ocsp_response1" | grep -q "Cert Status: revoked" && \
+ echo "$ocsp_response2" | grep -q "Serial Number: 1016" && \
+ echo "$ocsp_response2" | grep -q "Cert Status: revoked" && \
+ [ "$produced_at1_after" != "$(echo \"experimental-mode on; get var proc.produced_at1\" | socat \"${tmpdir}/h4/stats\")" ] && \
+ [ "$produced_at2_after" != "$(echo \"experimental-mode on; get var proc.produced_at2\" | socat \"${tmpdir}/h4/stats\")" ]
- echo "$ocsp_response" | grep -q "Serial Number: 1016" && \
- echo "$ocsp_response" | grep -q "Cert Status: revoked" && \
- [ "$new_produced_at" != "$produced_at" ]
}
haproxy h4 -wait
-process p3 -wait
+process p4 -wait
####################
@@ -376,16 +352,16 @@ process p3 -wait
# to the "show ssl ocsp-response" command.
-process p5 "openssl ocsp -index ${testdir}/ocsp_update/index.txt -rsigner ${testdir}/ocsp_update/ocsp.haproxy.com.pem -CA ${testdir}/ocsp_update/ocsp_update_rootca.crt -nrequest 2 -ndays 1 -port 12346 -timeout 5" -start
+process p5 "openssl ocsp -index ${testdir}/ocsp_update/index.txt -rsigner ${testdir}/ocsp_update/ocsp.haproxy.com.pem -CA ${testdir}/ocsp_update/ocsp_update_rootca.crt -nrequest 2 -ndays 1 -port 12345 -timeout 5" -start
barrier b5 cond 2 -cyclic
-syslog Syslog_http5 -level info {
+syslog Syslog_ocsp5 -level notice {
recv
- expect ~ "GET /MEMwQTA%2FMD0wOzAJBgUrDgMCGgUABBSKg%2BAGD6%2F3Ccp%2Bm5VSKi6BY1%2FaCgQU9lKw5DXV6pI4UVCPCtvpLYXeAHoCAhAV HTTP/1.1"
+ expect ~ "<OCSP-UPDATE> .*/ocsp_update/multicert_no_ocsp/server_ocsp_rsa.pem 1 \"Update successful\" 0 1"
recv
- expect ~ "GET /MEMwQTA%2FMD0wOzAJBgUrDgMCGgUABBSKg%2BAGD6%2F3Ccp%2Bm5VSKi6BY1%2FaCgQU9lKw5DXV6pI4UVCPCtvpLYXeAHoCAhAW HTTP/1.1"
+ expect ~ "<OCSP-UPDATE> .*/ocsp_update/multicert_no_ocsp/server_ocsp_ecdsa.pem 1 \"Update successful\" 0 1"
barrier b5 sync
} -start
@@ -396,6 +372,7 @@ haproxy h5 -conf {
tune.ssl.capture-buffer-size 1
stats socket "${tmpdir}/h5/stats" level admin
crt-base ${testdir}/ocsp_update
+ log ${Syslog_ocsp5_addr}:${Syslog_ocsp5_port} local0 notice notice
defaults
mode http
@@ -412,19 +389,10 @@ haproxy h5 -conf {
frontend ssl-ecdsa-fe
bind "${tmpdir}/ssl8.sock" ssl crt-list ${testdir}/ocsp_update/multicert_ecdsa.crt-list ca-file ${testdir}/set_cafile_rootCA.crt verify none crt-ignore-err all
http-request return status 200
-
- listen http_rebound_lst
- mode http
- option httplog
- log ${Syslog_http5_addr}:${Syslog_http5_port} local0
- bind "127.0.0.1:12345"
- server s1 "127.0.0.1:12346"
} -start
barrier b5 sync
-shell "sleep 1"
-
# Use "show ssl ocsp-updates" CLI command
# We should have one line per OCSP response and each one of them should have been successfully updated once
# The command's output follows this format:
@@ -469,13 +437,13 @@ process p5 -wait
# the 'ocsp-update on' option will be taken into account by the OCSP
# auto update task
#
-process p6 "openssl ocsp -index ${testdir}/ocsp_update/index.txt -rsigner ${testdir}/ocsp_update/ocsp.haproxy.com.pem -CA ${testdir}/ocsp_update/ocsp_update_rootca.crt -nrequest 1 -ndays 1 -port 12346 -timeout 5" -start
+process p6 "openssl ocsp -index ${testdir}/ocsp_update/index.txt -rsigner ${testdir}/ocsp_update/ocsp.haproxy.com.pem -CA ${testdir}/ocsp_update/ocsp_update_rootca.crt -nrequest 1 -ndays 1 -port 12345 -timeout 5" -start
barrier b6 cond 2 -cyclic
-syslog Syslog_http6 -level info {
+syslog Syslog_ocsp6 -level notice {
recv
- expect ~ "GET /MEMwQTA%2FMD0wOzAJBgUrDgMCGgUABBSKg%2BAGD6%2F3Ccp%2Bm5VSKi6BY1%2FaCgQU9lKw5DXV6pI4UVCPCtvpLYXeAHoCAhAV HTTP/1.1"
+ expect ~ "<OCSP-UPDATE> ${testdir}/ocsp_update/multicert/server_ocsp.pem.rsa 1 \"Update successful\" 0 1"
barrier b6 sync
} -start
@@ -486,6 +454,7 @@ haproxy h6 -conf {
tune.ssl.capture-buffer-size 1
stats socket "${tmpdir}/h6/stats" level admin
crt-base ${testdir}
+ log ${Syslog_ocsp6_addr}:${Syslog_ocsp6_port} local0 notice notice
defaults
mode http
@@ -500,12 +469,6 @@ haproxy h6 -conf {
bind "${tmpdir}/ssl9.sock" ssl crt-list ${testdir}/simple.crt-list ca-file ${testdir}/set_cafile_rootCA.crt verify none crt-ignore-err all
http-request return status 200
- listen http_rebound_lst
- mode http
- option httplog
- log ${Syslog_http6_addr}:${Syslog_http6_port} local0
- bind "127.0.0.1:12345"
- server s1 "127.0.0.1:12346"
} -start
# We need to "enable" the cli with a first cli call before using it only through socats
@@ -527,9 +490,258 @@ shell {
barrier b6 sync
-shell "sleep 1"
-
haproxy h6 -cli {
send "show ssl ocsp-updates"
expect ~ "303b300906052b0e03021a050004148a83e0060faff709ca7e9b95522a2e81635fda0a0414f652b0e435d5ea923851508f0adbe92d85de007a02021016 .*| 1 | 0 | 1 | Update successful"
}
+
+haproxy h6 -wait
+process p6 -wait
+
+
+######################
+# #
+# SEVENTH TEST CASE #
+# #
+######################
+
+# Check that the global "tune.ocsp-update.mode" option works and that it
+# applies to certificates added via the CLI as well.
+#
+process p7 "openssl ocsp -index ${testdir}/ocsp_update/index.txt -rsigner ${testdir}/ocsp_update/ocsp.haproxy.com.pem -CA ${testdir}/ocsp_update/ocsp_update_rootca.crt -nrequest 2 -ndays 1 -port 12345 -timeout 5" -start
+
+barrier b7 cond 2 -cyclic
+
+syslog Syslog_ocsp7 -level notice {
+ recv
+ expect ~ "<OCSP-UPDATE> ${testdir}/ocsp_update/multicert_no_ocsp/server_ocsp_ecdsa.pem 1 \"Update successful\" 0 1"
+
+ barrier b7 sync
+
+ recv
+ expect ~ "<OCSP-UPDATE> ${testdir}/server_ocsp_rsa.pem 1 \"Update successful\" 0 1"
+
+ barrier b7 sync
+} -start
+
+haproxy h7 -conf {
+ global
+ tune.ssl.default-dh-param 2048
+ tune.ssl.capture-buffer-size 1
+ stats socket "${tmpdir}/h7/stats" level admin
+ crt-base ${testdir}
+ ocsp-update.mode on
+ log ${Syslog_ocsp7_addr}:${Syslog_ocsp7_port} local0 notice notice
+
+ defaults
+ mode http
+ option httplog
+ log stderr local0 debug err
+ option logasap
+ timeout connect "${HAPROXY_TEST_TIMEOUT-5s}"
+ timeout client "${HAPROXY_TEST_TIMEOUT-5s}"
+ timeout server "${HAPROXY_TEST_TIMEOUT-5s}"
+
+ frontend ssl-fe
+ bind "${tmpdir}/ssl_h7.sock" ssl crt ${testdir}/ocsp_update/multicert_no_ocsp/server_ocsp_ecdsa.pem ca-file ${testdir}/set_cafile_rootCA.crt verify none crt-ignore-err all
+ bind "${tmpdir}/ssl_h7_2.sock" ssl crt-list ${testdir}/simple.crt-list ca-file ${testdir}/set_cafile_rootCA.crt verify none crt-ignore-err all
+ http-request return status 200
+} -start
+
+barrier b7 sync
+
+# Create a new certificate that has an OCSP uri and add it to the
+# existing CLI with the 'ocsp-update on' command.
+shell {
+ echo "new ssl cert ${testdir}/server_ocsp_rsa.pem" | socat "${tmpdir}/h7/stats" -
+ printf "set ssl cert ${testdir}/server_ocsp_rsa.pem <<\n$(cat ${testdir}/ocsp_update/multicert_no_ocsp/server_ocsp_rsa.pem)\n\n" | socat "${tmpdir}/h7/stats" -
+ echo "commit ssl cert ${testdir}/server_ocsp_rsa.pem" | socat "${tmpdir}/h7/stats" -
+
+ # We should have ocsp-update enabled via the global option
+ printf "add ssl crt-list ${testdir}/simple.crt-list <<\n${testdir}/server_ocsp_rsa.pem foo.com\n\n" | socat "${tmpdir}/h7/stats" -
+}
+
+barrier b7 sync
+
+haproxy h7 -cli {
+ send "show ssl ocsp-updates"
+ expect ~ "303b300906052b0e03021a050004148a83e0060faff709ca7e9b95522a2e81635fda0a0414f652b0e435d5ea923851508f0adbe92d85de007a02021016 | ${testdir}/ocsp_update/multicert_no_ocsp/server_ocsp_ecdsa.pem .*| 1 | 0 | 1 | Update successful"
+
+ send "show ssl ocsp-updates"
+ expect ~ "303b300906052b0e03021a050004148a83e0060faff709ca7e9b95522a2e81635fda0a0414f652b0e435d5ea923851508f0adbe92d85de007a02021015 | ${testdir}/server_ocsp_rsa.pem .*| 1 | 0 | 1 | Update successful"
+}
+
+haproxy h7 -wait
+process p7 -wait
+
+
+######################
+# #
+# EIGHTH TEST CASE #
+# #
+######################
+
+#
+# Check that removing crt-list instances does not remove the OCSP responses
+# from the tree but that they will not be auto updated anymore if the last
+# instance is removed (via del ssl crt-list).
+#
+
+haproxy h8 -conf {
+ global
+ tune.ssl.default-dh-param 2048
+ tune.ssl.capture-buffer-size 1
+ stats socket "${tmpdir}/h8/stats" level admin
+ crt-base ${testdir}/ocsp_update
+
+ defaults
+ mode http
+ option httplog
+ log stderr local0 debug err
+ option logasap
+ timeout connect "${HAPROXY_TEST_TIMEOUT-5s}"
+ timeout client "${HAPROXY_TEST_TIMEOUT-5s}"
+ timeout server "${HAPROXY_TEST_TIMEOUT-5s}"
+
+ frontend ssl-fe
+ bind "${tmpdir}/ssl-h8.sock" ssl crt-list ${testdir}/ocsp_update/multicert_both_certs.crt-list ca-file ${testdir}/set_cafile_rootCA.crt verify none crt-ignore-err all
+ http-request return status 200
+
+ listen http_rebound_lst
+ mode http
+ bind "127.0.0.1:12345"
+ server s1 "127.0.0.1:12346"
+} -start
+
+# Check that the two certificates are taken into account in the auto update process
+haproxy h8 -cli {
+ send "show ssl ocsp-updates"
+ expect ~ "303b300906052b0e03021a050004148a83e0060faff709ca7e9b95522a2e81635fda0a0414f652b0e435d5ea923851508f0adbe92d85de007a02021015 .*"
+
+ send "show ssl ocsp-updates"
+ expect ~ "303b300906052b0e03021a050004148a83e0060faff709ca7e9b95522a2e81635fda0a0414f652b0e435d5ea923851508f0adbe92d85de007a02021016 .*"
+}
+
+# Remove the second line from the crt-list and check that the corresponding
+# ocsp response was removed from the auto update list but is still present in the
+# system
+haproxy h8 -cli {
+ send "del ssl crt-list ${testdir}/ocsp_update/multicert_both_certs.crt-list ${testdir}/ocsp_update/multicert/server_ocsp.pem.ecdsa"
+ expect ~ "Entry.*deleted in crtlist"
+
+ send "show ssl ocsp-updates"
+ expect !~ "303b300906052b0e03021a050004148a83e0060faff709ca7e9b95522a2e81635fda0a0414f652b0e435d5ea923851508f0adbe92d85de007a02021016 .*"
+
+ send "show ssl ocsp-response"
+ expect ~ "Certificate ID key : 303b300906052b0e03021a050004148a83e0060faff709ca7e9b95522a2e81635fda0a0414f652b0e435d5ea923851508f0adbe92d85de007a02021016"
+
+ send "show ssl ocsp-response ${testdir}/ocsp_update/multicert/server_ocsp.pem.ecdsa"
+ expect ~ ".* Cert Status: good.*"
+}
+
+# Add the previously removed crt-list line with auto-update enabled and check that
+# the ocsp response appears in the auto update list
+shell {
+ printf "add ssl crt-list ${testdir}/ocsp_update/multicert_both_certs.crt-list <<\nmulticert/server_ocsp.pem.ecdsa [ocsp-update on] foo.bar\n\n" | socat "${tmpdir}/h8/stats" - | grep "Inserting certificate.*in crt-list"
+}
+
+haproxy h8 -cli {
+ send "show ssl ocsp-updates"
+ expect ~ "303b300906052b0e03021a050004148a83e0060faff709ca7e9b95522a2e81635fda0a0414f652b0e435d5ea923851508f0adbe92d85de007a02021016 .*"
+}
+
+# Check that the auto update option consistency check work even when crt-list
+# lines are added through the cli
+shell {
+ printf "add ssl crt-list ${testdir}/ocsp_update/multicert_both_certs.crt-list <<\nmulticert/server_ocsp.pem.ecdsa foo.foo\n\n" | socat "${tmpdir}/h8/stats" - | grep "different parameter 'ocsp-update'"
+}
+
+haproxy h8 -wait
+
+####################
+# #
+# NINTH TEST CASE #
+# #
+####################
+
+#
+# Check that a certificate created through the CLI and which does not have ocsp
+# update enabled can be updated via "update ssl ocsp-response" command.
+#
+
+process p9 "openssl ocsp -index ${testdir}/ocsp_update/index.txt -rsigner ${testdir}/ocsp_update/ocsp.haproxy.com.pem -CA ${testdir}/ocsp_update/ocsp_update_rootca.crt -nrequest 1 -ndays 1 -port 12345 -timeout 5" -start
+
+barrier b9 cond 2 -cyclic
+
+syslog Syslog_ocsp9 -level notice {
+ recv
+ expect ~ "<OCSP-UPDATE> ${testdir}/ocsp_update/rsa.pem 1 \"Update successful\" 0 1"
+
+ barrier b9 sync
+} -start
+
+
+haproxy h9 -conf {
+ global
+ tune.ssl.default-dh-param 2048
+ tune.ssl.capture-buffer-size 1
+ stats socket "${tmpdir}/h9/stats" level admin
+ crt-base ${testdir}/ocsp_update
+ log ${Syslog_ocsp9_addr}:${Syslog_ocsp9_port} local0 notice notice
+
+ defaults
+ mode http
+ option httplog
+ log stderr local0 debug err
+ option logasap
+ timeout connect "${HAPROXY_TEST_TIMEOUT-5s}"
+ timeout client "${HAPROXY_TEST_TIMEOUT-5s}"
+ timeout server "${HAPROXY_TEST_TIMEOUT-5s}"
+
+ frontend ssl-fe
+ bind "${tmpdir}/ssl-h9.sock" ssl crt-list ${testdir}/ocsp_update/multicert_ecdsa_no_update.crt-list ca-file ${testdir}/set_cafile_rootCA.crt verify none crt-ignore-err all
+ http-request return status 200
+} -start
+
+# We need to "enable" the cli with a first cli call before using it only through socats
+haproxy h9 -cli {
+ send "show ssl cert"
+ expect ~ ""
+}
+
+# Create a new certificate and add it in the crt-list with ocsp auto-update enabled
+shell {
+ echo "new ssl cert ${testdir}/ocsp_update/rsa.pem" | socat "${tmpdir}/h9/stats" -
+ printf "set ssl cert ${testdir}/ocsp_update/rsa.pem <<\n$(cat ${testdir}/ocsp_update/multicert/server_ocsp.pem.rsa)\n\n" | socat "${tmpdir}/h9/stats" -
+ printf "set ssl cert ${testdir}/ocsp_update/rsa.pem.issuer <<\n$(cat ${testdir}/ocsp_update/ocsp_update_rootca.crt)\n\n" | socat "${tmpdir}/h9/stats" -
+ printf "set ssl cert ${testdir}/ocsp_update/rsa.pem.ocsp <<\n$(base64 -w 1000 ${testdir}/ocsp_update/multicert/server_ocsp.pem.rsa.ocsp)\n\n" | socat "${tmpdir}/h9/stats" -
+ echo "commit ssl cert ${testdir}/ocsp_update/rsa.pem" | socat "${tmpdir}/h9/stats" -
+
+ printf "add ssl crt-list ${testdir}/ocsp_update/multicert_ecdsa_no_update.crt-list <<\nrsa.pem [ocsp-update off] foo.bar\n\n" | socat "${tmpdir}/h9/stats" -
+}
+
+# Check that the line is in the crt-list
+haproxy h9 -cli {
+ send "show ssl crt-list ${testdir}/ocsp_update/multicert_ecdsa_no_update.crt-list"
+ expect ~ "${testdir}/ocsp_update/rsa.pem.*ocsp-update off.*foo.bar"
+}
+
+# Check that the new certificate is NOT in the auto update list
+haproxy h9 -cli {
+ send "show ssl ocsp-updates"
+ expect !~ "303b300906052b0e03021a050004148a83e0060faff709ca7e9b95522a2e81635fda0a0414f652b0e435d5ea923851508f0adbe92d85de007a02021015.*"
+}
+
+shell {
+ echo "update ssl ocsp-response ${testdir}/ocsp_update/rsa.pem" | socat "${tmpdir}/h9/stats" -
+}
+
+barrier b9 sync
+
+haproxy h9 -cli {
+ send "show ssl ocsp-response ${testdir}/ocsp_update/rsa.pem"
+ expect ~ ".* Cert Status: revoked.*"
+}
+
+haproxy h9 -wait
+process p9 -wait
diff --git a/reg-tests/ssl/ocsp_compat_check.vtc b/reg-tests/ssl/ocsp_compat_check.vtc
new file mode 100644
index 0000000..7dbcdf9
--- /dev/null
+++ b/reg-tests/ssl/ocsp_compat_check.vtc
@@ -0,0 +1,401 @@
+#REGTEST_TYPE=devel
+
+# broken with BoringSSL.
+#
+# This reg-test tries loading multiple configurations that make use of the
+# 'ocsp-update' crt-list option and the global 'ocsp-update.mode'
+# option. It ensures that an error message is raised when the user provides an
+# incoherent configuration. Any configuration in which a given certificate has
+# the ocsp auto update mode set to 'on' as well as 'off' simultaneously should
+# raise an ALERT type message and not start.
+# The first batch of configurations should all raise errors and the second
+# batch should all load properly. We do not focus on the actual auto update in
+# this reg-test though so no actual proxy instance will be launched.
+
+varnishtest "Test the OCSP auto update feature"
+feature cmd "$HAPROXY_PROGRAM -cc 'version_atleast(3.0-dev0)'"
+feature cmd "$HAPROXY_PROGRAM -cc 'feature(OPENSSL) && !ssllib_name_startswith(BoringSSL) && openssl_version_atleast(1.1.1)'"
+feature ignore_unknown_macro
+
+
+#############################
+# #
+# WRONG CONFIGURATIONS #
+# #
+#############################
+
+
+# test1
+# global_option OFF
+# bind line DFLT (OFF) (first)
+# crt-list ON (second)
+shell {
+ cat << EOF > ${tmpdir}/ocsp_compat_check.list
+server_ocsp_ecdsa.pem [ocsp-update on] foo.com
+EOF
+
+ cat << EOF > ${tmpdir}/ocsp_compat_check.cfg
+global
+ crt-base ${testdir}/ocsp_update/multicert
+# ocsp-update.mode on
+
+defaults
+ log stderr local0 debug err
+
+listen ssl-lst
+ bind "${tmpdir}/ssl.sock" ssl crt server_ocsp_ecdsa.pem crt-list ${tmpdir}/ocsp_compat_check.list
+ server s1 127.0.0.1:80
+EOF
+
+ haproxy_output="$($HAPROXY_PROGRAM -f ${tmpdir}/ocsp_compat_check.cfg -c 2>&1)"
+ haproxy_ret=$?
+ echo "==== test 1"
+ echo "$haproxy_output"
+ echo "HAProxy return code: $haproxy_ret"
+ [ $haproxy_ret -ne 0 ] && echo "$haproxy_output" | grep -q "different parameter 'ocsp-update'"
+}
+
+# test2
+# global_option ON
+# bind line DFLT/ON (first)
+# crt-list OFF (second)
+shell {
+ cat << EOF > ${tmpdir}/ocsp_compat_check.list
+server_ocsp_ecdsa.pem [ocsp-update off] foo.com
+EOF
+
+ cat << EOF > ${tmpdir}/ocsp_compat_check.cfg
+global
+ crt-base ${testdir}/ocsp_update/multicert
+ ocsp-update.mode on
+
+defaults
+ log stderr local0 debug err
+
+listen ssl-lst
+ bind "${tmpdir}/ssl.sock" ssl crt server_ocsp_ecdsa.pem crt-list ${tmpdir}/ocsp_compat_check.list
+ server s1 127.0.0.1:80
+EOF
+
+ haproxy_output="$($HAPROXY_PROGRAM -f ${tmpdir}/ocsp_compat_check.cfg -c 2>&1)"
+ haproxy_ret=$?
+ echo "==== test 2"
+ echo "$haproxy_output"
+ echo "HAProxy return code: $haproxy_ret"
+ [ $haproxy_ret -ne 0 ] && echo "$haproxy_output" | grep -q "different parameter 'ocsp-update'"
+}
+
+# test3
+# global_option OFF
+# bind line DFLT/OFF(first)
+# crt-list ON (second)
+shell {
+ cat << EOF > ${tmpdir}/ocsp_compat_check.list
+server_ocsp_ecdsa.pem [ocsp-update on] foo.com
+EOF
+
+ cat << EOF > ${tmpdir}/ocsp_compat_check.cfg
+global
+ crt-base ${testdir}/ocsp_update/multicert
+ ocsp-update.mode off
+
+defaults
+ log stderr local0 debug err
+
+listen ssl-lst
+ bind "${tmpdir}/ssl.sock" ssl crt server_ocsp_ecdsa.pem crt-list ${tmpdir}/ocsp_compat_check.list
+ server s1 127.0.0.1:80
+EOF
+
+ haproxy_output="$($HAPROXY_PROGRAM -f ${tmpdir}/ocsp_compat_check.cfg -c 2>&1)"
+ haproxy_ret=$?
+ echo "==== test 3"
+ echo "$haproxy_output"
+ echo "HAProxy return code: $haproxy_ret"
+ [ $haproxy_ret -ne 0 ] && echo "$haproxy_output" | grep -q "different parameter 'ocsp-update'"
+}
+
+# test4
+# global_option OFF
+# bind line DFLT OFF (second)
+# crt-list ON (first)
+shell {
+ cat << EOF > ${tmpdir}/ocsp_compat_check.list
+server_ocsp_ecdsa.pem [ocsp-update on] foo.com
+EOF
+
+ cat << EOF > ${tmpdir}/ocsp_compat_check.cfg
+global
+ crt-base ${testdir}/ocsp_update/multicert
+# ocsp-update.mode off
+
+defaults
+ log stderr local0 debug err
+
+listen ssl-lst
+ bind "${tmpdir}/ssl.sock" ssl crt-list ${tmpdir}/ocsp_compat_check.list
+ bind "${tmpdir}/ssl2.sock" ssl crt server_ocsp_ecdsa.pem
+ server s1 127.0.0.1:80
+EOF
+
+ haproxy_output="$($HAPROXY_PROGRAM -f ${tmpdir}/ocsp_compat_check.cfg -c 2>&1)"
+ haproxy_ret=$?
+ echo "==== test 4"
+ echo "$haproxy_output"
+ echo "HAProxy return code: $haproxy_ret"
+ [ $haproxy_ret -ne 0 ] && echo "$haproxy_output" | grep -q "different parameter 'ocsp-update'"
+}
+
+# test5
+# global_option ON
+# bind line DFLT (second)
+# crt-list OFF (first)
+shell {
+ cat << EOF > ${tmpdir}/ocsp_compat_check.list
+server_ocsp_ecdsa.pem [ocsp-update off] foo.com
+EOF
+
+ cat << EOF > ${tmpdir}/ocsp_compat_check.cfg
+global
+ crt-base ${testdir}/ocsp_update/multicert
+ ocsp-update.mode on
+
+defaults
+ log stderr local0 debug err
+
+listen ssl-lst
+ bind "${tmpdir}/ssl.sock" ssl crt-list ${tmpdir}/ocsp_compat_check.list
+ bind "${tmpdir}/ssl2.sock" ssl crt server_ocsp_ecdsa.pem
+ server s1 127.0.0.1:80
+EOF
+
+ haproxy_output="$($HAPROXY_PROGRAM -f ${tmpdir}/ocsp_compat_check.cfg -c 2>&1)"
+ haproxy_ret=$?
+ echo "==== test 5"
+ echo "$haproxy_output"
+ echo "HAProxy return code: $haproxy_ret"
+ [ $haproxy_ret -ne 0 ] && echo "$haproxy_output" | grep -q "different parameter 'ocsp-update'"
+}
+
+# test6
+# global_option OFF
+# bind line DFLT (second)
+# crt-list ON (first)
+shell {
+ cat << EOF > ${tmpdir}/ocsp_compat_check.list
+server_ocsp_ecdsa.pem [ocsp-update on] foo.com
+EOF
+
+ cat << EOF > ${tmpdir}/ocsp_compat_check.cfg
+global
+ crt-base ${testdir}/ocsp_update/multicert
+ ocsp-update.mode off
+
+defaults
+ log stderr local0 debug err
+
+listen ssl-lst
+ bind "${tmpdir}/ssl.sock" ssl crt-list ${tmpdir}/ocsp_compat_check.list
+ bind "${tmpdir}/ssl2.sock" ssl crt server_ocsp_ecdsa.pem
+ server s1 127.0.0.1:80
+EOF
+
+ haproxy_output="$($HAPROXY_PROGRAM -f ${tmpdir}/ocsp_compat_check.cfg -c 2>&1)"
+ haproxy_ret=$?
+ echo "==== test 6"
+ echo "$haproxy_output"
+ echo "HAProxy return code: $haproxy_ret"
+ [ $haproxy_ret -ne 0 ] && echo "$haproxy_output" | grep -q "different parameter 'ocsp-update'"
+}
+
+# test7
+# global_option DFLT
+# bind line -
+# crt-list ON
+# crt-list DFLT
+shell {
+ cat << EOF > ${tmpdir}/ocsp_compat_check.list
+server_ocsp_ecdsa.pem [ocsp-update on] foo.com
+server_ocsp_ecdsa.pem bar.com
+EOF
+
+ cat << EOF > ${tmpdir}/ocsp_compat_check.cfg
+global
+ crt-base ${testdir}/ocsp_update/multicert
+# ocsp-update.mode off
+
+defaults
+ log stderr local0 debug err
+
+listen ssl-lst
+ bind "${tmpdir}/ssl.sock" ssl crt-list ${tmpdir}/ocsp_compat_check.list
+ server s1 127.0.0.1:80
+EOF
+
+ haproxy_output="$($HAPROXY_PROGRAM -f ${tmpdir}/ocsp_compat_check.cfg -c 2>&1)"
+ haproxy_ret=$?
+ echo "==== test 7"
+ echo "$haproxy_output"
+ [ $haproxy_ret -ne 0 ] && echo "$haproxy_output" | grep -q "different parameter 'ocsp-update'"
+}
+
+# test8
+# global_option DFLT
+# bind line -
+# crt-list DFLT
+# crt-list ON
+shell {
+ cat << EOF > ${tmpdir}/ocsp_compat_check.list
+server_ocsp_ecdsa.pem bar.com
+server_ocsp_ecdsa.pem [ocsp-update on] foo.com
+EOF
+
+ cat << EOF > ${tmpdir}/ocsp_compat_check.cfg
+global
+ crt-base ${testdir}/ocsp_update/multicert
+# ocsp-update.mode off
+
+defaults
+ log stderr local0 debug err
+
+listen ssl-lst
+ bind "${tmpdir}/ssl.sock" ssl crt-list ${tmpdir}/ocsp_compat_check.list
+ server s1 127.0.0.1:80
+EOF
+
+ haproxy_output="$($HAPROXY_PROGRAM -f ${tmpdir}/ocsp_compat_check.cfg -c 2>&1)"
+ haproxy_ret=$?
+ echo "==== test 8"
+ echo "$haproxy_output"
+ echo "HAProxy return code: $haproxy_ret"
+ [ $haproxy_ret -ne 0 ] && echo "$haproxy_output" | grep -q "different parameter 'ocsp-update'"
+}
+
+# test9
+# global_option ON
+# bind line -
+# crt-list OFF
+# crt-list DFLT
+shell {
+ cat << EOF > ${tmpdir}/ocsp_compat_check.list
+server_ocsp_ecdsa.pem [ocsp-update off] foo.com
+server_ocsp_ecdsa.pem bar.com
+EOF
+
+ cat << EOF > ${tmpdir}/ocsp_compat_check.cfg
+global
+ crt-base ${testdir}/ocsp_update/multicert
+ ocsp-update.mode on
+
+defaults
+ log stderr local0 debug err
+
+listen ssl-lst
+ bind "${tmpdir}/ssl.sock" ssl crt-list ${tmpdir}/ocsp_compat_check.list
+ server s1 127.0.0.1:80
+EOF
+
+ haproxy_output="$($HAPROXY_PROGRAM -f ${tmpdir}/ocsp_compat_check.cfg -c 2>&1)"
+ haproxy_ret=$?
+ echo "==== test 9"
+ echo "$haproxy_output"
+ echo "HAProxy return code: $haproxy_ret"
+ [ $haproxy_ret -ne 0 ] && echo "$haproxy_output" | grep -q "different parameter 'ocsp-update'"
+}
+
+# test10
+# global_option ON
+# bind line -
+# crt-list DFLT
+# crt-list OFF
+shell {
+ cat << EOF > ${tmpdir}/ocsp_compat_check.list
+server_ocsp_ecdsa.pem bar.com
+server_ocsp_ecdsa.pem [ocsp-update off] foo.com
+EOF
+
+ cat << EOF > ${tmpdir}/ocsp_compat_check.cfg
+global
+ crt-base ${testdir}/ocsp_update/multicert
+ ocsp-update.mode on
+
+defaults
+ log stderr local0 debug err
+
+listen ssl-lst
+ bind "${tmpdir}/ssl.sock" ssl crt-list ${tmpdir}/ocsp_compat_check.list
+ server s1 127.0.0.1:80
+EOF
+
+ haproxy_output="$($HAPROXY_PROGRAM -f ${tmpdir}/ocsp_compat_check.cfg -c 2>&1)"
+ haproxy_ret=$?
+ echo "==== test 10"
+ echo "$haproxy_output"
+ echo "HAProxy return code: $haproxy_ret"
+ [ $haproxy_ret -ne 0 ] && echo "$haproxy_output" | grep -q "different parameter 'ocsp-update'"
+}
+
+# test11
+# global_option OFF
+# bind line -
+# crt-list ON
+# crt-list DFLT
+shell {
+ cat << EOF > ${tmpdir}/ocsp_compat_check.list
+server_ocsp_ecdsa.pem [ocsp-update on] foo.com
+server_ocsp_ecdsa.pem bar.com
+EOF
+
+ cat << EOF > ${tmpdir}/ocsp_compat_check.cfg
+global
+ crt-base ${testdir}/ocsp_update/multicert
+ ocsp-update.mode off
+
+defaults
+ log stderr local0 debug err
+
+listen ssl-lst
+ bind "${tmpdir}/ssl.sock" ssl crt-list ${tmpdir}/ocsp_compat_check.list
+ server s1 127.0.0.1:80
+EOF
+
+ haproxy_output="$($HAPROXY_PROGRAM -f ${tmpdir}/ocsp_compat_check.cfg -c 2>&1)"
+ haproxy_ret=$?
+ echo "==== test 11"
+ echo "$haproxy_output"
+ echo "HAProxy return code: $haproxy_ret"
+ [ $haproxy_ret -ne 0 ] && echo "$haproxy_output" | grep -q "different parameter 'ocsp-update'"
+}
+
+# test12
+# global_option OFF
+# bind line -
+# crt-list DFLT
+# crt-list ON
+shell {
+ cat << EOF > ${tmpdir}/ocsp_compat_check.list
+server_ocsp_ecdsa.pem bar.com
+server_ocsp_ecdsa.pem [ocsp-update on] foo.com
+EOF
+
+ cat << EOF > ${tmpdir}/ocsp_compat_check.cfg
+global
+ crt-base ${testdir}/ocsp_update/multicert
+ ocsp-update.mode off
+
+defaults
+ log stderr local0 debug err
+
+listen ssl-lst
+ bind "${tmpdir}/ssl.sock" ssl crt-list ${tmpdir}/ocsp_compat_check.list
+ server s1 127.0.0.1:80
+EOF
+
+ haproxy_output="$($HAPROXY_PROGRAM -f ${tmpdir}/ocsp_compat_check.cfg -c 2>&1)"
+ haproxy_ret=$?
+ echo "==== test 12"
+ echo "$haproxy_output"
+ echo "HAProxy return code: $haproxy_ret"
+ [ $haproxy_ret -ne 0 ] && echo "$haproxy_output" | grep -q "different parameter 'ocsp-update'"
+}
+
diff --git a/reg-tests/ssl/ocsp_update/multicert_both_certs.crt-list b/reg-tests/ssl/ocsp_update/multicert_both_certs.crt-list
new file mode 100644
index 0000000..0ec641f
--- /dev/null
+++ b/reg-tests/ssl/ocsp_update/multicert_both_certs.crt-list
@@ -0,0 +1,2 @@
+multicert/server_ocsp.pem.rsa [ocsp-update on ssl-min-ver TLSv1.2] *
+multicert/server_ocsp.pem.ecdsa [ocsp-update on ssl-min-ver TLSv1.2] *
diff --git a/reg-tests/stats/sample-stats-file b/reg-tests/stats/sample-stats-file
new file mode 100644
index 0000000..4748579
--- /dev/null
+++ b/reg-tests/stats/sample-stats-file
@@ -0,0 +1,26 @@
+#fe guid,stot,
+
+// valid line
+guid-fe,1024,
+
+// invalid non numerical value must be silently ignored
+guid-fe,abc,
+
+// listener counters not allocated if no option socket-stats
+guid-feS-0,1024
+guid-fe2S-0,1024
+
+// unknown GUID must be silently ignored
+guid-unknown,1024,
+
+// invalid GUID side must be silently ignored
+guid-be,1024
+
+// unknown section line must be silently ignored
+#inval guid,other,
+guid-foo,0,0,
+
+// valid lines
+#be guid,unknown,stot,
+guid-be,512,1024,
+guid-srv,512,1024,
diff --git a/reg-tests/stats/stats-file.vtc b/reg-tests/stats/stats-file.vtc
new file mode 100644
index 0000000..d7c501a
--- /dev/null
+++ b/reg-tests/stats/stats-file.vtc
@@ -0,0 +1,35 @@
+varnishtest "Preload counters via stats-file"
+
+feature cmd "$HAPROXY_PROGRAM -cc 'version_atleast(3.0-dev9)'"
+feature ignore_unknown_macro
+
+haproxy h1 -conf {
+ global
+ stats-file ${testdir}/sample-stats-file
+
+ frontend fe
+ guid guid-fe
+ bind "fd@${feS}" guid-prefix guid-feS
+
+ frontend fe2
+ guid guid-fe2
+ option socket-stats
+ bind "fd@${fe2S}" guid-prefix guid-fe2S
+
+ backend be
+ guid guid-be
+ server srv ${s1_addr}:${s1_port} guid guid-srv
+} -start
+
+haproxy h1 -cli {
+ send "show stat fe 15 -1 typed"
+ expect ~ "F.*.*.*.stot.1:MCP:u64:1024"
+
+ send "show stat fe2 15 -1 typed"
+ expect ~ "L.*.*.*.stot.1:MCP:u64:1024"
+
+ send "show stat be 15 -1 typed"
+ expect ~ "B.*.*.*.stot.1:MCP:u64:1024"
+ send "show stat be 15 -1 typed"
+ expect ~ "S.*.*.*.stot.1:MCP:u64:1024"
+}
diff --git a/reg-tests/webstats/missing-stats-fields.vtc b/reg-tests/webstats/missing-stats-fields.vtc
index c85855d..8b292c3 100644
--- a/reg-tests/webstats/missing-stats-fields.vtc
+++ b/reg-tests/webstats/missing-stats-fields.vtc
@@ -1,6 +1,6 @@
varnishtest "Verifies the absence of (null) in 'show stats' header"
-# This can happen if a new ST_F_xxx enum is added without updating
+# This can happen if a new ST_I_PX_xxx enum is added without updating
# stats_fields[].
feature ignore_unknown_macro