From dridi.boukelmoune at gmail.com Wed Mar 1 09:22:05 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Wed, 01 Mar 2017 10:22:05 +0100 Subject: [master] bffb15e First stab at hit-for-pass documentation Message-ID: commit bffb15e9f58c4e4056c39093f19d1286a5df6066 Author: Dridi Boukelmoune Date: Wed Mar 1 10:14:54 2017 +0100 First stab at hit-for-pass documentation I wanted to update cache_fetch.dot to add the new transition from v_b_r but I wasn't sure how the 304 case would be handled. The documentation for built-in subs and the diagrams are also missing the fail transition. The latter may deserve a special treatment. diff --git a/doc/sphinx/users-guide/vcl-built-in-subs.rst b/doc/sphinx/users-guide/vcl-built-in-subs.rst index 0128233..a3106cd 100644 --- a/doc/sphinx/users-guide/vcl-built-in-subs.rst +++ b/doc/sphinx/users-guide/vcl-built-in-subs.rst @@ -335,6 +335,11 @@ The `vcl_backend_response` subroutine may terminate with calling delivery to any waiting client requests, possibly in parallel (streaming). + ``pass(duration)`` + Mark the object as a hit-for-pass for the given duration. Subsequent + lookups hitting this object will be turned into passed transactions, + as if ``vcl_recv`` had returned ``pass``. + ``abandon`` Abandon the backend request. Unless the backend request was a background fetch, control is passed to :ref:`vcl_synth` on the diff --git a/include/tbl/vsl_tags.h b/include/tbl/vsl_tags.h index 93a2bfe..2231b17 100644 --- a/include/tbl/vsl_tags.h +++ b/include/tbl/vsl_tags.h @@ -219,7 +219,7 @@ SLTM(TTL, 0, "TTL set on object", "\t| | | +------------------ Keep\n" "\t| | +--------------------- Grace\n" "\t| +------------------------ TTL\n" - "\t+--------------------------- \"RFC\" or \"VCL\"\n" + "\t+--------------------------- \"RFC\", \"VCL\" or \"HFP\"\n" "\n" "The last four fields are only present in \"RFC\" headers.\n\n" "Examples::\n\n" From phk at FreeBSD.org Wed Mar 1 21:21:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Wed, 01 Mar 2017 22:21:05 +0100 Subject: [master] 62d4ce7 Also try to ditch thread pool with poll waiter Message-ID: commit 62d4ce791fc9399f579ee129c57b8d6de60cf27c Author: Poul-Henning Kamp Date: Wed Mar 1 21:20:02 2017 +0000 Also try to ditch thread pool with poll waiter diff --git a/bin/varnishtest/tests/c00080.vtc b/bin/varnishtest/tests/c00080.vtc index b231b69..5a50fff 100644 --- a/bin/varnishtest/tests/c00080.vtc +++ b/bin/varnishtest/tests/c00080.vtc @@ -1,5 +1,7 @@ varnishtest "Deconfigure thread pool" +# First with default waiter + server s1 { rxreq txresp @@ -29,3 +31,33 @@ client c1 { rxresp } -run +# Then with poll waiter + +server s1 { + rxreq + txresp +} -start + +varnish v2 -arg "-Wpoll" -vcl+backend {} -start + +varnish v2 -cliok "param.set debug +drop_pools" +varnish v2 -cliok "param.set debug +slow_acceptor" +varnish v2 -cliok "param.set thread_pools 1" + +delay 2 + +client c2 -connect ${v2_sock} -repeat 2 { + txreq + rxresp +} -run + +delay 2 + +varnish v2 -vsc *thr* +varnish v2 -vsc *poo* +varnish v2 -expect MAIN.pools == 1 + +client c2 -connect ${v2_sock} { + txreq + rxresp +} -run From nils.goroll at uplex.de Wed Mar 1 21:27:05 2017 From: nils.goroll at uplex.de (Nils Goroll) Date: Wed, 01 Mar 2017 22:27:05 +0100 Subject: [master] 84b76e8 try to make coverty happy Message-ID: commit 84b76e8bb90f24ab40de293cbf03e25208fd3088 Author: Nils Goroll Date: Tue Feb 28 20:55:03 2017 +0100 try to make coverty happy diff --git a/lib/libvmod_directors/shard_cfg.c b/lib/libvmod_directors/shard_cfg.c index 7db0f88..f36d2d5 100644 --- a/lib/libvmod_directors/shard_cfg.c +++ b/lib/libvmod_directors/shard_cfg.c @@ -321,6 +321,9 @@ shardcfg_backend_cmp(const struct shard_backend *a, ai = a->ident; bi = b->ident; + assert(ai || a->backend); + assert(bi || b->backend); + /* vcl_names are unique, so we can compare the backend pointers */ if (ai == NULL && bi == NULL) return a->backend != b->backend; @@ -339,7 +342,9 @@ static int shardcfg_backend_del_cmp(const struct shard_backend *task, const struct shard_backend *b) { - if (task->backend && task->ident == NULL) + assert(task->backend || task->ident); + + if (task->ident == NULL) return task->backend != b->backend; return shardcfg_backend_cmp(task, b); From nils.goroll at uplex.de Thu Mar 2 09:06:05 2017 From: nils.goroll at uplex.de (Nils Goroll) Date: Thu, 02 Mar 2017 10:06:05 +0100 Subject: [master] 2591b9a fix the std.getenv example Message-ID: commit 2591b9a94a06a53572e59a0182cda0e4bf20da46 Author: Nils Goroll Date: Thu Mar 2 09:55:50 2017 +0100 fix the std.getenv example diff --git a/lib/libvmod_std/vmod.vcc b/lib/libvmod_std/vmod.vcc index 9917e0f..ecbd449 100644 --- a/lib/libvmod_std/vmod.vcc +++ b/lib/libvmod_std/vmod.vcc @@ -281,7 +281,7 @@ Description See getenv(3) Example - | set req.http.My-Env = getenv("MY_ENV"); + | set req.http.My-Env = std.getenv("MY_ENV"); $Function VOID late_100_continue(BOOL late) From nils.goroll at uplex.de Thu Mar 2 09:06:05 2017 From: nils.goroll at uplex.de (Nils Goroll) Date: Thu, 02 Mar 2017 10:06:05 +0100 Subject: [master] 428996a fix and improve std.late_100_continue documentation Message-ID: commit 428996a300e29d5ccb47fa4e45d7f51e6e5f711a Author: Nils Goroll Date: Thu Mar 2 10:02:38 2017 +0100 fix and improve std.late_100_continue documentation diff --git a/lib/libvmod_std/vmod.vcc b/lib/libvmod_std/vmod.vcc index ecbd449..61eed10 100644 --- a/lib/libvmod_std/vmod.vcc +++ b/lib/libvmod_std/vmod.vcc @@ -290,8 +290,8 @@ Description request header. Varnish always generates a `100 Continue` response if - requested by the by the client trough the `Expect: - 100-continue` header when waiting for request body data. + requested by the client trough the `Expect: 100-continue` + header when waiting for request body data. But, by default, the `100 Continue` response is already generated immediately after `vcl_recv` returns to reduce @@ -308,6 +308,17 @@ Description calling `std.cache_req_body()` or any other function consuming the request body. +Example + | vcl_recv { + | std.late_100_continue(true); + | + | if (req.method == "POST") { + | std.late_100_continue(false); + | return (pass); + | } + | ... + | } + SEE ALSO ======== From phk at FreeBSD.org Thu Mar 2 15:10:07 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Thu, 02 Mar 2017 16:10:07 +0100 Subject: [master] e5b99ec Split H2 session from protocol/frame processing Message-ID: commit e5b99ec618d95cdd11160ccfbdc6aa408c5333f4 Author: Poul-Henning Kamp Date: Thu Mar 2 10:49:17 2017 +0000 Split H2 session from protocol/frame processing diff --git a/bin/varnishd/Makefile.am b/bin/varnishd/Makefile.am index edc23f4..b07e9f0 100644 --- a/bin/varnishd/Makefile.am +++ b/bin/varnishd/Makefile.am @@ -71,6 +71,7 @@ varnishd_SOURCES = \ http2/cache_http2_hpack.c \ http2/cache_http2_panic.c \ http2/cache_http2_proto.c \ + http2/cache_http2_session.c \ http2/cache_http2_send.c \ mgt/mgt_acceptor.c \ mgt/mgt_child.c \ diff --git a/bin/varnishd/http2/cache_http2.h b/bin/varnishd/http2/cache_http2.h index f832e80..58acdeb 100644 --- a/bin/varnishd/http2/cache_http2.h +++ b/bin/varnishd/http2/cache_http2.h @@ -158,8 +158,9 @@ int H2_Send_Frame(struct worker *, const struct h2_sess *, int H2_Send(struct worker *, struct h2_req *, int flush, enum h2_frame_e type, uint8_t flags, uint32_t len, const void *); -typedef h2_error h2_frame_f(struct worker *, struct h2_sess *, - struct h2_req *); -#define H2_FRAME(l,u,t,f) h2_frame_f h2_rx_##l ; -#include "tbl/h2_frames.h" +/* cache_http2_proto.c */ +int h2_rxframe(struct worker *, struct h2_sess *); +void h2_req_body(struct req*); + + diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index 3148751..85fb45d 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -51,6 +51,8 @@ #undef H2EC2 #undef H2EC3 +typedef h2_error h2_frame_f(struct worker *, struct h2_sess *, struct h2_req *); + enum h2frame { #define H2_FRAME(l,u,t,f) H2F_##u = t, #include "tbl/h2_frames.h" @@ -84,28 +86,9 @@ h2_settingname(enum h2setting h2f) #define H2_FRAME_FLAGS(l,u,v) const uint8_t H2FF_##u = v; #include "tbl/h2_frames.h" -static const char h2_resp_101[] = - "HTTP/1.1 101 Switching Protocols\r\n" - "Connection: Upgrade\r\n" - "Upgrade: h2c\r\n" - "\r\n"; - -static const char H2_prism[24] = { - 0x50, 0x52, 0x49, 0x20, 0x2a, 0x20, 0x48, 0x54, - 0x54, 0x50, 0x2f, 0x32, 0x2e, 0x30, 0x0d, 0x0a, - 0x0d, 0x0a, 0x53, 0x4d, 0x0d, 0x0a, 0x0d, 0x0a -}; - -static const uint8_t H2_settings[] = { - 0x00, 0x03, - 0x00, 0x00, 0x00, 0x64, - 0x00, 0x04, - 0x00, 0x00, 0xff, 0xff -}; - /**********************************************************************/ #define DUMMY_FRAME(l) \ - h2_error __match_proto__(h2_frame_f) \ + static h2_error __match_proto__(h2_frame_f) \ h2_rx_##l(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) \ __match_proto__(h2_frame_f) \ { (void)wrk; (void)r2; VSLb(h2->vsl, SLT_Debug, "XXX implement " #l); INCOMPL(); } @@ -115,62 +98,6 @@ DUMMY_FRAME(push_promise) DUMMY_FRAME(continuation) /********************************************************************** - * The h2_sess struct needs many of the same things as a request, - * WS, VSL, HTC &c, but rather than implement all that stuff over, we - * grab an actual struct req, and mirror the relevant fields into - * struct h2_sess. - * To make things really incestuous, we allocate the h2_sess on - * the WS of that "Session ReQuest". - */ - -static struct h2_sess * -h2_new_sess(const struct worker *wrk, struct sess *sp, struct req *srq) -{ - uintptr_t *up; - struct h2_sess *h2; - - if (SES_Get_xport_priv(sp, &up)) { - /* Already reserved if we came via H1 */ - SES_Reserve_xport_priv(sp, &up); - *up = 0; - } - if (*up == 0) { - if (srq == NULL) - srq = Req_New(wrk, sp); - AN(srq); - h2 = WS_Alloc(srq->ws, sizeof *h2); - AN(h2); - INIT_OBJ(h2, H2_SESS_MAGIC); - h2->srq = srq; - h2->htc = srq->htc; - h2->ws = srq->ws; - h2->vsl = srq->vsl; - h2->vsl->wid = sp->vxid; - h2->htc->rfd = &sp->fd; - h2->sess = sp; - VTAILQ_INIT(&h2->streams); -#define H2_SETTINGS(n,v,d) \ - do { \ - assert(v < H2_SETTINGS_N); \ - h2->their_settings[v] = d; \ - h2->our_settings[v] = d; \ - } while (0); -#include "tbl/h2_settings.h" -#undef H2_SETTINGS - - /* XXX: Lacks a VHT_Fini counterpart. Will leak memory. */ - AZ(VHT_Init(h2->dectbl, - h2->our_settings[H2S_HEADER_TABLE_SIZE])); - - SES_Reserve_xport_priv(sp, &up); - *up = (uintptr_t)h2; - } - AN(up); - CAST_OBJ_NOTNULL(h2, (void*)(*up), H2_SESS_MAGIC); - return (h2); -} - -/********************************************************************** */ static struct h2_req * @@ -295,7 +222,7 @@ h2_vsl_frame(const struct h2_sess *h2, const void *ptr, size_t len) /********************************************************************** */ -h2_error __match_proto__(h2_frame_f) +static h2_error __match_proto__(h2_frame_f) h2_rx_ping(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) { @@ -313,7 +240,7 @@ h2_rx_ping(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) /********************************************************************** */ -h2_error __match_proto__(h2_frame_f) +static h2_error __match_proto__(h2_frame_f) h2_rx_goaway(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) { uint32_t error; @@ -327,7 +254,7 @@ h2_rx_goaway(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) return (0); } -h2_error __match_proto__(h2_frame_f) +static h2_error __match_proto__(h2_frame_f) h2_rx_window_update(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) { uint32_t wu; @@ -349,7 +276,7 @@ h2_rx_window_update(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) * Incoming PRIORITY, possibly an ACK of one we sent. */ -h2_error __match_proto__(h2_frame_f) +static h2_error __match_proto__(h2_frame_f) h2_rx_priority(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) { @@ -363,7 +290,7 @@ h2_rx_priority(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) * Incoming SETTINGS, possibly an ACK of one we sent. */ -h2_error __match_proto__(h2_frame_f) +static h2_error __match_proto__(h2_frame_f) h2_rx_settings(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) { const uint8_t *p = h2->rxf_data; @@ -410,7 +337,7 @@ h2_do_req(struct worker *wrk, void *priv) h2_del_req(wrk, r2); } -h2_error __match_proto__(h2_frame_f) +static h2_error __match_proto__(h2_frame_f) h2_rx_headers(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) { struct req *req; @@ -485,7 +412,7 @@ h2_rx_headers(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) /**********************************************************************/ -h2_error __match_proto__(h2_frame_f) +static h2_error __match_proto__(h2_frame_f) h2_rx_data(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) { (void)wrk; @@ -542,7 +469,7 @@ static const struct vfp h2_body = { .pull = h2_vfp_body, }; -static void __match_proto__(vtr_req_body_t) +void __match_proto__(vtr_req_body_t) h2_req_body(struct req *req) { struct h2_req *r2; @@ -557,21 +484,6 @@ h2_req_body(struct req *req) /**********************************************************************/ -enum htc_status_e __match_proto__(htc_complete_f) -H2_prism_complete(struct http_conn *htc) -{ - int l; - - CHECK_OBJ_NOTNULL(htc, HTTP_CONN_MAGIC); - l = htc->rxbuf_e - htc->rxbuf_b; - if (l >= sizeof(H2_prism) && - !memcmp(htc->rxbuf_b, H2_prism, sizeof(H2_prism))) - return (HTC_S_COMPLETE); - if (l < sizeof(H2_prism) && !memcmp(htc->rxbuf_b, H2_prism, l)) - return (HTC_S_MORE); - return (HTC_S_JUNK); -} - static enum htc_status_e __match_proto__(htc_complete_f) h2_frame_complete(struct http_conn *htc) { @@ -664,7 +576,7 @@ h2_procframe(struct worker *wrk, struct h2_sess *h2) return (0); } -static int +int h2_rxframe(struct worker *wrk, struct h2_sess *h2) { enum htc_status_e hs; @@ -705,215 +617,3 @@ h2_rxframe(struct worker *wrk, struct h2_sess *h2) Lck_Unlock(&h2->sess->mtx); return (h2e ? 0 : 1); } - - -/********************************************************************** - * Deal with the base64url (NB: ...url!) encoded SETTINGS in the H1 req - * of a H2C upgrade. - */ - -static int -h2_b64url_settings(struct h2_sess *h2, struct req *req) -{ - const char *p, *q; - uint8_t u[6], *up; - unsigned x; - int i, n; - static const char s[] = - "ABCDEFGHIJKLMNOPQRSTUVWXYZ" - "abcdefghijklmnopqrstuvwxyz" - "0123456789" - "-_="; - - /* - * If there is trouble with this, we could reject the upgrade - * but putting this on the H1 side is just plain wrong... - */ - AN(http_GetHdr(req->http, H_HTTP2_Settings, &p)); - if (p == NULL) - return (-1); - VSLb(req->vsl, SLT_Debug, "H2CS %s", p); - - n = 0; - x = 0; - up = u; - for (;*p; p++) { - q = strchr(s, *p); - if (q == NULL) - return (-1); - i = q - s; - assert(i >= 0 && i <= 63); - x <<= 6; - x |= i; - n += 6; - if (n < 8) - continue; - *up++ = (uint8_t)(x >> (n - 8)); - n -= 8; - if (up == u + sizeof u) { - AZ(n); - h2_setting(h2, (void*)u); - up = u; - } - } - if (up != u) - return (-1); - return (0); -} - -/**********************************************************************/ - -static int -h2_new_pu_session(struct worker *wrk, const struct h2_sess *h2) -{ - enum htc_status_e hs; - - (void)wrk; - - hs = H2_prism_complete(h2->htc); - if (hs == HTC_S_MORE) { - VSLb(h2->vsl, SLT_Debug, "Short pu PRISM"); - return (0); - } - if (hs != HTC_S_COMPLETE) { - VSLb(h2->vsl, SLT_Debug, "Wrong pu PRISM"); - return (0); - } - HTC_RxPipeline(h2->htc, h2->htc->rxbuf_b + sizeof(H2_prism)); - HTC_RxInit(h2->htc, wrk->aws); - - VSLb(h2->vsl, SLT_Debug, "H2: Got pu PRISM"); - return (1); -} - -/**********************************************************************/ - -static int -h2_new_ou_session(struct worker *wrk, struct h2_sess *h2, - struct req *req) -{ - ssize_t sz; - enum htc_status_e hs; - - sz = write(h2->sess->fd, h2_resp_101, strlen(h2_resp_101)); - assert(sz == strlen(h2_resp_101)); - - AZ(h2_b64url_settings(h2, req)); - http_Unset(req->http, H_Upgrade); - http_Unset(req->http, H_HTTP2_Settings); - - /* Steal pipelined read-ahead, if any */ - h2->htc->pipeline_b = req->htc->pipeline_b; - h2->htc->pipeline_e = req->htc->pipeline_e; - req->htc->pipeline_b = NULL; - req->htc->pipeline_e = NULL; - /* XXX: This call may assert on buffer overflow if the pipelined - data exceeds the available space in the aws workspace. What to - do about the overflowing data is an open issue. */ - HTC_RxInit(h2->htc, wrk->aws); - - /* Start req thread */ - (void)h2_new_req(wrk, h2, 1, req); - req->req_step = R_STP_RECV; - req->transport = &H2_transport; - req->task.func = h2_do_req; - req->task.priv = req; - req->err_code = 0; - http_SetH(req->http, HTTP_HDR_PROTO, "HTTP/2.0"); - XXXAZ(Pool_Task(wrk->pool, &req->task, TASK_QUEUE_REQ)); - - /* Wait for PRISM response */ - hs = HTC_RxStuff(h2->htc, H2_prism_complete, - NULL, NULL, NAN, h2->sess->t_idle + cache_param->timeout_idle, 256); - if (hs != HTC_S_COMPLETE) { - /* XXX clean up req thread */ - VSLb(h2->vsl, SLT_Debug, "H2: No OU PRISM (hs=%d)", hs); - Req_Release(req); - Lck_Unlock(&h2->sess->mtx); - SES_Delete(h2->sess, SC_RX_JUNK, NAN); - return (0); - } - HTC_RxPipeline(h2->htc, h2->htc->rxbuf_b + sizeof(H2_prism)); - HTC_RxInit(h2->htc, wrk->aws); - VSLb(h2->vsl, SLT_Debug, "H2: Got PRISM"); - return (1); -} - -static void __match_proto__(task_func_t) -h2_new_session(struct worker *wrk, void *arg) -{ - struct req *req; - struct sess *sp; - struct h2_sess *h2; - struct h2_req *r2, *r22; - uintptr_t wsp; - - CHECK_OBJ_NOTNULL(wrk, WORKER_MAGIC); - CAST_OBJ_NOTNULL(req, arg, REQ_MAGIC); - sp = req->sp; - CHECK_OBJ_NOTNULL(sp, SESS_MAGIC); - - assert(req->transport == &H2_transport); - - wsp = WS_Snapshot(wrk->aws); - - switch(req->err_code) { - case 0: - /* Direct H2 connection (via Proxy) */ - h2 = h2_new_sess(wrk, sp, req); - Lck_Lock(&h2->sess->mtx); - (void)h2_new_req(wrk, h2, 0, NULL); - break; - case 1: - /* Prior Knowledge H1->H2 upgrade */ - h2 = h2_new_sess(wrk, sp, req); - Lck_Lock(&h2->sess->mtx); - (void)h2_new_req(wrk, h2, 0, NULL); - - if (!h2_new_pu_session(wrk, h2)) - return; - break; - case 2: - /* Optimistic H1->H2 upgrade */ - h2 = h2_new_sess(wrk, sp, NULL); - Lck_Lock(&h2->sess->mtx); - (void)h2_new_req(wrk, h2, 0, NULL); - - if (!h2_new_ou_session(wrk, h2, req)) - return; - break; - default: - WRONG("Bad req->err_code"); - } - - THR_SetRequest(h2->srq); - - H2_Send_Frame(wrk, h2, - H2_FRAME_SETTINGS, H2FF_NONE, sizeof H2_settings, 0, H2_settings); - - /* and off we go... */ - h2->cond = &wrk->cond; - Lck_Unlock(&h2->sess->mtx); - - while (h2_rxframe(wrk, h2)) { - WS_Reset(wrk->aws, wsp); - HTC_RxInit(h2->htc, wrk->aws); - } - - /* Delete all idle streams */ - VTAILQ_FOREACH_SAFE(r2, &h2->streams, list, r22) { - if (r2->state == H2_S_IDLE) - h2_del_req(wrk, r2); - } - h2->cond = NULL; -} - -struct transport H2_transport = { - .name = "H2", - .magic = TRANSPORT_MAGIC, - .new_session = h2_new_session, - .sess_panic = h2_sess_panic, - .deliver = h2_deliver, - .req_body = h2_req_body, - .minimal_response = h2_minimal_response, -}; diff --git a/bin/varnishd/http2/cache_http2_session.c b/bin/varnishd/http2/cache_http2_session.c new file mode 100644 index 0000000..f63445c --- /dev/null +++ b/bin/varnishd/http2/cache_http2_session.c @@ -0,0 +1,460 @@ +/*- + * Copyright (c) 2016 Varnish Software AS + * All rights reserved. + * + * Author: Poul-Henning Kamp + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + */ + +#include "config.h" + +#include "cache/cache.h" + +#include + +#include "cache/cache_transport.h" +#include "cache/cache_filter.h" +#include "http2/cache_http2.h" + +#include "vend.h" + +static const char * +h2_settingname(enum h2setting h2f) +{ + + switch(h2f) { +#define H2_SETTINGS(n,v,d) case H2S_##n: return #n; +#include "tbl/h2_settings.h" +#undef H2_SETTINGS + default: + return (NULL); + } +} + +static const char h2_resp_101[] = + "HTTP/1.1 101 Switching Protocols\r\n" + "Connection: Upgrade\r\n" + "Upgrade: h2c\r\n" + "\r\n"; + +static const char H2_prism[24] = { + 0x50, 0x52, 0x49, 0x20, 0x2a, 0x20, 0x48, 0x54, + 0x54, 0x50, 0x2f, 0x32, 0x2e, 0x30, 0x0d, 0x0a, + 0x0d, 0x0a, 0x53, 0x4d, 0x0d, 0x0a, 0x0d, 0x0a +}; + +static const uint8_t H2_settings[] = { + 0x00, 0x03, + 0x00, 0x00, 0x00, 0x64, + 0x00, 0x04, + 0x00, 0x00, 0xff, 0xff +}; + +/********************************************************************** + * The h2_sess struct needs many of the same things as a request, + * WS, VSL, HTC &c, but rather than implement all that stuff over, we + * grab an actual struct req, and mirror the relevant fields into + * struct h2_sess. + * To make things really incestuous, we allocate the h2_sess on + * the WS of that "Session ReQuest". + */ + +static struct h2_sess * +h2_new_sess(const struct worker *wrk, struct sess *sp, struct req *srq) +{ + uintptr_t *up; + struct h2_sess *h2; + + if (SES_Get_xport_priv(sp, &up)) { + /* Already reserved if we came via H1 */ + SES_Reserve_xport_priv(sp, &up); + *up = 0; + } + if (*up == 0) { + if (srq == NULL) + srq = Req_New(wrk, sp); + AN(srq); + h2 = WS_Alloc(srq->ws, sizeof *h2); + AN(h2); + INIT_OBJ(h2, H2_SESS_MAGIC); + h2->srq = srq; + h2->htc = srq->htc; + h2->ws = srq->ws; + h2->vsl = srq->vsl; + h2->vsl->wid = sp->vxid; + h2->htc->rfd = &sp->fd; + h2->sess = sp; + VTAILQ_INIT(&h2->streams); +#define H2_SETTINGS(n,v,d) \ + do { \ + assert(v < H2_SETTINGS_N); \ + h2->their_settings[v] = d; \ + h2->our_settings[v] = d; \ + } while (0); +#include "tbl/h2_settings.h" +#undef H2_SETTINGS + + /* XXX: Lacks a VHT_Fini counterpart. Will leak memory. */ + AZ(VHT_Init(h2->dectbl, + h2->our_settings[H2S_HEADER_TABLE_SIZE])); + + SES_Reserve_xport_priv(sp, &up); + *up = (uintptr_t)h2; + } + AN(up); + CAST_OBJ_NOTNULL(h2, (void*)(*up), H2_SESS_MAGIC); + return (h2); +} + +/********************************************************************** + */ + +static struct h2_req * +h2_new_req(const struct worker *wrk, struct h2_sess *h2, + unsigned stream, struct req *req) +{ + struct h2_req *r2; + + Lck_AssertHeld(&h2->sess->mtx); + if (req == NULL) + req = Req_New(wrk, h2->sess); + CHECK_OBJ_NOTNULL(req, REQ_MAGIC); + + r2 = WS_Alloc(req->ws, sizeof *r2); + AN(r2); + INIT_OBJ(r2, H2_REQ_MAGIC); + r2->state = H2_S_IDLE; + r2->h2sess = h2; + r2->stream = stream; + r2->req = req; + req->transport_priv = r2; + // XXX: ordering ? + VTAILQ_INSERT_TAIL(&h2->streams, r2, list); + h2->refcnt++; + return (r2); +} + +static void +h2_del_req(struct worker *wrk, struct h2_req *r2) +{ + struct h2_sess *h2; + struct sess *sp; + struct req *req; + int r; + + h2 = r2->h2sess; + sp = h2->sess; + Lck_Lock(&sp->mtx); + assert(h2->refcnt > 0); + r = --h2->refcnt; + /* XXX: PRIORITY reshuffle */ + VTAILQ_REMOVE(&h2->streams, r2, list); + Lck_Unlock(&sp->mtx); + Req_Cleanup(sp, wrk, r2->req); + Req_Release(r2->req); + if (r) + return; + + /* All streams gone, including stream #0, clean up */ + req = h2->srq; + Req_Cleanup(sp, wrk, req); + Req_Release(req); + SES_Delete(sp, SC_RX_JUNK, NAN); +} + +/********************************************************************** + * Update and VSL a single SETTING rx'ed from the other side + * 'd' must point to six bytes. + */ + +static void +h2_setting(struct h2_sess *h2, const uint8_t *d) +{ + uint16_t x; + uint32_t y; + const char *n; + char nb[8]; + + x = vbe16dec(d); + y = vbe32dec(d + 2); + n = h2_settingname((enum h2setting)x); + if (n == NULL) { + bprintf(nb, "0x%04x", x); + n = nb; + } + VSLb(h2->vsl, SLT_Debug, "H2SETTING %s 0x%08x", n, y); + if (x > 0 && x < H2_SETTINGS_N) + h2->their_settings[x] = y; +} + +/********************************************************************** + * Incoming HEADERS, this is where the partys at... + */ + +static void __match_proto__(task_func_t) +h2_do_req(struct worker *wrk, void *priv) +{ + struct req *req; + struct h2_req *r2; + + CAST_OBJ_NOTNULL(req, priv, REQ_MAGIC); + CAST_OBJ_NOTNULL(r2, req->transport_priv, H2_REQ_MAGIC); + THR_SetRequest(req); + if (!CNT_GotReq(wrk, req)) + assert(CNT_Request(wrk, req) != REQ_FSM_DISEMBARK); + THR_SetRequest(NULL); + VSL(SLT_Debug, 0, "H2REQ CNT done"); + /* XXX clean up req */ + r2->state = H2_S_CLOSED; + h2_del_req(wrk, r2); +} + +/**********************************************************************/ + +enum htc_status_e __match_proto__(htc_complete_f) +H2_prism_complete(struct http_conn *htc) +{ + int l; + + CHECK_OBJ_NOTNULL(htc, HTTP_CONN_MAGIC); + l = htc->rxbuf_e - htc->rxbuf_b; + if (l >= sizeof(H2_prism) && + !memcmp(htc->rxbuf_b, H2_prism, sizeof(H2_prism))) + return (HTC_S_COMPLETE); + if (l < sizeof(H2_prism) && !memcmp(htc->rxbuf_b, H2_prism, l)) + return (HTC_S_MORE); + return (HTC_S_JUNK); +} + + +/********************************************************************** + * Deal with the base64url (NB: ...url!) encoded SETTINGS in the H1 req + * of a H2C upgrade. + */ + +static int +h2_b64url_settings(struct h2_sess *h2, struct req *req) +{ + const char *p, *q; + uint8_t u[6], *up; + unsigned x; + int i, n; + static const char s[] = + "ABCDEFGHIJKLMNOPQRSTUVWXYZ" + "abcdefghijklmnopqrstuvwxyz" + "0123456789" + "-_="; + + /* + * If there is trouble with this, we could reject the upgrade + * but putting this on the H1 side is just plain wrong... + */ + AN(http_GetHdr(req->http, H_HTTP2_Settings, &p)); + if (p == NULL) + return (-1); + VSLb(req->vsl, SLT_Debug, "H2CS %s", p); + + n = 0; + x = 0; + up = u; + for (;*p; p++) { + q = strchr(s, *p); + if (q == NULL) + return (-1); + i = q - s; + assert(i >= 0 && i <= 63); + x <<= 6; + x |= i; + n += 6; + if (n < 8) + continue; + *up++ = (uint8_t)(x >> (n - 8)); + n -= 8; + if (up == u + sizeof u) { + AZ(n); + h2_setting(h2, (void*)u); + up = u; + } + } + if (up != u) + return (-1); + return (0); +} + +/**********************************************************************/ + +static int +h2_new_pu_session(struct worker *wrk, const struct h2_sess *h2) +{ + enum htc_status_e hs; + + (void)wrk; + + hs = H2_prism_complete(h2->htc); + if (hs == HTC_S_MORE) { + VSLb(h2->vsl, SLT_Debug, "Short pu PRISM"); + return (0); + } + if (hs != HTC_S_COMPLETE) { + VSLb(h2->vsl, SLT_Debug, "Wrong pu PRISM"); + return (0); + } + HTC_RxPipeline(h2->htc, h2->htc->rxbuf_b + sizeof(H2_prism)); + HTC_RxInit(h2->htc, wrk->aws); + + VSLb(h2->vsl, SLT_Debug, "H2: Got pu PRISM"); + return (1); +} + +/**********************************************************************/ + +static int +h2_new_ou_session(struct worker *wrk, struct h2_sess *h2, + struct req *req) +{ + ssize_t sz; + enum htc_status_e hs; + + sz = write(h2->sess->fd, h2_resp_101, strlen(h2_resp_101)); + assert(sz == strlen(h2_resp_101)); + + AZ(h2_b64url_settings(h2, req)); + http_Unset(req->http, H_Upgrade); + http_Unset(req->http, H_HTTP2_Settings); + + /* Steal pipelined read-ahead, if any */ + h2->htc->pipeline_b = req->htc->pipeline_b; + h2->htc->pipeline_e = req->htc->pipeline_e; + req->htc->pipeline_b = NULL; + req->htc->pipeline_e = NULL; + /* XXX: This call may assert on buffer overflow if the pipelined + data exceeds the available space in the aws workspace. What to + do about the overflowing data is an open issue. */ + HTC_RxInit(h2->htc, wrk->aws); + + /* Start req thread */ + (void)h2_new_req(wrk, h2, 1, req); + req->req_step = R_STP_RECV; + req->transport = &H2_transport; + req->task.func = h2_do_req; + req->task.priv = req; + req->err_code = 0; + http_SetH(req->http, HTTP_HDR_PROTO, "HTTP/2.0"); + XXXAZ(Pool_Task(wrk->pool, &req->task, TASK_QUEUE_REQ)); + + /* Wait for PRISM response */ + hs = HTC_RxStuff(h2->htc, H2_prism_complete, + NULL, NULL, NAN, h2->sess->t_idle + cache_param->timeout_idle, 256); + if (hs != HTC_S_COMPLETE) { + /* XXX clean up req thread */ + VSLb(h2->vsl, SLT_Debug, "H2: No OU PRISM (hs=%d)", hs); + Req_Release(req); + Lck_Unlock(&h2->sess->mtx); + SES_Delete(h2->sess, SC_RX_JUNK, NAN); + return (0); + } + HTC_RxPipeline(h2->htc, h2->htc->rxbuf_b + sizeof(H2_prism)); + HTC_RxInit(h2->htc, wrk->aws); + VSLb(h2->vsl, SLT_Debug, "H2: Got PRISM"); + return (1); +} + +static void __match_proto__(task_func_t) +h2_new_session(struct worker *wrk, void *arg) +{ + struct req *req; + struct sess *sp; + struct h2_sess *h2; + struct h2_req *r2, *r22; + uintptr_t wsp; + + CHECK_OBJ_NOTNULL(wrk, WORKER_MAGIC); + CAST_OBJ_NOTNULL(req, arg, REQ_MAGIC); + sp = req->sp; + CHECK_OBJ_NOTNULL(sp, SESS_MAGIC); + + assert(req->transport == &H2_transport); + + wsp = WS_Snapshot(wrk->aws); + + switch(req->err_code) { + case 0: + /* Direct H2 connection (via Proxy) */ + h2 = h2_new_sess(wrk, sp, req); + Lck_Lock(&h2->sess->mtx); + (void)h2_new_req(wrk, h2, 0, NULL); + break; + case 1: + /* Prior Knowledge H1->H2 upgrade */ + h2 = h2_new_sess(wrk, sp, req); + Lck_Lock(&h2->sess->mtx); + (void)h2_new_req(wrk, h2, 0, NULL); + + if (!h2_new_pu_session(wrk, h2)) + return; + break; + case 2: + /* Optimistic H1->H2 upgrade */ + h2 = h2_new_sess(wrk, sp, NULL); + Lck_Lock(&h2->sess->mtx); + (void)h2_new_req(wrk, h2, 0, NULL); + + if (!h2_new_ou_session(wrk, h2, req)) + return; + break; + default: + WRONG("Bad req->err_code"); + } + + THR_SetRequest(h2->srq); + + H2_Send_Frame(wrk, h2, + H2_FRAME_SETTINGS, H2FF_NONE, sizeof H2_settings, 0, H2_settings); + + /* and off we go... */ + h2->cond = &wrk->cond; + Lck_Unlock(&h2->sess->mtx); + + while (h2_rxframe(wrk, h2)) { + WS_Reset(wrk->aws, wsp); + HTC_RxInit(h2->htc, wrk->aws); + } + + /* Delete all idle streams */ + VTAILQ_FOREACH_SAFE(r2, &h2->streams, list, r22) { + if (r2->state == H2_S_IDLE) + h2_del_req(wrk, r2); + } + h2->cond = NULL; +} + +struct transport H2_transport = { + .name = "H2", + .magic = TRANSPORT_MAGIC, + .new_session = h2_new_session, + .sess_panic = h2_sess_panic, + .deliver = h2_deliver, + .req_body = h2_req_body, + .minimal_response = h2_minimal_response, +}; From phk at FreeBSD.org Thu Mar 2 15:10:07 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Thu, 02 Mar 2017 16:10:07 +0100 Subject: [master] 9138957 Handle bogus ping -ack packets Message-ID: commit 9138957c23c7af72dfa417eb3cbc9a4810fe327d Author: Poul-Henning Kamp Date: Thu Mar 2 13:21:27 2017 +0000 Handle bogus ping -ack packets diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index 85fb45d..26c6814 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -231,7 +231,8 @@ h2_rx_ping(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) return (H2CE_FRAME_SIZE_ERROR); if (h2->rxf_stream != 0) return (H2CE_PROTOCOL_ERROR); - xxxassert(h2->rxf_flags == 0); // XXX: we never send pings + if (h2->rxf_flags != 0) + return (H2SE_PROTOCOL_ERROR); H2_Send_Frame(wrk, h2, H2_FRAME_PING, H2FF_PING_ACK, 8, 0, h2->rxf_data); return (0); @@ -501,6 +502,8 @@ h2_frame_complete(struct http_conn *htc) return (HTC_S_COMPLETE); } +/**********************************************************************/ + struct h2flist_s { const char *name; h2_frame_f *func; @@ -576,6 +579,10 @@ h2_procframe(struct worker *wrk, struct h2_sess *h2) return (0); } +/*********************************************************************** + * Called in loop from h2_new_session() + */ + int h2_rxframe(struct worker *wrk, struct h2_sess *h2) { @@ -608,11 +615,9 @@ h2_rxframe(struct worker *wrk, struct h2_sess *h2) Lck_Lock(&h2->sess->mtx); h2e = h2_procframe(wrk, h2); if (h2e) { - VSLb(h2->vsl, SLT_Debug, "H2: stream 0: %s", h2e->txt); vbe32enc(b, h2->highest_stream); vbe32enc(b + 4, h2e->val); - (void)H2_Send_Frame(wrk, h2, H2_FRAME_GOAWAY, - 0, sizeof b, 0, b); + (void)H2_Send_Frame(wrk, h2, H2_FRAME_GOAWAY, 0, 8, 0, b); } Lck_Unlock(&h2->sess->mtx); return (h2e ? 0 : 1); diff --git a/bin/varnishtest/tests/t02003.vtc b/bin/varnishtest/tests/t02003.vtc index f2e26db..1e3824b 100644 --- a/bin/varnishtest/tests/t02003.vtc +++ b/bin/varnishtest/tests/t02003.vtc @@ -74,3 +74,14 @@ client c1 { expect goaway.err == FLOW_CONTROL_ERROR } -run } -run + +# Test PING error conditions + +client c1 { + stream 0 { + txping -ack -data "FOOBAR42" + rxgoaway + expect goaway.laststream == 0 + expect goaway.err == PROTOCOL_ERROR + } -run +} -run From phk at FreeBSD.org Thu Mar 2 15:10:07 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Thu, 02 Mar 2017 16:10:07 +0100 Subject: [master] bc38ebe More nitpicking while waiting in train. Message-ID: commit bc38ebed8bb349ee3e4332d18eac03ecc178abe9 Author: Poul-Henning Kamp Date: Thu Mar 2 15:00:43 2017 +0000 More nitpicking while waiting in train. diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index 26c6814..93e22ec 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -86,17 +86,6 @@ h2_settingname(enum h2setting h2f) #define H2_FRAME_FLAGS(l,u,v) const uint8_t H2FF_##u = v; #include "tbl/h2_frames.h" -/**********************************************************************/ -#define DUMMY_FRAME(l) \ - static h2_error __match_proto__(h2_frame_f) \ - h2_rx_##l(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) \ - __match_proto__(h2_frame_f) \ - { (void)wrk; (void)r2; VSLb(h2->vsl, SLT_Debug, "XXX implement " #l); INCOMPL(); } - -DUMMY_FRAME(rst_stream) -DUMMY_FRAME(push_promise) -DUMMY_FRAME(continuation) - /********************************************************************** */ @@ -153,31 +142,6 @@ h2_del_req(struct worker *wrk, struct h2_req *r2) SES_Delete(sp, SC_RX_JUNK, NAN); } -/********************************************************************** - * Update and VSL a single SETTING rx'ed from the other side - * 'd' must point to six bytes. - */ - -static void -h2_setting(struct h2_sess *h2, const uint8_t *d) -{ - uint16_t x; - uint32_t y; - const char *n; - char nb[8]; - - x = vbe16dec(d); - y = vbe32dec(d + 2); - n = h2_settingname((enum h2setting)x); - if (n == NULL) { - bprintf(nb, "0x%04x", x); - n = nb; - } - VSLb(h2->vsl, SLT_Debug, "H2SETTING %s 0x%08x", n, y); - if (x > 0 && x < H2_SETTINGS_N) - h2->their_settings[x] = y; -} - /**********************************************************************/ static void @@ -242,6 +206,42 @@ h2_rx_ping(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) */ static h2_error __match_proto__(h2_frame_f) +h2_rx_continuation(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) +{ + (void)wrk; + (void)h2; + (void)r2; + INCOMPL(); +} + +/********************************************************************** + */ + +static h2_error __match_proto__(h2_frame_f) +h2_rx_push_promise(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) +{ + (void)wrk; + (void)h2; + (void)r2; + return (H2CE_PROTOCOL_ERROR); +} + +/********************************************************************** + */ + +static h2_error __match_proto__(h2_frame_f) +h2_rx_rst_stream(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) +{ + (void)wrk; + (void)h2; + (void)r2; + INCOMPL(); +} + +/********************************************************************** + */ + +static h2_error __match_proto__(h2_frame_f) h2_rx_goaway(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) { uint32_t error; @@ -255,6 +255,9 @@ h2_rx_goaway(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) return (0); } +/********************************************************************** + */ + static h2_error __match_proto__(h2_frame_f) h2_rx_window_update(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) { @@ -291,6 +294,26 @@ h2_rx_priority(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) * Incoming SETTINGS, possibly an ACK of one we sent. */ +static void +h2_setting(struct h2_sess *h2, const uint8_t *d) +{ + uint16_t x; + uint32_t y; + const char *n; + char nb[8]; + + x = vbe16dec(d); + y = vbe32dec(d + 2); + n = h2_settingname((enum h2setting)x); + if (n == NULL) { + bprintf(nb, "0x%04x", x); + n = nb; + } + VSLb(h2->vsl, SLT_Debug, "H2SETTING %s 0x%08x", n, y); + if (x > 0 && x < H2_SETTINGS_N) + h2->their_settings[x] = y; +} + static h2_error __match_proto__(h2_frame_f) h2_rx_settings(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) { diff --git a/bin/varnishtest/tests/t02003.vtc b/bin/varnishtest/tests/t02003.vtc index 1e3824b..4d7db98 100644 --- a/bin/varnishtest/tests/t02003.vtc +++ b/bin/varnishtest/tests/t02003.vtc @@ -85,3 +85,17 @@ client c1 { expect goaway.err == PROTOCOL_ERROR } -run } -run + +# Test PUSH_PROMISE error conditions + +client c1 { + stream 0 { + rxgoaway + expect goaway.err == PROTOCOL_ERROR + expect goaway.laststream == 1 + } -start + stream 1 { + sendhex "000008 05 00 00000001 0001020304050607" + } -run + stream 0 -wait +} -run From phk at FreeBSD.org Thu Mar 2 18:22:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Thu, 02 Mar 2017 19:22:05 +0100 Subject: [master] 0ce6565 add needless returns Message-ID: commit 0ce656526df0b0e2a93d0a8734663476c3b5ca2d Author: Poul-Henning Kamp Date: Thu Mar 2 18:21:09 2017 +0000 add needless returns diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index 93e22ec..63eeb4e 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -212,6 +212,7 @@ h2_rx_continuation(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) (void)h2; (void)r2; INCOMPL(); + NEEDLESS(return (H2CE_PROTOCOL_ERROR)); } /********************************************************************** @@ -236,6 +237,7 @@ h2_rx_rst_stream(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) (void)h2; (void)r2; INCOMPL(); + NEEDLESS(return (H2CE_PROTOCOL_ERROR)); } /********************************************************************** From varnish-commit at varnish-cache.org Thu Mar 2 18:20:47 2017 From: varnish-commit at varnish-cache.org (oca) Date: Fri, 3 Mar 2017 02:20:47 +0800 Subject: =?utf-8?B?dmFybmlzaC1jb21taXTvvJrmgqjmg7PlrabkuaDpmL8=?= =?utf-8?B?6YeM5Yib5paw566h55CG5pa56Z2i55qE5oiQ5Yqf57uP6aqM5ZCX77yfIDMyNTMy?= Message-ID: <20170303022101854101@svb.org> varnish-commit???? ???????????????????????????????? ???? ????????????????????????? ????????????????????????????571??????? ????????????????????????????????????????????????????????????????? ??????????????????????????????? 2:21:012017/3/3 ??? -------------- next part -------------- An HTML attachment was scrubbed... URL: -------------- next part -------------- A non-text attachment was scrubbed... Name: ??????????????.doc Type: application/msword Size: 66048 bytes Desc: not available URL: From fgsch at lodoss.net Fri Mar 3 12:30:07 2017 From: fgsch at lodoss.net (Federico G. Schwindt) Date: Fri, 03 Mar 2017 13:30:07 +0100 Subject: [master] 8f33a90 These are fatal as well Message-ID: commit 8f33a9078a537e5051ed9dc57715a52f72698cc5 Author: Federico G. Schwindt Date: Fri Mar 3 12:26:29 2017 +0000 These are fatal as well diff --git a/bin/varnishtest/vtc_server.c b/bin/varnishtest/vtc_server.c index c1ad16b..f9b01a1 100644 --- a/bin/varnishtest/vtc_server.c +++ b/bin/varnishtest/vtc_server.c @@ -81,6 +81,8 @@ server_new(const char *name) REPLACE(s->name, name); s->vl = vtc_logopen(s->name); AN(s->vl); + if (*s->name != 's') + vtc_fatal(s->vl, "Server name must start with 's'"); bprintf(s->listen, "%s", "127.0.0.1 0"); s->repeat = 1; @@ -361,12 +363,6 @@ cmd_server(CMD_ARGS) AZ(strcmp(av[0], "server")); av++; - if (*av[0] != 's') { - fprintf(stderr, "Server name must start with 's' (is: %s)\n", - av[0]); - exit(1); - } - AZ(pthread_mutex_lock(&server_mtx)); VTAILQ_FOREACH(s, &servers, list) if (!strcmp(s->name, av[0])) @@ -417,11 +413,9 @@ cmd_server(CMD_ARGS) continue; } if (!strcmp(*av, "-dispatch")) { - if (strcmp(s->name, "s0")) { - fprintf(stderr, - "server -dispatch only works on s0\n"); - exit(1); - } + if (strcmp(s->name, "s0")) + vtc_fatal(s->vl, + "server -dispatch only works on s0"); server_dispatch(s); continue; } From nils.goroll at uplex.de Fri Mar 3 13:00:07 2017 From: nils.goroll at uplex.de (Nils Goroll) Date: Fri, 03 Mar 2017 14:00:07 +0100 Subject: [master] d466f8e vcc: support negative DURATION constants Message-ID: commit d466f8ebb3bf7303cba60831caa29db289388e00 Author: Nils Goroll Date: Fri Mar 3 13:57:53 2017 +0100 vcc: support negative DURATION constants we should probably unify the '-' and CNUM case in vcc_expr4() some time diff --git a/bin/varnishtest/tests/v00020.vtc b/bin/varnishtest/tests/v00020.vtc index 5f734fc..ba76e2d 100644 --- a/bin/varnishtest/tests/v00020.vtc +++ b/bin/varnishtest/tests/v00020.vtc @@ -37,15 +37,6 @@ varnish v1 -errvcl {Symbol not found: 'vcl_recv' (expected type STRING_LIST)} { } } -# XXX: not obvious if this actually fails for the desired reason ? -varnish v1 -errvcl {Unknown token '-' when looking for DURATION} { - sub vcl_recv { - if (req.ttl < -3s || req.ttl) { - set req.http.foo = vcl_recv; - } - } -} - varnish v1 -errvcl {Operator * not possible on type STRING.} { sub vcl_recv { set req.http.foo = "bla" * "foo"; @@ -113,6 +104,7 @@ varnish v1 -vcl { set req.http.foo = client.ip + ", " + server.ip; + set req.ttl = -1s; set req.ttl = 1s; set req.ttl *= 1.5; set req.ttl = 1.5 s * 2.5; diff --git a/lib/libvcc/vcc_expr.c b/lib/libvcc/vcc_expr.c index 5ec79cc..d116b9c 100644 --- a/lib/libvcc/vcc_expr.c +++ b/lib/libvcc/vcc_expr.c @@ -869,15 +869,21 @@ vcc_expr4(struct vcc *tl, struct expr **e, vcc_type_t fmt) *e = e1; return; case '-': - if (fmt == INT || fmt == REAL) { + if (fmt == INT || fmt == REAL || fmt == DURATION) { vcc_NextToken(tl); ExpectErr(tl, CNUM); if (fmt == INT) { - e1 = vcc_mk_expr(INT, "-%.*s", PF(tl->t)); + e1 = vcc_mk_expr(fmt, "-%.*s", PF(tl->t)); vcc_NextToken(tl); + } else if (fmt == REAL) { + e1 = vcc_mk_expr(fmt, "-%f", vcc_DoubleVal(tl)); + } else if (fmt == DURATION) { + vcc_NumVal(tl, &d, &i); + ERRCHK(tl); + e1 = vcc_mk_expr(fmt, "-%g", + d * vcc_TimeUnit(tl)); } else { - e1 = vcc_mk_expr(REAL, "-%f", - vcc_DoubleVal(tl)); + INCOMPL(); } ERRCHK(tl); e1->constant = EXPR_CONST; From fgsch at lodoss.net Fri Mar 3 14:47:05 2017 From: fgsch at lodoss.net (Federico G. Schwindt) Date: Fri, 03 Mar 2017 15:47:05 +0100 Subject: [master] 994f073 Polish Message-ID: commit 994f073602ff0e2a52dd92a2bdd2ece6269237cd Author: Federico G. Schwindt Date: Fri Mar 3 14:32:11 2017 +0000 Polish diff --git a/lib/libvcc/vcc_expr.c b/lib/libvcc/vcc_expr.c index d116b9c..b2f1dc4 100644 --- a/lib/libvcc/vcc_expr.c +++ b/lib/libvcc/vcc_expr.c @@ -875,16 +875,15 @@ vcc_expr4(struct vcc *tl, struct expr **e, vcc_type_t fmt) if (fmt == INT) { e1 = vcc_mk_expr(fmt, "-%.*s", PF(tl->t)); vcc_NextToken(tl); - } else if (fmt == REAL) { - e1 = vcc_mk_expr(fmt, "-%f", vcc_DoubleVal(tl)); } else if (fmt == DURATION) { - vcc_NumVal(tl, &d, &i); + vcc_Duration(tl, &d); ERRCHK(tl); - e1 = vcc_mk_expr(fmt, "-%g", - d * vcc_TimeUnit(tl)); - } else { + e1 = vcc_mk_expr(fmt, "-%g", d); + } else if (fmt == REAL) + e1 = vcc_mk_expr(fmt, "-%f", + vcc_DoubleVal(tl)); + else INCOMPL(); - } ERRCHK(tl); e1->constant = EXPR_CONST; *e = e1; diff --git a/lib/libvmod_std/vmod_std.c b/lib/libvmod_std/vmod_std.c index 81e49f7..557e88d 100644 --- a/lib/libvmod_std/vmod_std.c +++ b/lib/libvmod_std/vmod_std.c @@ -260,8 +260,6 @@ vmod_getenv(VRT_CTX, VCL_STRING name) VCL_VOID __match_proto__(td_std_late_100_continue) vmod_late_100_continue(VRT_CTX, VCL_BOOL late) { - struct req *req; - CHECK_OBJ_NOTNULL(ctx, VRT_CTX_MAGIC); if (ctx->method != VCL_MET_RECV) { VSLb(ctx->vsl, SLT_VCL_Error, @@ -269,11 +267,7 @@ vmod_late_100_continue(VRT_CTX, VCL_BOOL late) return; } - req = ctx->req; - CHECK_OBJ_NOTNULL(req, REQ_MAGIC); - - if (! req->want100cont) - return; - - req->late100cont = !!late; + CHECK_OBJ_NOTNULL(ctx->req, REQ_MAGIC); + if (ctx->req->want100cont) + ctx->req->late100cont = late; } From phk at FreeBSD.org Fri Mar 3 15:15:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Fri, 03 Mar 2017 16:15:06 +0100 Subject: [master] e5f8204 Make Continuation frames non-panicky. Message-ID: commit e5f8204e7161de46f15347c506112078159e95c4 Author: Poul-Henning Kamp Date: Fri Mar 3 15:14:32 2017 +0000 Make Continuation frames non-panicky. diff --git a/bin/varnishd/http2/cache_http2.h b/bin/varnishd/http2/cache_http2.h index 58acdeb..b950dad 100644 --- a/bin/varnishd/http2/cache_http2.h +++ b/bin/varnishd/http2/cache_http2.h @@ -28,6 +28,7 @@ */ struct h2_sess; +struct h2h_decode; #include "hpack/vhp.h" @@ -83,6 +84,7 @@ struct h2_req { struct req *req; VTAILQ_ENTRY(h2_req) list; int64_t window; + struct h2h_decode *decode; }; VTAILQ_HEAD(h2_req_s, h2_req); diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index 63eeb4e..602608f 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -32,6 +32,7 @@ #include "cache/cache.h" #include +#include #include "cache/cache_transport.h" #include "cache/cache_filter.h" @@ -206,19 +207,6 @@ h2_rx_ping(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) */ static h2_error __match_proto__(h2_frame_f) -h2_rx_continuation(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) -{ - (void)wrk; - (void)h2; - (void)r2; - INCOMPL(); - NEEDLESS(return (H2CE_PROTOCOL_ERROR)); -} - -/********************************************************************** - */ - -static h2_error __match_proto__(h2_frame_f) h2_rx_push_promise(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) { (void)wrk; @@ -363,20 +351,41 @@ h2_do_req(struct worker *wrk, void *priv) h2_del_req(wrk, r2); } +static h2_error +h2_end_headers(struct worker *wrk, struct h2_sess *h2, struct req *req, + struct h2_req *r2) +{ + h2_error h2e; + + h2e = h2h_decode_fini(h2, r2->decode); + FREE_OBJ(r2->decode); + if (h2e != NULL) { + VSL(SLT_Debug, 0, "H2H_DECODE_FINI %s", h2e->name); + return (h2e); + } + VSLb_ts_req(req, "Req", req->t_req); + + if (h2->rxf_flags & H2FF_HEADERS_END_STREAM) + req->req_body_status = REQ_BODY_NONE; + else + req->req_body_status = REQ_BODY_WITHOUT_LEN; + + req->task.func = h2_do_req; + req->task.priv = req; + XXXAZ(Pool_Task(wrk->pool, &req->task, TASK_QUEUE_REQ)); + return (0); +} + static h2_error __match_proto__(h2_frame_f) h2_rx_headers(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) { struct req *req; - struct h2h_decode d[1]; h2_error h2e; const uint8_t *p; size_t l; - /* XXX: This still lacks support for CONTINUATION frames, half - * read frames and proper error handling. - */ - - xxxassert(r2->state == H2_S_IDLE); + if (r2->state != H2_S_IDLE) + return (H2CE_PROTOCOL_ERROR); // XXX spec ? r2->state = H2_S_OPEN; req = r2->req; @@ -400,7 +409,12 @@ h2_rx_headers(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) wrk->vcl = NULL; HTTP_Setup(req->http, req->ws, req->vsl, SLT_ReqMethod); - h2h_decode_init(h2, d); + http_SetH(req->http, HTTP_HDR_PROTO, "HTTP/2.0"); + + ALLOC_OBJ(r2->decode, H2H_DECODE_MAGIC); + AN(r2->decode); + h2h_decode_init(h2, r2->decode); + /* XXX: Error handling */ p = h2->rxf_data; l = h2->rxf_len; @@ -412,27 +426,36 @@ h2_rx_headers(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) p += 5; l -= 5; } - h2e = h2h_decode_bytes(h2, d, p, l); + h2e = h2h_decode_bytes(h2, r2->decode, p, l); if (h2e != NULL) { VSL(SLT_Debug, 0, "H2H_DECODE_BYTES %s", h2e->name); return (h2e); } - h2e = h2h_decode_fini(h2, d); + if (h2->rxf_flags & H2FF_HEADERS_END_HEADERS) + return (h2_end_headers(wrk, h2, req, r2)); + return (0); +} + +/********************************************************************** + * XXX: Check hard sequence req. for Cont. + */ + +static h2_error __match_proto__(h2_frame_f) +h2_rx_continuation(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) +{ + struct req *req; + h2_error h2e; + + if (r2->state != H2_S_OPEN) + return (H2CE_PROTOCOL_ERROR); // XXX spec ? + req = r2->req; + h2e = h2h_decode_bytes(h2, r2->decode, h2->rxf_data, h2->rxf_len); if (h2e != NULL) { - VSL(SLT_Debug, 0, "H2H_DECODE_FINI %s", h2e->name); + VSL(SLT_Debug, 0, "H2H_DECODE_BYTES %s", h2e->name); return (h2e); } - VSLb_ts_req(req, "Req", req->t_req); - http_SetH(req->http, HTTP_HDR_PROTO, "HTTP/2.0"); - - if (h2->rxf_flags & H2FF_HEADERS_END_STREAM) - req->req_body_status = REQ_BODY_NONE; - else - req->req_body_status = REQ_BODY_WITHOUT_LEN; - - req->task.func = h2_do_req; - req->task.priv = req; - XXXAZ(Pool_Task(wrk->pool, &req->task, TASK_QUEUE_REQ)); + if (h2->rxf_flags & H2FF_HEADERS_END_HEADERS) + return (h2_end_headers(wrk, h2, req, r2)); return (0); } diff --git a/bin/varnishtest/tests/t02006.vtc b/bin/varnishtest/tests/t02006.vtc index 1fd54e1..0160090 100644 --- a/bin/varnishtest/tests/t02006.vtc +++ b/bin/varnishtest/tests/t02006.vtc @@ -11,7 +11,18 @@ varnish v1 -cliok "param.set debug +syncvsl" client c1 { stream 1 { - txreq -req POST -hdr expect 100-continue -hdr content-type text/plain -hdr content-length 7 -body request + txreq \ + -req POST \ + -hdr content-type text/plain \ + -nostrend \ + -nohdrend + txcont \ + -hdr expect 100-continue \ + -hdr content-length 7 \ + -nostrend + + txdata \ + -data request rxhdrs expect resp.status == 100 From fgsch at lodoss.net Fri Mar 3 16:18:05 2017 From: fgsch at lodoss.net (Federico G. Schwindt) Date: Fri, 03 Mar 2017 17:18:05 +0100 Subject: [master] ae15fd7 Don't increment the hitpass stat for HfM Message-ID: commit ae15fd7f67f42e9b3de4cfb9500b8610465117f9 Author: Federico G. Schwindt Date: Fri Mar 3 16:03:25 2017 +0000 Don't increment the hitpass stat for HfM diff --git a/bin/varnishd/cache/cache_hash.c b/bin/varnishd/cache/cache_hash.c index 5e08fc8..6102009 100644 --- a/bin/varnishd/cache/cache_hash.c +++ b/bin/varnishd/cache/cache_hash.c @@ -440,7 +440,6 @@ HSH_Lookup(struct req *req, struct objcore **ocp, struct objcore **bocp, wrk->stats->cache_hitpass++; oc = NULL; } else if (oc->flags & OC_F_PASS) { - wrk->stats->cache_hitpass++; oc = NULL; *bocp = hsh_insert_busyobj(wrk, oh); } else { diff --git a/bin/varnishtest/tests/c00014.vtc b/bin/varnishtest/tests/c00014.vtc index 41eb00b..34f816a 100644 --- a/bin/varnishtest/tests/c00014.vtc +++ b/bin/varnishtest/tests/c00014.vtc @@ -43,4 +43,5 @@ client c2 { client c1 -wait -varnish v1 -expect cache_hitpass == 1 +varnish v1 -expect cache_hitpass == 0 +varnish v1 -expect cache_miss == 2 diff --git a/bin/varnishtest/tests/c00081.vtc b/bin/varnishtest/tests/c00081.vtc index f119570..24f3b21 100644 --- a/bin/varnishtest/tests/c00081.vtc +++ b/bin/varnishtest/tests/c00081.vtc @@ -44,3 +44,6 @@ client c1 { rxresp expect resp.http.miss == True } -run + +varnish v1 -expect MAIN.cache_hitpass == 1 +varnish v1 -expect MAIN.cache_miss == 2 diff --git a/bin/varnishtest/tests/r00425.vtc b/bin/varnishtest/tests/r00425.vtc index 1c2c19f..6c131cf 100644 --- a/bin/varnishtest/tests/r00425.vtc +++ b/bin/varnishtest/tests/r00425.vtc @@ -29,4 +29,5 @@ client c1 { rxresp } -run -varnish v1 -expect cache_hitpass == 2 +varnish v1 -expect cache_hitpass == 0 +varnish v1 -expect cache_miss == 3 From fgsch at lodoss.net Fri Mar 3 22:06:05 2017 From: fgsch at lodoss.net (Federico G. Schwindt) Date: Fri, 03 Mar 2017 23:06:05 +0100 Subject: [master] a0249cf Merge CNUM and '-' handling Message-ID: commit a0249cf26b713de1bd460358af7be49f24b9c5de Author: Federico G. Schwindt Date: Fri Mar 3 22:04:04 2017 +0000 Merge CNUM and '-' handling diff --git a/lib/libvcc/vcc_expr.c b/lib/libvcc/vcc_expr.c index b2f1dc4..eab2453 100644 --- a/lib/libvcc/vcc_expr.c +++ b/lib/libvcc/vcc_expr.c @@ -756,12 +756,13 @@ static void vcc_expr4(struct vcc *tl, struct expr **e, vcc_type_t fmt) { struct expr *e1, *e2; - const char *ip; + const char *ip, *sign; const struct symbol *sym; enum symkind kind; double d; int i; + sign = ""; *e = NULL; if (tl->t->tok == '(') { SkipToken(tl, '('); @@ -842,6 +843,13 @@ vcc_expr4(struct vcc *tl, struct expr **e, vcc_type_t fmt) vcc_NextToken(tl); *e = e1; return; + case '-': + if (fmt != INT && fmt != REAL && fmt != DURATION) + break; + vcc_NextToken(tl); + ExpectErr(tl, CNUM); + sign = "-"; + /* FALLTHROUGH */ case CNUM: /* * XXX: %g may not have enough decimals by default @@ -856,40 +864,19 @@ vcc_expr4(struct vcc *tl, struct expr **e, vcc_type_t fmt) vcc_NumVal(tl, &d, &i); ERRCHK(tl); if (tl->t->tok == ID) { - e1 = vcc_mk_expr(DURATION, "%g", - d * vcc_TimeUnit(tl)); + e1 = vcc_mk_expr(DURATION, "%s%g", + sign, d * vcc_TimeUnit(tl)); ERRCHK(tl); } else if (i || fmt == REAL) - e1 = vcc_mk_expr(REAL, "%f", d); + e1 = vcc_mk_expr(REAL, "%s%f", + sign, d); else - e1 = vcc_mk_expr(INT, "%ld", - (unsigned long)d); + e1 = vcc_mk_expr(INT, "%s%ld", + sign, (unsigned long)d); } e1->constant = EXPR_CONST; *e = e1; return; - case '-': - if (fmt == INT || fmt == REAL || fmt == DURATION) { - vcc_NextToken(tl); - ExpectErr(tl, CNUM); - if (fmt == INT) { - e1 = vcc_mk_expr(fmt, "-%.*s", PF(tl->t)); - vcc_NextToken(tl); - } else if (fmt == DURATION) { - vcc_Duration(tl, &d); - ERRCHK(tl); - e1 = vcc_mk_expr(fmt, "-%g", d); - } else if (fmt == REAL) - e1 = vcc_mk_expr(fmt, "-%f", - vcc_DoubleVal(tl)); - else - INCOMPL(); - ERRCHK(tl); - e1->constant = EXPR_CONST; - *e = e1; - return; - } - break; default: break; } From noreply at github.com Sat Mar 4 00:54:05 2017 From: noreply at github.com (GitHub) Date: Sat, 04 Mar 2017 01:54:05 +0100 Subject: [master] 91ee053 Merge pull request #2216 from rezan/fix/age_rounding Message-ID: commit 91ee053e3ae54fa052ef0cf0b80c235c1b7b5203 Merge: a0249cf 104af2a Author: Reza Naghibi Date: Fri Mar 3 19:53:19 2017 -0500 Merge pull request #2216 from rezan/fix/age_rounding Make sure Age is always less than max-age From phk at FreeBSD.org Sat Mar 4 09:22:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Sat, 04 Mar 2017 10:22:05 +0100 Subject: [master] 89af3f9 Some of the special cases of RST_STREAM Message-ID: commit 89af3f991d01d7b80f2c424171679c5f35a8ce32 Author: Poul-Henning Kamp Date: Sat Mar 4 09:14:29 2017 +0000 Some of the special cases of RST_STREAM diff --git a/bin/varnishd/http2/cache_http2.h b/bin/varnishd/http2/cache_http2.h index b950dad..3bf6eb0 100644 --- a/bin/varnishd/http2/cache_http2.h +++ b/bin/varnishd/http2/cache_http2.h @@ -110,6 +110,7 @@ struct h2_sess { struct vht_table dectbl[1]; unsigned rxf_len; + unsigned rxf_type; unsigned rxf_flags; unsigned rxf_stream; uint8_t *rxf_data; diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index 602608f..0c1565b 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -352,8 +352,8 @@ h2_do_req(struct worker *wrk, void *priv) } static h2_error -h2_end_headers(struct worker *wrk, struct h2_sess *h2, struct req *req, - struct h2_req *r2) +h2_end_headers(const struct worker *wrk, const struct h2_sess *h2, + struct req *req, struct h2_req *r2) { h2_error h2e; @@ -583,6 +583,19 @@ h2_procframe(struct worker *wrk, struct h2_sess *h2) VTAILQ_FOREACH(r2, &h2->streams, list) if (r2->stream == h2->rxf_stream) break; + + if (h2->rxf_type == H2_FRAME_RST_STREAM) { + /* Special case RST_STREAM to avoid creating streams */ + if (h2->rxf_len != 4) + return (H2CE_FRAME_SIZE_ERROR); // rfc7540 6.4 + if (h2->rxf_stream == 0) + return (H2CE_PROTOCOL_ERROR); // rfc7540 6.4 + if (h2->rxf_stream > h2->highest_stream) + return (H2CE_PROTOCOL_ERROR); // rfc7540 6.4 + if (r2 == NULL) + return (0); + } + if (r2 == NULL) { if (h2->rxf_stream <= h2->highest_stream) return (H2CE_PROTOCOL_ERROR); // rfc7540 5.1.1 @@ -591,17 +604,17 @@ h2_procframe(struct worker *wrk, struct h2_sess *h2) AN(r2); } - if (h2->htc->rxbuf_b[3] >= H2FMAX) { + if (h2->rxf_type >= H2FMAX) { h2->bogosity++; VSLb(h2->vsl, SLT_Debug, - "H2: Unknown Frame 0x%02x", h2->htc->rxbuf_b[3]); + "H2: Unknown Frame 0x%02x", h2->rxf_type); return (0); // rfc7540 4.1 } - h2f = h2flist + h2->htc->rxbuf_b[3]; + h2f = h2flist + h2->rxf_type; if (h2f->name == NULL || h2f->func == NULL) { h2->bogosity++; VSLb(h2->vsl, SLT_Debug, - "H2: Unimplemented Frame 0x%02x", h2->htc->rxbuf_b[3]); + "H2: Unimplemented Frame 0x%02x", h2->rxf_type); return (0); // rfc7540 4.1 } if (h2->rxf_flags & ~h2f->flags) { @@ -652,6 +665,7 @@ h2_rxframe(struct worker *wrk, struct h2_sess *h2) } h2->rxf_len = vbe32dec(h2->htc->rxbuf_b) >> 8; + h2->rxf_type = h2->htc->rxbuf_b[3]; h2->rxf_flags = h2->htc->rxbuf_b[4]; h2->rxf_stream = vbe32dec(h2->htc->rxbuf_b + 5); h2->rxf_data = (void*)(h2->htc->rxbuf_b + 9); diff --git a/bin/varnishtest/tests/t02003.vtc b/bin/varnishtest/tests/t02003.vtc index 4d7db98..89f6298 100644 --- a/bin/varnishtest/tests/t02003.vtc +++ b/bin/varnishtest/tests/t02003.vtc @@ -10,6 +10,7 @@ varnish v1 -vcl+backend {} -start varnish v1 -cliok "param.set feature +http2" varnish v1 -cliok "param.set debug +syncvsl" +####################################################################### # Test Even stream numbers client c1 { @@ -24,6 +25,7 @@ client c1 { stream 0 -wait } -run +####################################################################### # Test reverse order stream numbers client c1 { @@ -41,6 +43,7 @@ client c1 { stream 0 -wait } -run +####################################################################### # Test WINDOW_UPDATE error conditions client c1 { @@ -75,6 +78,7 @@ client c1 { } -run } -run +####################################################################### # Test PING error conditions client c1 { @@ -86,6 +90,7 @@ client c1 { } -run } -run +####################################################################### # Test PUSH_PROMISE error conditions client c1 { @@ -99,3 +104,35 @@ client c1 { } -run stream 0 -wait } -run + +# Test RST_STREAM error conditions + +client c1 { + stream 0 { + # RST idle stream + sendhex "000004 03 00 00000007 00000008" + rxgoaway + expect goaway.err == PROTOCOL_ERROR + expect goaway.laststream == 0 + } -run +} -run + +client c1 { + stream 0 { + # RST wrong length + sendhex "000005 03 00 00000001 0000000800" + rxgoaway + expect goaway.err == FRAME_SIZE_ERROR + expect goaway.laststream == 0 + } -run +} -run + +client c1 { + stream 0 { + # RST stream zero + sendhex "000000 03 00 00000000 00000008" + rxgoaway + expect goaway.err == FRAME_SIZE_ERROR + expect goaway.laststream == 0 + } -run +} -run From phk at FreeBSD.org Sat Mar 4 18:55:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Sat, 04 Mar 2017 19:55:05 +0100 Subject: [master] e9f32d6 HTTP2 is too complex, cite RFC's by line-numbers to give people a chance. Message-ID: commit e9f32d6284e063f31bd283ff8d0fda1e689bb75f Author: Poul-Henning Kamp Date: Sat Mar 4 10:51:47 2017 +0000 HTTP2 is too complex, cite RFC's by line-numbers to give people a chance. diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index 0c1565b..b2326e8 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -192,11 +192,11 @@ h2_rx_ping(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) { (void)r2; - if (h2->rxf_len != 8) + if (h2->rxf_len != 8) // rfc7540,l,2364,2366 return (H2CE_FRAME_SIZE_ERROR); - if (h2->rxf_stream != 0) + if (h2->rxf_stream != 0) // rfc7540,l,2359,2362 return (H2CE_PROTOCOL_ERROR); - if (h2->rxf_flags != 0) + if (h2->rxf_flags != 0) // We never send pings return (H2SE_PROTOCOL_ERROR); H2_Send_Frame(wrk, h2, H2_FRAME_PING, H2FF_PING_ACK, 8, 0, h2->rxf_data); @@ -209,6 +209,7 @@ h2_rx_ping(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) static h2_error __match_proto__(h2_frame_f) h2_rx_push_promise(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) { + // rfc7540,l,2262,2267 (void)wrk; (void)h2; (void)r2; @@ -574,10 +575,12 @@ h2_procframe(struct worker *wrk, struct h2_sess *h2) char b[4]; if (h2->rxf_stream != 0 && !(h2->rxf_stream & 1)) { + // rfc7540,l,1140,1145 + // rfc7540,l,1153,1158 /* No even streams, we don't do PUSH_PROMISE */ VSLb(h2->vsl, SLT_Debug, "H2: illegal stream (=%u)", h2->rxf_stream); - return (H2CE_PROTOCOL_ERROR); // rfc7540 5.1.1 + return (H2CE_PROTOCOL_ERROR); } VTAILQ_FOREACH(r2, &h2->streams, list) @@ -586,42 +589,45 @@ h2_procframe(struct worker *wrk, struct h2_sess *h2) if (h2->rxf_type == H2_FRAME_RST_STREAM) { /* Special case RST_STREAM to avoid creating streams */ - if (h2->rxf_len != 4) - return (H2CE_FRAME_SIZE_ERROR); // rfc7540 6.4 - if (h2->rxf_stream == 0) - return (H2CE_PROTOCOL_ERROR); // rfc7540 6.4 - if (h2->rxf_stream > h2->highest_stream) - return (H2CE_PROTOCOL_ERROR); // rfc7540 6.4 + if (h2->rxf_len != 4) // rfc7540,l,2003,2004 + return (H2CE_FRAME_SIZE_ERROR); + if (h2->rxf_stream == 0) // rfc7540,l,1993,1996 + return (H2CE_PROTOCOL_ERROR); + if (h2->rxf_stream > h2->highest_stream)// rfc7540,l,1998,2001 + return (H2CE_PROTOCOL_ERROR); if (r2 == NULL) return (0); } if (r2 == NULL) { if (h2->rxf_stream <= h2->highest_stream) - return (H2CE_PROTOCOL_ERROR); // rfc7540 5.1.1 + return (H2CE_PROTOCOL_ERROR); // rfc7540,l,1153,1158 h2->highest_stream = h2->rxf_stream; r2 = h2_new_req(wrk, h2, h2->rxf_stream, NULL); AN(r2); } if (h2->rxf_type >= H2FMAX) { + // rfc7540,l,679,681 h2->bogosity++; VSLb(h2->vsl, SLT_Debug, "H2: Unknown Frame 0x%02x", h2->rxf_type); - return (0); // rfc7540 4.1 + return (0); } h2f = h2flist + h2->rxf_type; if (h2f->name == NULL || h2f->func == NULL) { + // rfc7540,l,679,681 h2->bogosity++; VSLb(h2->vsl, SLT_Debug, "H2: Unimplemented Frame 0x%02x", h2->rxf_type); - return (0); // rfc7540 4.1 + return (0); } if (h2->rxf_flags & ~h2f->flags) { + // rfc7540,l,687,688 h2->bogosity++; VSLb(h2->vsl, SLT_Debug, "H2: Bad flags 0x%02x on %s", h2->rxf_flags, h2f->name); - h2->rxf_flags &= h2f->flags; // rfc7540 4.1 + h2->rxf_flags &= h2f->flags; } h2e = h2f->func(wrk, h2, r2); if (h2e == 0) From phk at FreeBSD.org Sat Mar 4 18:55:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Sat, 04 Mar 2017 19:55:05 +0100 Subject: [master] c0330b4 Tabelize a lot of rfc7540 "MUST" error handling Message-ID: commit c0330b4217714537f6f8463e88c3c7ee91209385 Author: Poul-Henning Kamp Date: Sat Mar 4 18:54:09 2017 +0000 Tabelize a lot of rfc7540 "MUST" error handling diff --git a/bin/varnishd/http2/cache_http2.h b/bin/varnishd/http2/cache_http2.h index 3bf6eb0..38bf8c6 100644 --- a/bin/varnishd/http2/cache_http2.h +++ b/bin/varnishd/http2/cache_http2.h @@ -54,7 +54,7 @@ typedef const struct h2_error_s *h2_error; enum h2_frame_e { H2_FRAME__DUMMY = -1, -#define H2_FRAME(l,u,t,f) H2_FRAME_##u = t, +#define H2_FRAME(l,u,t,f,...) H2_FRAME_##u = t, #include "tbl/h2_frames.h" }; diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index b2326e8..dd7f61c 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -55,7 +55,7 @@ typedef h2_error h2_frame_f(struct worker *, struct h2_sess *, struct h2_req *); enum h2frame { -#define H2_FRAME(l,u,t,f) H2F_##u = t, +#define H2_FRAME(l,u,t,f,...) H2F_##u = t, #include "tbl/h2_frames.h" }; @@ -64,7 +64,7 @@ h2_framename(enum h2frame h2f) { switch(h2f) { -#define H2_FRAME(l,u,t,f) case H2F_##u: return #u; +#define H2_FRAME(l,u,t,f,...) case H2F_##u: return #u; #include "tbl/h2_frames.h" default: return (NULL); @@ -557,10 +557,13 @@ struct h2flist_s { const char *name; h2_frame_f *func; uint8_t flags; + h2_error act_szero; + h2_error act_snonzero; + h2_error act_sidle; }; static const struct h2flist_s h2flist[] = { -#define H2_FRAME(l,U,t,f) [t] = { #U, h2_rx_##l, f }, +#define H2_FRAME(l,U,t,f,az,anz,ai) [t] = { #U, h2_rx_##l, f, az, anz,ai }, #include "tbl/h2_frames.h" }; @@ -574,6 +577,38 @@ h2_procframe(struct worker *wrk, struct h2_sess *h2) h2_error h2e; char b[4]; + if (h2->rxf_type >= H2FMAX) { + // rfc7540,l,679,681 + h2->bogosity++; + VSLb(h2->vsl, SLT_Debug, + "H2: Unknown Frame 0x%02x", h2->rxf_type); + return (0); + } + h2f = h2flist + h2->rxf_type; + if (h2f->name == NULL || h2f->func == NULL) { + // rfc7540,l,679,681 + h2->bogosity++; + VSLb(h2->vsl, SLT_Debug, + "H2: Unimplemented Frame 0x%02x", h2->rxf_type); + return (0); + } + if (h2->rxf_flags & ~h2f->flags) { + // rfc7540,l,687,688 + h2->bogosity++; + VSLb(h2->vsl, SLT_Debug, "H2: Bad flags 0x%02x on %s", + h2->rxf_flags, h2f->name); + h2->rxf_flags &= h2f->flags; + } + + if (h2->rxf_stream == 0 && h2f->act_szero != 0) + return (h2f->act_szero); + + if (h2->rxf_stream != 0 && h2f->act_snonzero != 0) + return (h2f->act_snonzero); + + if (h2->rxf_stream > h2->highest_stream && h2f->act_sidle != 0) + return (h2f->act_sidle); + if (h2->rxf_stream != 0 && !(h2->rxf_stream & 1)) { // rfc7540,l,1140,1145 // rfc7540,l,1153,1158 @@ -594,7 +629,7 @@ h2_procframe(struct worker *wrk, struct h2_sess *h2) if (h2->rxf_stream == 0) // rfc7540,l,1993,1996 return (H2CE_PROTOCOL_ERROR); if (h2->rxf_stream > h2->highest_stream)// rfc7540,l,1998,2001 - return (H2CE_PROTOCOL_ERROR); + return (H2CE_PROTOCOL_ERROR); if (r2 == NULL) return (0); } @@ -607,28 +642,6 @@ h2_procframe(struct worker *wrk, struct h2_sess *h2) AN(r2); } - if (h2->rxf_type >= H2FMAX) { - // rfc7540,l,679,681 - h2->bogosity++; - VSLb(h2->vsl, SLT_Debug, - "H2: Unknown Frame 0x%02x", h2->rxf_type); - return (0); - } - h2f = h2flist + h2->rxf_type; - if (h2f->name == NULL || h2f->func == NULL) { - // rfc7540,l,679,681 - h2->bogosity++; - VSLb(h2->vsl, SLT_Debug, - "H2: Unimplemented Frame 0x%02x", h2->rxf_type); - return (0); - } - if (h2->rxf_flags & ~h2f->flags) { - // rfc7540,l,687,688 - h2->bogosity++; - VSLb(h2->vsl, SLT_Debug, "H2: Bad flags 0x%02x on %s", - h2->rxf_flags, h2f->name); - h2->rxf_flags &= h2f->flags; - } h2e = h2f->func(wrk, h2, r2); if (h2e == 0) return (0); diff --git a/bin/varnishtest/tests/t02003.vtc b/bin/varnishtest/tests/t02003.vtc index 89f6298..ed7ce70 100644 --- a/bin/varnishtest/tests/t02003.vtc +++ b/bin/varnishtest/tests/t02003.vtc @@ -35,10 +35,10 @@ client c1 { expect goaway.err == PROTOCOL_ERROR } -start stream 3 { - txwinup -size 1 + txprio } -run stream 1 { - txwinup -size 1 + txprio } -run stream 0 -wait } -run @@ -48,11 +48,13 @@ client c1 { client c1 { stream 1 { + txprio txwinup -size 0 rxrst expect rst.err == PROTOCOL_ERROR } -run stream 3 { + txprio txwinup -size 0x40000000 txwinup -size 0x40000000 rxrst @@ -64,6 +66,7 @@ client c1 { expect goaway.err == FRAME_SIZE_ERROR } -start stream 5 { + txprio sendhex "000003 08 00 00000005 010203" } -run stream 0 -wait @@ -97,7 +100,7 @@ client c1 { stream 0 { rxgoaway expect goaway.err == PROTOCOL_ERROR - expect goaway.laststream == 1 + expect goaway.laststream == 0 } -start stream 1 { sendhex "000008 05 00 00000001 0001020304050607" @@ -119,12 +122,16 @@ client c1 { client c1 { stream 0 { - # RST wrong length - sendhex "000005 03 00 00000001 0000000800" rxgoaway expect goaway.err == FRAME_SIZE_ERROR - expect goaway.laststream == 0 + expect goaway.laststream == 1 + } -start + stream 1 { + txprio + # RST wrong length + sendhex "000005 03 00 00000001 0000000800" } -run + stream 0 -wait } -run client c1 { @@ -132,7 +139,7 @@ client c1 { # RST stream zero sendhex "000000 03 00 00000000 00000008" rxgoaway - expect goaway.err == FRAME_SIZE_ERROR + expect goaway.err == PROTOCOL_ERROR expect goaway.laststream == 0 } -run } -run diff --git a/bin/varnishtest/vtc_http2.c b/bin/varnishtest/vtc_http2.c index 6b8f7d7..f1f03f6 100644 --- a/bin/varnishtest/vtc_http2.c +++ b/bin/varnishtest/vtc_http2.c @@ -62,7 +62,7 @@ static const char *const h2_errs[] = { }; static const char *const h2_types[] = { -#define H2_FRAME(l,u,t,f) [t] = #u, +#define H2_FRAME(l,u,t,f,...) [t] = #u, #include NULL }; @@ -77,7 +77,7 @@ static const char * const h2_settings[] = { }; enum h2_type { -#define H2_FRAME(l,u,t,f) TYPE_##u = t, +#define H2_FRAME(l,u,t,f,...) TYPE_##u = t, #include TYPE_MAX }; diff --git a/include/tbl/h2_frames.h b/include/tbl/h2_frames.h index c7dc822..29c338f 100644 --- a/include/tbl/h2_frames.h +++ b/include/tbl/h2_frames.h @@ -31,17 +31,61 @@ /*lint -save -e525 -e539 */ #ifdef H2_FRAME -/* lower, upper, type, valid flags */ - H2_FRAME(data, DATA, 0x0, 0x09) - H2_FRAME(headers, HEADERS, 0x1, 0x2d) - H2_FRAME(priority, PRIORITY, 0x2, 0x00) - H2_FRAME(rst_stream, RST_STREAM, 0x3, 0x00) - H2_FRAME(settings, SETTINGS, 0x4, 0x01) - H2_FRAME(push_promise, PUSH_PROMISE, 0x5, 0x0c) - H2_FRAME(ping, PING, 0x6, 0x01) - H2_FRAME(goaway, GOAWAY, 0x7, 0x00) - H2_FRAME(window_update, WINDOW_UPDATE, 0x8, 0x00) - H2_FRAME(continuation, CONTINUATION, 0x9, 0x04) +/* lower, upper, type, flags + * stream-zero + * stream-nonzero + * stream-idle + */ + H2_FRAME(data, DATA, 0x0, 0x09, + H2CE_PROTOCOL_ERROR, // rfc7540,l,1758,1761 + 0, + H2CE_PROTOCOL_ERROR + ) + H2_FRAME(headers, HEADERS, 0x1, 0x2d, + H2CE_PROTOCOL_ERROR, // rfc7540,l,1876,1879 + 0, + 0 // rfc7540,l,938,940 + ) + H2_FRAME(priority, PRIORITY, 0x2, 0x00, + H2CE_PROTOCOL_ERROR, // rfc7540,l,1933,1936 + 0, + 0 // rfc7540,l,938,940 + ) + H2_FRAME(rst_stream, RST_STREAM, 0x3, 0x00, + H2CE_PROTOCOL_ERROR, // rfc7540,l,1993,1996 + 0, + H2CE_PROTOCOL_ERROR + ) + H2_FRAME(settings, SETTINGS, 0x4, 0x01, + 0, + H2CE_PROTOCOL_ERROR, // rfc7540,l,2052,2056 + H2CE_PROTOCOL_ERROR + ) + H2_FRAME(push_promise, PUSH_PROMISE, 0x5, 0x0c, + H2CE_PROTOCOL_ERROR, // rfc7540,l,2262,2263 + 0, + H2CE_PROTOCOL_ERROR + ) + H2_FRAME(ping, PING, 0x6, 0x01, + 0, + H2CE_PROTOCOL_ERROR, // rfc7540,l,2359,2362 + H2CE_PROTOCOL_ERROR + ) + H2_FRAME(goaway, GOAWAY, 0x7, 0x00, + 0, + H2CE_PROTOCOL_ERROR, // rfc7540,l,2432,2435 + H2CE_PROTOCOL_ERROR + ) + H2_FRAME(window_update, WINDOW_UPDATE, 0x8, 0x00, + 0, + 0, + H2CE_PROTOCOL_ERROR + ) + H2_FRAME(continuation, CONTINUATION, 0x9, 0x04, + H2CE_PROTOCOL_ERROR, // rfc7540,l,2764,2767 + 0, + H2CE_PROTOCOL_ERROR + ) #undef H2_FRAME #endif From phk at FreeBSD.org Sat Mar 4 19:01:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Sat, 04 Mar 2017 20:01:05 +0100 Subject: [master] 17ad98c With table-driven MUST handling, some checks become simpler. Message-ID: commit 17ad98cdac9d0a4228adb1be0325b1cbb6f9ce6b Author: Poul-Henning Kamp Date: Sat Mar 4 19:00:01 2017 +0000 With table-driven MUST handling, some checks become simpler. diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index dd7f61c..264ff90 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -223,8 +223,11 @@ static h2_error __match_proto__(h2_frame_f) h2_rx_rst_stream(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) { (void)wrk; - (void)h2; - (void)r2; + + if (h2->rxf_len != 4) // rfc7540,l,2003,2004 + return (H2CE_FRAME_SIZE_ERROR); + if (r2 == NULL) + return (0); INCOMPL(); NEEDLESS(return (H2CE_PROTOCOL_ERROR)); } @@ -622,19 +625,7 @@ h2_procframe(struct worker *wrk, struct h2_sess *h2) if (r2->stream == h2->rxf_stream) break; - if (h2->rxf_type == H2_FRAME_RST_STREAM) { - /* Special case RST_STREAM to avoid creating streams */ - if (h2->rxf_len != 4) // rfc7540,l,2003,2004 - return (H2CE_FRAME_SIZE_ERROR); - if (h2->rxf_stream == 0) // rfc7540,l,1993,1996 - return (H2CE_PROTOCOL_ERROR); - if (h2->rxf_stream > h2->highest_stream)// rfc7540,l,1998,2001 - return (H2CE_PROTOCOL_ERROR); - if (r2 == NULL) - return (0); - } - - if (r2 == NULL) { + if (r2 == NULL && h2f->act_sidle == 0) { if (h2->rxf_stream <= h2->highest_stream) return (H2CE_PROTOCOL_ERROR); // rfc7540,l,1153,1158 h2->highest_stream = h2->rxf_stream; diff --git a/bin/varnishd/http2/cache_http2_session.c b/bin/varnishd/http2/cache_http2_session.c index f63445c..15c5fbd 100644 --- a/bin/varnishd/http2/cache_http2_session.c +++ b/bin/varnishd/http2/cache_http2_session.c @@ -156,7 +156,7 @@ h2_new_req(const struct worker *wrk, struct h2_sess *h2, } static void -h2_del_req(struct worker *wrk, struct h2_req *r2) +h2_del_req(struct worker *wrk, const struct h2_req *r2) { struct h2_sess *h2; struct sess *sp; From phk at FreeBSD.org Sat Mar 4 20:27:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Sat, 04 Mar 2017 21:27:05 +0100 Subject: [master] 3369999 The proto/session split ended up with three duplicated functions, GC them. Message-ID: commit 3369999a9f12f4031d1570ddd115d1426414309a Author: Poul-Henning Kamp Date: Sat Mar 4 20:26:12 2017 +0000 The proto/session split ended up with three duplicated functions, GC them. diff --git a/bin/varnishd/http2/cache_http2.h b/bin/varnishd/http2/cache_http2.h index 38bf8c6..4bcfe21 100644 --- a/bin/varnishd/http2/cache_http2.h +++ b/bin/varnishd/http2/cache_http2.h @@ -162,7 +162,11 @@ int H2_Send(struct worker *, struct h2_req *, int flush, enum h2_frame_e type, uint8_t flags, uint32_t len, const void *); /* cache_http2_proto.c */ +struct h2_req * h2_new_req(const struct worker *, struct h2_sess *, + unsigned stream, struct req *); +void h2_del_req(struct worker *, struct h2_req *); int h2_rxframe(struct worker *, struct h2_sess *); +void h2_setting(struct h2_sess *, const uint8_t *); void h2_req_body(struct req*); diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index 264ff90..15cb232 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -87,16 +87,26 @@ h2_settingname(enum h2setting h2f) #define H2_FRAME_FLAGS(l,u,v) const uint8_t H2FF_##u = v; #include "tbl/h2_frames.h" +/**********************************************************************/ + +struct h2flist_s { + const char *name; + h2_frame_f *func; + uint8_t flags; + h2_error act_szero; + h2_error act_snonzero; + h2_error act_sidle; +}; + /********************************************************************** */ -static struct h2_req * +struct h2_req * h2_new_req(const struct worker *wrk, struct h2_sess *h2, unsigned stream, struct req *req) { struct h2_req *r2; - Lck_AssertHeld(&h2->sess->mtx); if (req == NULL) req = Req_New(wrk, h2->sess); CHECK_OBJ_NOTNULL(req, REQ_MAGIC); @@ -110,12 +120,14 @@ h2_new_req(const struct worker *wrk, struct h2_sess *h2, r2->req = req; req->transport_priv = r2; // XXX: ordering ? + Lck_Lock(&h2->sess->mtx); VTAILQ_INSERT_TAIL(&h2->streams, r2, list); + Lck_Unlock(&h2->sess->mtx); h2->refcnt++; return (r2); } -static void +void h2_del_req(struct worker *wrk, struct h2_req *r2) { struct h2_sess *h2; @@ -123,7 +135,9 @@ h2_del_req(struct worker *wrk, struct h2_req *r2) struct req *req; int r; + CHECK_OBJ_NOTNULL(r2, H2_REQ_MAGIC); h2 = r2->h2sess; + CHECK_OBJ_NOTNULL(h2, H2_SESS_MAGIC); sp = h2->sess; Lck_Lock(&sp->mtx); assert(h2->refcnt > 0); @@ -198,8 +212,10 @@ h2_rx_ping(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) return (H2CE_PROTOCOL_ERROR); if (h2->rxf_flags != 0) // We never send pings return (H2SE_PROTOCOL_ERROR); + Lck_Lock(&h2->sess->mtx); H2_Send_Frame(wrk, h2, H2_FRAME_PING, H2FF_PING_ACK, 8, 0, h2->rxf_data); + Lck_Unlock(&h2->sess->mtx); return (0); } @@ -223,7 +239,7 @@ static h2_error __match_proto__(h2_frame_f) h2_rx_rst_stream(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) { (void)wrk; - + if (h2->rxf_len != 4) // rfc7540,l,2003,2004 return (H2CE_FRAME_SIZE_ERROR); if (r2 == NULL) @@ -258,13 +274,14 @@ h2_rx_window_update(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) uint32_t wu; (void)wrk; - Lck_AssertHeld(&h2->sess->mtx); if (h2->rxf_len != 4) return (H2CE_FRAME_SIZE_ERROR); wu = vbe32dec(h2->rxf_data) & ~(1LU<<31); if (wu == 0) return (H2SE_PROTOCOL_ERROR); + Lck_Lock(&h2->sess->mtx); r2->window += wu; + Lck_Unlock(&h2->sess->mtx); if (r2->window >= (1LLU << 31)) return (H2SE_FLOW_CONTROL_ERROR); return (0); @@ -288,7 +305,7 @@ h2_rx_priority(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) * Incoming SETTINGS, possibly an ACK of one we sent. */ -static void +void h2_setting(struct h2_sess *h2, const uint8_t *d) { uint16_t x; @@ -325,8 +342,10 @@ h2_rx_settings(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) if (l > 0) VSLb(h2->vsl, SLT_Debug, "NB: SETTINGS had %u dribble-bytes", l); + Lck_Lock(&h2->sess->mtx); H2_Send_Frame(wrk, h2, H2_FRAME_SETTINGS, H2FF_SETTINGS_ACK, 0, 0, NULL); + Lck_Unlock(&h2->sess->mtx); } else { WRONG("SETTINGS FRAME"); } @@ -469,12 +488,13 @@ static h2_error __match_proto__(h2_frame_f) h2_rx_data(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) { (void)wrk; - Lck_AssertHeld(&h2->sess->mtx); AZ(h2->mailcall); h2->mailcall = r2; + Lck_Lock(&h2->sess->mtx); AZ(pthread_cond_broadcast(h2->cond)); while (h2->mailcall != NULL) AZ(Lck_CondWait(h2->cond, &h2->sess->mtx, 0)); + Lck_Unlock(&h2->sess->mtx); return (0); } @@ -556,53 +576,14 @@ h2_frame_complete(struct http_conn *htc) /**********************************************************************/ -struct h2flist_s { - const char *name; - h2_frame_f *func; - uint8_t flags; - h2_error act_szero; - h2_error act_snonzero; - h2_error act_sidle; -}; - -static const struct h2flist_s h2flist[] = { -#define H2_FRAME(l,U,t,f,az,anz,ai) [t] = { #U, h2_rx_##l, f, az, anz,ai }, -#include "tbl/h2_frames.h" -}; - -#define H2FMAX (sizeof(h2flist) / sizeof(h2flist[0])) - static h2_error -h2_procframe(struct worker *wrk, struct h2_sess *h2) +h2_procframe(struct worker *wrk, struct h2_sess *h2, + const struct h2flist_s *h2f) { struct h2_req *r2 = NULL; - const struct h2flist_s *h2f; h2_error h2e; char b[4]; - if (h2->rxf_type >= H2FMAX) { - // rfc7540,l,679,681 - h2->bogosity++; - VSLb(h2->vsl, SLT_Debug, - "H2: Unknown Frame 0x%02x", h2->rxf_type); - return (0); - } - h2f = h2flist + h2->rxf_type; - if (h2f->name == NULL || h2f->func == NULL) { - // rfc7540,l,679,681 - h2->bogosity++; - VSLb(h2->vsl, SLT_Debug, - "H2: Unimplemented Frame 0x%02x", h2->rxf_type); - return (0); - } - if (h2->rxf_flags & ~h2f->flags) { - // rfc7540,l,687,688 - h2->bogosity++; - VSLb(h2->vsl, SLT_Debug, "H2: Bad flags 0x%02x on %s", - h2->rxf_flags, h2f->name); - h2->rxf_flags &= h2f->flags; - } - if (h2->rxf_stream == 0 && h2f->act_szero != 0) return (h2f->act_szero); @@ -639,14 +620,15 @@ h2_procframe(struct worker *wrk, struct h2_sess *h2) if (h2->rxf_stream == 0 || h2e->connection) return (h2e); // Connection errors one level up - VSLb(h2->vsl, SLT_Debug, "H2: stream %u: %s", - h2->rxf_stream, h2e->txt); + VSLb(h2->vsl, SLT_Debug, "H2: stream %u: %s", h2->rxf_stream, h2e->txt); vbe32enc(b, h2e->val); + + Lck_Lock(&h2->sess->mtx); (void)H2_Send_Frame(wrk, h2, H2_FRAME_RST_STREAM, 0, sizeof b, h2->rxf_stream, b); Lck_Unlock(&h2->sess->mtx); + h2_del_req(wrk, r2); - Lck_Lock(&h2->sess->mtx); return (0); } @@ -654,10 +636,18 @@ h2_procframe(struct worker *wrk, struct h2_sess *h2) * Called in loop from h2_new_session() */ +static const struct h2flist_s h2flist[] = { +#define H2_FRAME(l,U,t,f,az,anz,ai) [t] = { #U, h2_rx_##l, f, az, anz,ai }, +#include "tbl/h2_frames.h" +}; + +#define H2FMAX (sizeof(h2flist) / sizeof(h2flist[0])) + int h2_rxframe(struct worker *wrk, struct h2_sess *h2) { enum htc_status_e hs; + const struct h2flist_s *h2f; h2_error h2e; char b[8]; @@ -678,19 +668,47 @@ h2_rxframe(struct worker *wrk, struct h2_sess *h2) h2->rxf_type = h2->htc->rxbuf_b[3]; h2->rxf_flags = h2->htc->rxbuf_b[4]; h2->rxf_stream = vbe32dec(h2->htc->rxbuf_b + 5); + h2->rxf_stream &= ~(1LU<<31); // rfc7450,l,690,692 h2->rxf_data = (void*)(h2->htc->rxbuf_b + 9); /* XXX: later full DATA will not be rx'ed yet. */ HTC_RxPipeline(h2->htc, h2->htc->rxbuf_b + h2->rxf_len + 9); + if (h2->rxf_type >= H2FMAX) { + // rfc7540,l,679,681 + // XXX: later, drain rest of frame + h2->bogosity++; + VSLb(h2->vsl, SLT_Debug, + "H2: Unknown frame type 0x%02x (ignored)", h2->rxf_type); + return (1); + } + h2f = h2flist + h2->rxf_type; + if (h2f->name == NULL || h2f->func == NULL) { + // rfc7540,l,679,681 + // XXX: later, drain rest of frame + h2->bogosity++; + VSLb(h2->vsl, SLT_Debug, + "H2: Unimplemented frame type 0x%02x (ignored)", + h2->rxf_type); + return (0); + } + if (h2->rxf_flags & ~h2f->flags) { + // rfc7540,l,687,688 + h2->bogosity++; + VSLb(h2->vsl, SLT_Debug, + "H2: Unknown flags 0x%02x on %s (ignored)", + h2->rxf_flags, h2f->name); + h2->rxf_flags &= h2f->flags; + } + h2_vsl_frame(h2, h2->htc->rxbuf_b, 9L + h2->rxf_len); - Lck_Lock(&h2->sess->mtx); - h2e = h2_procframe(wrk, h2); + h2e = h2_procframe(wrk, h2, h2f); if (h2e) { vbe32enc(b, h2->highest_stream); vbe32enc(b + 4, h2e->val); + Lck_Lock(&h2->sess->mtx); (void)H2_Send_Frame(wrk, h2, H2_FRAME_GOAWAY, 0, 8, 0, b); + Lck_Unlock(&h2->sess->mtx); } - Lck_Unlock(&h2->sess->mtx); return (h2e ? 0 : 1); } diff --git a/bin/varnishd/http2/cache_http2_session.c b/bin/varnishd/http2/cache_http2_session.c index 15c5fbd..35dc072 100644 --- a/bin/varnishd/http2/cache_http2_session.c +++ b/bin/varnishd/http2/cache_http2_session.c @@ -39,19 +39,6 @@ #include "vend.h" -static const char * -h2_settingname(enum h2setting h2f) -{ - - switch(h2f) { -#define H2_SETTINGS(n,v,d) case H2S_##n: return #n; -#include "tbl/h2_settings.h" -#undef H2_SETTINGS - default: - return (NULL); - } -} - static const char h2_resp_101[] = "HTTP/1.1 101 Switching Protocols\r\n" "Connection: Upgrade\r\n" @@ -128,87 +115,6 @@ h2_new_sess(const struct worker *wrk, struct sess *sp, struct req *srq) } /********************************************************************** - */ - -static struct h2_req * -h2_new_req(const struct worker *wrk, struct h2_sess *h2, - unsigned stream, struct req *req) -{ - struct h2_req *r2; - - Lck_AssertHeld(&h2->sess->mtx); - if (req == NULL) - req = Req_New(wrk, h2->sess); - CHECK_OBJ_NOTNULL(req, REQ_MAGIC); - - r2 = WS_Alloc(req->ws, sizeof *r2); - AN(r2); - INIT_OBJ(r2, H2_REQ_MAGIC); - r2->state = H2_S_IDLE; - r2->h2sess = h2; - r2->stream = stream; - r2->req = req; - req->transport_priv = r2; - // XXX: ordering ? - VTAILQ_INSERT_TAIL(&h2->streams, r2, list); - h2->refcnt++; - return (r2); -} - -static void -h2_del_req(struct worker *wrk, const struct h2_req *r2) -{ - struct h2_sess *h2; - struct sess *sp; - struct req *req; - int r; - - h2 = r2->h2sess; - sp = h2->sess; - Lck_Lock(&sp->mtx); - assert(h2->refcnt > 0); - r = --h2->refcnt; - /* XXX: PRIORITY reshuffle */ - VTAILQ_REMOVE(&h2->streams, r2, list); - Lck_Unlock(&sp->mtx); - Req_Cleanup(sp, wrk, r2->req); - Req_Release(r2->req); - if (r) - return; - - /* All streams gone, including stream #0, clean up */ - req = h2->srq; - Req_Cleanup(sp, wrk, req); - Req_Release(req); - SES_Delete(sp, SC_RX_JUNK, NAN); -} - -/********************************************************************** - * Update and VSL a single SETTING rx'ed from the other side - * 'd' must point to six bytes. - */ - -static void -h2_setting(struct h2_sess *h2, const uint8_t *d) -{ - uint16_t x; - uint32_t y; - const char *n; - char nb[8]; - - x = vbe16dec(d); - y = vbe32dec(d + 2); - n = h2_settingname((enum h2setting)x); - if (n == NULL) { - bprintf(nb, "0x%04x", x); - n = nb; - } - VSLb(h2->vsl, SLT_Debug, "H2SETTING %s 0x%08x", n, y); - if (x > 0 && x < H2_SETTINGS_N) - h2->their_settings[x] = y; -} - -/********************************************************************** * Incoming HEADERS, this is where the partys at... */ @@ -370,7 +276,6 @@ h2_new_ou_session(struct worker *wrk, struct h2_sess *h2, /* XXX clean up req thread */ VSLb(h2->vsl, SLT_Debug, "H2: No OU PRISM (hs=%d)", hs); Req_Release(req); - Lck_Unlock(&h2->sess->mtx); SES_Delete(h2->sess, SC_RX_JUNK, NAN); return (0); } @@ -402,13 +307,11 @@ h2_new_session(struct worker *wrk, void *arg) case 0: /* Direct H2 connection (via Proxy) */ h2 = h2_new_sess(wrk, sp, req); - Lck_Lock(&h2->sess->mtx); (void)h2_new_req(wrk, h2, 0, NULL); break; case 1: /* Prior Knowledge H1->H2 upgrade */ h2 = h2_new_sess(wrk, sp, req); - Lck_Lock(&h2->sess->mtx); (void)h2_new_req(wrk, h2, 0, NULL); if (!h2_new_pu_session(wrk, h2)) @@ -417,7 +320,6 @@ h2_new_session(struct worker *wrk, void *arg) case 2: /* Optimistic H1->H2 upgrade */ h2 = h2_new_sess(wrk, sp, NULL); - Lck_Lock(&h2->sess->mtx); (void)h2_new_req(wrk, h2, 0, NULL); if (!h2_new_ou_session(wrk, h2, req)) @@ -429,6 +331,7 @@ h2_new_session(struct worker *wrk, void *arg) THR_SetRequest(h2->srq); + Lck_Lock(&h2->sess->mtx); H2_Send_Frame(wrk, h2, H2_FRAME_SETTINGS, H2FF_NONE, sizeof H2_settings, 0, H2_settings); From phk at FreeBSD.org Sat Mar 4 23:55:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Sun, 05 Mar 2017 00:55:05 +0100 Subject: [master] 6207b70 Fix a self-recursion during cleanup Message-ID: commit 6207b703bd581a321950f996f324daab55d9e3ab Author: Poul-Henning Kamp Date: Sat Mar 4 21:15:58 2017 +0000 Fix a self-recursion during cleanup diff --git a/bin/varnishtest/vtc_varnish.c b/bin/varnishtest/vtc_varnish.c index 544a63c..f22e5cc 100644 --- a/bin/varnishtest/vtc_varnish.c +++ b/bin/varnishtest/vtc_varnish.c @@ -107,11 +107,11 @@ varnish_ask_cli(const struct varnish *v, const char *cmd, char **repl) if (cmd != NULL) { vtc_dump(v->vl, 4, "CLI TX", cmd, -1); i = write(v->cli_fd, cmd, strlen(cmd)); - if (i != strlen(cmd)) + if (i != strlen(cmd) && !vtc_stop) vtc_fatal(v->vl, "CLI write failed (%s) = %u %s", cmd, errno, strerror(errno)); i = write(v->cli_fd, "\n", 1); - if (i != 1) + if (i != 1 && !vtc_stop) vtc_fatal(v->vl, "CLI write failed (%s) = %u %s", cmd, errno, strerror(errno)); } From phk at FreeBSD.org Sat Mar 4 23:55:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Sun, 05 Mar 2017 00:55:05 +0100 Subject: [master] 6e8e590 Set correct mode on -C mode workdir Message-ID: commit 6e8e590cf4d645e0720ed74d2501b90e9ed561f4 Author: Poul-Henning Kamp Date: Sat Mar 4 22:10:58 2017 +0000 Set correct mode on -C mode workdir Fixes #2227 diff --git a/bin/varnishd/mgt/mgt_main.c b/bin/varnishd/mgt/mgt_main.c index 1eadebf..ae81022 100644 --- a/bin/varnishd/mgt/mgt_main.c +++ b/bin/varnishd/mgt/mgt_main.c @@ -40,6 +40,7 @@ #include #include #include +#include #include "mgt/mgt.h" #include "common/heritage.h" @@ -730,6 +731,7 @@ main(int argc, char * const *argv) if (C_flag) { if (n_arg == NULL) { AN(mkdtemp(Cn_arg)); + AZ(chmod(Cn_arg, 0755)); n_arg = Cn_arg; } } From phk at FreeBSD.org Sat Mar 4 23:55:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Sun, 05 Mar 2017 00:55:05 +0100 Subject: [master] 391d472 Have VCC report VMODs to Varnishd out of band (like VCL dependencies). Message-ID: commit 391d4720ce7fc39999ff0b292bc00a14c74795c5 Author: Poul-Henning Kamp Date: Sat Mar 4 22:32:52 2017 +0000 Have VCC report VMODs to Varnishd out of band (like VCL dependencies). diff --git a/bin/varnishd/mgt/mgt_vcc.c b/bin/varnishd/mgt/mgt_vcc.c index 087078a..bfb8b6f 100644 --- a/bin/varnishd/mgt/mgt_vcc.c +++ b/bin/varnishd/mgt/mgt_vcc.c @@ -373,8 +373,10 @@ mgt_VccCompile(struct cli *cli, struct vclprog *vcl, const char *vclname, AZ(av[0]); AZ(strcmp(av[1], "/*")); AZ(strcmp(av[ac-1], "*/")); - AZ(strcmp(av[3], "VCL")); - mgt_vcl_depends(vcl, av[4]); + if (!strcmp(av[3], "VCL")) + mgt_vcl_depends(vcl, av[4]); + else if (strcmp(av[3], "VMOD")) + WRONG("Wrong VCCINFO"); VAV_Free(av); } AZ(fclose(fcs)); diff --git a/lib/libvcc/vcc_vmod.c b/lib/libvcc/vcc_vmod.c index c6e08c1..b378ccf 100644 --- a/lib/libvcc/vcc_vmod.c +++ b/lib/libvcc/vcc_vmod.c @@ -37,6 +37,7 @@ #include "vcs_version.h" +#include "libvcc.h" #include "vfil.h" #include "vmod_abi.h" #include "vrt.h" @@ -212,6 +213,9 @@ vcc_ParseImport(struct vcc *tl) VSB_printf(ifp->ini, "\t ))\n"); VSB_printf(ifp->ini, "\t\treturn(1);"); + VSB_printf(tl->fi, "%s VMOD %s ./vmod_cache/_vmod_%.*s.%s */\n", + VCC_INFO_PREFIX, fnp, PF(mod), vmd->file_id); + /* XXX: zero the function pointer structure ?*/ VSB_printf(ifp->fin, "\t\tVRT_priv_fini(&vmod_priv_%.*s);\n", PF(mod)); VSB_printf(ifp->fin, "\t\t\tVRT_Vmod_Fini(&VGC_vmod_%.*s);", PF(mod)); From phk at FreeBSD.org Sat Mar 4 23:55:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Sun, 05 Mar 2017 00:55:05 +0100 Subject: [master] dfe4b5e Create vmod_cache subdirectory in master rather than child Message-ID: commit dfe4b5e66685996471bf435d926c448429b6cff6 Author: Poul-Henning Kamp Date: Sat Mar 4 22:46:50 2017 +0000 Create vmod_cache subdirectory in master rather than child diff --git a/bin/varnishd/mgt/mgt_child.c b/bin/varnishd/mgt/mgt_child.c index f6fc0c3..8a6acf7 100644 --- a/bin/varnishd/mgt/mgt_child.c +++ b/bin/varnishd/mgt/mgt_child.c @@ -292,12 +292,6 @@ mgt_launch_child(struct cli *cli) child_state = CH_STARTING; - if (VJ_make_vcldir("vmod_cache")) { - VCLI_Out(cli, "Could not create vmod cache dir"); - VCLI_SetResult(cli, CLIS_UNKNOWN); - return; - } - /* Open pipe for mgr->child CLI */ AZ(pipe(cp)); heritage.cli_in = cp[0]; diff --git a/bin/varnishd/mgt/mgt_main.c b/bin/varnishd/mgt/mgt_main.c index ae81022..9056a9d 100644 --- a/bin/varnishd/mgt/mgt_main.c +++ b/bin/varnishd/mgt/mgt_main.c @@ -771,6 +771,12 @@ main(int argc, char * const *argv) ARGV_ERR("Cannot create working directory (%s): %s\n", dirname, strerror(errno)); + if (VJ_make_vcldir("vmod_cache")) { + ARGV_ERR( + "Cannot create vmod directory (%s/vmod_cache): %s\n", + dirname, strerror(errno)); + } + VJ_master(JAIL_MASTER_FILE); if (P_arg && (pfh = VPF_Open(P_arg, 0644, NULL)) == NULL) ARGV_ERR("Could not open pid/lock (-P) file (%s): %s\n", From phk at FreeBSD.org Sat Mar 4 23:55:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Sun, 05 Mar 2017 00:55:05 +0100 Subject: [master] 4752b12 Move the VMOD caching from worker to master to avoid too many Jail contortions. Message-ID: commit 4752b126dd729c6f708ea8f6b89cc7eaea5e308b Author: Poul-Henning Kamp Date: Sat Mar 4 23:51:54 2017 +0000 Move the VMOD caching from worker to master to avoid too many Jail contortions. Fixes #2245 diff --git a/bin/varnishd/cache/cache_vrt_vmod.c b/bin/varnishd/cache/cache_vrt_vmod.c index 009da54..97a18b2 100644 --- a/bin/varnishd/cache/cache_vrt_vmod.c +++ b/bin/varnishd/cache/cache_vrt_vmod.c @@ -68,46 +68,6 @@ struct vmod { static VTAILQ_HEAD(,vmod) vmods = VTAILQ_HEAD_INITIALIZER(vmods); -static int -vrt_vmod_backup_copy(VRT_CTX, const char *nm, const char *fm, const char *to) -{ - int fi, fo; - int ret = 0; - ssize_t sz; - char buf[BUFSIZ]; - - fo = open(to, O_WRONLY | O_CREAT | O_EXCL, 0744); - if (fo < 0 && errno == EEXIST) - return (0); - if (fo < 0) { - VSB_printf(ctx->msg, "Creating copy of vmod %s: %s\n", - nm, strerror(errno)); - return (1); - } - fi = open(fm, O_RDONLY); - if (fi < 0) { - VSB_printf(ctx->msg, "Opening vmod %s from %s: %s\n", - nm, fm, strerror(errno)); - AZ(unlink(to)); - closefd(&fo); - return (1); - } - while (1) { - sz = read(fi, buf, sizeof buf); - if (sz == 0) - break; - if (sz < 0 || sz != write(fo, buf, sz)) { - VSB_printf(ctx->msg, "Copying vmod %s: %s\n", - nm, strerror(errno)); - AZ(unlink(to)); - ret = 1; - break; - } - } - closefd(&fi); - closefd(&fo); - return(ret); -} int VRT_Vmod_Init(VRT_CTX, struct vmod **hdl, void *ptr, int len, const char *nm, @@ -124,14 +84,6 @@ VRT_Vmod_Init(VRT_CTX, struct vmod **hdl, void *ptr, int len, const char *nm, AN(hdl); AZ(*hdl); - /* - * We make a backup copy of the VMOD shlib in our working directory - * and dlopen that, so that we can still restart the VCL's we have - * already compiled when people updated their VMOD package. - */ - if (vrt_vmod_backup_copy(ctx, nm, path, backup)) - return (1); - dlhdl = dlopen(backup, RTLD_NOW | RTLD_LOCAL); if (dlhdl == NULL) { VSB_printf(ctx->msg, "Loading vmod %s from %s:\n", nm, backup); @@ -222,7 +174,6 @@ VRT_Vmod_Fini(struct vmod **hdl) return; free(v->nm); free(v->path); - AZ(unlink(v->backup)); free(v->backup); VTAILQ_REMOVE(&vmods, v, list); VSC_C_main->vmods--; diff --git a/bin/varnishd/mgt/mgt.h b/bin/varnishd/mgt/mgt.h index 041dba4..02c58fe 100644 --- a/bin/varnishd/mgt/mgt.h +++ b/bin/varnishd/mgt/mgt.h @@ -188,6 +188,7 @@ int mgt_push_vcls_and_start(struct cli *, unsigned *status, char **p); void mgt_vcl_export_labels(struct vcc *); int mgt_has_vcl(void); void mgt_vcl_depends(struct vclprog *vp1, const char *name); +void mgt_vcl_vmod(struct vclprog *, const char *src, const char *dst); extern char *mgt_cc_cmd; extern const char *mgt_vcl_path; extern const char *mgt_vmod_path; diff --git a/bin/varnishd/mgt/mgt_vcc.c b/bin/varnishd/mgt/mgt_vcc.c index bfb8b6f..d2fcdb1 100644 --- a/bin/varnishd/mgt/mgt_vcc.c +++ b/bin/varnishd/mgt/mgt_vcc.c @@ -375,7 +375,9 @@ mgt_VccCompile(struct cli *cli, struct vclprog *vcl, const char *vclname, AZ(strcmp(av[ac-1], "*/")); if (!strcmp(av[3], "VCL")) mgt_vcl_depends(vcl, av[4]); - else if (strcmp(av[3], "VMOD")) + else if (!strcmp(av[3], "VMOD")) + mgt_vcl_vmod(vcl, av[4], av[5]); + else WRONG("Wrong VCCINFO"); VAV_Free(av); } diff --git a/bin/varnishd/mgt/mgt_vcl.c b/bin/varnishd/mgt/mgt_vcl.c index 7d9e52e..9c1e412 100644 --- a/bin/varnishd/mgt/mgt_vcl.c +++ b/bin/varnishd/mgt/mgt_vcl.c @@ -31,6 +31,7 @@ #include "config.h" +#include #include #include #include @@ -51,6 +52,15 @@ static const char * const VCL_STATE_AUTO = "auto"; static const char * const VCL_STATE_LABEL = "label"; struct vclprog; +struct vmodfile; + +struct vmoddep { + unsigned magic; +#define VMODDEP_MAGIC 0xc1490542 + VTAILQ_ENTRY(vmoddep) lfrom; + struct vmodfile *to; + VTAILQ_ENTRY(vmoddep) lto; +}; struct vcldep { unsigned magic; @@ -74,9 +84,19 @@ struct vclprog { VTAILQ_HEAD(, vcldep) dto; int nto; int loaded; + VTAILQ_HEAD(, vmoddep) vmods; +}; + +struct vmodfile { + unsigned magic; +#define VMODFILE_MAGIC 0xffa1a0d5 + char *fname; + VTAILQ_ENTRY(vmodfile) list; + VTAILQ_HEAD(, vmoddep) vcls; }; static VTAILQ_HEAD(, vclprog) vclhead = VTAILQ_HEAD_INITIALIZER(vclhead); +static VTAILQ_HEAD(, vmodfile) vmodhead = VTAILQ_HEAD_INITIALIZER(vmodhead); static struct vclprog *active_vcl; static struct vev *e_poker; @@ -202,6 +222,7 @@ mgt_vcl_add(const char *name, const char *state) REPLACE(vp->name, name); VTAILQ_INIT(&vp->dfrom); VTAILQ_INIT(&vp->dto); + VTAILQ_INIT(&vp->vmods); vp->state = state; if (vp->state != VCL_STATE_COLD) @@ -215,6 +236,8 @@ static void mgt_vcl_del(struct vclprog *vp) { char *p; + struct vmoddep *vd; + struct vmodfile *vf; CHECK_OBJ_NOTNULL(vp, VCLPROG_MAGIC); while (!VTAILQ_EMPTY(&vp->dto)) @@ -239,6 +262,22 @@ mgt_vcl_del(struct vclprog *vp) VJ_master(JAIL_MASTER_LOW); free(vp->fname); } + while (!VTAILQ_EMPTY(&vp->vmods)) { + vd = VTAILQ_FIRST(&vp->vmods); + CHECK_OBJ(vd, VMODDEP_MAGIC); + vf = vd->to; + CHECK_OBJ(vf, VMODFILE_MAGIC); + VTAILQ_REMOVE(&vp->vmods, vd, lfrom); + VTAILQ_REMOVE(&vf->vcls, vd, lto); + FREE_OBJ(vd); + + if (VTAILQ_EMPTY(&vf->vcls)) { + AZ(unlink(vf->fname)); + VTAILQ_REMOVE(&vmodhead, vf, list); + free(vf->fname); + FREE_OBJ(vf); + } + } free(vp->name); FREE_OBJ(vp); } @@ -255,6 +294,78 @@ mgt_vcl_depends(struct vclprog *vp1, const char *name) mgt_vcl_dep_add(vp1, vp2); } +static int +mgt_vcl_cache_vmod(const char *nm, const char *fm, const char *to) +{ + int fi, fo; + int ret = 0; + ssize_t sz; + char buf[BUFSIZ]; + + fo = open(to, O_WRONLY | O_CREAT | O_EXCL, 0744); + if (fo < 0 && errno == EEXIST) + return (0); + if (fo < 0) { + fprintf(stderr, "Creating copy of vmod %s: %s\n", + nm, strerror(errno)); + return (1); + } + fi = open(fm, O_RDONLY); + if (fi < 0) { + fprintf(stderr, "Opening vmod %s from %s: %s\n", + nm, fm, strerror(errno)); + AZ(unlink(to)); + closefd(&fo); + return (1); + } + while (1) { + sz = read(fi, buf, sizeof buf); + if (sz == 0) + break; + if (sz < 0 || sz != write(fo, buf, sz)) { + fprintf(stderr, "Copying vmod %s: %s\n", + nm, strerror(errno)); + AZ(unlink(to)); + ret = 1; + break; + } + } + closefd(&fi); + AZ(fchmod(fo, 0444)); + closefd(&fo); + return(ret); +} + +void +mgt_vcl_vmod(struct vclprog *vp, const char *src, const char *dst) +{ + struct vmodfile *vf; + struct vmoddep *vd; + + CHECK_OBJ_NOTNULL(vp, VCLPROG_MAGIC); + AN(src); + AN(dst); + assert(!strncmp(dst, "./vmod_cache/", 13)); + + VTAILQ_FOREACH(vf, &vmodhead, list) + if (!strcmp(vf->fname, dst)) + break; + if (vf == NULL) { + ALLOC_OBJ(vf, VMODFILE_MAGIC); + AN(vf); + REPLACE(vf->fname, dst); + AN(vf->fname); + VTAILQ_INIT(&vf->vcls); + AZ(mgt_vcl_cache_vmod(vp->name, src, dst)); + VTAILQ_INSERT_TAIL(&vmodhead, vf, list); + } + ALLOC_OBJ(vd, VMODDEP_MAGIC); + AN(vd); + vd->to = vf; + VTAILQ_INSERT_TAIL(&vp->vmods, vd, lfrom); + VTAILQ_INSERT_TAIL(&vf->vcls, vd, lto); +} + int mgt_has_vcl(void) { From phk at FreeBSD.org Sun Mar 5 00:12:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Sun, 05 Mar 2017 01:12:05 +0100 Subject: [master] 5c46217 Check -T and -M arguments sooner. Message-ID: commit 5c46217512f24aae44a086f3ebeade234cb08f5f Author: Poul-Henning Kamp Date: Sun Mar 5 00:01:10 2017 +0000 Check -T and -M arguments sooner. Fixes #2217 diff --git a/bin/varnishd/mgt/mgt_main.c b/bin/varnishd/mgt/mgt_main.c index 9056a9d..fa69dcd 100644 --- a/bin/varnishd/mgt/mgt_main.c +++ b/bin/varnishd/mgt/mgt_main.c @@ -758,6 +758,11 @@ main(int argc, char * const *argv) VJ_master(JAIL_MASTER_LOW); } + if (M_arg != NULL) + mgt_cli_master(M_arg); + if (T_arg != NULL) + mgt_cli_telnet(T_arg); + if (VIN_N_Arg(n_arg, &heritage.name, &dirname, NULL) != 0) ARGV_ERR("Invalid instance (-n) name: %s\n", strerror(errno)); @@ -844,11 +849,6 @@ main(int argc, char * const *argv) if (strcmp(S_arg, "none")) mgt_cli_secret(S_arg); - if (M_arg != NULL) - mgt_cli_master(M_arg); - if (T_arg != NULL) - mgt_cli_telnet(T_arg); - mgt_SHM_Create(); if (!d_flag && !mgt_has_vcl() && !novcl) From phk at FreeBSD.org Sun Mar 5 00:12:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Sun, 05 Mar 2017 01:12:05 +0100 Subject: [master] 2986c1f Ok, not quite _that_ early, we need to have access to SHM. Message-ID: commit 2986c1f0f2e36ebcb6f666211ee013631e84ed23 Author: Poul-Henning Kamp Date: Sun Mar 5 00:11:13 2017 +0000 Ok, not quite _that_ early, we need to have access to SHM. diff --git a/bin/varnishd/mgt/mgt_main.c b/bin/varnishd/mgt/mgt_main.c index fa69dcd..edc89df 100644 --- a/bin/varnishd/mgt/mgt_main.c +++ b/bin/varnishd/mgt/mgt_main.c @@ -758,11 +758,6 @@ main(int argc, char * const *argv) VJ_master(JAIL_MASTER_LOW); } - if (M_arg != NULL) - mgt_cli_master(M_arg); - if (T_arg != NULL) - mgt_cli_telnet(T_arg); - if (VIN_N_Arg(n_arg, &heritage.name, &dirname, NULL) != 0) ARGV_ERR("Invalid instance (-n) name: %s\n", strerror(errno)); @@ -833,6 +828,11 @@ main(int argc, char * const *argv) mgt_SHM_Init(); + if (M_arg != NULL) + mgt_cli_master(M_arg); + if (T_arg != NULL) + mgt_cli_telnet(T_arg); + AZ(VSB_finish(vident)); if (S_arg == NULL) From phk at FreeBSD.org Sun Mar 5 09:51:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Sun, 05 Mar 2017 10:51:05 +0100 Subject: [master] ab8c1f5 Typo Message-ID: commit ab8c1f5bc12d7b1b4642b0b0ff67e5221155d95a Author: Poul-Henning Kamp Date: Sun Mar 5 00:31:57 2017 +0000 Typo diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index 15cb232..50417d4 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -668,7 +668,7 @@ h2_rxframe(struct worker *wrk, struct h2_sess *h2) h2->rxf_type = h2->htc->rxbuf_b[3]; h2->rxf_flags = h2->htc->rxbuf_b[4]; h2->rxf_stream = vbe32dec(h2->htc->rxbuf_b + 5); - h2->rxf_stream &= ~(1LU<<31); // rfc7450,l,690,692 + h2->rxf_stream &= ~(1LU<<31); // rfc7540,l,690,692 h2->rxf_data = (void*)(h2->htc->rxbuf_b + 9); /* XXX: later full DATA will not be rx'ed yet. */ HTC_RxPipeline(h2->htc, h2->htc->rxbuf_b + h2->rxf_len + 9); From phk at FreeBSD.org Sun Mar 5 09:51:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Sun, 05 Mar 2017 10:51:05 +0100 Subject: [master] 3b30c88 Fix an off-by-one error in the place-holder VSLbin() Message-ID: commit 3b30c88cbca016f2c777cb11907abc1151396c83 Author: Poul-Henning Kamp Date: Sun Mar 5 09:50:35 2017 +0000 Fix an off-by-one error in the place-holder VSLbin() diff --git a/bin/varnishd/cache/cache_shmlog.c b/bin/varnishd/cache/cache_shmlog.c index c9776ab..d8e3c7d 100644 --- a/bin/varnishd/cache/cache_shmlog.c +++ b/bin/varnishd/cache/cache_shmlog.c @@ -385,20 +385,22 @@ VSLb_bin(struct vsl_log *vsl, enum VSL_tag_e tag, ssize_t len, const void *ptr) char *p; const uint8_t *pp = ptr; int suff = 0; - size_t ll; + size_t tl, ll; assert(len >= 0); AN(pp); if (vsl_tag_is_masked(tag)) return; vsl_sanity(vsl); - if (len * 2 + 1 > cache_param->vsl_reclen) { + tl = len * 2 + 1; + if (tl > cache_param->vsl_reclen) { len = (cache_param->vsl_reclen - 2) / 2; + tl = len * 2 + 2; suff = 1; } - if (VSL_END(vsl->wlp, len * 2 + 1) >= vsl->wle) + if (VSL_END(vsl->wlp, tl) >= vsl->wle) VSL_Flush(vsl, 1); - assert(VSL_END(vsl->wlp, len * 2 + 1) < vsl->wle); + assert(VSL_END(vsl->wlp, tl) < vsl->wle); p = VSL_DATA(vsl->wlp); for (ll = 0; ll < len; ll++) { assert(snprintf(p, 3, "%02x", *pp) == 2); @@ -408,7 +410,7 @@ VSLb_bin(struct vsl_log *vsl, enum VSL_tag_e tag, ssize_t len, const void *ptr) if (suff) *p++ = '-'; *p = '\0'; - vsl->wlp = vsl_hdr(tag, vsl->wlp, len * 2 + 1, vsl->wid); + vsl->wlp = vsl_hdr(tag, vsl->wlp, tl, vsl->wid); assert(vsl->wlp < vsl->wle); vsl->wlr++; } From phk at FreeBSD.org Sun Mar 5 10:33:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Sun, 05 Mar 2017 11:33:05 +0100 Subject: [master] 4060412 Deal with WINDOWS_UPDATES on closed streams Message-ID: commit 4060412e76fe6094c20ec823d20178ea7aee85be Author: Poul-Henning Kamp Date: Sun Mar 5 10:32:14 2017 +0000 Deal with WINDOWS_UPDATES on closed streams diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index 50417d4..d9e0cbb 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -279,6 +279,8 @@ h2_rx_window_update(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) wu = vbe32dec(h2->rxf_data) & ~(1LU<<31); if (wu == 0) return (H2SE_PROTOCOL_ERROR); + if (r2 == NULL) + return (0); Lck_Lock(&h2->sess->mtx); r2->window += wu; Lck_Unlock(&h2->sess->mtx); diff --git a/bin/varnishtest/tests/t02003.vtc b/bin/varnishtest/tests/t02003.vtc index ed7ce70..4d7de36 100644 --- a/bin/varnishtest/tests/t02003.vtc +++ b/bin/varnishtest/tests/t02003.vtc @@ -81,6 +81,17 @@ client c1 { } -run } -run +client c1 { + stream 1 { + txreq + rxresp + } -run + stream 1 { + # WINDOW_UPDATE on closed stream + txwinup -size 0x4000 + } -run +} -run + ####################################################################### # Test PING error conditions From phk at FreeBSD.org Sun Mar 5 14:16:04 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Sun, 05 Mar 2017 15:16:04 +0100 Subject: [master] 550b926 Hold lock over h2req->vsl Message-ID: commit 550b9264a2559153ab3a07d25f52573c92c65e21 Author: Poul-Henning Kamp Date: Sun Mar 5 14:01:12 2017 +0000 Hold lock over h2req->vsl diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index d9e0cbb..018c15e 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -702,7 +702,9 @@ h2_rxframe(struct worker *wrk, struct h2_sess *h2) h2->rxf_flags &= h2f->flags; } + Lck_Lock(&h2->sess->mtx); h2_vsl_frame(h2, h2->htc->rxbuf_b, 9L + h2->rxf_len); + Lck_Unlock(&h2->sess->mtx); h2e = h2_procframe(wrk, h2, h2f); if (h2e) { From phk at FreeBSD.org Mon Mar 6 07:37:04 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Mon, 06 Mar 2017 08:37:04 +0100 Subject: [master] 9029079 Improve test coverage Message-ID: commit 9029079f9a7b7a122fd0054052b5c2c56dffb1b1 Author: Poul-Henning Kamp Date: Mon Mar 6 07:31:37 2017 +0000 Improve test coverage diff --git a/bin/varnishtest/tests/t02003.vtc b/bin/varnishtest/tests/t02003.vtc index 4d7de36..893d296 100644 --- a/bin/varnishtest/tests/t02003.vtc +++ b/bin/varnishtest/tests/t02003.vtc @@ -20,7 +20,7 @@ client c1 { expect goaway.err == PROTOCOL_ERROR } -start stream 2 { - txwinup -size 1 + txprio } -run stream 0 -wait } -run @@ -104,6 +104,15 @@ client c1 { } -run } -run +client c1 { + stream 0 { + sendhex "000008 06 00 00000001 0102030405060708" + rxgoaway + expect goaway.laststream == 0 + expect goaway.err == PROTOCOL_ERROR + } -run +} -run + ####################################################################### # Test PUSH_PROMISE error conditions @@ -111,9 +120,10 @@ client c1 { stream 0 { rxgoaway expect goaway.err == PROTOCOL_ERROR - expect goaway.laststream == 0 + expect goaway.laststream == 1 } -start stream 1 { + txprio sendhex "000008 05 00 00000001 0001020304050607" } -run stream 0 -wait From dridi.boukelmoune at gmail.com Mon Mar 6 12:55:06 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Mon, 06 Mar 2017 13:55:06 +0100 Subject: [master] 9837045 Send a PROXY v1 line with backend probes Message-ID: commit 9837045a011db7496b6a0680687c48fbbac41186 Author: Dridi Boukelmoune Date: Fri Mar 3 10:46:31 2017 +0100 Send a PROXY v1 line with backend probes It consists in the source and destination being the same socket address. Refs #2151 diff --git a/bin/varnishd/cache/cache_backend_probe.c b/bin/varnishd/cache/cache_backend_probe.c index 1d743f8..9f451c7 100644 --- a/bin/varnishd/cache/cache_backend_probe.c +++ b/bin/varnishd/cache/cache_backend_probe.c @@ -43,6 +43,9 @@ #include #include +#include +#include + #include "binary_heap.h" #include "vcli_serve.h" #include "vrt.h" @@ -213,6 +216,49 @@ vbp_reset(struct vbp_target *vt) * want to measure the backends response without local distractions. */ +static int +vbp_write(struct vbp_target *vt, int sock, const void *buf, size_t len) +{ + int i; + + i = write(sock, buf, len); + if (i != len) { + if (i < 0) + vt->err_xmit |= 1; + VTCP_close(&sock); + return (-1); + } + return (0); +} + +static int +vbp_write_proxy_v1(struct vbp_target *vt, int sock) +{ + char buf[105]; /* maximum size for a TCP6 PROXY line with null char */ + char addr[VTCP_ADDRBUFSIZE]; + char port[VTCP_PORTBUFSIZE]; + struct sockaddr_storage ss; + struct vsb vsb; + socklen_t l; + + VTCP_myname(sock, addr, sizeof addr, port, sizeof port); + AN(VSB_new(&vsb, buf, sizeof buf, VSB_FIXEDLEN)); + AZ(VSB_cat(&vsb, "PROXY")); + + l = sizeof ss; + AZ(getsockname(sock, (void *)&ss, &l)); + if (ss.ss_family == AF_INET6) + VSB_printf(&vsb, " TCP6 "); + else if (ss.ss_family == AF_INET) + VSB_printf(&vsb, " TCP4 "); + else + WRONG("Unknown family"); + VSB_printf(&vsb, "%s %s %s %s\r\n", addr, addr, port, port); + AZ(VSB_finish(&vsb)); + + return (vbp_write(vt, sock, VSB_data(&vsb), VSB_len(&vsb))); +} + static void vbp_poke(struct vbp_target *vt) { @@ -248,14 +294,18 @@ vbp_poke(struct vbp_target *vt) return; } + /* Send the PROXY header */ + assert(vt->backend->proxy_header >= 0); + assert(vt->backend->proxy_header <= 2); + if (vt->backend->proxy_header == 1) { + if (vbp_write_proxy_v1(vt, s) != 0) + return; + } else if (vt->backend->proxy_header == 2) + INCOMPL(); + /* Send the request */ - i = write(s, vt->req, vt->req_len); - if (i != vt->req_len) { - if (i < 0) - vt->err_xmit |= 1; - VTCP_close(&s); + if (vbp_write(vt, s, vt->req, vt->req_len) != 0) return; - } vt->good_xmit |= 1; pfd->fd = s; diff --git a/bin/varnishtest/tests/o00004.vtc b/bin/varnishtest/tests/o00004.vtc new file mode 100644 index 0000000..03c67d5 --- /dev/null +++ b/bin/varnishtest/tests/o00004.vtc @@ -0,0 +1,50 @@ +varnishtest "Sending proxy headers via health probes" + +# Double-proxy scheme stolen from o00002.vtc + +server s1 { + rxreq + expect req.http.x-forwarded-for == "127.0.0.1" + txresp +} -start + +varnish v1 -proto PROXY -vcl+backend { + import debug; + + sub vcl_recv { + if (client.ip != remote.ip || server.ip != local.ip) { + return (synth(400)); + } + } +} -start + +varnish v2 -proto PROXY -vcl { + import std; + + probe p { + .window = 1; + .threshold = 1; + .interval =0.5s; + } + backend bp1 { + .host = "${v1_addr}"; + .port = "${v1_port}"; + .proxy_header = 1; + .probe = p; + } + backend bp2 { + .host = "${v1_addr}"; + .port = "${v1_port}"; + .proxy_header = 2; + } + + sub vcl_init { + # dummy backend ref + if (bp2) { } + } +} -start + +server s1 -wait + +delay 1 +varnish v2 -cliexpect "vcl1.bp1[ ]+probe[ ]+Healthy[ ]+1/1" backend.list From dridi.boukelmoune at gmail.com Mon Mar 6 12:55:07 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Mon, 06 Mar 2017 13:55:07 +0100 Subject: [master] 1087f15 Send PROXY v2 LOCAL header with probes Message-ID: commit 1087f15425daca463d137d5ba187fdb0c5c32026 Author: Dridi Boukelmoune Date: Fri Mar 3 14:03:36 2017 +0100 Send PROXY v2 LOCAL header with probes Fixes #2151 diff --git a/bin/varnishd/cache/cache_backend_probe.c b/bin/varnishd/cache/cache_backend_probe.c index 9f451c7..e862431 100644 --- a/bin/varnishd/cache/cache_backend_probe.c +++ b/bin/varnishd/cache/cache_backend_probe.c @@ -92,6 +92,11 @@ static struct lock vbp_mtx; static pthread_cond_t vbp_cond; static struct binheap *vbp_heap; +static unsigned char vbp_proxy_local[] = { + 0x0d, 0x0a, 0x0d, 0x0a, 0x00, 0x0d, 0x0a, 0x51, + 0x55, 0x49, 0x54, 0x0a, 0x20, 0x00, 0x00, 0x00, +}; + /*--------------------------------------------------------------------*/ static void @@ -300,8 +305,9 @@ vbp_poke(struct vbp_target *vt) if (vt->backend->proxy_header == 1) { if (vbp_write_proxy_v1(vt, s) != 0) return; - } else if (vt->backend->proxy_header == 2) - INCOMPL(); + } else if (vt->backend->proxy_header == 2 && + vbp_write(vt, s, vbp_proxy_local, sizeof vbp_proxy_local) != 0) + return; /* Send the request */ if (vbp_write(vt, s, vt->req, vt->req_len) != 0) diff --git a/bin/varnishtest/tests/o00004.vtc b/bin/varnishtest/tests/o00004.vtc index 03c67d5..4d4c082 100644 --- a/bin/varnishtest/tests/o00004.vtc +++ b/bin/varnishtest/tests/o00004.vtc @@ -21,7 +21,7 @@ varnish v1 -proto PROXY -vcl+backend { varnish v2 -proto PROXY -vcl { import std; - probe p { + probe default { .window = 1; .threshold = 1; .interval =0.5s; @@ -30,7 +30,6 @@ varnish v2 -proto PROXY -vcl { .host = "${v1_addr}"; .port = "${v1_port}"; .proxy_header = 1; - .probe = p; } backend bp2 { .host = "${v1_addr}"; @@ -48,3 +47,4 @@ server s1 -wait delay 1 varnish v2 -cliexpect "vcl1.bp1[ ]+probe[ ]+Healthy[ ]+1/1" backend.list +varnish v2 -cliexpect "vcl1.bp2[ ]+probe[ ]+Healthy[ ]+1/1" backend.list From dridi.boukelmoune at gmail.com Mon Mar 6 13:34:06 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Mon, 06 Mar 2017 14:34:06 +0100 Subject: [master] ba721c2 Tautological assert Message-ID: commit ba721c27062202ef191a2f48dc8c6d708abb71ca Author: Dridi Boukelmoune Date: Mon Mar 6 14:33:25 2017 +0100 Tautological assert diff --git a/bin/varnishd/cache/cache_backend_probe.c b/bin/varnishd/cache/cache_backend_probe.c index e862431..5dbf11f 100644 --- a/bin/varnishd/cache/cache_backend_probe.c +++ b/bin/varnishd/cache/cache_backend_probe.c @@ -300,7 +300,6 @@ vbp_poke(struct vbp_target *vt) } /* Send the PROXY header */ - assert(vt->backend->proxy_header >= 0); assert(vt->backend->proxy_header <= 2); if (vt->backend->proxy_header == 1) { if (vbp_write_proxy_v1(vt, s) != 0) From phk at FreeBSD.org Mon Mar 6 15:07:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Mon, 06 Mar 2017 16:07:06 +0100 Subject: [master] e5a7775 More coverage Message-ID: commit e5a777586d7ab3341feddb5a6cf84dffc3ed9fcf Author: Poul-Henning Kamp Date: Mon Mar 6 08:22:38 2017 +0000 More coverage diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index 018c15e..1eb4b6b 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -680,10 +680,16 @@ h2_rxframe(struct worker *wrk, struct h2_sess *h2) // XXX: later, drain rest of frame h2->bogosity++; VSLb(h2->vsl, SLT_Debug, - "H2: Unknown frame type 0x%02x (ignored)", h2->rxf_type); + "H2: Unknown frame type 0x%02x (ignored)", + (uint8_t)h2->rxf_type); return (1); } h2f = h2flist + h2->rxf_type; +#if 1 + AN(h2f->name); + AN(h2f->func); +#else + /* If we ever get holes in the frame table... */ if (h2f->name == NULL || h2f->func == NULL) { // rfc7540,l,679,681 // XXX: later, drain rest of frame @@ -693,12 +699,13 @@ h2_rxframe(struct worker *wrk, struct h2_sess *h2) h2->rxf_type); return (0); } +#endif if (h2->rxf_flags & ~h2f->flags) { // rfc7540,l,687,688 h2->bogosity++; VSLb(h2->vsl, SLT_Debug, "H2: Unknown flags 0x%02x on %s (ignored)", - h2->rxf_flags, h2f->name); + (uint8_t)h2->rxf_flags, h2f->name); h2->rxf_flags &= h2f->flags; } diff --git a/bin/varnishtest/tests/t02003.vtc b/bin/varnishtest/tests/t02003.vtc index 893d296..0686628 100644 --- a/bin/varnishtest/tests/t02003.vtc +++ b/bin/varnishtest/tests/t02003.vtc @@ -20,6 +20,7 @@ client c1 { expect goaway.err == PROTOCOL_ERROR } -start stream 2 { + sendhex "000003 80 00 00000002 010203" txprio } -run stream 0 -wait @@ -106,7 +107,7 @@ client c1 { client c1 { stream 0 { - sendhex "000008 06 00 00000001 0102030405060708" + sendhex "000008 06 80 00000001 0102030405060708" rxgoaway expect goaway.laststream == 0 expect goaway.err == PROTOCOL_ERROR From phk at FreeBSD.org Mon Mar 6 15:07:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Mon, 06 Mar 2017 16:07:06 +0100 Subject: [master] 429d2a1 Log all received frames, even if we throw them away. Message-ID: commit 429d2a13e3c02012a282db9982a989d34f4e19aa Author: Poul-Henning Kamp Date: Mon Mar 6 08:33:22 2017 +0000 Log all received frames, even if we throw them away. diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index 1eb4b6b..3154537 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -675,6 +675,10 @@ h2_rxframe(struct worker *wrk, struct h2_sess *h2) /* XXX: later full DATA will not be rx'ed yet. */ HTC_RxPipeline(h2->htc, h2->htc->rxbuf_b + h2->rxf_len + 9); + Lck_Lock(&h2->sess->mtx); + h2_vsl_frame(h2, h2->htc->rxbuf_b, 9L + h2->rxf_len); + Lck_Unlock(&h2->sess->mtx); + if (h2->rxf_type >= H2FMAX) { // rfc7540,l,679,681 // XXX: later, drain rest of frame @@ -709,10 +713,6 @@ h2_rxframe(struct worker *wrk, struct h2_sess *h2) h2->rxf_flags &= h2f->flags; } - Lck_Lock(&h2->sess->mtx); - h2_vsl_frame(h2, h2->htc->rxbuf_b, 9L + h2->rxf_len); - Lck_Unlock(&h2->sess->mtx); - h2e = h2_procframe(wrk, h2, h2f); if (h2e) { vbe32enc(b, h2->highest_stream); From phk at FreeBSD.org Mon Mar 6 15:07:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Mon, 06 Mar 2017 16:07:06 +0100 Subject: [master] b335906 Make H2_F_* a self-describing object and ditch the enum. Message-ID: commit b33590604e9982bc1a6c13ef9d955bf8ee3c0021 Author: Poul-Henning Kamp Date: Mon Mar 6 10:17:13 2017 +0000 Make H2_F_* a self-describing object and ditch the enum. diff --git a/bin/varnishd/http2/cache_http2.h b/bin/varnishd/http2/cache_http2.h index 4bcfe21..1dd618e 100644 --- a/bin/varnishd/http2/cache_http2.h +++ b/bin/varnishd/http2/cache_http2.h @@ -28,6 +28,7 @@ */ struct h2_sess; +struct h2_req; struct h2h_decode; #include "hpack/vhp.h" @@ -42,6 +43,24 @@ struct h2_error_s { typedef const struct h2_error_s *h2_error; +typedef h2_error h2_rxframe_f(struct worker *, struct h2_sess *, + struct h2_req *); + +struct h2_frame_s { + const char *name; + h2_rxframe_f *rxfunc; + uint8_t type; + uint8_t flags; + h2_error act_szero; + h2_error act_snonzero; + h2_error act_sidle; +}; + +typedef const struct h2_frame_s *h2_frame; + +#define H2_FRAME(l,U,...) extern const struct h2_frame_s H2_F_##U[1]; +#include "tbl/h2_frames.h" + #define H2EC0(U,v,d) #define H2EC1(U,v,d) extern const struct h2_error_s H2CE_##U[1]; #define H2EC2(U,v,d) extern const struct h2_error_s H2SE_##U[1]; @@ -52,12 +71,6 @@ typedef const struct h2_error_s *h2_error; #undef H2EC2 #undef H2EC3 -enum h2_frame_e { - H2_FRAME__DUMMY = -1, -#define H2_FRAME(l,u,t,f,...) H2_FRAME_##u = t, -#include "tbl/h2_frames.h" -}; - enum h2_stream_e { H2_STREAM__DUMMY = -1, #define H2_STREAM(U,s,d) H2_S_##U, @@ -155,11 +168,11 @@ h2_error h2h_decode_bytes(struct h2_sess *h2, struct h2h_decode *d, const uint8_t *ptr, size_t len); int H2_Send_Frame(struct worker *, const struct h2_sess *, - enum h2_frame_e type, uint8_t flags, uint32_t len, uint32_t stream, + h2_frame type, uint8_t flags, uint32_t len, uint32_t stream, const void *); int H2_Send(struct worker *, struct h2_req *, int flush, - enum h2_frame_e type, uint8_t flags, uint32_t len, const void *); + h2_frame type, uint8_t flags, uint32_t len, const void *); /* cache_http2_proto.c */ struct h2_req * h2_new_req(const struct worker *, struct h2_sess *, diff --git a/bin/varnishd/http2/cache_http2_deliver.c b/bin/varnishd/http2/cache_http2_deliver.c index 27ce4b3..9e2665e 100644 --- a/bin/varnishd/http2/cache_http2_deliver.c +++ b/bin/varnishd/http2/cache_http2_deliver.c @@ -86,8 +86,7 @@ h2_bytes(struct req *req, enum vdp_action act, void **priv, AZ(req->vdp_nxt); /* always at the bottom of the pile */ H2_Send(req->wrk, r2, - act == VDP_FLUSH ? 1 : 0, - H2_FRAME_DATA, H2FF_NONE, len, ptr); + act == VDP_FLUSH ? 1 : 0, H2_F_DATA, H2FF_NONE, len, ptr); return (0); } @@ -142,7 +141,7 @@ h2_minimal_response(struct req *req, uint16_t status) /* XXX return code checking once H2_Send returns anything but 0 */ H2_Send(req->wrk, r2, 1, - H2_FRAME_HEADERS, + H2_F_HEADERS, H2FF_HEADERS_END_HEADERS | (status < 200 ? 0 : H2FF_HEADERS_END_STREAM), l, buf); @@ -241,7 +240,7 @@ h2_deliver(struct req *req, struct boc *boc, int sendbody) sz = (char*)p - req->ws->f; /* XXX: Optimize !sendbody case */ - H2_Send(req->wrk, r2, 1, H2_FRAME_HEADERS, H2FF_HEADERS_END_HEADERS, + H2_Send(req->wrk, r2, 1, H2_F_HEADERS, H2FF_HEADERS_END_HEADERS, sz, req->ws->f); WS_Release(req->ws, 0); @@ -255,7 +254,7 @@ h2_deliver(struct req *req, struct boc *boc, int sendbody) err = VDP_DeliverObj(req); /*XXX*/(void)err; - H2_Send(req->wrk, r2, 1, H2_FRAME_DATA, H2FF_DATA_END_STREAM, 0, NULL); + H2_Send(req->wrk, r2, 1, H2_F_DATA, H2FF_DATA_END_STREAM, 0, NULL); AZ(req->wrk->v1l); VDP_close(req); diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index 3154537..2f271ff 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -52,8 +52,6 @@ #undef H2EC2 #undef H2EC3 -typedef h2_error h2_frame_f(struct worker *, struct h2_sess *, struct h2_req *); - enum h2frame { #define H2_FRAME(l,u,t,f,...) H2F_##u = t, #include "tbl/h2_frames.h" @@ -87,17 +85,6 @@ h2_settingname(enum h2setting h2f) #define H2_FRAME_FLAGS(l,u,v) const uint8_t H2FF_##u = v; #include "tbl/h2_frames.h" -/**********************************************************************/ - -struct h2flist_s { - const char *name; - h2_frame_f *func; - uint8_t flags; - h2_error act_szero; - h2_error act_snonzero; - h2_error act_sidle; -}; - /********************************************************************** */ @@ -214,7 +201,7 @@ h2_rx_ping(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) return (H2SE_PROTOCOL_ERROR); Lck_Lock(&h2->sess->mtx); H2_Send_Frame(wrk, h2, - H2_FRAME_PING, H2FF_PING_ACK, 8, 0, h2->rxf_data); + H2_F_PING, H2FF_PING_ACK, 8, 0, h2->rxf_data); Lck_Unlock(&h2->sess->mtx); return (0); } @@ -346,7 +333,7 @@ h2_rx_settings(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) "NB: SETTINGS had %u dribble-bytes", l); Lck_Lock(&h2->sess->mtx); H2_Send_Frame(wrk, h2, - H2_FRAME_SETTINGS, H2FF_SETTINGS_ACK, 0, 0, NULL); + H2_F_SETTINGS, H2FF_SETTINGS_ACK, 0, 0, NULL); Lck_Unlock(&h2->sess->mtx); } else { WRONG("SETTINGS FRAME"); @@ -580,7 +567,7 @@ h2_frame_complete(struct http_conn *htc) static h2_error h2_procframe(struct worker *wrk, struct h2_sess *h2, - const struct h2flist_s *h2f) + h2_frame h2f) { struct h2_req *r2 = NULL; h2_error h2e; @@ -616,7 +603,7 @@ h2_procframe(struct worker *wrk, struct h2_sess *h2, AN(r2); } - h2e = h2f->func(wrk, h2, r2); + h2e = h2f->rxfunc(wrk, h2, r2); if (h2e == 0) return (0); if (h2->rxf_stream == 0 || h2e->connection) @@ -626,7 +613,7 @@ h2_procframe(struct worker *wrk, struct h2_sess *h2, vbe32enc(b, h2e->val); Lck_Lock(&h2->sess->mtx); - (void)H2_Send_Frame(wrk, h2, H2_FRAME_RST_STREAM, + (void)H2_Send_Frame(wrk, h2, H2_F_RST_STREAM, 0, sizeof b, h2->rxf_stream, b); Lck_Unlock(&h2->sess->mtx); @@ -638,8 +625,12 @@ h2_procframe(struct worker *wrk, struct h2_sess *h2, * Called in loop from h2_new_session() */ -static const struct h2flist_s h2flist[] = { -#define H2_FRAME(l,U,t,f,az,anz,ai) [t] = { #U, h2_rx_##l, f, az, anz,ai }, +#define H2_FRAME(l,U,...) const struct h2_frame_s H2_F_##U[1] = \ + {{ #U, h2_rx_##l, __VA_ARGS__ }}; +#include "tbl/h2_frames.h" + +static const h2_frame h2flist[] = { +#define H2_FRAME(l,U,t,...) [t] = H2_F_##U, #include "tbl/h2_frames.h" }; @@ -649,7 +640,7 @@ int h2_rxframe(struct worker *wrk, struct h2_sess *h2) { enum htc_status_e hs; - const struct h2flist_s *h2f; + h2_frame h2f; h2_error h2e; char b[8]; @@ -688,10 +679,10 @@ h2_rxframe(struct worker *wrk, struct h2_sess *h2) (uint8_t)h2->rxf_type); return (1); } - h2f = h2flist + h2->rxf_type; + h2f = h2flist[h2->rxf_type]; #if 1 AN(h2f->name); - AN(h2f->func); + AN(h2f->rxfunc); #else /* If we ever get holes in the frame table... */ if (h2f->name == NULL || h2f->func == NULL) { @@ -718,7 +709,7 @@ h2_rxframe(struct worker *wrk, struct h2_sess *h2) vbe32enc(b, h2->highest_stream); vbe32enc(b + 4, h2e->val); Lck_Lock(&h2->sess->mtx); - (void)H2_Send_Frame(wrk, h2, H2_FRAME_GOAWAY, 0, 8, 0, b); + (void)H2_Send_Frame(wrk, h2, H2_F_GOAWAY, 0, 8, 0, b); Lck_Unlock(&h2->sess->mtx); } return (h2e ? 0 : 1); diff --git a/bin/varnishd/http2/cache_http2_send.c b/bin/varnishd/http2/cache_http2_send.c index f6f9587..eeffae3 100644 --- a/bin/varnishd/http2/cache_http2_send.c +++ b/bin/varnishd/http2/cache_http2_send.c @@ -37,14 +37,14 @@ #include "vend.h" static void -h2_mk_hdr(uint8_t *hdr, enum h2_frame_e type, uint8_t flags, +h2_mk_hdr(uint8_t *hdr, h2_frame ftyp, uint8_t flags, uint32_t len, uint32_t stream) { AN(hdr); assert(len < (1U << 24)); vbe32enc(hdr, len << 8); - hdr[3] = (uint8_t)type; + hdr[3] = ftyp->type; hdr[4] = flags; vbe32enc(hdr + 5, stream); } @@ -57,7 +57,7 @@ h2_mk_hdr(uint8_t *hdr, enum h2_frame_e type, uint8_t flags, int H2_Send_Frame(struct worker *wrk, const struct h2_sess *h2, - enum h2_frame_e type, uint8_t flags, + h2_frame ftyp, uint8_t flags, uint32_t len, uint32_t stream, const void *ptr) { uint8_t hdr[9]; @@ -65,7 +65,7 @@ H2_Send_Frame(struct worker *wrk, const struct h2_sess *h2, Lck_AssertHeld(&h2->sess->mtx); (void)wrk; - h2_mk_hdr(hdr, type, flags, len, stream); + h2_mk_hdr(hdr, ftyp, flags, len, stream); VSLb_bin(h2->vsl, SLT_H2TxHdr, 9, hdr); /*XXX*/(void)write(h2->sess->fd, hdr, sizeof hdr); @@ -84,7 +84,7 @@ H2_Send_Frame(struct worker *wrk, const struct h2_sess *h2, int H2_Send(struct worker *wrk, struct h2_req *r2, int flush, - enum h2_frame_e type, uint8_t flags, uint32_t len, const void *ptr) + h2_frame ftyp, uint8_t flags, uint32_t len, const void *ptr) { int retval; struct h2_sess *h2; @@ -102,8 +102,8 @@ H2_Send(struct worker *wrk, struct h2_req *r2, int flush, mfs = h2->their_settings[H2S_MAX_FRAME_SIZE]; if (len < mfs) { retval = H2_Send_Frame(wrk, h2, - type, flags, len, r2->stream, ptr); - } else if (type == H2_FRAME_DATA) { + ftyp, flags, len, r2->stream, ptr); + } else if (ftyp == H2_F_DATA) { AN(ptr); AN(len); p = ptr; @@ -111,7 +111,7 @@ H2_Send(struct worker *wrk, struct h2_req *r2, int flush, tf = mfs; if (tf > len) tf = len; - retval = H2_Send_Frame(wrk, h2, type, + retval = H2_Send_Frame(wrk, h2, ftyp, tf == len ? flags : 0, tf, r2->stream, p); p += tf; diff --git a/bin/varnishd/http2/cache_http2_session.c b/bin/varnishd/http2/cache_http2_session.c index 35dc072..4857500 100644 --- a/bin/varnishd/http2/cache_http2_session.c +++ b/bin/varnishd/http2/cache_http2_session.c @@ -333,7 +333,7 @@ h2_new_session(struct worker *wrk, void *arg) Lck_Lock(&h2->sess->mtx); H2_Send_Frame(wrk, h2, - H2_FRAME_SETTINGS, H2FF_NONE, sizeof H2_settings, 0, H2_settings); + H2_F_SETTINGS, H2FF_NONE, sizeof H2_settings, 0, H2_settings); /* and off we go... */ h2->cond = &wrk->cond; From phk at FreeBSD.org Mon Mar 6 15:07:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Mon, 06 Mar 2017 16:07:06 +0100 Subject: [master] d8cef06 Add transmit properties to the frame descriptors. Message-ID: commit d8cef066b37254187de0fcdc33730b443579f442 Author: Poul-Henning Kamp Date: Mon Mar 6 11:12:27 2017 +0000 Add transmit properties to the frame descriptors. diff --git a/bin/varnishd/http2/cache_http2.h b/bin/varnishd/http2/cache_http2.h index 1dd618e..4f9b3b0 100644 --- a/bin/varnishd/http2/cache_http2.h +++ b/bin/varnishd/http2/cache_http2.h @@ -30,6 +30,7 @@ struct h2_sess; struct h2_req; struct h2h_decode; +struct h2_frame_s; #include "hpack/vhp.h" @@ -46,6 +47,8 @@ typedef const struct h2_error_s *h2_error; typedef h2_error h2_rxframe_f(struct worker *, struct h2_sess *, struct h2_req *); +typedef const struct h2_frame_s *h2_frame; + struct h2_frame_s { const char *name; h2_rxframe_f *rxfunc; @@ -54,9 +57,10 @@ struct h2_frame_s { h2_error act_szero; h2_error act_snonzero; h2_error act_sidle; + int respect_window; + h2_frame continuation; }; -typedef const struct h2_frame_s *h2_frame; #define H2_FRAME(l,U,...) extern const struct h2_frame_s H2_F_##U[1]; #include "tbl/h2_frames.h" @@ -167,11 +171,11 @@ h2_error h2h_decode_fini(const struct h2_sess *h2, struct h2h_decode *d); h2_error h2h_decode_bytes(struct h2_sess *h2, struct h2h_decode *d, const uint8_t *ptr, size_t len); -int H2_Send_Frame(struct worker *, const struct h2_sess *, +h2_error H2_Send_Frame(struct worker *, const struct h2_sess *, h2_frame type, uint8_t flags, uint32_t len, uint32_t stream, const void *); -int H2_Send(struct worker *, struct h2_req *, int flush, +h2_error H2_Send(struct worker *, struct h2_req *, int flush, h2_frame type, uint8_t flags, uint32_t len, const void *); /* cache_http2_proto.c */ diff --git a/bin/varnishd/http2/cache_http2_send.c b/bin/varnishd/http2/cache_http2_send.c index eeffae3..076cc1d 100644 --- a/bin/varnishd/http2/cache_http2_send.c +++ b/bin/varnishd/http2/cache_http2_send.c @@ -55,22 +55,34 @@ h2_mk_hdr(uint8_t *hdr, h2_frame ftyp, uint8_t flags, * the session mtx must be held. */ -int +h2_error H2_Send_Frame(struct worker *wrk, const struct h2_sess *h2, h2_frame ftyp, uint8_t flags, uint32_t len, uint32_t stream, const void *ptr) { uint8_t hdr[9]; + ssize_t s; - Lck_AssertHeld(&h2->sess->mtx); (void)wrk; + Lck_AssertHeld(&h2->sess->mtx); + + AN(ftyp); + AZ(flags & ~(ftyp->flags)); + if (stream == 0) + AZ(ftyp->act_szero); + else + AZ(ftyp->act_snonzero); h2_mk_hdr(hdr, ftyp, flags, len, stream); VSLb_bin(h2->vsl, SLT_H2TxHdr, 9, hdr); - /*XXX*/(void)write(h2->sess->fd, hdr, sizeof hdr); + s = write(h2->sess->fd, hdr, sizeof hdr); + if (s != sizeof hdr) + return (H2CE_PROTOCOL_ERROR); // XXX Need private ? if (len > 0) { - /*XXX*/(void)write(h2->sess->fd, ptr, len); + s = write(h2->sess->fd, ptr, len); + if (s != len) + return (H2CE_PROTOCOL_ERROR); // XXX Need private ? VSLb_bin(h2->vsl, SLT_H2TxBody, len, ptr); } return (0); @@ -82,11 +94,11 @@ H2_Send_Frame(struct worker *wrk, const struct h2_sess *h2, * XXX: priority */ -int +h2_error H2_Send(struct worker *wrk, struct h2_req *r2, int flush, h2_frame ftyp, uint8_t flags, uint32_t len, const void *ptr) { - int retval; + h2_error retval; struct h2_sess *h2; uint32_t mfs, tf; const char *p; @@ -98,16 +110,24 @@ H2_Send(struct worker *wrk, struct h2_req *r2, int flush, CHECK_OBJ_NOTNULL(h2, H2_SESS_MAGIC); assert(len == 0 || ptr != NULL); + AN(ftyp); + AZ(flags & ~(ftyp->flags)); + if (r2->stream == 0) + AZ(ftyp->act_szero); + else + AZ(ftyp->act_snonzero); + Lck_Lock(&h2->sess->mtx); mfs = h2->their_settings[H2S_MAX_FRAME_SIZE]; if (len < mfs) { retval = H2_Send_Frame(wrk, h2, ftyp, flags, len, r2->stream, ptr); - } else if (ftyp == H2_F_DATA) { + } else { AN(ptr); AN(len); p = ptr; do { + AN(ftyp->continuation); tf = mfs; if (tf > len) tf = len; @@ -116,9 +136,8 @@ H2_Send(struct worker *wrk, struct h2_req *r2, int flush, tf, r2->stream, p); p += tf; len -= tf; - } while (len > 0); - } else { - INCOMPL(); + ftyp = ftyp->continuation; + } while (len > 0 && retval == 0); } Lck_Unlock(&h2->sess->mtx); return (retval); diff --git a/include/tbl/h2_frames.h b/include/tbl/h2_frames.h index 29c338f..c8eb31f 100644 --- a/include/tbl/h2_frames.h +++ b/include/tbl/h2_frames.h @@ -32,59 +32,81 @@ #ifdef H2_FRAME /* lower, upper, type, flags - * stream-zero - * stream-nonzero - * stream-idle + * rx_stream-zero + * rx_stream-nonzero + * rx_stream-idle + * tx_flow-control // rfc7540,l,1265,1270 + * tx_continuation */ H2_FRAME(data, DATA, 0x0, 0x09, H2CE_PROTOCOL_ERROR, // rfc7540,l,1758,1761 0, - H2CE_PROTOCOL_ERROR + H2CE_PROTOCOL_ERROR, + 1, + H2_F_DATA ) H2_FRAME(headers, HEADERS, 0x1, 0x2d, H2CE_PROTOCOL_ERROR, // rfc7540,l,1876,1879 0, - 0 // rfc7540,l,938,940 + 0, // rfc7540,l,938,940 + 0, + H2_F_CONTINUATION ) H2_FRAME(priority, PRIORITY, 0x2, 0x00, H2CE_PROTOCOL_ERROR, // rfc7540,l,1933,1936 0, - 0 // rfc7540,l,938,940 + 0, // rfc7540,l,938,940 + 0, + 0 ) H2_FRAME(rst_stream, RST_STREAM, 0x3, 0x00, H2CE_PROTOCOL_ERROR, // rfc7540,l,1993,1996 0, - H2CE_PROTOCOL_ERROR + H2CE_PROTOCOL_ERROR, + 0, + 0 ) H2_FRAME(settings, SETTINGS, 0x4, 0x01, 0, H2CE_PROTOCOL_ERROR, // rfc7540,l,2052,2056 - H2CE_PROTOCOL_ERROR + H2CE_PROTOCOL_ERROR, + 0, + 0 ) H2_FRAME(push_promise, PUSH_PROMISE, 0x5, 0x0c, H2CE_PROTOCOL_ERROR, // rfc7540,l,2262,2263 0, - H2CE_PROTOCOL_ERROR + H2CE_PROTOCOL_ERROR, + 0, + H2_F_CONTINUATION ) H2_FRAME(ping, PING, 0x6, 0x01, 0, H2CE_PROTOCOL_ERROR, // rfc7540,l,2359,2362 - H2CE_PROTOCOL_ERROR + H2CE_PROTOCOL_ERROR, + 0, + 0 ) H2_FRAME(goaway, GOAWAY, 0x7, 0x00, 0, H2CE_PROTOCOL_ERROR, // rfc7540,l,2432,2435 - H2CE_PROTOCOL_ERROR + H2CE_PROTOCOL_ERROR, + 0, + 0 ) H2_FRAME(window_update, WINDOW_UPDATE, 0x8, 0x00, 0, 0, - H2CE_PROTOCOL_ERROR + H2CE_PROTOCOL_ERROR, + 0, + 0 ) H2_FRAME(continuation, CONTINUATION, 0x9, 0x04, H2CE_PROTOCOL_ERROR, // rfc7540,l,2764,2767 0, - H2CE_PROTOCOL_ERROR + H2CE_PROTOCOL_ERROR, + 0, + H2_F_CONTINUATION ) #undef H2_FRAME #endif From phk at FreeBSD.org Mon Mar 6 15:07:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Mon, 06 Mar 2017 16:07:06 +0100 Subject: [master] a1eb3da Due to the incompetent H2 protocol design, we also need to keep track of which per-frame flags only get sent on the last frame of a continued frame-sequence. Message-ID: commit a1eb3dad0a1bf343249aded1096691c7c1497e46 Author: Poul-Henning Kamp Date: Mon Mar 6 11:29:33 2017 +0000 Due to the incompetent H2 protocol design, we also need to keep track of which per-frame flags only get sent on the last frame of a continued frame-sequence. diff --git a/bin/varnishd/http2/cache_http2.h b/bin/varnishd/http2/cache_http2.h index 4f9b3b0..041bced 100644 --- a/bin/varnishd/http2/cache_http2.h +++ b/bin/varnishd/http2/cache_http2.h @@ -59,6 +59,7 @@ struct h2_frame_s { h2_error act_sidle; int respect_window; h2_frame continuation; + uint8_t final_flags; }; diff --git a/bin/varnishd/http2/cache_http2_send.c b/bin/varnishd/http2/cache_http2_send.c index 076cc1d..75fcc43 100644 --- a/bin/varnishd/http2/cache_http2_send.c +++ b/bin/varnishd/http2/cache_http2_send.c @@ -102,6 +102,7 @@ H2_Send(struct worker *wrk, struct h2_req *r2, int flush, struct h2_sess *h2; uint32_t mfs, tf; const char *p; + uint8_t final_flags; (void)flush; @@ -126,14 +127,20 @@ H2_Send(struct worker *wrk, struct h2_req *r2, int flush, AN(ptr); AN(len); p = ptr; + final_flags = ftyp->final_flags & flags; + flags &= ~ftyp->final_flags; do { AN(ftyp->continuation); tf = mfs; - if (tf > len) + if (tf > len) { tf = len; - retval = H2_Send_Frame(wrk, h2, ftyp, - tf == len ? flags : 0, - tf, r2->stream, p); + retval = H2_Send_Frame(wrk, h2, ftyp, + flags, tf, r2->stream, p); + flags = 0; + } else { + retval = H2_Send_Frame(wrk, h2, ftyp, + final_flags, tf, r2->stream, p); + } p += tf; len -= tf; ftyp = ftyp->continuation; diff --git a/include/tbl/h2_frames.h b/include/tbl/h2_frames.h index c8eb31f..039937d 100644 --- a/include/tbl/h2_frames.h +++ b/include/tbl/h2_frames.h @@ -37,26 +37,30 @@ * rx_stream-idle * tx_flow-control // rfc7540,l,1265,1270 * tx_continuation + * tx_final-flags */ H2_FRAME(data, DATA, 0x0, 0x09, H2CE_PROTOCOL_ERROR, // rfc7540,l,1758,1761 0, H2CE_PROTOCOL_ERROR, 1, - H2_F_DATA + H2_F_DATA, + H2FF_DATA_END_STREAM // rfc7540,l,1750,1753 ) H2_FRAME(headers, HEADERS, 0x1, 0x2d, H2CE_PROTOCOL_ERROR, // rfc7540,l,1876,1879 0, 0, // rfc7540,l,938,940 0, - H2_F_CONTINUATION + H2_F_CONTINUATION, + H2FF_HEADERS_END_HEADERS, // rfc7540,l,1855,1857 ) H2_FRAME(priority, PRIORITY, 0x2, 0x00, H2CE_PROTOCOL_ERROR, // rfc7540,l,1933,1936 0, 0, // rfc7540,l,938,940 0, + 0, 0 ) H2_FRAME(rst_stream, RST_STREAM, 0x3, 0x00, @@ -64,6 +68,7 @@ 0, H2CE_PROTOCOL_ERROR, 0, + 0, 0 ) H2_FRAME(settings, SETTINGS, 0x4, 0x01, @@ -71,6 +76,7 @@ H2CE_PROTOCOL_ERROR, // rfc7540,l,2052,2056 H2CE_PROTOCOL_ERROR, 0, + 0, 0 ) H2_FRAME(push_promise, PUSH_PROMISE, 0x5, 0x0c, @@ -78,13 +84,15 @@ 0, H2CE_PROTOCOL_ERROR, 0, - H2_F_CONTINUATION + H2_F_CONTINUATION, + H2FF_PUSH_PROMISE_END_HEADERS, // rfc7540,l,2249,2251 ) H2_FRAME(ping, PING, 0x6, 0x01, 0, H2CE_PROTOCOL_ERROR, // rfc7540,l,2359,2362 H2CE_PROTOCOL_ERROR, 0, + 0, 0 ) H2_FRAME(goaway, GOAWAY, 0x7, 0x00, @@ -92,6 +100,7 @@ H2CE_PROTOCOL_ERROR, // rfc7540,l,2432,2435 H2CE_PROTOCOL_ERROR, 0, + 0, 0 ) H2_FRAME(window_update, WINDOW_UPDATE, 0x8, 0x00, @@ -99,6 +108,7 @@ 0, H2CE_PROTOCOL_ERROR, 0, + 0, 0 ) H2_FRAME(continuation, CONTINUATION, 0x9, 0x04, @@ -106,7 +116,8 @@ 0, H2CE_PROTOCOL_ERROR, 0, - H2_F_CONTINUATION + H2_F_CONTINUATION, + H2FF_CONTINUATION_END_HEADERS // rfc7540,l,2753,2754 ) #undef H2_FRAME #endif From phk at FreeBSD.org Mon Mar 6 15:07:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Mon, 06 Mar 2017 16:07:06 +0100 Subject: [master] e1e2c72 Overhaul H2 Settings handling Message-ID: commit e1e2c723885d06ad98509a22fccb7d1fe1e2eb5f Author: Poul-Henning Kamp Date: Mon Mar 6 15:01:18 2017 +0000 Overhaul H2 Settings handling I guess if you can't say anything else good about it, H2 is forcing me to invent new ways to implement table-driven object-oriented programming. diff --git a/bin/varnishd/http2/cache_http2.h b/bin/varnishd/http2/cache_http2.h index 041bced..d1de3a8 100644 --- a/bin/varnishd/http2/cache_http2.h +++ b/bin/varnishd/http2/cache_http2.h @@ -34,6 +34,8 @@ struct h2_frame_s; #include "hpack/vhp.h" +/**********************************************************************/ + struct h2_error_s { const char *name; const char *txt; @@ -44,6 +46,18 @@ struct h2_error_s { typedef const struct h2_error_s *h2_error; +#define H2EC0(U,v,d) +#define H2EC1(U,v,d) extern const struct h2_error_s H2CE_##U[1]; +#define H2EC2(U,v,d) extern const struct h2_error_s H2SE_##U[1]; +#define H2EC3(U,v,d) H2EC1(U,v,d) H2EC2(U,v,d) +#define H2_ERROR(NAME, val, sc, desc) H2EC##sc(NAME, val, desc) +#include "tbl/h2_error.h" +#undef H2EC1 +#undef H2EC2 +#undef H2EC3 + +/**********************************************************************/ + typedef h2_error h2_rxframe_f(struct worker *, struct h2_sess *, struct h2_req *); @@ -62,19 +76,32 @@ struct h2_frame_s { uint8_t final_flags; }; - #define H2_FRAME(l,U,...) extern const struct h2_frame_s H2_F_##U[1]; #include "tbl/h2_frames.h" -#define H2EC0(U,v,d) -#define H2EC1(U,v,d) extern const struct h2_error_s H2CE_##U[1]; -#define H2EC2(U,v,d) extern const struct h2_error_s H2SE_##U[1]; -#define H2EC3(U,v,d) H2EC1(U,v,d) H2EC2(U,v,d) -#define H2_ERROR(NAME, val, sc, desc) H2EC##sc(NAME, val, desc) -#include "tbl/h2_error.h" -#undef H2EC1 -#undef H2EC2 -#undef H2EC3 +/**********************************************************************/ + +struct h2_settings { +#define H2_SETTING(U,l,...) uint32_t l; +#include "tbl/h2_settings.h" +}; + +typedef void h2_setsetting_f(struct h2_settings*, uint32_t); + +struct h2_setting_s { + const char *name; + h2_setsetting_f *setfunc; + uint16_t ident; + uint32_t defval; + uint32_t minval; + uint32_t maxval; + h2_error range_error; +}; + +#define H2_SETTING(U,...) extern const struct h2_setting_s H2_SET_##U[1]; +#include "tbl/h2_settings.h" + +/**********************************************************************/ enum h2_stream_e { H2_STREAM__DUMMY = -1, @@ -85,14 +112,6 @@ enum h2_stream_e { #define H2_FRAME_FLAGS(l,u,v) extern const uint8_t H2FF_##u; #include "tbl/h2_frames.h" -enum h2setting { - H2_SETTINGS__DUMMY = -1, -#define H2_SETTINGS(n,v,d) H2S_##n = v, -#include "tbl/h2_settings.h" -#undef H2_SETTINGS - H2_SETTINGS_N -}; - struct h2_req { unsigned magic; #define H2_REQ_MAGIC 0x03411584 @@ -133,8 +152,8 @@ struct h2_sess { unsigned rxf_stream; uint8_t *rxf_data; - uint32_t their_settings[H2_SETTINGS_N]; - uint32_t our_settings[H2_SETTINGS_N]; + struct h2_settings remote_settings; + struct h2_settings local_settings; struct req *new_req; int go_away; @@ -184,7 +203,7 @@ struct h2_req * h2_new_req(const struct worker *, struct h2_sess *, unsigned stream, struct req *); void h2_del_req(struct worker *, struct h2_req *); int h2_rxframe(struct worker *, struct h2_sess *); -void h2_setting(struct h2_sess *, const uint8_t *); +h2_error h2_set_setting(struct h2_sess *, const uint8_t *); void h2_req_body(struct req*); diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index 2f271ff..9dbef5b 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -69,19 +69,6 @@ h2_framename(enum h2frame h2f) } } -static const char * -h2_settingname(enum h2setting h2f) -{ - - switch(h2f) { -#define H2_SETTINGS(n,v,d) case H2S_##n: return #n; -#include "tbl/h2_settings.h" -#undef H2_SETTINGS - default: - return (NULL); - } -} - #define H2_FRAME_FLAGS(l,u,v) const uint8_t H2FF_##u = v; #include "tbl/h2_frames.h" @@ -294,49 +281,85 @@ h2_rx_priority(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) * Incoming SETTINGS, possibly an ACK of one we sent. */ -void -h2_setting(struct h2_sess *h2, const uint8_t *d) +#define H2_SETTING(U,l, ...) \ +static void __match_proto__(h2_setsetting_f) \ +h2_setting_##l(struct h2_settings* s, uint32_t v) \ +{ \ + s -> l = v; \ +} +#include + +#define H2_SETTING(U, l, ...) \ +const struct h2_setting_s H2_SET_##U[1] = {{ \ + #l, \ + h2_setting_##l, \ + __VA_ARGS__ \ +}}; +#include + +static const struct h2_setting_s * const h2_setting_tbl[] = { +#define H2_SETTING(U,l,v, ...) [v] = H2_SET_##U, +#include +}; + +#define H2_SETTING_TBL_LEN (sizeof(h2_setting_tbl)/sizeof(h2_setting_tbl[0])) + +h2_error +h2_set_setting(struct h2_sess *h2, const uint8_t *d) { + const struct h2_setting_s *s; uint16_t x; uint32_t y; - const char *n; - char nb[8]; x = vbe16dec(d); y = vbe32dec(d + 2); - n = h2_settingname((enum h2setting)x); - if (n == NULL) { - bprintf(nb, "0x%04x", x); - n = nb; + if (x >= H2_SETTING_TBL_LEN || h2_setting_tbl[x] == NULL) { + // rfc7540,l,2181,2182 + VSLb(h2->vsl, SLT_Debug, + "H2SETTING unknown setting 0x%04x=%08x (ignored)", x, y); + return (0); + } + s = h2_setting_tbl[x]; + AN(s); + if (y < s->minval || y > s->maxval) { + VSLb(h2->vsl, SLT_Debug, "H2SETTING invalid %s=0x%08x", + s->name, y); + AN(s->range_error); + return (s->range_error); } - VSLb(h2->vsl, SLT_Debug, "H2SETTING %s 0x%08x", n, y); - if (x > 0 && x < H2_SETTINGS_N) - h2->their_settings[x] = y; + VSLb(h2->vsl, SLT_Debug, "H2SETTING %s=0x%08x", s->name, y); + AN(s->setfunc); + s->setfunc(&h2->remote_settings, y); + return (0); } static h2_error __match_proto__(h2_frame_f) h2_rx_settings(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) { - const uint8_t *p = h2->rxf_data; - unsigned l = h2->rxf_len; + const uint8_t *p; + unsigned l; + h2_error retval = 0; - (void)wrk; - (void)r2; + AN(wrk); + AN(r2); AZ(h2->rxf_stream); if (h2->rxf_flags == H2FF_SETTINGS_ACK) { - XXXAZ(h2->rxf_len); - } else if (h2->rxf_flags == 0) { - for (;l >= 6; l -= 6, p += 6) - h2_setting(h2, p); - if (l > 0) - VSLb(h2->vsl, SLT_Debug, - "NB: SETTINGS had %u dribble-bytes", l); + if (h2->rxf_len > 0) // rfc7540,l,2047,2049 + return (H2CE_FRAME_SIZE_ERROR); + return (0); + } else { + if (h2->rxf_len % 6) // rfc7540,l,2062,2064 + return (H2CE_PROTOCOL_ERROR); + p = h2->rxf_data; + for (l = h2->rxf_len; l >= 6; l -= 6, p += 6) { + retval = h2_set_setting(h2, p); + if (retval) + return (retval); + } Lck_Lock(&h2->sess->mtx); H2_Send_Frame(wrk, h2, H2_F_SETTINGS, H2FF_SETTINGS_ACK, 0, 0, NULL); Lck_Unlock(&h2->sess->mtx); - } else { - WRONG("SETTINGS FRAME"); } return (0); } diff --git a/bin/varnishd/http2/cache_http2_send.c b/bin/varnishd/http2/cache_http2_send.c index 75fcc43..197d9f4 100644 --- a/bin/varnishd/http2/cache_http2_send.c +++ b/bin/varnishd/http2/cache_http2_send.c @@ -119,7 +119,7 @@ H2_Send(struct worker *wrk, struct h2_req *r2, int flush, AZ(ftyp->act_snonzero); Lck_Lock(&h2->sess->mtx); - mfs = h2->their_settings[H2S_MAX_FRAME_SIZE]; + mfs = h2->remote_settings.max_frame_size; if (len < mfs) { retval = H2_Send_Frame(wrk, h2, ftyp, flags, len, r2->stream, ptr); diff --git a/bin/varnishd/http2/cache_http2_session.c b/bin/varnishd/http2/cache_http2_session.c index 4857500..2681b67 100644 --- a/bin/varnishd/http2/cache_http2_session.c +++ b/bin/varnishd/http2/cache_http2_session.c @@ -58,6 +58,12 @@ static const uint8_t H2_settings[] = { 0x00, 0x00, 0xff, 0xff }; +static const struct h2_settings H2_proto_settings = { +#define H2_SETTING(U,l,v,d,...) . l = d, +#include "tbl/h2_settings.h" +}; + + /********************************************************************** * The h2_sess struct needs many of the same things as a request, * WS, VSL, HTC &c, but rather than implement all that stuff over, we @@ -93,18 +99,12 @@ h2_new_sess(const struct worker *wrk, struct sess *sp, struct req *srq) h2->htc->rfd = &sp->fd; h2->sess = sp; VTAILQ_INIT(&h2->streams); -#define H2_SETTINGS(n,v,d) \ - do { \ - assert(v < H2_SETTINGS_N); \ - h2->their_settings[v] = d; \ - h2->our_settings[v] = d; \ - } while (0); -#include "tbl/h2_settings.h" -#undef H2_SETTINGS + h2->local_settings = H2_proto_settings; + h2->remote_settings = H2_proto_settings; /* XXX: Lacks a VHT_Fini counterpart. Will leak memory. */ AZ(VHT_Init(h2->dectbl, - h2->our_settings[H2S_HEADER_TABLE_SIZE])); + h2->local_settings.header_table_size)); SES_Reserve_xport_priv(sp, &up); *up = (uintptr_t)h2; @@ -199,7 +199,7 @@ h2_b64url_settings(struct h2_sess *h2, struct req *req) n -= 8; if (up == u + sizeof u) { AZ(n); - h2_setting(h2, (void*)u); + h2_set_setting(h2, (void*)u); up = u; } } From phk at FreeBSD.org Mon Mar 6 15:07:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Mon, 06 Mar 2017 16:07:06 +0100 Subject: [master] 1468655 Missed these in previous commit. Message-ID: commit 1468655f61335e333f377b21bc37444c48944eb5 Author: Poul-Henning Kamp Date: Mon Mar 6 15:02:34 2017 +0000 Missed these in previous commit. diff --git a/bin/varnishtest/tests/t02003.vtc b/bin/varnishtest/tests/t02003.vtc index 0686628..62b0fe7 100644 --- a/bin/varnishtest/tests/t02003.vtc +++ b/bin/varnishtest/tests/t02003.vtc @@ -165,3 +165,45 @@ client c1 { expect goaway.laststream == 0 } -run } -run + +####################################################################### +# Test SETTING error conditions + +client c1 { + stream 0 { + # SETTING ACK with data + sendhex "000001 04 01 00000000 aa" + rxgoaway + expect goaway.err == FRAME_SIZE_ERROR + expect goaway.laststream == 0 + } -run +} -run + +client c1 { + stream 0 { + # SETTING ACK with bad length + sendhex "000001 04 00 00000000 aa" + rxgoaway + expect goaway.err == PROTOCOL_ERROR + expect goaway.laststream == 0 + } -run +} -run + +client c1 { + stream 0 { + # SETTING ACK with bad value + txsettings -winsize 0x80000000 + rxgoaway + expect goaway.err == FLOW_CONTROL_ERROR + expect goaway.laststream == 0 + } -run +} -run + +client c1 { + stream 0 { + # SETTING unknown vlaue + sendhex "000006 04 00 00000000 ffff00000000" + txping + rxping + } -run +} -run diff --git a/bin/varnishtest/vtc_http2.c b/bin/varnishtest/vtc_http2.c index f1f03f6..420a4db 100644 --- a/bin/varnishtest/vtc_http2.c +++ b/bin/varnishtest/vtc_http2.c @@ -71,7 +71,7 @@ static const char *const h2_types[] = { static const char * const h2_settings[] = { [0] = "unknown", -#define H2_SETTINGS(U,v,d) [v] = #U, +#define H2_SETTING(U,l,v,...) [v] = #U, #include NULL }; diff --git a/include/tbl/h2_settings.h b/include/tbl/h2_settings.h index 929094c..765ee18 100644 --- a/include/tbl/h2_settings.h +++ b/include/tbl/h2_settings.h @@ -26,16 +26,72 @@ * SUCH DAMAGE. * * RFC7540 section 11.3 + * + * Upper + * lower + * tag + * default + * min + * max + * range_error */ /*lint -save -e525 -e539 */ -H2_SETTINGS(HEADER_TABLE_SIZE, 0x1, 4096) -H2_SETTINGS(ENABLE_PUSH, 0x2, 1) -H2_SETTINGS(MAX_CONCURRENT_STREAMS, 0x3, 0xffffffff) -H2_SETTINGS(INITIAL_WINDOW_SIZE, 0x4, 65535) -H2_SETTINGS(MAX_FRAME_SIZE, 0x5, 16384) -H2_SETTINGS(MAX_HEADER_LIST_SIZE, 0x6, 0xffffffff) -#undef H2_SETTINGS +H2_SETTING( // rfc7540,l,2097,2103 + HEADER_TABLE_SIZE, + header_table_size, + 0x1, + 4096, + 0, + 0xffffffff, + 0 +) +H2_SETTING( // rfc7540,l,2105,2114 + ENABLE_PUSH, + enable_push, + 0x2, + 1, + 0, + 1, + H2CE_PROTOCOL_ERROR +) +H2_SETTING( // rfc7540,l,2116,2121 + MAX_CONCURRENT_STREAMS, + max_concurrent_streams, + 0x3, + 0xffffffff, + 0, + 0xffffffff, + 0 +) +H2_SETTING( // rfc7540,l,2139,2148 + INITIAL_WINDOW_SIZE, + initial_window_size, + 0x4, + 65535, + 0, + 0x7fffffff, + H2CE_FLOW_CONTROL_ERROR +) +H2_SETTING( // rfc7540,l,2150,2157 + MAX_FRAME_SIZE, + max_frame_size, + 0x5, + 16384, + 16384, + 0x00ffffff, + H2CE_PROTOCOL_ERROR +) +H2_SETTING( // rfc7540,l,2159,2167 + MAX_HEADER_LIST_SIZE, + max_header_list_size, + 0x6, + 0xffffffff, + 0, + 0xffffffff, + 0 +) +#undef H2_SETTING /*lint -restore */ From phk at FreeBSD.org Mon Mar 6 15:42:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Mon, 06 Mar 2017 16:42:05 +0100 Subject: [master] 7b13cad Don't use symbolic names for flags, GCC and Sun's C-compiler are not as smart as LLVM about const. Message-ID: commit 7b13cad08b7d3975962eb68ebca63a63039e8c57 Author: Poul-Henning Kamp Date: Mon Mar 6 15:40:56 2017 +0000 Don't use symbolic names for flags, GCC and Sun's C-compiler are not as smart as LLVM about const. diff --git a/include/tbl/h2_frames.h b/include/tbl/h2_frames.h index 039937d..4089d9e 100644 --- a/include/tbl/h2_frames.h +++ b/include/tbl/h2_frames.h @@ -45,7 +45,7 @@ H2CE_PROTOCOL_ERROR, 1, H2_F_DATA, - H2FF_DATA_END_STREAM // rfc7540,l,1750,1753 + 0x01 // rfc7540,l,1750,1753 ) H2_FRAME(headers, HEADERS, 0x1, 0x2d, H2CE_PROTOCOL_ERROR, // rfc7540,l,1876,1879 @@ -53,7 +53,7 @@ 0, // rfc7540,l,938,940 0, H2_F_CONTINUATION, - H2FF_HEADERS_END_HEADERS, // rfc7540,l,1855,1857 + 0x04 // rfc7540,l,1855,1857 ) H2_FRAME(priority, PRIORITY, 0x2, 0x00, H2CE_PROTOCOL_ERROR, // rfc7540,l,1933,1936 @@ -85,7 +85,7 @@ H2CE_PROTOCOL_ERROR, 0, H2_F_CONTINUATION, - H2FF_PUSH_PROMISE_END_HEADERS, // rfc7540,l,2249,2251 + 0x04 // rfc7540,l,2249,2251 ) H2_FRAME(ping, PING, 0x6, 0x01, 0, @@ -117,7 +117,7 @@ H2CE_PROTOCOL_ERROR, 0, H2_F_CONTINUATION, - H2FF_CONTINUATION_END_HEADERS // rfc7540,l,2753,2754 + 0x04 // rfc7540,l,2753,2754 ) #undef H2_FRAME #endif From phk at FreeBSD.org Mon Mar 6 15:49:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Mon, 06 Mar 2017 16:49:05 +0100 Subject: [master] 3adc381 Make this test jail-compatible Message-ID: commit 3adc381f9b528707f3508faeda1e73f10e05714c Author: Poul-Henning Kamp Date: Mon Mar 6 15:48:40 2017 +0000 Make this test jail-compatible diff --git a/bin/varnishtest/tests/o00004.vtc b/bin/varnishtest/tests/o00004.vtc index 4d4c082..c9fb5d4 100644 --- a/bin/varnishtest/tests/o00004.vtc +++ b/bin/varnishtest/tests/o00004.vtc @@ -2,13 +2,16 @@ varnishtest "Sending proxy headers via health probes" # Double-proxy scheme stolen from o00002.vtc +# Get ${v1_addr} defined so s1 can use it so v1 can use ${s1_addr} +varnish v1 -proto PROXY -vcl {backend foo { .host = ":80"; }} -start + server s1 { rxreq - expect req.http.x-forwarded-for == "127.0.0.1" + expect req.http.x-forwarded-for == ${v1_addr} txresp } -start -varnish v1 -proto PROXY -vcl+backend { +varnish v1 -vcl+backend { import debug; sub vcl_recv { @@ -16,7 +19,7 @@ varnish v1 -proto PROXY -vcl+backend { return (synth(400)); } } -} -start +} varnish v2 -proto PROXY -vcl { import std; From dridi.boukelmoune at gmail.com Mon Mar 6 16:01:05 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Mon, 06 Mar 2017 17:01:05 +0100 Subject: [master] 2b94cd5 v1 actually forwards traffic for v2 Message-ID: commit 2b94cd5e70cef26414400248fcc5c1b0f83d1b34 Author: Dridi Boukelmoune Date: Mon Mar 6 16:58:26 2017 +0100 v1 actually forwards traffic for v2 Remains of copy/pasta made that v2 listened with PROXY protocol which is not needed. It's a passive instance that only does health checking using a probe. diff --git a/bin/varnishtest/tests/o00004.vtc b/bin/varnishtest/tests/o00004.vtc index c9fb5d4..f51bcc6 100644 --- a/bin/varnishtest/tests/o00004.vtc +++ b/bin/varnishtest/tests/o00004.vtc @@ -2,16 +2,16 @@ varnishtest "Sending proxy headers via health probes" # Double-proxy scheme stolen from o00002.vtc -# Get ${v1_addr} defined so s1 can use it so v1 can use ${s1_addr} -varnish v1 -proto PROXY -vcl {backend foo { .host = ":80"; }} -start +# Get ${v2_addr} defined so s1 can use it +varnish v2 -arg "-b '${bad_backend}'" -start server s1 { rxreq - expect req.http.x-forwarded-for == ${v1_addr} + expect req.http.x-forwarded-for == ${v2_addr} txresp } -start -varnish v1 -vcl+backend { +varnish v1 -proto PROXY -vcl+backend { import debug; sub vcl_recv { @@ -19,9 +19,9 @@ varnish v1 -vcl+backend { return (synth(400)); } } -} +} -start -varnish v2 -proto PROXY -vcl { +varnish v2 -vcl { import std; probe default { @@ -44,7 +44,7 @@ varnish v2 -proto PROXY -vcl { # dummy backend ref if (bp2) { } } -} -start +} server s1 -wait From varnish-commit at varnish-cache.org Mon Mar 6 20:05:47 2017 From: varnish-commit at varnish-cache.org (xnykgeps) Date: Tue, 7 Mar 2017 04:05:47 +0800 Subject: =?utf-8?B?dmFybmlzaC1jb21taXQtLeWtpuS8muinhOmBvw==?= =?utf-8?B?5ZCI5LyZ5Lq66aOO6Zmp55qENOenjeaWueazlSAgNDowNTo1OA==?= Message-ID: <20170307040558673765@frp.org> varnish-commit???? 1????????????????????? 2???5?????????????? 3???????????4???? 4??????????????? ????????????????? 2017-3-74:05:58 -------------- next part -------------- An HTML attachment was scrubbed... URL: -------------- next part -------------- A non-text attachment was scrubbed... Name: ?????--????? 2017.docx Type: application/vnd.openxmlformats-officedocument.wordprocessingml.document Size: 24847 bytes Desc: not available URL: From phk at FreeBSD.org Mon Mar 6 23:56:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Tue, 07 Mar 2017 00:56:05 +0100 Subject: [master] ed9d11c More test coverage Message-ID: commit ed9d11cf46e65e2f226ca446c772b74ebe8c4c24 Author: Poul-Henning Kamp Date: Mon Mar 6 23:49:18 2017 +0000 More test coverage diff --git a/bin/varnishtest/tests/m00008.vtc b/bin/varnishtest/tests/m00008.vtc index 5912dc5..202ce56 100644 --- a/bin/varnishtest/tests/m00008.vtc +++ b/bin/varnishtest/tests/m00008.vtc @@ -1,7 +1,13 @@ -varnishtest "Test import vs. unsafe_path" +varnishtest "VCL compiler vmod coverage / vmod loading" feature topbuild +varnish v1 -errvcl {Module debug conflicts with other symbol.} { + backend b { .host = "127.0.0.1"; } + sub debug {} + import debug; +} + server s1 { rxreq txresp @@ -32,3 +38,9 @@ varnish v1 -cliok "param.set vmod_path /nowhere:/else" varnish v1 -vcl+backend { import std from "${topbuild}/lib/libvmod_std/.libs/"; } + +varnish v1 -errvcl {Malformed VMOD std} { + backend default { .host = "${s1_sock}"; } + import std from "${topbuild}/lib/libvmod_debug/.libs/libvmod_debug.so"; +} + diff --git a/bin/varnishtest/tests/v00016.vtc b/bin/varnishtest/tests/v00016.vtc index 2c3c232..8337ba7 100644 --- a/bin/varnishtest/tests/v00016.vtc +++ b/bin/varnishtest/tests/v00016.vtc @@ -2,6 +2,8 @@ varnishtest "Various VCL compiler coverage tests" shell "true > ${tmpdir}/_varnishtest_empty_file" +feature dns + varnish v1 -vcl { backend b { .host = "127.0.0.1"; } include "${tmpdir}/_varnishtest_empty_file" ; @@ -72,3 +74,21 @@ varnish v1 -errvcl {Symbol not found: 'c' (expected type BACKEND):} { } } } + +varnish v1 -errvcl {Regexp compilation error:} { + backend b { .host = "127.0.0.1"; } + sub vcl_recv { + if (req.url ~ "[a") {} + } +} + +varnish v1 -errvcl {resolves to neither IPv4 nor IPv6 addresses.} { + backend b { .host = "/"; } +} + +varnish v1 -errvcl {resolves to too many addresses} { + backend b { .host = "127.0.0.1"; } + sub vcl_recv { + if (remote.ip == "varnish-cache.org") {} + } +} diff --git a/bin/varnishtest/tests/v00021.vtc b/bin/varnishtest/tests/v00021.vtc index 5288ff5..8dd69ad 100644 --- a/bin/varnishtest/tests/v00021.vtc +++ b/bin/varnishtest/tests/v00021.vtc @@ -90,3 +90,8 @@ varnish v1 -vcl { set resp.http.buckinghambuckinghambuckinghambuckinghambuckinghambuckinghambuckinghambuckinghambuckinghambuckinghambuckinghambuckinghambuckin = "foobar"; } } + +varnish v1 -errvcl {Unknown variable 'req.foobar'} { + backend foo { .host = "127.0.0.1"; } + sub vcl_recv { set req.foobar = 3; } +} From phk at FreeBSD.org Tue Mar 7 00:17:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Tue, 07 Mar 2017 01:17:05 +0100 Subject: [master] 917a2c3 Ok, drop that test, it's not portable Message-ID: commit 917a2c34e65bee91a80148dff92d654a52d17cae Author: Poul-Henning Kamp Date: Tue Mar 7 00:16:08 2017 +0000 Ok, drop that test, it's not portable diff --git a/bin/varnishtest/tests/v00016.vtc b/bin/varnishtest/tests/v00016.vtc index 8337ba7..e8a57a6 100644 --- a/bin/varnishtest/tests/v00016.vtc +++ b/bin/varnishtest/tests/v00016.vtc @@ -82,10 +82,6 @@ varnish v1 -errvcl {Regexp compilation error:} { } } -varnish v1 -errvcl {resolves to neither IPv4 nor IPv6 addresses.} { - backend b { .host = "/"; } -} - varnish v1 -errvcl {resolves to too many addresses} { backend b { .host = "127.0.0.1"; } sub vcl_recv { From phk at FreeBSD.org Tue Mar 7 10:37:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Tue, 07 Mar 2017 11:37:05 +0100 Subject: [master] 414d9f7 Add "-hdrlen
" Message-ID: commit 414d9f7ffaff480592d99e3ba385674c2bb1877f Author: Poul-Henning Kamp Date: Tue Mar 7 10:32:55 2017 +0000 Add "-hdrlen
" diff --git a/bin/varnishtest/vtc_http.c b/bin/varnishtest/vtc_http.c index b81bb70..4df6dd2 100644 --- a/bin/varnishtest/vtc_http.c +++ b/bin/varnishtest/vtc_http.c @@ -872,6 +872,7 @@ http_tx_parse_args(char * const *av, struct vtclog *vl, struct http *hp, char *b, *c; char *nullbody = NULL; int nolen = 0; + int l; (void)vl; nullbody = body; @@ -882,6 +883,13 @@ http_tx_parse_args(char * const *av, struct vtclog *vl, struct http *hp, } else if (!strcmp(*av, "-hdr")) { VSB_printf(hp->vsb, "%s%s", av[1], nl); av++; + } else if (!strcmp(*av, "-hdrlen")) { + VSB_printf(hp->vsb, "%s: ", av[1]); + l = atoi(av[2]); + while (l-- > 0) + VSB_putc(hp->vsb, '0' + (l % 10)); + VSB_printf(hp->vsb, "%s", nl); + av+=2; } else break; } @@ -977,6 +985,9 @@ http_tx_parse_args(char * const *av, struct vtclog *vl, struct http *hp, * Add STRING as a header, it must follow this format: * "name: value". It can be called multiple times. * + * \-hdrlen STRING NUMBER + * Add STRING as a header with NUMBER bytes of content. + * * You can then use the arguments related to the body: * * \-body STRING From phk at FreeBSD.org Tue Mar 7 10:37:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Tue, 07 Mar 2017 11:37:05 +0100 Subject: [master] 39211f9 Add a debug option for setting bogus H2 settings so VTC's dont have to test with 16k frame sizes. Message-ID: commit 39211f974fd3b7243c58d79b5c6ad3a4d4f66de1 Author: Poul-Henning Kamp Date: Tue Mar 7 10:33:30 2017 +0000 Add a debug option for setting bogus H2 settings so VTC's dont have to test with 16k frame sizes. diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index 9dbef5b..915a2d8 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -325,7 +325,8 @@ h2_set_setting(struct h2_sess *h2, const uint8_t *d) VSLb(h2->vsl, SLT_Debug, "H2SETTING invalid %s=0x%08x", s->name, y); AN(s->range_error); - return (s->range_error); + if (!DO_DEBUG(DBG_H2_NOCHECK)) + return (s->range_error); } VSLb(h2->vsl, SLT_Debug, "H2SETTING %s=0x%08x", s->name, y); AN(s->setfunc); diff --git a/include/tbl/debug_bits.h b/include/tbl/debug_bits.h index 1db9db8..e089022 100644 --- a/include/tbl/debug_bits.h +++ b/include/tbl/debug_bits.h @@ -46,6 +46,7 @@ DEBUG_BIT(WITNESS, witness, "Emit WITNESS lock records") DEBUG_BIT(VSM_KEEP, vsm_keep, "Keep the VSM file on restart") DEBUG_BIT(DROP_POOLS, drop_pools, "Drop thread pools (testing)") DEBUG_BIT(SLOW_ACCEPTOR, slow_acceptor, "Slow down Acceptor") +DEBUG_BIT(H2_NOCHECK, h2_nocheck, "Disable various H2 checks") #undef DEBUG_BIT /*lint -restore */ From phk at FreeBSD.org Tue Mar 7 10:37:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Tue, 07 Mar 2017 11:37:05 +0100 Subject: [master] b8506b3 Test H2 Continuation headers Message-ID: commit b8506b30c0453d16b5810424c64ffec71765887d Author: Poul-Henning Kamp Date: Tue Mar 7 10:35:48 2017 +0000 Test H2 Continuation headers diff --git a/bin/varnishd/http2/cache_http2_send.c b/bin/varnishd/http2/cache_http2_send.c index 197d9f4..00c553a 100644 --- a/bin/varnishd/http2/cache_http2_send.c +++ b/bin/varnishd/http2/cache_http2_send.c @@ -125,21 +125,20 @@ H2_Send(struct worker *wrk, struct h2_req *r2, int flush, ftyp, flags, len, r2->stream, ptr); } else { AN(ptr); - AN(len); p = ptr; final_flags = ftyp->final_flags & flags; flags &= ~ftyp->final_flags; do { AN(ftyp->continuation); tf = mfs; - if (tf > len) { - tf = len; + if (tf < len) { retval = H2_Send_Frame(wrk, h2, ftyp, flags, tf, r2->stream, p); - flags = 0; } else { + tf = len; retval = H2_Send_Frame(wrk, h2, ftyp, final_flags, tf, r2->stream, p); + flags = 0; } p += tf; len -= tf; diff --git a/bin/varnishtest/tests/t02007.vtc b/bin/varnishtest/tests/t02007.vtc new file mode 100644 index 0000000..b0e329e --- /dev/null +++ b/bin/varnishtest/tests/t02007.vtc @@ -0,0 +1,41 @@ +varnishtest "H2 Huge response headers" + +server s1 { + rxreq + expect req.proto == HTTP/1.1 + txresp -hdr "Content-Type: text/plain" -hdrlen Foo 100 -bodylen 100 +} -start + +varnish v1 -vcl+backend {} -cliok "param.set feature +http2" -start +varnish v1 -cliok "param.set debug +syncvsl" +varnish v1 -cliok "param.set debug +h2_nocheck" + +client c1 { + stream 0 { + txsettings -framesize 64 + rxsettings + } -run + stream 1 { + txreq \ + -req POST \ + -hdr content-type text/plain \ + -nostrend \ + -nohdrend + txcont \ + -hdr expect 100-continue \ + -hdr content-length 7 \ + -nostrend + + txdata \ + -data request + + rxhdrs + expect resp.status == 100 + + rxresp + expect resp.status == 200 + expect resp.http.content-Type == "text/plain" + expect resp.bodylen == 100 + } -run +} -run + From phk at FreeBSD.org Tue Mar 7 12:33:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Tue, 07 Mar 2017 13:33:05 +0100 Subject: [master] c14a818 Move H2 Rx buf onto srq->ws Message-ID: commit c14a81855ab6a2b86e6deaa62cc9e094c3fceb88 Author: Poul-Henning Kamp Date: Tue Mar 7 11:42:39 2017 +0000 Move H2 Rx buf onto srq->ws diff --git a/bin/varnishd/http2/cache_http2_session.c b/bin/varnishd/http2/cache_http2_session.c index 2681b67..b33b21e 100644 --- a/bin/varnishd/http2/cache_http2_session.c +++ b/bin/varnishd/http2/cache_http2_session.c @@ -227,7 +227,7 @@ h2_new_pu_session(struct worker *wrk, const struct h2_sess *h2) return (0); } HTC_RxPipeline(h2->htc, h2->htc->rxbuf_b + sizeof(H2_prism)); - HTC_RxInit(h2->htc, wrk->aws); + HTC_RxInit(h2->htc, h2->ws); VSLb(h2->vsl, SLT_Debug, "H2: Got pu PRISM"); return (1); @@ -255,9 +255,9 @@ h2_new_ou_session(struct worker *wrk, struct h2_sess *h2, req->htc->pipeline_b = NULL; req->htc->pipeline_e = NULL; /* XXX: This call may assert on buffer overflow if the pipelined - data exceeds the available space in the aws workspace. What to + data exceeds the available space in the ws workspace. What to do about the overflowing data is an open issue. */ - HTC_RxInit(h2->htc, wrk->aws); + HTC_RxInit(h2->htc, h2->ws); /* Start req thread */ (void)h2_new_req(wrk, h2, 1, req); @@ -280,7 +280,7 @@ h2_new_ou_session(struct worker *wrk, struct h2_sess *h2, return (0); } HTC_RxPipeline(h2->htc, h2->htc->rxbuf_b + sizeof(H2_prism)); - HTC_RxInit(h2->htc, wrk->aws); + HTC_RxInit(h2->htc, h2->ws); VSLb(h2->vsl, SLT_Debug, "H2: Got PRISM"); return (1); } @@ -301,17 +301,18 @@ h2_new_session(struct worker *wrk, void *arg) assert(req->transport == &H2_transport); - wsp = WS_Snapshot(wrk->aws); switch(req->err_code) { case 0: /* Direct H2 connection (via Proxy) */ h2 = h2_new_sess(wrk, sp, req); + wsp = WS_Snapshot(h2->ws); (void)h2_new_req(wrk, h2, 0, NULL); break; case 1: /* Prior Knowledge H1->H2 upgrade */ h2 = h2_new_sess(wrk, sp, req); + wsp = WS_Snapshot(h2->ws); (void)h2_new_req(wrk, h2, 0, NULL); if (!h2_new_pu_session(wrk, h2)) @@ -320,6 +321,7 @@ h2_new_session(struct worker *wrk, void *arg) case 2: /* Optimistic H1->H2 upgrade */ h2 = h2_new_sess(wrk, sp, NULL); + wsp = WS_Snapshot(h2->ws); (void)h2_new_req(wrk, h2, 0, NULL); if (!h2_new_ou_session(wrk, h2, req)) @@ -340,8 +342,8 @@ h2_new_session(struct worker *wrk, void *arg) Lck_Unlock(&h2->sess->mtx); while (h2_rxframe(wrk, h2)) { - WS_Reset(wrk->aws, wsp); - HTC_RxInit(h2->htc, wrk->aws); + WS_Reset(h2->ws, wsp); + HTC_RxInit(h2->htc, h2->ws); } /* Delete all idle streams */ From phk at FreeBSD.org Tue Mar 7 12:33:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Tue, 07 Mar 2017 13:33:05 +0100 Subject: [master] 856d562 The beginnings of a TX-scheduling facility. Message-ID: commit 856d5627e8a110c7121c30a925e1eda3e4200459 Author: Poul-Henning Kamp Date: Tue Mar 7 12:31:38 2017 +0000 The beginnings of a TX-scheduling facility. diff --git a/bin/varnishd/http2/cache_http2.h b/bin/varnishd/http2/cache_http2.h index d1de3a8..cba5676 100644 --- a/bin/varnishd/http2/cache_http2.h +++ b/bin/varnishd/http2/cache_http2.h @@ -122,6 +122,9 @@ struct h2_req { VTAILQ_ENTRY(h2_req) list; int64_t window; struct h2h_decode *decode; + + struct worker *tx_wrk; + VTAILQ_ENTRY(h2_req) tx_list; }; VTAILQ_HEAD(h2_req_s, h2_req); @@ -158,6 +161,10 @@ struct h2_sess { struct req *new_req; int go_away; uint32_t go_away_last_stream; + + VTAILQ_HEAD(,h2_req) txqueue; + + struct h2_req req0[1]; }; /* http2/cache_http2_panic.c */ @@ -191,6 +198,10 @@ h2_error h2h_decode_fini(const struct h2_sess *h2, struct h2h_decode *d); h2_error h2h_decode_bytes(struct h2_sess *h2, struct h2h_decode *d, const uint8_t *ptr, size_t len); +/* cache_http2_send.c */ +void H2_Send_Get(struct worker *, struct h2_sess *, struct h2_req *); +void H2_Send_Rel(struct worker *, struct h2_sess *, struct h2_req *); + h2_error H2_Send_Frame(struct worker *, const struct h2_sess *, h2_frame type, uint8_t flags, uint32_t len, uint32_t stream, const void *); diff --git a/bin/varnishd/http2/cache_http2_deliver.c b/bin/varnishd/http2/cache_http2_deliver.c index 9e2665e..afd088e 100644 --- a/bin/varnishd/http2/cache_http2_deliver.c +++ b/bin/varnishd/http2/cache_http2_deliver.c @@ -85,8 +85,10 @@ h2_bytes(struct req *req, enum vdp_action act, void **priv, return (0); AZ(req->vdp_nxt); /* always at the bottom of the pile */ + H2_Send_Get(req->wrk, r2->h2sess, r2); H2_Send(req->wrk, r2, act == VDP_FLUSH ? 1 : 0, H2_F_DATA, H2FF_NONE, len, ptr); + H2_Send_Rel(req->wrk, r2->h2sess, r2); return (0); } @@ -140,11 +142,13 @@ h2_minimal_response(struct req *req, uint16_t status) req->err_code = status; /* XXX return code checking once H2_Send returns anything but 0 */ + H2_Send_Get(req->wrk, r2->h2sess, r2); H2_Send(req->wrk, r2, 1, H2_F_HEADERS, H2FF_HEADERS_END_HEADERS | (status < 200 ? 0 : H2FF_HEADERS_END_STREAM), l, buf); + H2_Send_Rel(req->wrk, r2->h2sess, r2); return (0); } @@ -240,8 +244,10 @@ h2_deliver(struct req *req, struct boc *boc, int sendbody) sz = (char*)p - req->ws->f; /* XXX: Optimize !sendbody case */ + H2_Send_Get(req->wrk, r2->h2sess, r2); H2_Send(req->wrk, r2, 1, H2_F_HEADERS, H2FF_HEADERS_END_HEADERS, sz, req->ws->f); + H2_Send_Rel(req->wrk, r2->h2sess, r2); WS_Release(req->ws, 0); @@ -254,7 +260,9 @@ h2_deliver(struct req *req, struct boc *boc, int sendbody) err = VDP_DeliverObj(req); /*XXX*/(void)err; + H2_Send_Get(req->wrk, r2->h2sess, r2); H2_Send(req->wrk, r2, 1, H2_F_DATA, H2FF_DATA_END_STREAM, 0, NULL); + H2_Send_Rel(req->wrk, r2->h2sess, r2); AZ(req->wrk->v1l); VDP_close(req); diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index 915a2d8..f22cb44 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -186,10 +186,10 @@ h2_rx_ping(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) return (H2CE_PROTOCOL_ERROR); if (h2->rxf_flags != 0) // We never send pings return (H2SE_PROTOCOL_ERROR); - Lck_Lock(&h2->sess->mtx); + H2_Send_Get(wrk, h2, r2); H2_Send_Frame(wrk, h2, H2_F_PING, H2FF_PING_ACK, 8, 0, h2->rxf_data); - Lck_Unlock(&h2->sess->mtx); + H2_Send_Rel(wrk, h2, r2); return (0); } @@ -357,10 +357,10 @@ h2_rx_settings(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) if (retval) return (retval); } - Lck_Lock(&h2->sess->mtx); + H2_Send_Get(wrk, h2, r2); H2_Send_Frame(wrk, h2, H2_F_SETTINGS, H2FF_SETTINGS_ACK, 0, 0, NULL); - Lck_Unlock(&h2->sess->mtx); + H2_Send_Rel(wrk, h2, r2); } return (0); } @@ -636,10 +636,10 @@ h2_procframe(struct worker *wrk, struct h2_sess *h2, VSLb(h2->vsl, SLT_Debug, "H2: stream %u: %s", h2->rxf_stream, h2e->txt); vbe32enc(b, h2e->val); - Lck_Lock(&h2->sess->mtx); + H2_Send_Get(wrk, h2, r2); (void)H2_Send_Frame(wrk, h2, H2_F_RST_STREAM, 0, sizeof b, h2->rxf_stream, b); - Lck_Unlock(&h2->sess->mtx); + H2_Send_Rel(wrk, h2, r2); h2_del_req(wrk, r2); return (0); @@ -732,9 +732,9 @@ h2_rxframe(struct worker *wrk, struct h2_sess *h2) if (h2e) { vbe32enc(b, h2->highest_stream); vbe32enc(b + 4, h2e->val); - Lck_Lock(&h2->sess->mtx); + H2_Send_Get(wrk, h2, h2->req0); (void)H2_Send_Frame(wrk, h2, H2_F_GOAWAY, 0, 8, 0, b); - Lck_Unlock(&h2->sess->mtx); + H2_Send_Rel(wrk, h2, h2->req0); } return (h2e ? 0 : 1); } diff --git a/bin/varnishd/http2/cache_http2_send.c b/bin/varnishd/http2/cache_http2_send.c index 00c553a..2acd39b 100644 --- a/bin/varnishd/http2/cache_http2_send.c +++ b/bin/varnishd/http2/cache_http2_send.c @@ -36,6 +36,36 @@ #include "vend.h" +void +H2_Send_Get(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) +{ + CHECK_OBJ_NOTNULL(wrk, WORKER_MAGIC); + CHECK_OBJ_NOTNULL(h2, H2_SESS_MAGIC); + CHECK_OBJ_NOTNULL(r2, H2_REQ_MAGIC); + + r2->tx_wrk = wrk; + Lck_Lock(&h2->sess->mtx); + VTAILQ_INSERT_TAIL(&h2->txqueue, r2, tx_list); + while (VTAILQ_FIRST(&h2->txqueue) != r2) + Lck_CondWait(&wrk->cond, &h2->sess->mtx, 0); + Lck_Unlock(&h2->sess->mtx); +} + +void +H2_Send_Rel(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) +{ + CHECK_OBJ_NOTNULL(wrk, WORKER_MAGIC); + CHECK_OBJ_NOTNULL(h2, H2_SESS_MAGIC); + CHECK_OBJ_NOTNULL(r2, H2_REQ_MAGIC); + Lck_Lock(&h2->sess->mtx); + assert(VTAILQ_FIRST(&h2->txqueue) == r2); + VTAILQ_REMOVE(&h2->txqueue, r2, tx_list); + r2 = VTAILQ_FIRST(&h2->txqueue); + if (r2 != NULL) + AZ(pthread_cond_signal(&r2->tx_wrk->cond)); + Lck_Unlock(&h2->sess->mtx); +} + static void h2_mk_hdr(uint8_t *hdr, h2_frame ftyp, uint8_t flags, uint32_t len, uint32_t stream) @@ -64,7 +94,6 @@ H2_Send_Frame(struct worker *wrk, const struct h2_sess *h2, ssize_t s; (void)wrk; - Lck_AssertHeld(&h2->sess->mtx); AN(ftyp); AZ(flags & ~(ftyp->flags)); @@ -74,7 +103,9 @@ H2_Send_Frame(struct worker *wrk, const struct h2_sess *h2, AZ(ftyp->act_snonzero); h2_mk_hdr(hdr, ftyp, flags, len, stream); + Lck_Lock(&h2->sess->mtx); VSLb_bin(h2->vsl, SLT_H2TxHdr, 9, hdr); + Lck_Unlock(&h2->sess->mtx); s = write(h2->sess->fd, hdr, sizeof hdr); if (s != sizeof hdr) @@ -83,7 +114,9 @@ H2_Send_Frame(struct worker *wrk, const struct h2_sess *h2, s = write(h2->sess->fd, ptr, len); if (s != len) return (H2CE_PROTOCOL_ERROR); // XXX Need private ? + Lck_Lock(&h2->sess->mtx); VSLb_bin(h2->vsl, SLT_H2TxBody, len, ptr); + Lck_Unlock(&h2->sess->mtx); } return (0); } @@ -106,11 +139,14 @@ H2_Send(struct worker *wrk, struct h2_req *r2, int flush, (void)flush; + CHECK_OBJ_NOTNULL(wrk, WORKER_MAGIC); CHECK_OBJ_NOTNULL(r2, H2_REQ_MAGIC); h2 = r2->h2sess; CHECK_OBJ_NOTNULL(h2, H2_SESS_MAGIC); assert(len == 0 || ptr != NULL); + assert(VTAILQ_FIRST(&h2->txqueue) == r2); + AN(ftyp); AZ(flags & ~(ftyp->flags)); if (r2->stream == 0) @@ -120,6 +156,7 @@ H2_Send(struct worker *wrk, struct h2_req *r2, int flush, Lck_Lock(&h2->sess->mtx); mfs = h2->remote_settings.max_frame_size; + Lck_Unlock(&h2->sess->mtx); if (len < mfs) { retval = H2_Send_Frame(wrk, h2, ftyp, flags, len, r2->stream, ptr); @@ -145,6 +182,5 @@ H2_Send(struct worker *wrk, struct h2_req *r2, int flush, ftyp = ftyp->continuation; } while (len > 0 && retval == 0); } - Lck_Unlock(&h2->sess->mtx); return (retval); } diff --git a/bin/varnishd/http2/cache_http2_session.c b/bin/varnishd/http2/cache_http2_session.c index b33b21e..522e252 100644 --- a/bin/varnishd/http2/cache_http2_session.c +++ b/bin/varnishd/http2/cache_http2_session.c @@ -99,6 +99,7 @@ h2_new_sess(const struct worker *wrk, struct sess *sp, struct req *srq) h2->htc->rfd = &sp->fd; h2->sess = sp; VTAILQ_INIT(&h2->streams); + VTAILQ_INIT(&h2->txqueue); h2->local_settings = H2_proto_settings; h2->remote_settings = H2_proto_settings; @@ -108,6 +109,8 @@ h2_new_sess(const struct worker *wrk, struct sess *sp, struct req *srq) SES_Reserve_xport_priv(sp, &up); *up = (uintptr_t)h2; + INIT_OBJ(h2->req0, H2_REQ_MAGIC); + h2->req0->h2sess = h2; } AN(up); CAST_OBJ_NOTNULL(h2, (void*)(*up), H2_SESS_MAGIC); @@ -333,13 +336,13 @@ h2_new_session(struct worker *wrk, void *arg) THR_SetRequest(h2->srq); - Lck_Lock(&h2->sess->mtx); + H2_Send_Get(wrk, h2, h2->req0); H2_Send_Frame(wrk, h2, H2_F_SETTINGS, H2FF_NONE, sizeof H2_settings, 0, H2_settings); + H2_Send_Rel(wrk, h2, h2->req0); /* and off we go... */ h2->cond = &wrk->cond; - Lck_Unlock(&h2->sess->mtx); while (h2_rxframe(wrk, h2)) { WS_Reset(h2->ws, wsp); From geoff at uplex.de Tue Mar 7 12:35:07 2017 From: geoff at uplex.de (Geoff Simmons) Date: Tue, 07 Mar 2017 13:35:07 +0100 Subject: [master] 650b78b Update docs for *.uncacheable in generate.py regarding hit-for-miss/-pass Message-ID: commit 650b78b75b74e466f10962a5f801b11518956740 Author: Geoff Simmons Date: Tue Mar 7 13:33:33 2017 +0100 Update docs for *.uncacheable in generate.py regarding hit-for-miss/-pass diff --git a/lib/libvcc/generate.py b/lib/libvcc/generate.py index 604970e..4515940 100755 --- a/lib/libvcc/generate.py +++ b/lib/libvcc/generate.py @@ -452,8 +452,8 @@ sp_variables = [ ('backend', ), (), """ Indicates whether this request is uncacheable due - to a pass in the client side or a hit on an existing - uncacheable object (aka hit-for-pass). + to a pass in the client side or a hit on an hit-for-pass + object. """ ), ('bereq.connect_timeout', @@ -578,7 +578,7 @@ sp_variables = [ Inherited from bereq.uncacheable, see there. Setting this variable makes the object uncacheable, which may - get stored as a hit-for-pass object in the cache. + get stored as a hit-for-miss object in the cache. Clearing the variable has no effect and will log the warning "Ignoring attempt to reset beresp.uncacheable". @@ -727,7 +727,8 @@ sp_variables = [ 'BOOL', ('deliver',), (), """ - Whether the object is uncacheable (pass or hit-for-pass). + Whether the object is uncacheable (pass, hit-for-pass or + hit-for-miss). """ ), ('resp', From martin at varnish-software.com Tue Mar 7 16:18:06 2017 From: martin at varnish-software.com (Martin Blix Grydeland) Date: Tue, 07 Mar 2017 17:18:06 +0100 Subject: [master] acd2198 Fix race in the VSL segment counter initialization Message-ID: commit acd219844d551883507829984964ad880db27fef Author: Martin Blix Grydeland Date: Tue Mar 7 17:13:26 2017 +0100 Fix race in the VSL segment counter initialization Fix a stupid misstake where the segment counter in the VSL segment was set just before the entire struct was cleared during initialization. This didn't cause problems in the common case because it would be set correctly on the very first log line produced. But it did open a race where an unfortunate early log client would assume it was lagging indefinetely behind varnishd on the log reading and report overflow error. This was most commonly experienced with varnishtest. Fixes: #2241 diff --git a/bin/varnishd/cache/cache_shmlog.c b/bin/varnishd/cache/cache_shmlog.c index d8e3c7d..66fac59 100644 --- a/bin/varnishd/cache/cache_shmlog.c +++ b/bin/varnishd/cache/cache_shmlog.c @@ -507,13 +507,13 @@ VSM_Init(void) problems with regard to readers on that event visible */ vsl_segment_n = UINT_MAX - (VSL_SEGMENTS - 1); AZ(vsl_segment_n % VSL_SEGMENTS); - vsl_head->segment_n = vsl_segment_n; vsl_ptr = vsl_head->log; *vsl_ptr = VSL_ENDMARKER; memset(vsl_head, 0, sizeof *vsl_head); vsl_head->segsize = vsl_segsize; vsl_head->offset[0] = 0; + vsl_head->segment_n = vsl_segment_n; for (i = 1; i < VSL_SEGMENTS; i++) vsl_head->offset[i] = -1; VWMB(); From geoff at uplex.de Tue Mar 7 17:32:05 2017 From: geoff at uplex.de (Geoff Simmons) Date: Tue, 07 Mar 2017 18:32:05 +0100 Subject: [master] f464a94 Revive use of the VSL HitPass tag. Message-ID: commit f464a94cf91e630c241bcf49974655a7d8b24b8b Author: Geoff Simmons Date: Tue Mar 7 14:50:19 2017 +0100 Revive use of the VSL HitPass tag. diff --git a/bin/varnishd/cache/cache_hash.c b/bin/varnishd/cache/cache_hash.c index 48e3ec9..7059826 100644 --- a/bin/varnishd/cache/cache_hash.c +++ b/bin/varnishd/cache/cache_hash.c @@ -438,6 +438,8 @@ HSH_Lookup(struct req *req, struct objcore **ocp, struct objcore **bocp, assert(oc->objhead == oh); if (oc->flags & OC_F_HFP) { wrk->stats->cache_hitpass++; + VSLb(req->vsl, SLT_HitPass, "%u", + ObjGetXID(wrk, oc)); oc = NULL; } else if (oc->flags & OC_F_PASS) { wrk->stats->cache_hitmiss++; diff --git a/bin/varnishtest/tests/c00081.vtc b/bin/varnishtest/tests/c00081.vtc index 31b79be..0cf9827 100644 --- a/bin/varnishtest/tests/c00081.vtc +++ b/bin/varnishtest/tests/c00081.vtc @@ -29,6 +29,10 @@ varnish v1 -vcl+backend { } -start +logexpect l1 -v v1 -g vxid { + expect 1003 * HitPass "^1002$" +} -start + client c1 { txreq rxresp @@ -45,6 +49,8 @@ client c1 { expect resp.http.miss == True } -run +logexpect l1 -wait + varnish v1 -expect MAIN.cache_hitpass == 1 varnish v1 -expect MAIN.cache_miss == 2 varnish v1 -expect MAIN.cache_hitmiss == 0 From geoff at uplex.de Tue Mar 7 17:32:05 2017 From: geoff at uplex.de (Geoff Simmons) Date: Tue, 07 Mar 2017 18:32:05 +0100 Subject: [master] 70923dc Add SLT tag HitMiss to log hits on hit-for-miss objects. Message-ID: commit 70923dc0a3e9bed5b5bacffd7c5db8b8c93f886c Author: Geoff Simmons Date: Tue Mar 7 16:10:51 2017 +0100 Add SLT tag HitMiss to log hits on hit-for-miss objects. diff --git a/bin/varnishd/cache/cache_hash.c b/bin/varnishd/cache/cache_hash.c index 7059826..8019591 100644 --- a/bin/varnishd/cache/cache_hash.c +++ b/bin/varnishd/cache/cache_hash.c @@ -443,6 +443,8 @@ HSH_Lookup(struct req *req, struct objcore **ocp, struct objcore **bocp, oc = NULL; } else if (oc->flags & OC_F_PASS) { wrk->stats->cache_hitmiss++; + VSLb(req->vsl, SLT_HitMiss, "%u", + ObjGetXID(wrk, oc)); oc = NULL; *bocp = hsh_insert_busyobj(wrk, oh); } else { @@ -466,6 +468,7 @@ HSH_Lookup(struct req *req, struct objcore **ocp, struct objcore **bocp, if (exp_oc != NULL && exp_oc->flags & OC_F_PASS) { wrk->stats->cache_hitmiss++; + VSLb(req->vsl, SLT_HitMiss, "%u", ObjGetXID(wrk, exp_oc)); exp_oc = NULL; busy_found = 0; } diff --git a/bin/varnishtest/tests/c00011.vtc b/bin/varnishtest/tests/c00011.vtc index 02dd470..38a91f2 100644 --- a/bin/varnishtest/tests/c00011.vtc +++ b/bin/varnishtest/tests/c00011.vtc @@ -1,4 +1,4 @@ -varnishtest "Test hit for pass (pass from fetch)" +varnishtest "Test hit for miss (beresp.uncacheable = true)" server s1 { rxreq @@ -22,6 +22,10 @@ varnish v1 -vcl+backend { } } -start +logexpect l1 -v v1 -g vxid { + expect 1003 * HitMiss "^1002$" +} -start + client c1 { txreq -url "/foo" rxresp @@ -49,3 +53,5 @@ client c1 { } client c1 -run + +logexpect l1 -wait diff --git a/bin/varnishtest/tests/r01858.vtc b/bin/varnishtest/tests/r01858.vtc index 817c469..23ff7c2 100644 --- a/bin/varnishtest/tests/r01858.vtc +++ b/bin/varnishtest/tests/r01858.vtc @@ -22,6 +22,11 @@ varnish v1 -vcl+backend { } } -start +# Tests logging hit-for-miss on an expired object +logexpect l1 -v v1 -g vxid { + expect 1003 * HitMiss "^1002$" +} -start + client c1 { txreq rxresp @@ -36,3 +41,4 @@ client c1 { expect resp.body == "bar" } -run +logexpect l1 -wait diff --git a/include/tbl/vsl_tags.h b/include/tbl/vsl_tags.h index 2231b17..e434aac 100644 --- a/include/tbl/vsl_tags.h +++ b/include/tbl/vsl_tags.h @@ -541,6 +541,11 @@ SLTM(H2TxBody, 0, "Transmitted HTTP2 frame body", "Binary data" ) +SLTM(HitMiss, 0, "Hit for miss object in cache.", + "Hit-for-miss object looked up in cache. Shows the VXID of the" + " hit-for-miss object.\n\n" +) + #undef NODEF_NOTICE #undef SLTM From phk at FreeBSD.org Tue Mar 7 17:41:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Tue, 07 Mar 2017 18:41:05 +0100 Subject: [master] 2087b3c Simplify the H2:body delivery Message-ID: commit 2087b3c178e8d351c01a83f8dc03b5f4eba98915 Author: Poul-Henning Kamp Date: Tue Mar 7 15:27:51 2017 +0000 Simplify the H2:body delivery diff --git a/bin/varnishd/http2/cache_http2_deliver.c b/bin/varnishd/http2/cache_http2_deliver.c index afd088e..48f0513 100644 --- a/bin/varnishd/http2/cache_http2_deliver.c +++ b/bin/varnishd/http2/cache_http2_deliver.c @@ -81,13 +81,14 @@ h2_bytes(struct req *req, enum vdp_action act, void **priv, CHECK_OBJ_NOTNULL(req, REQ_MAGIC); CAST_OBJ_NOTNULL(r2, req->transport_priv, H2_REQ_MAGIC); (void)priv; - if (act == VDP_INIT || act == VDP_FINI) + if (act == VDP_INIT) return (0); - AZ(req->vdp_nxt); /* always at the bottom of the pile */ - H2_Send_Get(req->wrk, r2->h2sess, r2); H2_Send(req->wrk, r2, - act == VDP_FLUSH ? 1 : 0, H2_F_DATA, H2FF_NONE, len, ptr); + act != VDP_NULL ? 1 : 0, + H2_F_DATA, + act == VDP_FINI ? H2FF_DATA_END_STREAM : H2FF_NONE, + len, ptr); H2_Send_Rel(req->wrk, r2->h2sess, r2); return (0); @@ -171,7 +172,6 @@ h2_deliver(struct req *req, struct boc *boc, int sendbody) CAST_OBJ_NOTNULL(r2, req->transport_priv, H2_REQ_MAGIC); sp = req->sp; CHECK_OBJ_NOTNULL(sp, SESS_MAGIC); - (void)sendbody; VSLb(req->vsl, SLT_Debug, "H2: Deliver"); @@ -243,26 +243,27 @@ h2_deliver(struct req *req, struct boc *boc, int sendbody) } sz = (char*)p - req->ws->f; + AZ(req->wrk->v1l); + /* XXX: Optimize !sendbody case */ + + if (sendbody && req->resp_len == 0) + sendbody = 0; + H2_Send_Get(req->wrk, r2->h2sess, r2); - H2_Send(req->wrk, r2, 1, H2_F_HEADERS, H2FF_HEADERS_END_HEADERS, + H2_Send(req->wrk, r2, 1, H2_F_HEADERS, + (sendbody ? 0 : H2FF_HEADERS_END_STREAM) | H2FF_HEADERS_END_HEADERS, sz, req->ws->f); H2_Send_Rel(req->wrk, r2->h2sess, r2); WS_Release(req->ws, 0); - if (sendbody && req->resp_len != 0) - VDP_push(req, h2_bytes, NULL, 1, "H2"); - AZ(req->wrk->v1l); - - if (sendbody && req->resp_len != 0) + if (sendbody) { + VDP_push(req, h2_bytes, NULL, 1, "H2"); err = VDP_DeliverObj(req); - /*XXX*/(void)err; - - H2_Send_Get(req->wrk, r2->h2sess, r2); - H2_Send(req->wrk, r2, 1, H2_F_DATA, H2FF_DATA_END_STREAM, 0, NULL); - H2_Send_Rel(req->wrk, r2->h2sess, r2); + /*XXX*/(void)err; + } AZ(req->wrk->v1l); VDP_close(req); From geoff at uplex.de Tue Mar 7 17:42:05 2017 From: geoff at uplex.de (Geoff Simmons) Date: Tue, 07 Mar 2017 18:42:05 +0100 Subject: [master] a95f496 Document the use of HitMiss and HitPass in VSL in What's New for 5.1. Message-ID: commit a95f496835e3b95be5fe1032884745d82f05b1ba Author: Geoff Simmons Date: Tue Mar 7 18:40:33 2017 +0100 Document the use of HitMiss and HitPass in VSL in What's New for 5.1. diff --git a/doc/sphinx/whats-new/upgrading-5.1.rst b/doc/sphinx/whats-new/upgrading-5.1.rst index da898a2..7291736 100644 --- a/doc/sphinx/whats-new/upgrading-5.1.rst +++ b/doc/sphinx/whats-new/upgrading-5.1.rst @@ -16,10 +16,20 @@ vcl_backend_response Other changes ============= -* Added the ``cache_hitmiss`` stat to ``varnishstat(1)`` to count hits on - hit-for-miss objects. +* ``varnishstat(1)``: -* The ``cache_hitpass`` stat now only counts hits on hit-for-pass objects. + * Added the ``cache_hitmiss`` stat to to count hits on + hit-for-miss objects. -* An entry with the ``TTL`` tag and the prefix ``HFP`` is logged in - ``varnishlog(1)`` to record the duration set for hit-for-pass objects. + * The ``cache_hitpass`` stat now only counts hits on hit-for-pass + objects. + +* ``varnishlog(1)``: + + * Hits on hit-for-miss and hit-for-pass objects are logged with + the ``HitMiss`` and ``HitPass`` tags, respectively. In each case, + the log payload is the VXID of the previous transaction in which + the object was saved in the cache (as with ``Hit``). + + * An entry with the ``TTL`` tag and the prefix ``HFP`` is logged to + record the duration set for hit-for-pass objects. From fgsch at lodoss.net Tue Mar 7 20:02:05 2017 From: fgsch at lodoss.net (Federico G. Schwindt) Date: Tue, 07 Mar 2017 21:02:05 +0100 Subject: [master] 75da9a8 Add an HFP record example Message-ID: commit 75da9a8f18e2581883a6baebe6efbd4206bf255b Author: Federico G. Schwindt Date: Tue Mar 7 19:39:42 2017 +0000 Add an HFP record example diff --git a/include/tbl/vsl_tags.h b/include/tbl/vsl_tags.h index e434aac..9d52f7e 100644 --- a/include/tbl/vsl_tags.h +++ b/include/tbl/vsl_tags.h @@ -225,6 +225,7 @@ SLTM(TTL, 0, "TTL set on object", "Examples::\n\n" "\tRFC 60 10 -1 1312966109 1312966109 1312966109 0 60\n" "\tVCL 120 10 0 1312966111\n" + "\tHFP 2 0 0 1312966113\n" "\n" ) From fgsch at lodoss.net Tue Mar 7 22:44:05 2017 From: fgsch at lodoss.net (Federico G. Schwindt) Date: Tue, 07 Mar 2017 23:44:05 +0100 Subject: [master] 0144634 This test requires 64bits Message-ID: commit 0144634ea7b6c9fbd9deadb5c3df7f3649f11367 Author: Federico G. Schwindt Date: Tue Mar 7 22:23:10 2017 +0000 This test requires 64bits diff --git a/bin/varnishtest/tests/r02233.vtc b/bin/varnishtest/tests/r02233.vtc index a17a701..fad35b2 100644 --- a/bin/varnishtest/tests/r02233.vtc +++ b/bin/varnishtest/tests/r02233.vtc @@ -1,5 +1,7 @@ varnishtest "Fail earlier if we cannot fit the query string" +feature 64bit + server s1 { rxreq txresp @@ -17,16 +19,6 @@ client c1 { send "GET /?a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1" send "&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1" send "&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1" - send "&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1" - send "&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1" - send "&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1" - send "&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1" - send "&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1" - send "&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1" - send "&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1" - send "&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1" - send "&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1" - send "&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1&a=1" send " HTTP/1.1\r\n" send "Host: foo\r\n\r\n" rxresp From dridi.boukelmoune at gmail.com Wed Mar 8 13:00:08 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Wed, 08 Mar 2017 14:00:08 +0100 Subject: [master] 3a27f6f Missing logexpect name Message-ID: commit 3a27f6f24b9d8fb4986d6cf8c8496acaaefbd471 Author: Dridi Boukelmoune Date: Wed Mar 8 13:59:30 2017 +0100 Missing logexpect name diff --git a/bin/varnishtest/tests/b00050.vtc b/bin/varnishtest/tests/b00050.vtc index 399df82..ef9918b 100644 --- a/bin/varnishtest/tests/b00050.vtc +++ b/bin/varnishtest/tests/b00050.vtc @@ -16,7 +16,7 @@ client c1 { rxresp } -run -logexpect -wait +logexpect l1 -wait # vxid only supports integer operations From geoff at uplex.de Wed Mar 8 17:48:06 2017 From: geoff at uplex.de (Geoff Simmons) Date: Wed, 08 Mar 2017 18:48:06 +0100 Subject: [master] 2843de8 Added a placeholder chapter about HTTP/2 support to What's New for 5.1. Message-ID: commit 2843de85c31f8fb1e1bd2b6d9718ad990bb4736b Author: Geoff Simmons Date: Wed Mar 8 16:02:24 2017 +0100 Added a placeholder chapter about HTTP/2 support to What's New for 5.1. diff --git a/doc/sphinx/whats-new/changes-5.1.rst b/doc/sphinx/whats-new/changes-5.1.rst index 26e1fc3..be18208 100644 --- a/doc/sphinx/whats-new/changes-5.1.rst +++ b/doc/sphinx/whats-new/changes-5.1.rst @@ -6,6 +6,11 @@ Changes in Varnish 5.1 Varnish 5.1 ... XXX +Progress on HTTP/2 support +~~~~~~~~~~~~~~~~~~~~~~~~~~ + +XXX + .. _whatsnew_changes_5.1_hitpass: Hit-For-Pass has returned From geoff at uplex.de Wed Mar 8 17:48:06 2017 From: geoff at uplex.de (Geoff Simmons) Date: Wed, 08 Mar 2017 18:48:06 +0100 Subject: [master] e274785 Add the "Issues fixed" list to changes.rst for 5.1. This is just what I could find with "Fixes" or "Closes" in git log varnish-5.0.0..HEAD Message-ID: commit e2747855a5150cec4f11d81588807dc88a5ce6e7 Author: Geoff Simmons Date: Wed Mar 8 18:45:39 2017 +0100 Add the "Issues fixed" list to changes.rst for 5.1. This is just what I could find with "Fixes" or "Closes" in git log varnish-5.0.0..HEAD diff --git a/doc/changes.rst b/doc/changes.rst index 5f5afde..048641c 100644 --- a/doc/changes.rst +++ b/doc/changes.rst @@ -5,6 +5,122 @@ Varnish Cache 5.1.0 (unreleased) * The fallback director has now an extra, optional parameter to keep using the current backend until it falls sick. +Issues fixed: + +* 2245_ - [trunk]Varnish doesn't start, if use vmod (vmod_cache dir was permission denied) +* 2241_ - VSL fails to get hold of SHM +* 2233_ - Varnish 4.1.5 crash on "Assert error in WS_Assert(), cache/cache_ws.c line 59" +* 2227_ - `-C` flag broken at HEAD +* 2217_ - fix argument processing -C regression +* 2207_ - Assert error in V1L_Write() +* 2205_ - Strange bug when I set client.ip with another string +* 2203_ - unhandled SIGPIPE +* 2200_ - Assert error in vev_compact_pfd(), vev.c line 394 +* 2197_ - ESI parser panic on malformed src URL +* 2190_ - varnishncsa: The %r formatter is NOT equivalent to "%m http://%{Host}i%U%q %H" +* 2186_ - Assert error in sml_iterator(), storage/storage_simple.c line 263 +* 2184_ - Cannot subtract a negative number +* 2177_ - Clarify interactions between restarts and labels +* 2175_ - Backend leak between a top VCL and a label +* 2174_ - Cflags overhaul +* 2167_ - VCC will not parse a literal negative number where INT is expected +* 2155_ - vmodtool removes text following $Event from RST docs +* 2151_ - Health probes do not honor a backend's PROXY protocol setting +* 2142_ - ip comparison fails +* 2148_ - varnishncsa cannot decode Authorization header if the format is incorrect. +* 2143_ - Assert error in exp_inbox(), cache/cache_expire.c line 195 +* 2134_ - Disable Nagle's +* 2129_ - stack overflow with >4 level esi +* 2128_ - SIGSEGV NULL Pointer in STV__iter() +* 2118_ - "varnishstat -f MAIN.sess_conn -1" produces empty output #2118 +* 2117_ - SES_Close() EBADF / Wait_Enter() wp->fd <= 0 +* 2115_ - VSM temporary files are not always deleted +* 2110_ - [CLI] vcl.inline failures +* 2104_ - Assert error in VFP_Open(), cache/cache_fetch_proc.c line 139: Condition((vc->wrk->vsl) != 0) not true +* 2099_ - VCC BACKEND/HDR comparison produces duplicate gethdr_s definition +* 2096_ - H2 t2002 fail on arm64/arm32 +* 2094_ - H2 t2000 fail on arm64/arm32 +* 2078_ - VCL comparison doesn't fold STRING_LIST +* 2052_ - d12.vtc flaky when compiling with suncc +* 2042_ - Send a 304 response for a just-gone-stale hitpass object when appropriate +* 2041_ - Parent process should exit if it fails to start child +* 2035_ - varnishd stalls with two consecutive Range requests using HTTP persistent connections +* 2026_ - Add restart of poll in read_tmo +* 2021_ - vcc "used before defined" check +* 2017_ - "%r" field is wrong +* 2016_ - confusing vcc error when acl referenced before definition +* 2014_ - req.ttl: retire or document+vtc +* 2010_ - varnishadm CLI behaving weirdly +* 1991_ - Starting varnish on Linux with boot param ipv6.disable=1 fails +* 1988_ - Lost req.url gives misleading error +* 1914_ - set a custom storage for cache_req_body +* 1899_ - varnishadm vcl.inline is overly obscure +* 1874_ - [4.1/master] clock-step related crash +* 1865_ - Panic accessing beresp.backend.ip in vcl_backend_error{} +* 1856_ - LostHeader setting req.url to an empty string +* 1834_ - WS_Assert(), cache/cache_ws.c line 59 +* 1830_ - VSL API: "duplicate link" errors in request grouping when vsl_buffer is increased +* 1764_ - nuke_limit is not honored +* 1750_ - Fail more gracefully on -l >= 4GB +* 1704_ - fetch_failed not incremented + +.. _2245: https://github.com/varnishcache/varnish-cache/issues/2245 +.. _2241: https://github.com/varnishcache/varnish-cache/issues/2241 +.. _2233: https://github.com/varnishcache/varnish-cache/issues/2233 +.. _2227: https://github.com/varnishcache/varnish-cache/issues/2227 +.. _2217: https://github.com/varnishcache/varnish-cache/issues/2217 +.. _2207: https://github.com/varnishcache/varnish-cache/issues/2207 +.. _2205: https://github.com/varnishcache/varnish-cache/issues/2205 +.. _2203: https://github.com/varnishcache/varnish-cache/issues/2203 +.. _2200: https://github.com/varnishcache/varnish-cache/issues/2200 +.. _2197: https://github.com/varnishcache/varnish-cache/issues/2197 +.. _2190: https://github.com/varnishcache/varnish-cache/issues/2190 +.. _2186: https://github.com/varnishcache/varnish-cache/issues/2186 +.. _2184: https://github.com/varnishcache/varnish-cache/issues/2184 +.. _2177: https://github.com/varnishcache/varnish-cache/issues/2177 +.. _2175: https://github.com/varnishcache/varnish-cache/issues/2175 +.. _2174: https://github.com/varnishcache/varnish-cache/issues/2174 +.. _2167: https://github.com/varnishcache/varnish-cache/issues/2167 +.. _2155: https://github.com/varnishcache/varnish-cache/issues/2155 +.. _2151: https://github.com/varnishcache/varnish-cache/issues/2151 +.. _2142: https://github.com/varnishcache/varnish-cache/issues/2142 +.. _2148: https://github.com/varnishcache/varnish-cache/issues/2148 +.. _2143: https://github.com/varnishcache/varnish-cache/issues/2143 +.. _2134: https://github.com/varnishcache/varnish-cache/issues/2134 +.. _2129: https://github.com/varnishcache/varnish-cache/issues/2129 +.. _2128: https://github.com/varnishcache/varnish-cache/issues/2128 +.. _2118: https://github.com/varnishcache/varnish-cache/issues/2118 +.. _2117: https://github.com/varnishcache/varnish-cache/issues/2117 +.. _2115: https://github.com/varnishcache/varnish-cache/issues/2115 +.. _2110: https://github.com/varnishcache/varnish-cache/issues/2110 +.. _2104: https://github.com/varnishcache/varnish-cache/issues/2104 +.. _2099: https://github.com/varnishcache/varnish-cache/issues/2099 +.. _2096: https://github.com/varnishcache/varnish-cache/issues/2096 +.. _2094: https://github.com/varnishcache/varnish-cache/issues/2094 +.. _2078: https://github.com/varnishcache/varnish-cache/issues/2078 +.. _2052: https://github.com/varnishcache/varnish-cache/issues/2052 +.. _2042: https://github.com/varnishcache/varnish-cache/issues/2042 +.. _2041: https://github.com/varnishcache/varnish-cache/issues/2041 +.. _2035: https://github.com/varnishcache/varnish-cache/issues/2035 +.. _2026: https://github.com/varnishcache/varnish-cache/issues/2026 +.. _2021: https://github.com/varnishcache/varnish-cache/issues/2021 +.. _2017: https://github.com/varnishcache/varnish-cache/issues/2017 +.. _2016: https://github.com/varnishcache/varnish-cache/issues/2016 +.. _2014: https://github.com/varnishcache/varnish-cache/issues/2014 +.. _2010: https://github.com/varnishcache/varnish-cache/issues/2010 +.. _1991: https://github.com/varnishcache/varnish-cache/issues/1991 +.. _1988: https://github.com/varnishcache/varnish-cache/issues/1988 +.. _1914: https://github.com/varnishcache/varnish-cache/issues/1914 +.. _1899: https://github.com/varnishcache/varnish-cache/issues/1899 +.. _1874: https://github.com/varnishcache/varnish-cache/issues/1874 +.. _1865: https://github.com/varnishcache/varnish-cache/issues/1865 +.. _1856: https://github.com/varnishcache/varnish-cache/issues/1856 +.. _1834: https://github.com/varnishcache/varnish-cache/issues/1834 +.. _1830: https://github.com/varnishcache/varnish-cache/issues/1830 +.. _1764: https://github.com/varnishcache/varnish-cache/issues/1764 +.. _1750: https://github.com/varnishcache/varnish-cache/issues/1750 +.. _1704: https://github.com/varnishcache/varnish-cache/issues/1704 + ================================ Varnish Cache 5.0.0 (2016-09-15) ================================ From dridi.boukelmoune at gmail.com Wed Mar 8 19:28:05 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Wed, 08 Mar 2017 20:28:05 +0100 Subject: [master] 17a456b Harmonize name checks in varnishtest Message-ID: commit 17a456bdc85359e4ec0d75f1d0a285a3db517d5b Author: Dridi Boukelmoune Date: Wed Mar 8 19:52:49 2017 +0100 Harmonize name checks in varnishtest It takes the barrier as a template and provides a consistent error message logged with the caller's vtclog. The name is the first thing checked when a new named entity is created, saving useless setup. Fixes #2249 diff --git a/bin/varnishtest/vtc.h b/bin/varnishtest/vtc.h index 5919913..4db8e78 100644 --- a/bin/varnishtest/vtc.h +++ b/bin/varnishtest/vtc.h @@ -41,6 +41,15 @@ #include "vqueue.h" #include "vsb.h" +#define VTC_CHECK_NAME(vl, name, type, chr) \ + do { \ + AN(name); \ + if (*(name) != chr) \ + vtc_fatal(vl, \ + type " name must start with '%c' (got %s)", \ + chr, name); \ + } while (0) + struct vtclog; struct cmds; struct suckaddr; diff --git a/bin/varnishtest/vtc_barrier.c b/bin/varnishtest/vtc_barrier.c index bafcb79..41cbf20 100644 --- a/bin/varnishtest/vtc_barrier.c +++ b/bin/varnishtest/vtc_barrier.c @@ -75,11 +75,9 @@ barrier_new(char *name, struct vtclog *vl) { struct barrier *b; + VTC_CHECK_NAME(vl, name, "Barrier", 'b'); ALLOC_OBJ(b, BARRIER_MAGIC); AN(b); - AN(name); - if (*name != 'b') - vtc_fatal(vl, "Barrier name must start with 'b' (%s)", name); if (pthread_self() != vtc_thread) vtc_fatal(vl, "Barrier %s can only be created on the top thread", name); diff --git a/bin/varnishtest/vtc_client.c b/bin/varnishtest/vtc_client.c index 3b7e6c8..18f5cef 100644 --- a/bin/varnishtest/vtc_client.c +++ b/bin/varnishtest/vtc_client.c @@ -165,18 +165,16 @@ client_thread(void *priv) */ static struct client * -client_new(const char *name) +client_new(char *name, struct vtclog *vl) { struct client *c; - AN(name); + VTC_CHECK_NAME(vl, name, "Client", 'c'); ALLOC_OBJ(c, CLIENT_MAGIC); AN(c); REPLACE(c->name, name); c->vl = vtc_logopen(name); AN(c->vl); - if (*c->name != 'c') - vtc_fatal(c->vl, "Client name must start with 'c'"); bprintf(c->connect, "%s", "${v1_sock}"); VTAILQ_INSERT_TAIL(&clients, c, list); @@ -256,7 +254,6 @@ cmd_client(CMD_ARGS) (void)priv; (void)cmd; - (void)vl; if (av == NULL) { /* Reset and free */ @@ -276,7 +273,7 @@ cmd_client(CMD_ARGS) if (!strcmp(c->name, av[0])) break; if (c == NULL) - c = client_new(av[0]); + c = client_new(av[0], vl); av++; for (; *av != NULL; av++) { diff --git a/bin/varnishtest/vtc_logexp.c b/bin/varnishtest/vtc_logexp.c index 3f205fb..df47ec4 100644 --- a/bin/varnishtest/vtc_logexp.c +++ b/bin/varnishtest/vtc_logexp.c @@ -199,11 +199,11 @@ logexp_delete(struct logexp *le) } static struct logexp * -logexp_new(const char *name) +logexp_new(char *name, struct vtclog *vl) { struct logexp *le; - AN(name); + VTC_CHECK_NAME(vl, name, "Logexpect", 'l'); ALLOC_OBJ(le, LOGEXP_MAGIC); AN(le); REPLACE(le->name, name); @@ -510,7 +510,6 @@ cmd_logexpect(CMD_ARGS) (void)priv; (void)cmd; - (void)vl; if (av == NULL) { /* Reset and free */ @@ -534,7 +533,7 @@ cmd_logexpect(CMD_ARGS) break; } if (le == NULL) - le = logexp_new(av[0]); + le = logexp_new(av[0], vl); av++; for (; *av != NULL; av++) { diff --git a/bin/varnishtest/vtc_process.c b/bin/varnishtest/vtc_process.c index 3c0b73c..b9249e0 100644 --- a/bin/varnishtest/vtc_process.c +++ b/bin/varnishtest/vtc_process.c @@ -85,13 +85,13 @@ static VTAILQ_HEAD(, process) processes = } while (0) static struct process * -process_new(const char *name) +process_new(char *name, struct vtclog *vl) { struct process *p; struct vsb *vsb; char buf[1024]; - AN(name); + VTC_CHECK_NAME(vl, name, "Process", 'p'); ALLOC_OBJ(p, PROCESS_MAGIC); AN(p); REPLACE(p->name, name); @@ -111,9 +111,6 @@ process_new(const char *name) p->fd_to = -1; p->fd_from = -1; - if (*p->name != 'p') - vtc_fatal(p->vl, "Process name must start with 'p'"); - VTAILQ_INSERT_TAIL(&processes, p, list); return (p); } @@ -436,7 +433,6 @@ cmd_process(CMD_ARGS) (void)priv; (void)cmd; - (void)vl; if (av == NULL) { /* Reset and free */ @@ -463,7 +459,7 @@ cmd_process(CMD_ARGS) if (!strcmp(p->name, av[0])) break; if (p == NULL) - p = process_new(av[0]); + p = process_new(av[0], vl); av++; for (; *av != NULL; av++) { diff --git a/bin/varnishtest/vtc_server.c b/bin/varnishtest/vtc_server.c index f9b01a1..18fe363 100644 --- a/bin/varnishtest/vtc_server.c +++ b/bin/varnishtest/vtc_server.c @@ -71,18 +71,16 @@ static VTAILQ_HEAD(, server) servers = */ static struct server * -server_new(const char *name) +server_new(char *name, struct vtclog *vl) { struct server *s; - AN(name); + VTC_CHECK_NAME(vl, name, "Server", 's'); ALLOC_OBJ(s, SERVER_MAGIC); AN(s); REPLACE(s->name, name); s->vl = vtc_logopen(s->name); AN(s->vl); - if (*s->name != 's') - vtc_fatal(s->vl, "Server name must start with 's'"); bprintf(s->listen, "%s", "127.0.0.1 0"); s->repeat = 1; @@ -240,6 +238,7 @@ server_dispatch_thread(void *priv) assert(s->sock >= 0); vl = vtc_logopen(s->name); + AN(vl); vtc_log(vl, 2, "Dispatch started on %s", s->listen); while (1) { @@ -250,7 +249,7 @@ server_dispatch_thread(void *priv) vtc_fatal(vl, "Accepted failed: %s", strerror(errno)); bprintf(snbuf, "s%d", sn++); vtc_log(vl, 3, "dispatch fd %d -> %s", fd, snbuf); - s2 = server_new(snbuf); + s2 = server_new(snbuf, vl); s2->spec = s->spec; strcpy(s2->listen, s->listen); s2->fd = fd; @@ -336,7 +335,6 @@ cmd_server(CMD_ARGS) (void)priv; (void)cmd; - (void)vl; if (av == NULL) { /* Reset and free */ @@ -369,7 +367,7 @@ cmd_server(CMD_ARGS) break; AZ(pthread_mutex_unlock(&server_mtx)); if (s == NULL) - s = server_new(av[0]); + s = server_new(av[0], vl); CHECK_OBJ_NOTNULL(s, SERVER_MAGIC); av++; diff --git a/bin/varnishtest/vtc_varnish.c b/bin/varnishtest/vtc_varnish.c index f22e5cc..a58bf6b 100644 --- a/bin/varnishtest/vtc_varnish.c +++ b/bin/varnishtest/vtc_varnish.c @@ -278,13 +278,13 @@ varnishlog_thread(void *priv) */ static struct varnish * -varnish_new(const char *name) +varnish_new(char *name, struct vtclog *vl) { struct varnish *v; struct vsb *vsb; char buf[1024]; - AN(name); + VTC_CHECK_NAME(vl, name, "Varnish", 'v'); ALLOC_OBJ(v, VARNISH_MAGIC); AN(v); REPLACE(v->name, name); @@ -306,9 +306,6 @@ varnish_new(const char *name) bprintf(buf, "rm -rf %s ; mkdir -p %s", v->workdir, v->workdir); AZ(system(buf)); - if (*v->name != 'v') - vtc_fatal(v->vl, "Varnish name must start with 'v'"); - v->args = VSB_new_auto(); v->cli_fd = -1; @@ -1077,7 +1074,6 @@ cmd_varnish(CMD_ARGS) (void)priv; (void)cmd; - (void)vl; if (av == NULL) { /* Reset and free */ @@ -1097,7 +1093,7 @@ cmd_varnish(CMD_ARGS) if (!strcmp(v->name, av[0])) break; if (v == NULL) - v = varnish_new(av[0]); + v = varnish_new(av[0], vl); av++; for (; *av != NULL; av++) { From dridi.boukelmoune at gmail.com Wed Mar 8 19:28:05 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Wed, 08 Mar 2017 20:28:05 +0100 Subject: [master] b101ec4 Needless branch Message-ID: commit b101ec43a52c041c5c4d0c1f5e47cc5c863a1469 Author: Dridi Boukelmoune Date: Wed Mar 8 19:56:25 2017 +0100 Needless branch diff --git a/bin/varnishtest/vtc_log.c b/bin/varnishtest/vtc_log.c index ae15e7e..7f31744 100644 --- a/bin/varnishtest/vtc_log.c +++ b/bin/varnishtest/vtc_log.c @@ -190,8 +190,6 @@ vtc_log(struct vtclog *vl, int lvl, const char *fmt, ...) va_end(ap); REL_VL(vl); - if (lvl > 0) - return; if (lvl == 0) vtc_logfail(); } From dridi.boukelmoune at gmail.com Wed Mar 8 19:28:05 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Wed, 08 Mar 2017 20:28:05 +0100 Subject: [master] 4c9b097 Move setenv to vtc_fatal Message-ID: commit 4c9b097f035cee98ed21817d66e911af901573fd Author: Dridi Boukelmoune Date: Wed Mar 8 20:01:23 2017 +0100 Move setenv to vtc_fatal diff --git a/bin/varnishtest/vtc.c b/bin/varnishtest/vtc.c index cf5e051..518635d 100644 --- a/bin/varnishtest/vtc.c +++ b/bin/varnishtest/vtc.c @@ -628,7 +628,7 @@ cmd_setenv(CMD_ARGS) AN(av[2]); } if (av[3] != NULL) - vtc_log(vl, 0, "CMD setenv: Unexpected argument '%s'", av[3]); + vtc_fatal(vl, "CMD setenv: Unexpected argument '%s'", av[3]); r = setenv(av[1], av[2], force); if (r != 0) vtc_log(vl, 0, "CMD setenv %s=\"%s\" failed: %s", From dridi.boukelmoune at gmail.com Wed Mar 8 19:28:05 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Wed, 08 Mar 2017 20:28:05 +0100 Subject: [master] 2d927b1 Don't protect the barriers list with a lock Message-ID: commit 2d927b1219da282b0d4594859461180bf827773d Author: Dridi Boukelmoune Date: Wed Mar 8 20:21:12 2017 +0100 Don't protect the barriers list with a lock A command like `barrier r1` would fail while holding the lock because of the invalid name, but the reset of the test case would then deadlock. It leads to a timeout like we see sometimes on VTEST so getting rid of them may just require to review when `vtc_fatal` is called while locking. In this very case we can only create barriers in the top thread so the lock is useless. diff --git a/bin/varnishtest/vtc.c b/bin/varnishtest/vtc.c index 518635d..76f5706 100644 --- a/bin/varnishtest/vtc.c +++ b/bin/varnishtest/vtc.c @@ -828,7 +828,6 @@ exec_file(const char *fn, const char *script, const char *tmpdir, AN(vltop); init_macro(); - init_barrier(); init_server(); /* Move into our tmpdir */ diff --git a/bin/varnishtest/vtc_barrier.c b/bin/varnishtest/vtc_barrier.c index 41cbf20..d621f68 100644 --- a/bin/varnishtest/vtc_barrier.c +++ b/bin/varnishtest/vtc_barrier.c @@ -67,7 +67,6 @@ struct barrier { volatile unsigned need_join; }; -static pthread_mutex_t barrier_mtx; static VTAILQ_HEAD(, barrier) barriers = VTAILQ_HEAD_INITIALIZER(barriers); static struct barrier * @@ -412,7 +411,6 @@ cmd_barrier(CMD_ARGS) (void)cmd; if (av == NULL) { - AZ(pthread_mutex_lock(&barrier_mtx)); /* Reset and free */ VTAILQ_FOREACH_SAFE(b, &barriers, list, b2) { r = pthread_mutex_trylock(&b->mtx); @@ -432,23 +430,20 @@ cmd_barrier(CMD_ARGS) } AZ(pthread_mutex_unlock(&b->mtx)); } - AZ(pthread_mutex_unlock(&barrier_mtx)); return; } AZ(strcmp(av[0], "barrier")); av++; - AZ(pthread_mutex_lock(&barrier_mtx)); VTAILQ_FOREACH(b, &barriers, list) if (!strcmp(b->name, av[0])) break; if (b == NULL) b = barrier_new(av[0], vl); av++; - AZ(pthread_mutex_lock(&b->mtx)); - AZ(pthread_mutex_unlock(&barrier_mtx)); + AZ(pthread_mutex_lock(&b->mtx)); for (; *av != NULL; av++) { if (!strcmp(*av, "cond")) { av++; @@ -474,10 +469,3 @@ cmd_barrier(CMD_ARGS) } AZ(pthread_mutex_unlock(&b->mtx)); } - -void -init_barrier(void) -{ - - AZ(pthread_mutex_init(&barrier_mtx, NULL)); -} From dridi.boukelmoune at gmail.com Wed Mar 8 19:43:06 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Wed, 08 Mar 2017 20:43:06 +0100 Subject: [master] dd17e5c Constify Message-ID: commit dd17e5c413c400b16ca6319c3735b47f5b89ed00 Author: Dridi Boukelmoune Date: Wed Mar 8 20:40:47 2017 +0100 Constify The qualifiers were accidentally lost in 17a456b, because barriers became the template and were the only non-const occurrence. diff --git a/bin/varnishtest/vtc_barrier.c b/bin/varnishtest/vtc_barrier.c index d621f68..6a131a0 100644 --- a/bin/varnishtest/vtc_barrier.c +++ b/bin/varnishtest/vtc_barrier.c @@ -70,7 +70,7 @@ struct barrier { static VTAILQ_HEAD(, barrier) barriers = VTAILQ_HEAD_INITIALIZER(barriers); static struct barrier * -barrier_new(char *name, struct vtclog *vl) +barrier_new(const char *name, struct vtclog *vl) { struct barrier *b; diff --git a/bin/varnishtest/vtc_client.c b/bin/varnishtest/vtc_client.c index 18f5cef..24296ba 100644 --- a/bin/varnishtest/vtc_client.c +++ b/bin/varnishtest/vtc_client.c @@ -165,7 +165,7 @@ client_thread(void *priv) */ static struct client * -client_new(char *name, struct vtclog *vl) +client_new(const char *name, struct vtclog *vl) { struct client *c; diff --git a/bin/varnishtest/vtc_logexp.c b/bin/varnishtest/vtc_logexp.c index df47ec4..4bed257 100644 --- a/bin/varnishtest/vtc_logexp.c +++ b/bin/varnishtest/vtc_logexp.c @@ -199,7 +199,7 @@ logexp_delete(struct logexp *le) } static struct logexp * -logexp_new(char *name, struct vtclog *vl) +logexp_new(const char *name, struct vtclog *vl) { struct logexp *le; diff --git a/bin/varnishtest/vtc_process.c b/bin/varnishtest/vtc_process.c index b9249e0..46d97ae 100644 --- a/bin/varnishtest/vtc_process.c +++ b/bin/varnishtest/vtc_process.c @@ -85,7 +85,7 @@ static VTAILQ_HEAD(, process) processes = } while (0) static struct process * -process_new(char *name, struct vtclog *vl) +process_new(const char *name, struct vtclog *vl) { struct process *p; struct vsb *vsb; diff --git a/bin/varnishtest/vtc_server.c b/bin/varnishtest/vtc_server.c index 18fe363..773e7fb 100644 --- a/bin/varnishtest/vtc_server.c +++ b/bin/varnishtest/vtc_server.c @@ -71,7 +71,7 @@ static VTAILQ_HEAD(, server) servers = */ static struct server * -server_new(char *name, struct vtclog *vl) +server_new(const char *name, struct vtclog *vl) { struct server *s; diff --git a/bin/varnishtest/vtc_varnish.c b/bin/varnishtest/vtc_varnish.c index a58bf6b..c3432f2 100644 --- a/bin/varnishtest/vtc_varnish.c +++ b/bin/varnishtest/vtc_varnish.c @@ -278,7 +278,7 @@ varnishlog_thread(void *priv) */ static struct varnish * -varnish_new(char *name, struct vtclog *vl) +varnish_new(const char *name, struct vtclog *vl) { struct varnish *v; struct vsb *vsb; From phk at FreeBSD.org Wed Mar 8 19:51:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Wed, 08 Mar 2017 20:51:05 +0100 Subject: [master] e32a440 Synchronize harder with the VSL thread in vtc_varnish.c Message-ID: commit e32a44091d50ffa2c6894b6331753904c6d7ce4b Author: Poul-Henning Kamp Date: Wed Mar 8 19:50:16 2017 +0000 Synchronize harder with the VSL thread in vtc_varnish.c Some lowhanging Flexelint nitpicking. diff --git a/bin/varnishtest/hpack.h b/bin/varnishtest/hpack.h index feca984..9df6785 100644 --- a/bin/varnishtest/hpack.h +++ b/bin/varnishtest/hpack.h @@ -49,5 +49,7 @@ uint32_t HPK_GetTblSize(const struct hpk_ctx *ctx); uint32_t HPK_GetTblMaxSize(const struct hpk_ctx *ctx); uint32_t HPK_GetTblLength(const struct hpk_ctx *ctx); +#if 0 /* DEBUG */ void dump_dyn_tbl(const struct hpk_ctx *ctx); +#endif diff --git a/bin/varnishtest/vtc.h b/bin/varnishtest/vtc.h index 4db8e78..0e09392 100644 --- a/bin/varnishtest/vtc.h +++ b/bin/varnishtest/vtc.h @@ -90,12 +90,9 @@ extern int leave_temp; extern int vtc_witness; extern int feature_dns; -void init_barrier(void); void init_server(void); int http_process(struct vtclog *vl, const char *spec, int sock, int *sfd); -int http2_process(struct vtclog *vl, const char *spec, int sock, int *sfd, - unsigned nosettings); char * synth_body(const char *len, int rnd); diff --git a/bin/varnishtest/vtc_h2_tbl.c b/bin/varnishtest/vtc_h2_tbl.c index 209fa47..cfb18b8 100644 --- a/bin/varnishtest/vtc_h2_tbl.c +++ b/bin/varnishtest/vtc_h2_tbl.c @@ -257,6 +257,7 @@ HPK_GetTblLength(const struct hpk_ctx *ctx) return (l); } +#if 0 void dump_dyn_tbl(const struct hpk_ctx *ctx) { @@ -269,6 +270,7 @@ dump_dyn_tbl(const struct hpk_ctx *ctx) } printf("DONE\n"); } +#endif struct hpk_ctx * HPK_NewCtx(uint32_t maxsize) diff --git a/bin/varnishtest/vtc_varnish.c b/bin/varnishtest/vtc_varnish.c index c3432f2..26d478d 100644 --- a/bin/varnishtest/vtc_varnish.c +++ b/bin/varnishtest/vtc_varnish.c @@ -55,10 +55,6 @@ #include "vtcp.h" #include "vtim.h" -extern int leave_temp; -extern char *vmod_path; -extern struct vsb *params_vsb; - struct varnish { unsigned magic; #define VARNISH_MAGIC 0x208cd8e3 @@ -85,7 +81,7 @@ struct varnish { unsigned vsl_tag_count[256]; - volatile int vsl_idle; + volatile int vsl_rec; }; #define NONSENSE "%XJEIFLH|)Xspa8P" @@ -209,9 +205,8 @@ varnishlog_thread(void *priv) c = NULL; opt = 0; - while (v->pid) { + while (v->pid || c != NULL) { if (c == NULL) { - v->vsl_idle++; VTIM_sleep(0.1); if (VSM_Open(vsm)) { VSM_ResetError(vsm); @@ -232,12 +227,10 @@ varnishlog_thread(void *priv) if (i != 1) break; - v->vsl_idle = 0; + v->vsl_rec = 1; tag = VSL_TAG(c->rec.ptr); vxid = VSL_ID(c->rec.ptr); - if (tag != SLT_CLI) - v->vsl_idle = 0; if (tag == SLT__Batch) continue; tagname = VSL_tags[tag]; @@ -251,7 +244,6 @@ varnishlog_thread(void *priv) vxid, tagname, type, (int)len, data); } if (i == 0) { - v->vsl_idle++; /* Nothing to do but wait */ VTIM_sleep(0.1); } else if (i == -2) { @@ -263,8 +255,6 @@ varnishlog_thread(void *priv) break; } - v->vsl_idle = 100; - if (c) VSL_DeleteCursor(c); VSL_Delete(vsl); @@ -568,7 +558,7 @@ varnish_start(struct varnish *v) macro_def(v->vl, v->name, "port", "%s", p); macro_def(v->vl, v->name, "sock", "%s %s", h, p); /* Wait for vsl logging to get underway */ - while (v->vsl_idle == 0) + while (v->vsl_rec == 0) VTIM_sleep(.1); } @@ -610,10 +600,6 @@ varnish_cleanup(struct varnish *v) int status, r; struct rusage ru; - /* Give the VSL log time to finish */ - while (v->vsl_idle < 10) - (void)usleep(200000); - /* Close the CLI connection */ closefd(&v->cli_fd); From fgsch at lodoss.net Wed Mar 8 20:32:05 2017 From: fgsch at lodoss.net (Federico G. Schwindt) Date: Wed, 08 Mar 2017 21:32:05 +0100 Subject: [master] 409114f Tidy up Message-ID: commit 409114f52f5c975ca83091214a7d2bfe5ab81788 Author: Federico G. Schwindt Date: Wed Mar 8 20:29:04 2017 +0000 Tidy up diff --git a/doc/changes.rst b/doc/changes.rst index 048641c..1dbba2a 100644 --- a/doc/changes.rst +++ b/doc/changes.rst @@ -5,12 +5,13 @@ Varnish Cache 5.1.0 (unreleased) * The fallback director has now an extra, optional parameter to keep using the current backend until it falls sick. -Issues fixed: +Bugs fixed +---------- -* 2245_ - [trunk]Varnish doesn't start, if use vmod (vmod_cache dir was permission denied) +* 2245_ - Varnish doesn't start, if use vmod (vmod_cache dir was permission denied) * 2241_ - VSL fails to get hold of SHM -* 2233_ - Varnish 4.1.5 crash on "Assert error in WS_Assert(), cache/cache_ws.c line 59" -* 2227_ - `-C` flag broken at HEAD +* 2233_ - Crash on "Assert error in WS_Assert(), cache/cache_ws.c line 59" +* 2227_ - -C flag broken in HEAD * 2217_ - fix argument processing -C regression * 2207_ - Assert error in V1L_Write() * 2205_ - Strange bug when I set client.ip with another string @@ -32,7 +33,7 @@ Issues fixed: * 2134_ - Disable Nagle's * 2129_ - stack overflow with >4 level esi * 2128_ - SIGSEGV NULL Pointer in STV__iter() -* 2118_ - "varnishstat -f MAIN.sess_conn -1" produces empty output #2118 +* 2118_ - "varnishstat -f MAIN.sess_conn -1" produces empty output * 2117_ - SES_Close() EBADF / Wait_Enter() wp->fd <= 0 * 2115_ - VSM temporary files are not always deleted * 2110_ - [CLI] vcl.inline failures @@ -55,7 +56,7 @@ Issues fixed: * 1988_ - Lost req.url gives misleading error * 1914_ - set a custom storage for cache_req_body * 1899_ - varnishadm vcl.inline is overly obscure -* 1874_ - [4.1/master] clock-step related crash +* 1874_ - clock-step related crash * 1865_ - Panic accessing beresp.backend.ip in vcl_backend_error{} * 1856_ - LostHeader setting req.url to an empty string * 1834_ - WS_Assert(), cache/cache_ws.c line 59 @@ -139,7 +140,8 @@ Varnish Cache 5.0.0 (2016-09-15) * std.integer() can now convert from REAL. -Issues fixed: +Bugs fixed +---------- * 2086_ - Ignore H2 upgrades if the feature is not enabled. * 2054_ - Introduce new macros for out-of-tree VMODs @@ -205,6 +207,7 @@ Varnish Cache 4.1.5-beta2 (2017-02-08) Bugs fixed ---------- + * 1704_ - Reverted the docfix and made the fech_failed counter do what the documentation says it should do * 1865_ - Panic accessing beresp.backend.ip in vcl_backend_error From phk at FreeBSD.org Wed Mar 8 20:35:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Wed, 08 Mar 2017 21:35:06 +0100 Subject: [master] d9698da Streamline the H1->H2 handover a bit Message-ID: commit d9698da29340c74c18e182c606e69d0c588df97a Author: Poul-Henning Kamp Date: Wed Mar 8 20:34:14 2017 +0000 Streamline the H1->H2 handover a bit diff --git a/bin/varnishd/cache/cache_transport.h b/bin/varnishd/cache/cache_transport.h index 447c427..22c10b2 100644 --- a/bin/varnishd/cache/cache_transport.h +++ b/bin/varnishd/cache/cache_transport.h @@ -70,6 +70,8 @@ extern struct transport PROXY_transport; extern struct transport HTTP1_transport; extern struct transport H2_transport; htc_complete_f H2_prism_complete; +void H2_PU_Sess(struct worker *, struct sess *, struct req *); +void H2_OU_Sess(struct worker *, struct sess *, struct req *); const struct transport *XPORT_ByNumber(uint16_t no); void VPX_Send_Proxy(int fd, int version, const struct sess *); diff --git a/bin/varnishd/http1/cache_http1_fsm.c b/bin/varnishd/http1/cache_http1_fsm.c index d386840..5e8d42e 100644 --- a/bin/varnishd/http1/cache_http1_fsm.c +++ b/bin/varnishd/http1/cache_http1_fsm.c @@ -408,11 +408,8 @@ HTTP1_Session(struct worker *wrk, struct req *req) http1_setstate(sp, H1CLEANUP); continue; } - VSLb(req->vsl, SLT_Debug, - "H2 Prior Knowledge Upgrade"); http1_setstate(sp, NULL); - req->err_code = 1; - SES_SetTransport(wrk, sp, req, &H2_transport); + H2_PU_Sess(wrk, sp, req); return; } @@ -433,12 +430,9 @@ HTTP1_Session(struct worker *wrk, struct req *req) VSLb(req->vsl, SLT_Debug, "H2 upgrade attempt has body"); } else { - VSLb(req->vsl, SLT_Debug, - "H2 Upgrade"); http1_setstate(sp, NULL); req->err_code = 2; - SES_SetTransport(wrk, sp, req, - &H2_transport); + H2_OU_Sess(wrk, sp, req); return; } } diff --git a/bin/varnishd/http2/cache_http2_session.c b/bin/varnishd/http2/cache_http2_session.c index 522e252..050ce4a 100644 --- a/bin/varnishd/http2/cache_http2_session.c +++ b/bin/varnishd/http2/cache_http2_session.c @@ -288,6 +288,28 @@ h2_new_ou_session(struct worker *wrk, struct h2_sess *h2, return (1); } +/********************************************************************** + */ + +#define H2_PU_MARKER 1 +#define H2_OU_MARKER 2 + +void +H2_PU_Sess(struct worker *wrk, struct sess *sp, struct req *req) +{ + VSLb(req->vsl, SLT_Debug, "H2 Prior Knowledge Upgrade"); + req->err_code = H2_PU_MARKER; + SES_SetTransport(wrk, sp, req, &H2_transport); +} + +void +H2_OU_Sess(struct worker *wrk, struct sess *sp, struct req *req) +{ + VSLb(req->vsl, SLT_Debug, "H2 Optimistic Upgrade"); + req->err_code = H2_OU_MARKER; + SES_SetTransport(wrk, sp, req, &H2_transport); +} + static void __match_proto__(task_func_t) h2_new_session(struct worker *wrk, void *arg) { @@ -304,35 +326,17 @@ h2_new_session(struct worker *wrk, void *arg) assert(req->transport == &H2_transport); + assert (req->err_code == H2_PU_MARKER || req->err_code == H2_OU_MARKER); - switch(req->err_code) { - case 0: - /* Direct H2 connection (via Proxy) */ - h2 = h2_new_sess(wrk, sp, req); - wsp = WS_Snapshot(h2->ws); - (void)h2_new_req(wrk, h2, 0, NULL); - break; - case 1: - /* Prior Knowledge H1->H2 upgrade */ - h2 = h2_new_sess(wrk, sp, req); - wsp = WS_Snapshot(h2->ws); - (void)h2_new_req(wrk, h2, 0, NULL); - - if (!h2_new_pu_session(wrk, h2)) - return; - break; - case 2: - /* Optimistic H1->H2 upgrade */ - h2 = h2_new_sess(wrk, sp, NULL); - wsp = WS_Snapshot(h2->ws); - (void)h2_new_req(wrk, h2, 0, NULL); - - if (!h2_new_ou_session(wrk, h2, req)) - return; - break; - default: - WRONG("Bad req->err_code"); - } + h2 = h2_new_sess(wrk, sp, req->err_code == H2_PU_MARKER ? req : NULL); + wsp = WS_Snapshot(h2->ws); + (void)h2_new_req(wrk, h2, 0, NULL); + + if (req->err_code == H2_PU_MARKER && !h2_new_pu_session(wrk, h2)) + return; + + if (req->err_code == H2_OU_MARKER && !h2_new_ou_session(wrk, h2, req)) + return; THR_SetRequest(h2->srq); From phk at FreeBSD.org Wed Mar 8 20:46:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Wed, 08 Mar 2017 21:46:06 +0100 Subject: [master] 1a2a70f Add text about -I Message-ID: commit 1a2a70f5fa6839626f6aa5badbf460627ac372a6 Author: Poul-Henning Kamp Date: Wed Mar 8 20:45:30 2017 +0000 Add text about -I diff --git a/doc/sphinx/whats-new/changes-5.1.rst b/doc/sphinx/whats-new/changes-5.1.rst index be18208..6fb6aff 100644 --- a/doc/sphinx/whats-new/changes-5.1.rst +++ b/doc/sphinx/whats-new/changes-5.1.rst @@ -3,8 +3,52 @@ Changes in Varnish 5.1 ====================== -Varnish 5.1 ... XXX - +We have a couple of new and interesting features in Varnish 5.1, +and we have a lot of smaller improvements and bugfixes all all over +the place, in total we have made about 750 commits since Varnish 5.0, +so this is just some of the highlights: + +Startup CLI command file +~~~~~~~~~~~~~~~~~~~~~~~~ + +The new '-I cli_file' option to varnishd will make it much more +practical to use the vcl labels introduced in Varnish 5.0. + +The cli commands in the file will be executed before the worker +process starts, so it could for instance contain:: + + vcl.load panic /etc/varnish_panic.vcl + vcl.load siteA0 /etc/varnish_siteA.vcl + vcl.load siteB0 /etc/varnish_siteB.vcl + vcl.load siteC0 /etc/varnish_siteC.vcl + vsl.label siteA siteA0 + vsl.label siteB siteB0 + vsl.label siteC siteC0 + vcl.load main /etc/varnish_main.vcl + vcl.use main + +If the command is prefixed with '-', failure will not abort +the startup. + +Related to this change we have reordered the argument checking so +that argument problems are reported more consistently. + +In case you didn't hear about them yet, labeling VCL programs +allows you to branch out to other VCLs in the main::vcl_recv{}, +which in the above example could look like:: + + sub vcl_recv { + if (req.http.host ~ "asite.example.com$") { + return(vcl(siteA)); + } + if (req.http.host ~ "bsite.example.com$") { + return(vcl(siteB)); + } + if (req.http.host ~ "csite.example.com$") { + return(vcl(siteC)); + } + // Main site processing ... + } Progress on HTTP/2 support ~~~~~~~~~~~~~~~~~~~~~~~~~~ From phk at FreeBSD.org Wed Mar 8 21:37:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Wed, 08 Mar 2017 22:37:05 +0100 Subject: [master] 64d2b7c More fodder for release notes Message-ID: commit 64d2b7cadc7272887b75cab28a38f692aef1f8f8 Author: Poul-Henning Kamp Date: Wed Mar 8 21:36:29 2017 +0000 More fodder for release notes diff --git a/doc/sphinx/whats-new/changes-5.1.rst b/doc/sphinx/whats-new/changes-5.1.rst index 6fb6aff..2e4e877 100644 --- a/doc/sphinx/whats-new/changes-5.1.rst +++ b/doc/sphinx/whats-new/changes-5.1.rst @@ -6,7 +6,25 @@ Changes in Varnish 5.1 We have a couple of new and interesting features in Varnish 5.1, and we have a lot of smaller improvements and bugfixes all all over the place, in total we have made about 750 commits since Varnish 5.0, -so this is just some of the highlights: +so this is just some of the highlights. + +Probably the biggest change in Varnish 5.1 is that a couple of very +significant contributors to Varnish have changed jobs, and therefore +stopped being active contributors to the Varnish Project. + +Per Buer was one of the first people who realized that Varnish was +not just "Some program for a couple of nordic newspapers", and he +started the company Varnish Software, which is one of the major +sponsors of the Varnish Project. + +Lasse Karstensen got roped into Varnish Software by Per, and in +addition to his other duties, he has taken care of the projects +system administration and release engineering for most of the 11 +years we have been around now. + +Guys, "Thanks" doesn't even start to cover it and we wish you all +the best for the future! + Startup CLI command file ~~~~~~~~~~~~~~~~~~~~~~~~ @@ -50,6 +68,31 @@ which in the above example could look like:: // Main site processing ... } +Universal VCL return(fail) +~~~~~~~~~~~~~~~~~~~~~~~~~~ + +It is now possible to ``return(fail)`` anywhere in VCL, +including inside VMODs. This will cause VCL processing +to terminate forthright. + +In addition to ``return(fail)``, this mechanism will be +used to handle all failure conditions without a safe +fallback, for instance workspace exhaustion, too many +headers etc. + +In ``vcl_init{}`` failing causes the ``vcl.load`` to fail. + +A failure in any of the client side VCL methods (``vcl_recv{}``, +``vcl_hash{}`` ...) *except* ``vcl_synth{}``, sends the request +to ``vcl_synth{}`` with a 503, and reason "VCL failed". + +A failure on the backend side (``vcl_backend_*{}``) causes the +fetch to fail. + +(VMOD writers should use the new ``VRT_fail(ctx, format_string, ...)`` +function which logs a SLT_VCL_Error record.) + + Progress on HTTP/2 support ~~~~~~~~~~~~~~~~~~~~~~~~~~ @@ -160,6 +203,36 @@ removing the ``ETag`` or ``Last-Modified`` headers in ``vcl_backend_response``, or by removing the If-* client request headers in ``vcl_pass``. +Project tool improvements +~~~~~~~~~~~~~~~~~~~~~~~~~ + +We have spent a fair amount of time on the tools we use internally +in the project. + +The ``varnishtest`` program has been improved in many small ways, +in particular it is now much easier to execute and examine +results from other programs with the ``shell`` and ``process`` +commands. + +The project now has *KISS* web-backend which summarizes +``make distcheck`` results from various platforms: + +http://varnish-cache.org/vtest/ + +If you want Varnish to be tested on a platform not already +covered, all you need to do is run the tools/vtest.sh script +from the source tree. We would love to see more platforms +covered (arm64, ppc, mips) and OS/X would also be nice. + +We also publish our code-coverage status now: + +http://varnish-cache.org/gcov/ + +Our goal is 90+% coverage, but we need to finish implementing +terminal emulation in ``varnishtest`` before we can test the curses(1) +based programs (top/stat/hist) comprehensively, so they currently +drag us down. + News for authors of VMODs and Varnish API client applications ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ @@ -186,3 +259,17 @@ News for authors of VMODs and Varnish API client applications * All of the ``VSB_*`` functions for working with safe string buffers. + + +* VMOD version coexistence improvements: In difference from executable + files, shared libraries are not protected against overwriting under + UNIX, and this has generally caused grief when VMODs were updated + by package management tools. + + We have decided to bite the bullet, and now the Varnishd management + process makes a copy of the VMOD shared library to a version-unique + name inside the workdir, from which the running VCL access it. This + ensures that Varnishd can always restart the worker process, no matter + what happened to the original VMOD file. + + From phk at FreeBSD.org Thu Mar 9 07:05:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Thu, 09 Mar 2017 08:05:06 +0100 Subject: [master] 025011a Make vrt.h standalone again, and add test to ensure it stays that way. Message-ID: commit 025011aef4a78f4fed9fe798c28ce8cd9e7aa1d3 Author: Poul-Henning Kamp Date: Thu Mar 9 07:03:22 2017 +0000 Make vrt.h standalone again, and add test to ensure it stays that way. Fixes #2250 diff --git a/include/Makefile.am b/include/Makefile.am index 2df7780..0861385 100644 --- a/include/Makefile.am +++ b/include/Makefile.am @@ -124,13 +124,21 @@ CLEANFILES = \ tbl/vrt_stv_var.h \ vcl.h \ vrt_obj.h \ - vmod_abi.h + vmod_abi.h \ + vrt_test \ + _vrt_test -TESTS = vbm_test +TESTS = vbm_test vrt_test noinst_PROGRAMS = ${TESTS} vbm_test_SOURCES = vbm_test.c vbm.h +vrt_test_SOURCES = + +vrt_test: + echo "exec ${CC} -c -o _vrt_test $(top_srcdir)/include/vrt.h" > vrt_test + chmod +x vrt_test + test: ${TESTS} @for test in ${TESTS} ; do ./$${test} ; done diff --git a/include/vrt.h b/include/vrt.h index 0e86013..06080ea 100644 --- a/include/vrt.h +++ b/include/vrt.h @@ -65,6 +65,10 @@ /***********************************************************************/ +#ifndef __v_printflike +# define __v_printflike(a,b) +#endif + struct VCL_conf; struct vrt_acl; struct busyobj; From dridi.boukelmoune at gmail.com Thu Mar 9 08:38:05 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Thu, 09 Mar 2017 09:38:05 +0100 Subject: [master] b4bd652 The file descriptor is not leaked Message-ID: commit b4bd652373f6c1084038b38df7b22268cf80e70c Author: Dridi Boukelmoune Date: Thu Mar 9 09:24:44 2017 +0100 The file descriptor is not leaked Instead of passing it by value, make sure to have one variable holding the file descriptor. This should help Coverity stop complaining about a resource leak. The steps: 9. Condition vbp_write_proxy_v1(vt, s) != 0, taking true branch. 10. leaked_handle: Handle variable s going out of scope leaks the handle. If the return value is non-zero the socket is VTCP_close'd. Refs #2244 diff --git a/bin/varnishd/cache/cache_backend_probe.c b/bin/varnishd/cache/cache_backend_probe.c index 5dbf11f..b12b94b 100644 --- a/bin/varnishd/cache/cache_backend_probe.c +++ b/bin/varnishd/cache/cache_backend_probe.c @@ -222,22 +222,22 @@ vbp_reset(struct vbp_target *vt) */ static int -vbp_write(struct vbp_target *vt, int sock, const void *buf, size_t len) +vbp_write(struct vbp_target *vt, int *sock, const void *buf, size_t len) { int i; - i = write(sock, buf, len); + i = write(*sock, buf, len); if (i != len) { if (i < 0) vt->err_xmit |= 1; - VTCP_close(&sock); + VTCP_close(sock); return (-1); } return (0); } static int -vbp_write_proxy_v1(struct vbp_target *vt, int sock) +vbp_write_proxy_v1(struct vbp_target *vt, int *sock) { char buf[105]; /* maximum size for a TCP6 PROXY line with null char */ char addr[VTCP_ADDRBUFSIZE]; @@ -246,12 +246,12 @@ vbp_write_proxy_v1(struct vbp_target *vt, int sock) struct vsb vsb; socklen_t l; - VTCP_myname(sock, addr, sizeof addr, port, sizeof port); + VTCP_myname(*sock, addr, sizeof addr, port, sizeof port); AN(VSB_new(&vsb, buf, sizeof buf, VSB_FIXEDLEN)); AZ(VSB_cat(&vsb, "PROXY")); l = sizeof ss; - AZ(getsockname(sock, (void *)&ss, &l)); + AZ(getsockname(*sock, (void *)&ss, &l)); if (ss.ss_family == AF_INET6) VSB_printf(&vsb, " TCP6 "); else if (ss.ss_family == AF_INET) @@ -302,14 +302,14 @@ vbp_poke(struct vbp_target *vt) /* Send the PROXY header */ assert(vt->backend->proxy_header <= 2); if (vt->backend->proxy_header == 1) { - if (vbp_write_proxy_v1(vt, s) != 0) + if (vbp_write_proxy_v1(vt, &s) != 0) return; } else if (vt->backend->proxy_header == 2 && - vbp_write(vt, s, vbp_proxy_local, sizeof vbp_proxy_local) != 0) + vbp_write(vt, &s, vbp_proxy_local, sizeof vbp_proxy_local) != 0) return; /* Send the request */ - if (vbp_write(vt, s, vt->req, vt->req_len) != 0) + if (vbp_write(vt, &s, vt->req, vt->req_len) != 0) return; vt->good_xmit |= 1; From phk at FreeBSD.org Thu Mar 9 10:31:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Thu, 09 Mar 2017 11:31:05 +0100 Subject: [master] e706b22 Cargo-culting for glorious victory for autocrap hegemony Message-ID: commit e706b22af13c6c5db5267da2a6322fd71c013664 Author: Poul-Henning Kamp Date: Thu Mar 9 07:55:52 2017 +0000 Cargo-culting for glorious victory for autocrap hegemony diff --git a/include/Makefile.am b/include/Makefile.am index 0861385..781dfd9 100644 --- a/include/Makefile.am +++ b/include/Makefile.am @@ -136,7 +136,7 @@ vbm_test_SOURCES = vbm_test.c vbm.h vrt_test_SOURCES = -vrt_test: +vrt_test$(EXEEXT): echo "exec ${CC} -c -o _vrt_test $(top_srcdir)/include/vrt.h" > vrt_test chmod +x vrt_test From phk at FreeBSD.org Thu Mar 9 10:31:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Thu, 09 Mar 2017 11:31:05 +0100 Subject: [master] f5179ab Try to isolate this even better. Message-ID: commit f5179ab2c0dea8febdd8f3f2142c804591b29409 Author: Poul-Henning Kamp Date: Thu Mar 9 10:29:37 2017 +0000 Try to isolate this even better. Fixes #2250 (again) diff --git a/include/vrt.h b/include/vrt.h index 06080ea..34da0ac 100644 --- a/include/vrt.h +++ b/include/vrt.h @@ -65,8 +65,10 @@ /***********************************************************************/ -#ifndef __v_printflike -# define __v_printflike(a,b) +#ifdef __v_printflike +# define __vrt_printflike(a,b) __v_printflike(a,b) +#else +# define __vrt_printflike(a,b) #endif struct VCL_conf; @@ -300,7 +302,7 @@ struct http *VRT_selecthttp(VRT_CTX, enum gethdr_e); const char *VRT_GetHdr(VRT_CTX, const struct gethdr_s *); void VRT_SetHdr(VRT_CTX, const struct gethdr_s *, const char *, ...); void VRT_handling(VRT_CTX, unsigned hand); -void VRT_fail(VRT_CTX, const char *fmt, ...) __v_printflike(2,3); +void VRT_fail(VRT_CTX, const char *fmt, ...) __vrt_printflike(2,3); void VRT_hashdata(VRT_CTX, const char *str, ...); From geoff at uplex.de Thu Mar 9 10:40:07 2017 From: geoff at uplex.de (Geoff Simmons) Date: Thu, 09 Mar 2017 11:40:07 +0100 Subject: [master] d906981 The test for standalone vrt.h runs on compilers that insist on a .c source. Message-ID: commit d906981a2de991e03606b4c446a8cbb910463253 Author: Geoff Simmons Date: Thu Mar 9 11:28:30 2017 +0100 The test for standalone vrt.h runs on compilers that insist on a .c source. diff --git a/.gitignore b/.gitignore index f2993f7..74fb278 100644 --- a/.gitignore +++ b/.gitignore @@ -110,6 +110,10 @@ cscope.*out /bin/varnishtest/tests/*.log /bin/varnishtest/tests/*.log-t /bin/varnishtest/test-suite.log +/include/vrt.c +/include/_vrt_test +/include/vrt_test +/include/vrt_test.* # vtest.sh droppings tmp/ diff --git a/include/Makefile.am b/include/Makefile.am index 781dfd9..9996b37 100644 --- a/include/Makefile.am +++ b/include/Makefile.am @@ -126,7 +126,8 @@ CLEANFILES = \ vrt_obj.h \ vmod_abi.h \ vrt_test \ - _vrt_test + _vrt_test \ + vrt.c TESTS = vbm_test vrt_test @@ -134,10 +135,13 @@ noinst_PROGRAMS = ${TESTS} vbm_test_SOURCES = vbm_test.c vbm.h -vrt_test_SOURCES = +vrt_test_SOURCES = vrt.c -vrt_test$(EXEEXT): - echo "exec ${CC} -c -o _vrt_test $(top_srcdir)/include/vrt.h" > vrt_test +vrt.c: vrt.h + cp vrt.h vrt.c + +vrt_test$(EXEEXT): vrt.c + echo "exec ${CC} -c -o _vrt_test $(top_srcdir)/include/vrt.c" > vrt_test chmod +x vrt_test test: ${TESTS} From geoff at uplex.de Thu Mar 9 11:55:07 2017 From: geoff at uplex.de (Geoff Simmons) Date: Thu, 09 Mar 2017 12:55:07 +0100 Subject: [master] 5f267a4 Restructure the chapter headings in the performance doc in the User's Guide. It had subsections of the Cookies chapter that had nothing to do with them. Message-ID: commit 5f267a48f6b4c96023d13c327abf3f12d13f6dc8 Author: Geoff Simmons Date: Mon Mar 6 07:14:16 2017 +0100 Restructure the chapter headings in the performance doc in the User's Guide. It had subsections of the Cookies chapter that had nothing to do with them. diff --git a/doc/sphinx/users-guide/increasing-your-hitrate.rst b/doc/sphinx/users-guide/increasing-your-hitrate.rst index 38dcc86..fdfbd22 100644 --- a/doc/sphinx/users-guide/increasing-your-hitrate.rst +++ b/doc/sphinx/users-guide/increasing-your-hitrate.rst @@ -102,7 +102,7 @@ https://addons.mozilla.org/en-US/firefox/addon/3829/ or by googling The role of HTTP Headers -~~~~~~~~~~~~~~~~~~~~~~~~ +------------------------ Along with each HTTP request and response comes a bunch of headers carrying metadata. Varnish will look at these headers to determine if @@ -122,7 +122,7 @@ Let's take a look at the important headers you should be aware of: .. _users-guide-cookies: Cookies -------- +~~~~~~~ Varnish will, in the default configuration, not cache an object coming from the backend with a 'Set-Cookie' header present. Also, if the client @@ -135,7 +135,7 @@ cookie is used by the client side javascript and is therefore of no interest to the server. Cookies from the client -~~~~~~~~~~~~~~~~~~~~~~~ ++++++++++++++++++++++++ For a lot of web applications it makes sense to completely disregard the cookies unless you are accessing a special part of the web site. This @@ -216,7 +216,7 @@ Varnish Cache Wiki. Cookies coming from the backend -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ ++++++++++++++++++++++++++++++++ If your backend server sets a cookie using the 'Set-Cookie' header Varnish will not cache the page when using the default configuration. From geoff at uplex.de Thu Mar 9 11:55:07 2017 From: geoff at uplex.de (Geoff Simmons) Date: Thu, 09 Mar 2017 12:55:07 +0100 Subject: [master] 8cc11c1 Add chapters about cache misses and uncacheable content to the User's Guide. Primarily to document the varieties of pass (pass, hit-for-miss and hit-for-pass). Reviewed by Dridi. Message-ID: commit 8cc11c1c888677adf68d7126bafb1c3224e850e4 Author: Geoff Simmons Date: Thu Mar 9 12:51:37 2017 +0100 Add chapters about cache misses and uncacheable content to the User's Guide. Primarily to document the varieties of pass (pass, hit-for-miss and hit-for-pass). Reviewed by Dridi. diff --git a/doc/sphinx/users-guide/increasing-your-hitrate.rst b/doc/sphinx/users-guide/increasing-your-hitrate.rst index fdfbd22..8df31a8 100644 --- a/doc/sphinx/users-guide/increasing-your-hitrate.rst +++ b/doc/sphinx/users-guide/increasing-your-hitrate.rst @@ -383,3 +383,304 @@ So if you *really* need to vary based on 'User-Agent' be sure to normalize the header or your hit rate will suffer badly. Use the above code as a template. +Cache misses +------------ + +When Varnish does not find an object for a request in the cache, then +by default it performs a fetch from the backend on the hypothesis that +the response might be cached. This has two important consequences: + +* Concurrent backend requests for the same object are *coalesced* -- + only one fetch is executed at a time, and the other pending fetches + wait for the result (unless you have brought about one of the states + described below in :ref:`users-guide-uncacheable`). This is to + prevent your backend from being hit by a "thundering herd" when the + cached response has expired, or if it was never cached in the first + place. If it turns out that the response to the first fetch is + cached, then that cache object can be delivered immediately to other + pending requests. + +* The backend request for the cache miss cannot be conditional if + Varnish does not have an object in the cache to validate; that is, + it cannot contain the headers ``If-Modified-Since`` or + ``If-None-Match``, which might cause the backend to return status + "304 Not Modified" with no response body. Otherwise, there might not + be a response to cache. If those headers were present in the client + request, they are removed from the backend request. + +By setting a grace time for cached objects (default 10 seconds), you +allow Varnish to serve stale content while waiting for coalesced fetches, +which are run asynchronously while the stale response is sent to the +client. For details see :ref:`users-guide-handling_misbehaving_servers`. + +Although the headers for a conditional request are removed from the +backend fetch on a cache miss, Varnish may nevertheless respond to the +client request with "304 Not Modified" if the resulting response +allows it. At delivery time, if the client request had an +``If-None-Match`` header that matches the ``ETag`` header in the +response, or if the time in an ``If-Modified-Since`` request header is +equal to or later than the time in the ``Last-Modified`` response +header, Varnish will send the 304 response to the client. This happens +for both hits and misses. + +Varnish can send conditional requests to the backend if it has an +object in the cache against which the validation can be performed. You +can ensure that an object is retained for this purpose by setting +``beresp.keep`` in ``vcl_backend_response``:: + + sub vcl_backend_response { + # Keep the response in cache for 4 hours if the response has + # validating headers. + if (beresp.http.ETag || beresp.http.Last-Modified) { + set beresp.keep = 4h; + } + } + +A stale object is not removed from the cache for the duration of +``beresp.keep`` after its TTL and grace time have expired. This will +increase the storage requirements for your cache, but if you have the +space, it might be worth it to keep stale objects that can be +validated for a fairly long time. If the backend can send a 304 +response long after the TTL has expired, you save bandwith on the +fetch and reduce pressure on the storage; if not, then it's no +different from any other cache miss. + +If, however, you would prefer that backend fetches are not +conditional, just remove the If-* headers in ``vcl_backend_fetch``:: + + sub vcl_backend_fetch { + # To prevent conditional backend fetches. + unset bereq.http.If-None-Match; + unset bereq.http.If-Modified-Since; + } + +That should only be necessary if the conditional fetches are +problematic for the backend, for example if evaluating whether the +response is unchanged is too costly for the backend app, or if the +responses are just buggy. From the perspective of Varnish, 304 +responses are clearly preferable; fetches with the empty response body +save bandwidth, and storage does not have to be allocated in the +cache, since the existing cache object is re-used. + +To summarize, you can improve performance even in the case of cache +misses by: + +* ensuring that cached objects have a grace time during which a stale + object can be served to the client while fetches are performed in + the background, and + +* setting a keep time for cached objects that can be validated with + a 304 response after they have gone stale. + + +.. _users-guide-uncacheable: + +Uncacheable content +------------------- + +Some responses cannot be cached, for various reasons. The content may +be personalized, depending on the content of the ``Cookie`` header, or +it might just be the sort of thing that is generated anew on each +request. The cache can't help with that, but nevertheless there are +some decisions you can make that will help Varnish deal with +uncacheable responses in a way that is best for your requirements. + +The issues to consider are: + +* preventing request coalescing + +* whether (and how soon) the response for the same object may become + cacheable again + +* whether you want to pass along ``If-Modified-Since`` and + ``If-None-Match`` headers from the client request to the backend, to + allow the backend to respond with status 304 + +Passing client requests +~~~~~~~~~~~~~~~~~~~~~~~ + +Depending on how your site works, you may be able to recognize a +client request for a response that cannot be cached, for example if +the URL matches certain patterns, or due to the contents of a request +header. In that case, you can set the fetch to *pass* with +``return(pass)`` from ``vcl_recv``:: + + sub vcl_recv { + if (req.url ~ "^/this/is/personal/") { + return(pass); + } + } + +For passes there is no request coalescing. Since pass indicates that +the response will not be cacheable, there is no point in waiting for a +response that might be cached, and all pending fetches for the object +are concurrent. Otherwise, fetches waiting for an object that turns +out to be uncacheable after all may be serialized -- pending fetches +would wait for the first one, and when the result is not entered into +the cache, the next fetch begins while all of the others wait, and so +on. + +When a request is passed, this can be recognized in the +``vcl_backend_*`` subroutines by the fact that ``bereq.uncacheable`` +and ``beresp.uncachable`` are both true. The backend response will not +be cached, even if it fulfills conditions that otherwise would allow +it, for example if ``Cache-Control`` sets a positive TTL. + +Pass is the default (that is, ``builtin.vcl`` calls ``return(pass)`` in +``vcl_recv``) if the client request meets these conditions: + +* the request method is a standard HTTP/1.1 method, but not ``GET`` or + ``HEAD`` + +* there is either a ``Cookie`` or an ``Authorization`` header, indicating + that the response may be personalized + +If you want to override the default, say if you are certain that the +response may be cacheable despite the presence of a Cookie, make sure +that a ``return`` gets called at the end of any path that may be taken +through your own ``vcl_recv``. But if you do that, no part of the +built-in ``vcl_recv`` gets executed; so take a close look at +``vcl_recv`` in ``builtin.vcl``, and duplicate any part of it that you +require in your own ``vcl_recv``. + +As with cache hits and misses, Varnish decides to send a 304 response +to the client after a pass if the client request headers and the +response headers allow it. This might mean that Varnish will send a +304 response to the client even after the backend saw the same request +headers (``If-Modified-Since`` and/or ``If-None-Match``), but decided +not to respond with status 304, while nevertheless setting the +response headers ``ETag`` and/or ``Last-Modified`` so that 304 would +appear to be warranted. If you would prefer that Varnish doesn't do +that, then remove the If-* client request headers in ``vcl_pass``:: + + sub vcl_pass { + # To prevent 304 client responses after a pass. + unset req.http.If-None-Match; + unset req.http.If-Modified-Since; + } + +hit-for-miss +~~~~~~~~~~~~ + +You may not be able to recognize all requests for uncacheable content +in ``vcl_recv``. You might want to allow backends to determine their +own cacheability by setting the ``Cache-Control`` header, but that +cannot be seen until Varnish receives the backend response, so +``vcl_recv`` can't know about it. + +By default, if a request is not passed and the backend response turns +out to be uncacheable, the cache object is set to "hit-for-miss", by +setting ``beresp.uncacheable`` to ``true`` in +``vcl_backend_response``. A minimal object is saved in the cache, so +that the "hit-for-miss" state can be recognized on subsequent +lookups. (The cache is used to remember that the object is +uncacheable, for a limited time.) In that case, no request coalescing +is performed, so that fetches can run concurrently. Otherwise, fetches +for hit-for-miss are just like cache misses, meaning that: + +* the response may become cacheable on a later request, for example + if it sets a positive TTL with ``Cache-Control``, and + +* fetches cannot be conditional, so ``If-Modified-Since`` and + ``If-None-Match`` headers are removed from the backend request. + +When ``beresp.uncacheable`` is set to ``true``, then ``beresp.ttl`` +determines how long the hit-for-miss state may last at most. The +hit-for-miss state ends after this period of time elapses, or if a +cacheable response is returned by the backend before it elapses (the +elapse of ``beresp.ttl`` just means that the minimal cache object +expires, like any other cache object expiration). If a cacheable +response is returned, then that object replaces the hit-for-miss +object, and subsequent requests for it will be cache hits. If no +cacheable response is returned before ``beresp.ttl`` elapses, then the +next request for that object will be an ordinary miss, and hence will +be subject to request coalescing. + +When Varnish sees that it has hit a hit-for-miss object on a new +request, it executes ``vcl_miss``, so any custom VCL you have written +for cache misses will apply in the hit-for-miss case as well. + +``builtin.vcl`` sets ``beresp.uncacheable`` to ``true``, invoking the +hit-for-miss state, under a number of conditions that indicate that +the response cannot be cached, for example if the TTL was computed to +be 0 or if there is a ``Set-Cookie`` header. ``beresp.ttl`` is set to +two minutes by ``builtin.vcl`` in this case, so that is how long +hit-for-miss lasts by default. + +You can set ``beresp.uncacheable`` yourself if you need hit-for-miss +on other conditions:: + + sub vcl_backend_response { + if (beresp.http.X-This-Is == "personal") { + set beresp.uncacheable = true; + } + } + +Note that once ``beresp.uncacheable`` has been set to ``true`` it +cannot be set back to ``false``; attempts to do so in VCL are ignored. + +Although the backend fetches are never conditional for hit-for-miss, +Varnish may decide (as in all other cases) to send a 304 response to +the client if the client request headers and response headers ``ETag`` +or ``Last-Modified`` allow it. If you want to prevent that, remove +the If-* client request headers in ``vcl_miss``:: + + sub vcl_miss { + # To prevent 304 client responses on hit-for-miss. + unset req.http.If-None-Match; + unset req.http.If-Modified-Since; + } + +hit-for-pass +~~~~~~~~~~~~ + +A consequence of hit-for-miss is that backend fetches cannot be +conditional, since hit-for-miss allows subsequent responses to be +cacheable. This may be problematic for responses that are very large +and not cacheable, but may be validated with a 304 response. For +example, you may want clients to validate an object via the backend +every time, only sending the response when it has been changed. + +For a situation like this, you can set an object to "hit-for-pass" with +``return(pass(DURATION))`` from ``vcl_backend_response``, where the +DURATION determines how long the hit-for-pass state lasts:: + + sub vcl_backend_response { + # Set hit-for-pass for two minutes if TTL is 0 and response headers + # allow for validation. + if (beresp.ttl <= 0s && (beresp.http.ETag || beresp.http.Last-Modified)) { + return(pass(120s)); + } + } + +As with hit-for-miss, a minimal object is entered into the cache so +that the hit-for-pass state is recognized on subsequent requests. The +request is then processed as a pass, just as if ``vcl_recv`` had +returned pass. This means that there is no request coalescing, and +that ``If-Modified-Since`` and ``If-None-Match`` headers in the client +request are passed along to the backend, so that the backend response +may be 304. + +Varnish executes ``vcl_pass`` when it hits a hit-for-pass object. So +again, you can arrange for your own handling of both pass and +hit-for-pass with the same code in VCL. + +If you want to prevent Varnish from sending conditional requests to +the backend, then remove the If-* headers from the backend request in +``vcl_backend_fetch``, as shown above for cache misses. And if you +want to prevent Varnish from deciding at delivery time to send a 304 +response to the client based on the client request and response +headers, then remove the headers from the client request in +``vcl_pass``, as shown above for pass. + +The hit-for-pass state ends when the "hit-for-pass TTL" given in the +``return`` statement elapses. As with passes, the response to a +hit-for-pass fetch is never cached, even if it would otherwise fulfill +conditions for cacheability. So unlike hit-for-miss, it is not +possible to end the hit-for-pass state ahead of time with a cacheable +response. After the "hit-for-pass TTL" elapses, the next request for +that object is handled as an ordinary miss. + +hit-for-miss is the default treatment of uncacheable content. No part +of ``builtin.vcl`` invokes hit-for-pass, so if you need it, you have to +add the necessary ``return`` statement to your own VCL. From dridi.boukelmoune at gmail.com Thu Mar 9 13:15:07 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Thu, 09 Mar 2017 14:15:07 +0100 Subject: [master] 06f9176 A hash_always_miss can override a hit-for-pass Message-ID: commit 06f9176f68c1dfd3318b52ecd68530d2ba9fc111 Author: Dridi Boukelmoune Date: Thu Mar 9 14:13:45 2017 +0100 A hash_always_miss can override a hit-for-pass diff --git a/bin/varnishtest/tests/c00082.vtc b/bin/varnishtest/tests/c00082.vtc new file mode 100644 index 0000000..6d0c27b --- /dev/null +++ b/bin/varnishtest/tests/c00082.vtc @@ -0,0 +1,39 @@ +varnishtest "hash_always_miss overrides hit-for-pass" + +server s1 { + rxreq + txresp -hdr "Hit-Pass: forever" + + rxreq + txresp +} -start + +varnish v1 -vcl+backend { + sub vcl_recv { + set req.hash_always_miss = (req.http.Hash == "always-miss"); + } + + sub vcl_backend_response { + if (beresp.http.Hit-Pass == "forever") { + return (pass(1y)); + } + } + + sub vcl_deliver { + set resp.http.Obj-Hits = obj.hits; + } +} -start + +client c1 { + txreq + rxresp + expect resp.http.Obj-Hits == 0 + + txreq -hdr "Hash: always-miss" + rxresp + expect resp.http.Obj-Hits == 0 + + txreq + rxresp + expect resp.http.Obj-Hits == 1 +} -run From dridi.boukelmoune at gmail.com Thu Mar 9 13:41:05 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Thu, 09 Mar 2017 14:41:05 +0100 Subject: [master] 213a251 A hash_always_miss can override a hit-for-pass Message-ID: commit 213a251e7d8f70f5e0e86da38e9e70f8e35d283e Author: Dridi Boukelmoune Date: Thu Mar 9 14:39:20 2017 +0100 A hash_always_miss can override a hit-for-pass With a more assertive test this time. diff --git a/bin/varnishtest/tests/c00082.vtc b/bin/varnishtest/tests/c00082.vtc index 6d0c27b..65da5ad 100644 --- a/bin/varnishtest/tests/c00082.vtc +++ b/bin/varnishtest/tests/c00082.vtc @@ -2,9 +2,15 @@ varnishtest "hash_always_miss overrides hit-for-pass" server s1 { rxreq + expect req.http.Uncacheable == false txresp -hdr "Hit-Pass: forever" rxreq + expect req.http.Uncacheable == true + txresp + + rxreq + expect req.http.Uncacheable == false txresp } -start @@ -13,6 +19,10 @@ varnish v1 -vcl+backend { set req.hash_always_miss = (req.http.Hash == "always-miss"); } + sub vcl_backend_fetch { + set bereq.http.Uncacheable = bereq.uncacheable; + } + sub vcl_backend_response { if (beresp.http.Hit-Pass == "forever") { return (pass(1y)); @@ -24,11 +34,27 @@ varnish v1 -vcl+backend { } } -start +logexpect l1 -v v1 -g request { + expect * 1001 VCL_return lookup + expect * 1001 VCL_call MISS + expect * 1002 TTL "^HFP 31536000 " + expect * 1003 VCL_return lookup + expect * 1003 VCL_call PASS + expect * 1005 VCL_return lookup + expect * 1005 VCL_call MISS + expect * 1007 VCL_return lookup + expect * 1007 VCL_call HIT +} -start + client c1 { txreq rxresp expect resp.http.Obj-Hits == 0 + txreq + rxresp + expect resp.http.Obj-Hits == 0 + txreq -hdr "Hash: always-miss" rxresp expect resp.http.Obj-Hits == 0 @@ -37,3 +63,5 @@ client c1 { rxresp expect resp.http.Obj-Hits == 1 } -run + +logexpect l1 -wait From phk at FreeBSD.org Thu Mar 9 14:47:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Thu, 09 Mar 2017 15:47:05 +0100 Subject: [master] 3db2f6a Constify Message-ID: commit 3db2f6a0b74c48e41a220d41cf56d21531eeb4a2 Author: Poul-Henning Kamp Date: Thu Mar 9 14:45:59 2017 +0000 Constify diff --git a/bin/varnishd/cache/cache_backend_probe.c b/bin/varnishd/cache/cache_backend_probe.c index b12b94b..4c18854 100644 --- a/bin/varnishd/cache/cache_backend_probe.c +++ b/bin/varnishd/cache/cache_backend_probe.c @@ -92,7 +92,7 @@ static struct lock vbp_mtx; static pthread_cond_t vbp_cond; static struct binheap *vbp_heap; -static unsigned char vbp_proxy_local[] = { +static const unsigned char vbp_proxy_local[] = { 0x0d, 0x0a, 0x0d, 0x0a, 0x00, 0x0d, 0x0a, 0x51, 0x55, 0x49, 0x54, 0x0a, 0x20, 0x00, 0x00, 0x00, }; From phk at FreeBSD.org Thu Mar 9 14:47:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Thu, 09 Mar 2017 15:47:05 +0100 Subject: [master] 39ea60c Some work on H2 RST_STREAM and GOAWAY Message-ID: commit 39ea60c0e75276eac619306f0811560eba8c1a09 Author: Poul-Henning Kamp Date: Thu Mar 9 14:46:11 2017 +0000 Some work on H2 RST_STREAM and GOAWAY diff --git a/bin/varnishd/http2/cache_http2.h b/bin/varnishd/http2/cache_http2.h index cba5676..d6971d9 100644 --- a/bin/varnishd/http2/cache_http2.h +++ b/bin/varnishd/http2/cache_http2.h @@ -123,8 +123,11 @@ struct h2_req { int64_t window; struct h2h_decode *decode; - struct worker *tx_wrk; + /* Where to wake this stream up */ + struct worker *wrk; + VTAILQ_ENTRY(h2_req) tx_list; + h2_error error; }; VTAILQ_HEAD(h2_req_s, h2_req); @@ -159,12 +162,12 @@ struct h2_sess { struct h2_settings local_settings; struct req *new_req; - int go_away; - uint32_t go_away_last_stream; + uint32_t goaway_last_stream; VTAILQ_HEAD(,h2_req) txqueue; struct h2_req req0[1]; + h2_error error; }; /* http2/cache_http2_panic.c */ @@ -200,13 +203,13 @@ h2_error h2h_decode_bytes(struct h2_sess *h2, struct h2h_decode *d, /* cache_http2_send.c */ void H2_Send_Get(struct worker *, struct h2_sess *, struct h2_req *); -void H2_Send_Rel(struct worker *, struct h2_sess *, struct h2_req *); +void H2_Send_Rel(struct h2_sess *, const struct h2_req *); h2_error H2_Send_Frame(struct worker *, const struct h2_sess *, h2_frame type, uint8_t flags, uint32_t len, uint32_t stream, const void *); -h2_error H2_Send(struct worker *, struct h2_req *, int flush, +h2_error H2_Send(struct worker *, const struct h2_req *, h2_frame type, uint8_t flags, uint32_t len, const void *); /* cache_http2_proto.c */ @@ -216,6 +219,5 @@ void h2_del_req(struct worker *, struct h2_req *); int h2_rxframe(struct worker *, struct h2_sess *); h2_error h2_set_setting(struct h2_sess *, const uint8_t *); void h2_req_body(struct req*); - - - +h2_error H2_StreamError(uint32_t); +h2_error H2_ConnectionError(uint32_t); diff --git a/bin/varnishd/http2/cache_http2_deliver.c b/bin/varnishd/http2/cache_http2_deliver.c index 48f0513..f9a6fa1 100644 --- a/bin/varnishd/http2/cache_http2_deliver.c +++ b/bin/varnishd/http2/cache_http2_deliver.c @@ -85,11 +85,10 @@ h2_bytes(struct req *req, enum vdp_action act, void **priv, return (0); H2_Send_Get(req->wrk, r2->h2sess, r2); H2_Send(req->wrk, r2, - act != VDP_NULL ? 1 : 0, H2_F_DATA, act == VDP_FINI ? H2FF_DATA_END_STREAM : H2FF_NONE, len, ptr); - H2_Send_Rel(req->wrk, r2->h2sess, r2); + H2_Send_Rel(r2->h2sess, r2); return (0); } @@ -144,12 +143,12 @@ h2_minimal_response(struct req *req, uint16_t status) /* XXX return code checking once H2_Send returns anything but 0 */ H2_Send_Get(req->wrk, r2->h2sess, r2); - H2_Send(req->wrk, r2, 1, + H2_Send(req->wrk, r2, H2_F_HEADERS, H2FF_HEADERS_END_HEADERS | (status < 200 ? 0 : H2FF_HEADERS_END_STREAM), l, buf); - H2_Send_Rel(req->wrk, r2->h2sess, r2); + H2_Send_Rel(r2->h2sess, r2); return (0); } @@ -251,10 +250,10 @@ h2_deliver(struct req *req, struct boc *boc, int sendbody) sendbody = 0; H2_Send_Get(req->wrk, r2->h2sess, r2); - H2_Send(req->wrk, r2, 1, H2_F_HEADERS, + H2_Send(req->wrk, r2, H2_F_HEADERS, (sendbody ? 0 : H2FF_HEADERS_END_STREAM) | H2FF_HEADERS_END_HEADERS, sz, req->ws->f); - H2_Send_Rel(req->wrk, r2->h2sess, r2); + H2_Send_Rel(r2->h2sess, r2); WS_Release(req->ws, 0); diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index f22cb44..e22a1c9 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -42,7 +42,6 @@ #include "vtcp.h" #include "vtim.h" -#define H2EC0(U,v,d) #define H2EC1(U,v,d) const struct h2_error_s H2CE_##U[1] = {{#U,d,v,0,1}}; #define H2EC2(U,v,d) const struct h2_error_s H2SE_##U[1] = {{#U,d,v,1,0}}; #define H2EC3(U,v,d) H2EC1(U,v,d) H2EC2(U,v,d) @@ -52,6 +51,14 @@ #undef H2EC2 #undef H2EC3 +static const struct h2_error_s H2NN_ERROR[1] = {{ + "UNKNOWN_ERROR", + "Unknown error number", + 0xffffffff, + 1, + 1 +}}; + enum h2frame { #define H2_FRAME(l,u,t,f,...) H2F_##u = t, #include "tbl/h2_frames.h" @@ -75,6 +82,56 @@ h2_framename(enum h2frame h2f) /********************************************************************** */ +static const h2_error stream_errors[] = { +#define H2EC1(U,v,d) +#define H2EC2(U,v,d) [v] = H2SE_##U, +#define H2EC3(U,v,d) H2EC1(U,v,d) H2EC2(U,v,d) +#define H2_ERROR(NAME, val, sc, desc) H2EC##sc(NAME, val, desc) +#include "tbl/h2_error.h" +#undef H2EC1 +#undef H2EC2 +#undef H2EC3 +}; + +#define NSTREAMERRORS (sizeof(stream_errors)/sizeof(stream_errors[0])) + +h2_error +H2_StreamError(uint32_t u) +{ + if (u < NSTREAMERRORS && stream_errors[u] != NULL) + return (stream_errors[u]); + else + return (H2NN_ERROR); +} + +/********************************************************************** + */ + +static const h2_error conn_errors[] = { +#define H2EC1(U,v,d) [v] = H2CE_##U, +#define H2EC2(U,v,d) +#define H2EC3(U,v,d) H2EC1(U,v,d) H2EC2(U,v,d) +#define H2_ERROR(NAME, val, sc, desc) H2EC##sc(NAME, val, desc) +#include "tbl/h2_error.h" +#undef H2EC1 +#undef H2EC2 +#undef H2EC3 +}; + +#define NCONNERRORS (sizeof(conn_errors)/sizeof(conn_errors[0])) + +h2_error +H2_ConnectionError(uint32_t u) +{ + if (u < NCONNERRORS && conn_errors[u] != NULL) + return (conn_errors[u]); + else + return (H2NN_ERROR); +} + +/********************************************************************** + */ + struct h2_req * h2_new_req(const struct worker *wrk, struct h2_sess *h2, unsigned stream, struct req *req) @@ -189,7 +246,7 @@ h2_rx_ping(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) H2_Send_Get(wrk, h2, r2); H2_Send_Frame(wrk, h2, H2_F_PING, H2FF_PING_ACK, 8, 0, h2->rxf_data); - H2_Send_Rel(wrk, h2, r2); + H2_Send_Rel(h2, r2); return (0); } @@ -218,8 +275,11 @@ h2_rx_rst_stream(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) return (H2CE_FRAME_SIZE_ERROR); if (r2 == NULL) return (0); - INCOMPL(); - NEEDLESS(return (H2CE_PROTOCOL_ERROR)); + Lck_Lock(&h2->sess->mtx); + r2->error = H2_StreamError(vbe32dec(h2->rxf_data)); + if (r2->wrk != NULL) + AZ(pthread_cond_signal(&r2->wrk->cond)); + return (0); } /********************************************************************** @@ -228,14 +288,11 @@ h2_rx_rst_stream(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) static h2_error __match_proto__(h2_frame_f) h2_rx_goaway(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) { - uint32_t error; (void)wrk; (void)r2; - h2->go_away_last_stream = vbe32dec(h2->rxf_data); - error = vbe32dec(h2->rxf_data + 4); - /*XXX*/(void)error; - h2->go_away = 1; + h2->goaway_last_stream = vbe32dec(h2->rxf_data); + h2->error = H2_ConnectionError(vbe32dec(h2->rxf_data + 4)); return (0); } @@ -360,7 +417,7 @@ h2_rx_settings(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) H2_Send_Get(wrk, h2, r2); H2_Send_Frame(wrk, h2, H2_F_SETTINGS, H2FF_SETTINGS_ACK, 0, 0, NULL); - H2_Send_Rel(wrk, h2, r2); + H2_Send_Rel(h2, r2); } return (0); } @@ -639,7 +696,7 @@ h2_procframe(struct worker *wrk, struct h2_sess *h2, H2_Send_Get(wrk, h2, r2); (void)H2_Send_Frame(wrk, h2, H2_F_RST_STREAM, 0, sizeof b, h2->rxf_stream, b); - H2_Send_Rel(wrk, h2, r2); + H2_Send_Rel(h2, r2); h2_del_req(wrk, r2); return (0); @@ -734,7 +791,7 @@ h2_rxframe(struct worker *wrk, struct h2_sess *h2) vbe32enc(b + 4, h2e->val); H2_Send_Get(wrk, h2, h2->req0); (void)H2_Send_Frame(wrk, h2, H2_F_GOAWAY, 0, 8, 0, b); - H2_Send_Rel(wrk, h2, h2->req0); + H2_Send_Rel(h2, h2->req0); } return (h2e ? 0 : 1); } diff --git a/bin/varnishd/http2/cache_http2_send.c b/bin/varnishd/http2/cache_http2_send.c index 2acd39b..a220b1e 100644 --- a/bin/varnishd/http2/cache_http2_send.c +++ b/bin/varnishd/http2/cache_http2_send.c @@ -43,26 +43,28 @@ H2_Send_Get(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) CHECK_OBJ_NOTNULL(h2, H2_SESS_MAGIC); CHECK_OBJ_NOTNULL(r2, H2_REQ_MAGIC); - r2->tx_wrk = wrk; Lck_Lock(&h2->sess->mtx); + r2->wrk = wrk; VTAILQ_INSERT_TAIL(&h2->txqueue, r2, tx_list); while (VTAILQ_FIRST(&h2->txqueue) != r2) - Lck_CondWait(&wrk->cond, &h2->sess->mtx, 0); + AZ(Lck_CondWait(&wrk->cond, &h2->sess->mtx, 0)); + r2->wrk = NULL; Lck_Unlock(&h2->sess->mtx); } void -H2_Send_Rel(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) +H2_Send_Rel(struct h2_sess *h2, const struct h2_req *r2) { - CHECK_OBJ_NOTNULL(wrk, WORKER_MAGIC); CHECK_OBJ_NOTNULL(h2, H2_SESS_MAGIC); CHECK_OBJ_NOTNULL(r2, H2_REQ_MAGIC); Lck_Lock(&h2->sess->mtx); assert(VTAILQ_FIRST(&h2->txqueue) == r2); VTAILQ_REMOVE(&h2->txqueue, r2, tx_list); r2 = VTAILQ_FIRST(&h2->txqueue); - if (r2 != NULL) - AZ(pthread_cond_signal(&r2->tx_wrk->cond)); + if (r2 != NULL) { + CHECK_OBJ_NOTNULL(r2->wrk, WORKER_MAGIC); + AZ(pthread_cond_signal(&r2->wrk->cond)); + } Lck_Unlock(&h2->sess->mtx); } @@ -128,7 +130,7 @@ H2_Send_Frame(struct worker *wrk, const struct h2_sess *h2, */ h2_error -H2_Send(struct worker *wrk, struct h2_req *r2, int flush, +H2_Send(struct worker *wrk, const struct h2_req *r2, h2_frame ftyp, uint8_t flags, uint32_t len, const void *ptr) { h2_error retval; @@ -137,8 +139,6 @@ H2_Send(struct worker *wrk, struct h2_req *r2, int flush, const char *p; uint8_t final_flags; - (void)flush; - CHECK_OBJ_NOTNULL(wrk, WORKER_MAGIC); CHECK_OBJ_NOTNULL(r2, H2_REQ_MAGIC); h2 = r2->h2sess; @@ -147,6 +147,12 @@ H2_Send(struct worker *wrk, struct h2_req *r2, int flush, assert(VTAILQ_FIRST(&h2->txqueue) == r2); + if (r2->error) + return (r2->error); + + if (h2->error && r2->stream > h2->goaway_last_stream) + return (h2->error); + AN(ftyp); AZ(flags & ~(ftyp->flags)); if (r2->stream == 0) diff --git a/bin/varnishd/http2/cache_http2_session.c b/bin/varnishd/http2/cache_http2_session.c index 050ce4a..c125d8e 100644 --- a/bin/varnishd/http2/cache_http2_session.c +++ b/bin/varnishd/http2/cache_http2_session.c @@ -239,7 +239,7 @@ h2_new_pu_session(struct worker *wrk, const struct h2_sess *h2) /**********************************************************************/ static int -h2_new_ou_session(struct worker *wrk, struct h2_sess *h2, +h2_new_ou_session(const struct worker *wrk, struct h2_sess *h2, struct req *req) { ssize_t sz; @@ -343,7 +343,7 @@ h2_new_session(struct worker *wrk, void *arg) H2_Send_Get(wrk, h2, h2->req0); H2_Send_Frame(wrk, h2, H2_F_SETTINGS, H2FF_NONE, sizeof H2_settings, 0, H2_settings); - H2_Send_Rel(wrk, h2, h2->req0); + H2_Send_Rel(h2, h2->req0); /* and off we go... */ h2->cond = &wrk->cond; From dridi.boukelmoune at gmail.com Thu Mar 9 15:50:07 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Thu, 09 Mar 2017 16:50:07 +0100 Subject: [master] 3b70eaa Revert "Cargo-culting for glorious victory for autocrap hegemony" Message-ID: commit 3b70eaaed7e7b992cf912290127ce1f7878c1d85 Author: Dridi Boukelmoune Date: Thu Mar 9 14:50:21 2017 +0100 Revert "Cargo-culting for glorious victory for autocrap hegemony" This reverts commit e706b22af13c6c5db5267da2a6322fd71c013664. The real problem was solved in d906981a2de991e03606b4c446a8cbb910463253. The extension adds noise considering the make rules below don't comply with the target name. diff --git a/include/Makefile.am b/include/Makefile.am index 9996b37..3075147 100644 --- a/include/Makefile.am +++ b/include/Makefile.am @@ -140,7 +140,7 @@ vrt_test_SOURCES = vrt.c vrt.c: vrt.h cp vrt.h vrt.c -vrt_test$(EXEEXT): vrt.c +vrt_test: vrt.c echo "exec ${CC} -c -o _vrt_test $(top_srcdir)/include/vrt.c" > vrt_test chmod +x vrt_test From dridi.boukelmoune at gmail.com Thu Mar 9 15:50:07 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Thu, 09 Mar 2017 16:50:07 +0100 Subject: [master] 448d26c Fix VPATH builds Message-ID: commit 448d26c345371df59eac997b4fdb2e727722f32f Author: Dridi Boukelmoune Date: Thu Mar 9 14:58:47 2017 +0100 Fix VPATH builds We aren't building a vrt_test binary, it's a script. We also don't need to distribute vrt.c, the cost of a copy doesn't matter and it ensures that this file is always in the $(buildir). I also cleaned other wrong assumptions regarding $(srcdir) vs $(builddir). diff --git a/include/Makefile.am b/include/Makefile.am index 3075147..f6a08eb 100644 --- a/include/Makefile.am +++ b/include/Makefile.am @@ -131,18 +131,16 @@ CLEANFILES = \ TESTS = vbm_test vrt_test -noinst_PROGRAMS = ${TESTS} +noinst_PROGRAMS = vbm_test vbm_test_SOURCES = vbm_test.c vbm.h -vrt_test_SOURCES = vrt.c - vrt.c: vrt.h - cp vrt.h vrt.c + cp $(srcdir)/vrt.h $@ vrt_test: vrt.c - echo "exec ${CC} -c -o _vrt_test $(top_srcdir)/include/vrt.c" > vrt_test - chmod +x vrt_test + echo "exec ${CC} -c -o _vrt_test vrt.c" > $@ + chmod +x $@ test: ${TESTS} @for test in ${TESTS} ; do ./$${test} ; done diff --git a/lib/libvcc/generate.py b/lib/libvcc/generate.py index 4515940..fac8ee4 100755 --- a/lib/libvcc/generate.py +++ b/lib/libvcc/generate.py @@ -1417,7 +1417,7 @@ if i != "/* " + v + " */": fo.write('#define VCS_Branch "%s"\n' % b) fo.close() - for i in open(os.path.join(srcroot, "Makefile")): + for i in open(os.path.join(buildroot, "Makefile")): if i[:14] == "PACKAGE_STRING": break i = i.split("=")[1].strip() From geoff at uplex.de Thu Mar 9 16:03:06 2017 From: geoff at uplex.de (Geoff Simmons) Date: Thu, 09 Mar 2017 17:03:06 +0100 Subject: [master] 37de1a0 Document the use of req.hash_always_miss to end a hit-for-pass state. Message-ID: commit 37de1a0d4ee5935c7a714e9e406af5358b456b70 Author: Geoff Simmons Date: Thu Mar 9 17:02:22 2017 +0100 Document the use of req.hash_always_miss to end a hit-for-pass state. diff --git a/doc/sphinx/users-guide/increasing-your-hitrate.rst b/doc/sphinx/users-guide/increasing-your-hitrate.rst index 8df31a8..80eec9f 100644 --- a/doc/sphinx/users-guide/increasing-your-hitrate.rst +++ b/doc/sphinx/users-guide/increasing-your-hitrate.rst @@ -681,6 +681,14 @@ possible to end the hit-for-pass state ahead of time with a cacheable response. After the "hit-for-pass TTL" elapses, the next request for that object is handled as an ordinary miss. +It is possible to end the hit-for-pass state of a cache object by +setting ``req.hash_always_miss`` to ``true`` in ``vcl_recv`` for a +request that will hit the object (you'll have to write VCL that brings +that about). The request in which that happens is forced to be a cache +miss, and the state of the object afterwards depends on the +disposition of the backend response -- it may become a cache hit, +hit-for-miss, or may be set to hit-for-pass again. + hit-for-miss is the default treatment of uncacheable content. No part of ``builtin.vcl`` invokes hit-for-pass, so if you need it, you have to add the necessary ``return`` statement to your own VCL. From dridi.boukelmoune at gmail.com Thu Mar 9 16:35:07 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Thu, 09 Mar 2017 17:35:07 +0100 Subject: [master] 0e4174c Fail name checks early in varnishtest Message-ID: commit 0e4174c0d3187e126494443a9588ef3a6e5f2b1d Author: Dridi Boukelmoune Date: Thu Mar 9 17:30:56 2017 +0100 Fail name checks early in varnishtest It closes a race for barriers because the list could be updated by the top thread while walked by another thread. It also saves useless lookups by rejecting names earlier. This is not the case for servers because a) they have proper locking of the servers list and b) there is the dispatch special case. It would otherwise be harmless to do it for the server too because dispatched servers don't depend on user input. diff --git a/bin/varnishtest/vtc_barrier.c b/bin/varnishtest/vtc_barrier.c index 6a131a0..8cd80d9 100644 --- a/bin/varnishtest/vtc_barrier.c +++ b/bin/varnishtest/vtc_barrier.c @@ -74,7 +74,6 @@ barrier_new(const char *name, struct vtclog *vl) { struct barrier *b; - VTC_CHECK_NAME(vl, name, "Barrier", 'b'); ALLOC_OBJ(b, BARRIER_MAGIC); AN(b); if (pthread_self() != vtc_thread) @@ -436,6 +435,7 @@ cmd_barrier(CMD_ARGS) AZ(strcmp(av[0], "barrier")); av++; + VTC_CHECK_NAME(vl, av[0], "Barrier", 'b'); VTAILQ_FOREACH(b, &barriers, list) if (!strcmp(b->name, av[0])) break; diff --git a/bin/varnishtest/vtc_client.c b/bin/varnishtest/vtc_client.c index 24296ba..7f317ac 100644 --- a/bin/varnishtest/vtc_client.c +++ b/bin/varnishtest/vtc_client.c @@ -165,11 +165,10 @@ client_thread(void *priv) */ static struct client * -client_new(const char *name, struct vtclog *vl) +client_new(const char *name) { struct client *c; - VTC_CHECK_NAME(vl, name, "Client", 'c'); ALLOC_OBJ(c, CLIENT_MAGIC); AN(c); REPLACE(c->name, name); @@ -269,11 +268,12 @@ cmd_client(CMD_ARGS) AZ(strcmp(av[0], "client")); av++; + VTC_CHECK_NAME(vl, av[0], "Client", 'c'); VTAILQ_FOREACH(c, &clients, list) if (!strcmp(c->name, av[0])) break; if (c == NULL) - c = client_new(av[0], vl); + c = client_new(av[0]); av++; for (; *av != NULL; av++) { diff --git a/bin/varnishtest/vtc_logexp.c b/bin/varnishtest/vtc_logexp.c index 4bed257..45e856e 100644 --- a/bin/varnishtest/vtc_logexp.c +++ b/bin/varnishtest/vtc_logexp.c @@ -199,11 +199,10 @@ logexp_delete(struct logexp *le) } static struct logexp * -logexp_new(const char *name, struct vtclog *vl) +logexp_new(const char *name) { struct logexp *le; - VTC_CHECK_NAME(vl, name, "Logexpect", 'l'); ALLOC_OBJ(le, LOGEXP_MAGIC); AN(le); REPLACE(le->name, name); @@ -528,12 +527,13 @@ cmd_logexpect(CMD_ARGS) AZ(strcmp(av[0], "logexpect")); av++; + VTC_CHECK_NAME(vl, av[0], "Logexpect", 'l'); VTAILQ_FOREACH(le, &logexps, list) { if (!strcmp(le->name, av[0])) break; } if (le == NULL) - le = logexp_new(av[0], vl); + le = logexp_new(av[0]); av++; for (; *av != NULL; av++) { diff --git a/bin/varnishtest/vtc_process.c b/bin/varnishtest/vtc_process.c index 46d97ae..8960692 100644 --- a/bin/varnishtest/vtc_process.c +++ b/bin/varnishtest/vtc_process.c @@ -85,13 +85,12 @@ static VTAILQ_HEAD(, process) processes = } while (0) static struct process * -process_new(const char *name, struct vtclog *vl) +process_new(const char *name) { struct process *p; struct vsb *vsb; char buf[1024]; - VTC_CHECK_NAME(vl, name, "Process", 'p'); ALLOC_OBJ(p, PROCESS_MAGIC); AN(p); REPLACE(p->name, name); @@ -455,11 +454,12 @@ cmd_process(CMD_ARGS) AZ(strcmp(av[0], "process")); av++; + VTC_CHECK_NAME(vl, av[0], "Process", 'p'); VTAILQ_FOREACH(p, &processes, list) if (!strcmp(p->name, av[0])) break; if (p == NULL) - p = process_new(av[0], vl); + p = process_new(av[0]); av++; for (; *av != NULL; av++) { diff --git a/bin/varnishtest/vtc_varnish.c b/bin/varnishtest/vtc_varnish.c index 26d478d..5941848 100644 --- a/bin/varnishtest/vtc_varnish.c +++ b/bin/varnishtest/vtc_varnish.c @@ -268,13 +268,12 @@ varnishlog_thread(void *priv) */ static struct varnish * -varnish_new(const char *name, struct vtclog *vl) +varnish_new(const char *name) { struct varnish *v; struct vsb *vsb; char buf[1024]; - VTC_CHECK_NAME(vl, name, "Varnish", 'v'); ALLOC_OBJ(v, VARNISH_MAGIC); AN(v); REPLACE(v->name, name); @@ -1075,11 +1074,12 @@ cmd_varnish(CMD_ARGS) AZ(strcmp(av[0], "varnish")); av++; + VTC_CHECK_NAME(vl, av[0], "Varnish", 'v'); VTAILQ_FOREACH(v, &varnishes, list) if (!strcmp(v->name, av[0])) break; if (v == NULL) - v = varnish_new(av[0], vl); + v = varnish_new(av[0]); av++; for (; *av != NULL; av++) { From phk at FreeBSD.org Thu Mar 9 23:47:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Fri, 10 Mar 2017 00:47:05 +0100 Subject: [master] 0bc64c6 A bit more H2 polishing in the train. Message-ID: commit 0bc64c600c3707cbab4a176230105f39fd3ea76b Author: Poul-Henning Kamp Date: Thu Mar 9 23:46:40 2017 +0000 A bit more H2 polishing in the train. diff --git a/bin/varnishd/http2/cache_http2_session.c b/bin/varnishd/http2/cache_http2_session.c index c125d8e..0b063b7 100644 --- a/bin/varnishd/http2/cache_http2_session.c +++ b/bin/varnishd/http2/cache_http2_session.c @@ -202,7 +202,8 @@ h2_b64url_settings(struct h2_sess *h2, struct req *req) n -= 8; if (up == u + sizeof u) { AZ(n); - h2_set_setting(h2, (void*)u); + if (h2_set_setting(h2, (void*)u)) + return (-1); up = u; } } @@ -245,10 +246,15 @@ h2_new_ou_session(const struct worker *wrk, struct h2_sess *h2, ssize_t sz; enum htc_status_e hs; + + if (h2_b64url_settings(h2, req)) { + VSLb(h2->vsl, SLT_Debug, "H2: Bad HTTP-Settings"); + return (0); + } + sz = write(h2->sess->fd, h2_resp_101, strlen(h2_resp_101)); assert(sz == strlen(h2_resp_101)); - AZ(h2_b64url_settings(h2, req)); http_Unset(req->http, H_Upgrade); http_Unset(req->http, H_HTTP2_Settings); @@ -270,18 +276,15 @@ h2_new_ou_session(const struct worker *wrk, struct h2_sess *h2, req->task.priv = req; req->err_code = 0; http_SetH(req->http, HTTP_HDR_PROTO, "HTTP/2.0"); - XXXAZ(Pool_Task(wrk->pool, &req->task, TASK_QUEUE_REQ)); /* Wait for PRISM response */ hs = HTC_RxStuff(h2->htc, H2_prism_complete, NULL, NULL, NAN, h2->sess->t_idle + cache_param->timeout_idle, 256); if (hs != HTC_S_COMPLETE) { - /* XXX clean up req thread */ VSLb(h2->vsl, SLT_Debug, "H2: No OU PRISM (hs=%d)", hs); - Req_Release(req); - SES_Delete(h2->sess, SC_RX_JUNK, NAN); return (0); } + XXXAZ(Pool_Task(wrk->pool, &req->task, TASK_QUEUE_REQ)); HTC_RxPipeline(h2->htc, h2->htc->rxbuf_b + sizeof(H2_prism)); HTC_RxInit(h2->htc, h2->ws); VSLb(h2->vsl, SLT_Debug, "H2: Got PRISM"); @@ -335,8 +338,13 @@ h2_new_session(struct worker *wrk, void *arg) if (req->err_code == H2_PU_MARKER && !h2_new_pu_session(wrk, h2)) return; - if (req->err_code == H2_OU_MARKER && !h2_new_ou_session(wrk, h2, req)) + if (req->err_code == H2_OU_MARKER && !h2_new_ou_session(wrk, h2, req)) { + CNT_AcctLogCharge(wrk->stats, req); + VCL_Rel(&req->vcl); + Req_Release(req); + SES_Delete(h2->sess, SC_RX_JUNK, NAN); return; + } THR_SetRequest(h2->srq); diff --git a/bin/varnishtest/tests/t02001.vtc b/bin/varnishtest/tests/t02001.vtc index dafcded..d461f53 100644 --- a/bin/varnishtest/tests/t02001.vtc +++ b/bin/varnishtest/tests/t02001.vtc @@ -61,6 +61,31 @@ client c1 { } -run } -run +client c1 { + # Illegal HTTP2-Settings + send "GET /noupgrade HTTP/1.1\r\n" + send "Host: foo.bar\r\n" + send "Upgrade: h2c\r\n" + send "HTTP2-Settings: #######\r\n" + send "\r\n" + expect_close +} -run + +client c1 { + # PRISM with error in last bit + send "GET /noupgrade HTTP/1.1\r\n" + send "Host: foo.bar\r\n" + send "Upgrade: h2c\r\n" + send "HTTP2-Settings: AAMAAABkAAQAAP__\r\n" + send "\r\n" + rxresp + expect resp.status == 101 + expect resp.http.upgrade == h2c + expect resp.http.connection == Upgrade + sendhex "505249202a20485454502f322e300d0a0d0a534d0d0a0d0b" + expect_close +} -run + # XXX: Tests temporarily neutered, they are too flakey #varnish v1 -expect MEMPOOL.req0.live == 0 #varnish v1 -expect MEMPOOL.req1.live == 0 From phk at FreeBSD.org Fri Mar 10 06:47:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Fri, 10 Mar 2017 07:47:05 +0100 Subject: [master] 8cecc14 Simplify Message-ID: commit 8cecc142221aa7e65521761d64c8254c5b448694 Author: Poul-Henning Kamp Date: Fri Mar 10 06:45:50 2017 +0000 Simplify diff --git a/bin/varnishd/http2/cache_http2.h b/bin/varnishd/http2/cache_http2.h index d6971d9..ff49237 100644 --- a/bin/varnishd/http2/cache_http2.h +++ b/bin/varnishd/http2/cache_http2.h @@ -144,6 +144,8 @@ struct h2_sess { uint32_t highest_stream; int bogosity; + struct h2_req *req0; + struct h2_req_s streams; struct req *srq; @@ -166,7 +168,6 @@ struct h2_sess { VTAILQ_HEAD(,h2_req) txqueue; - struct h2_req req0[1]; h2_error error; }; diff --git a/bin/varnishd/http2/cache_http2_session.c b/bin/varnishd/http2/cache_http2_session.c index 0b063b7..46dbd6c 100644 --- a/bin/varnishd/http2/cache_http2_session.c +++ b/bin/varnishd/http2/cache_http2_session.c @@ -109,8 +109,6 @@ h2_new_sess(const struct worker *wrk, struct sess *sp, struct req *srq) SES_Reserve_xport_priv(sp, &up); *up = (uintptr_t)h2; - INIT_OBJ(h2->req0, H2_REQ_MAGIC); - h2->req0->h2sess = h2; } AN(up); CAST_OBJ_NOTNULL(h2, (void*)(*up), H2_SESS_MAGIC); @@ -215,7 +213,7 @@ h2_b64url_settings(struct h2_sess *h2, struct req *req) /**********************************************************************/ static int -h2_new_pu_session(struct worker *wrk, const struct h2_sess *h2) +h2_pu_session(struct worker *wrk, const struct h2_sess *h2) { enum htc_status_e hs; @@ -240,7 +238,7 @@ h2_new_pu_session(struct worker *wrk, const struct h2_sess *h2) /**********************************************************************/ static int -h2_new_ou_session(const struct worker *wrk, struct h2_sess *h2, +h2_ou_session(const struct worker *wrk, struct h2_sess *h2, struct req *req) { ssize_t sz; @@ -333,12 +331,10 @@ h2_new_session(struct worker *wrk, void *arg) h2 = h2_new_sess(wrk, sp, req->err_code == H2_PU_MARKER ? req : NULL); wsp = WS_Snapshot(h2->ws); - (void)h2_new_req(wrk, h2, 0, NULL); + h2->req0 = h2_new_req(wrk, h2, 0, NULL); - if (req->err_code == H2_PU_MARKER && !h2_new_pu_session(wrk, h2)) - return; - - if (req->err_code == H2_OU_MARKER && !h2_new_ou_session(wrk, h2, req)) { + if ((req->err_code == H2_PU_MARKER && !h2_pu_session(wrk, h2)) || + (req->err_code == H2_OU_MARKER && !h2_ou_session(wrk, h2, req))) { CNT_AcctLogCharge(wrk->stats, req); VCL_Rel(&req->vcl); Req_Release(req); From phk at FreeBSD.org Fri Mar 10 07:38:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Fri, 10 Mar 2017 08:38:05 +0100 Subject: [master] d430063 Simplify Message-ID: commit d4300630e5d7c4c7b3f9c7013e8aae95236c323b Author: Poul-Henning Kamp Date: Fri Mar 10 07:37:04 2017 +0000 Simplify diff --git a/bin/varnishd/http2/cache_http2_session.c b/bin/varnishd/http2/cache_http2_session.c index 46dbd6c..e6c6973 100644 --- a/bin/varnishd/http2/cache_http2_session.c +++ b/bin/varnishd/http2/cache_http2_session.c @@ -210,30 +210,6 @@ h2_b64url_settings(struct h2_sess *h2, struct req *req) return (0); } -/**********************************************************************/ - -static int -h2_pu_session(struct worker *wrk, const struct h2_sess *h2) -{ - enum htc_status_e hs; - - (void)wrk; - - hs = H2_prism_complete(h2->htc); - if (hs == HTC_S_MORE) { - VSLb(h2->vsl, SLT_Debug, "Short pu PRISM"); - return (0); - } - if (hs != HTC_S_COMPLETE) { - VSLb(h2->vsl, SLT_Debug, "Wrong pu PRISM"); - return (0); - } - HTC_RxPipeline(h2->htc, h2->htc->rxbuf_b + sizeof(H2_prism)); - HTC_RxInit(h2->htc, h2->ws); - - VSLb(h2->vsl, SLT_Debug, "H2: Got pu PRISM"); - return (1); -} /**********************************************************************/ @@ -244,7 +220,6 @@ h2_ou_session(const struct worker *wrk, struct h2_sess *h2, ssize_t sz; enum htc_status_e hs; - if (h2_b64url_settings(h2, req)) { VSLb(h2->vsl, SLT_Debug, "H2: Bad HTTP-Settings"); return (0); @@ -283,9 +258,6 @@ h2_ou_session(const struct worker *wrk, struct h2_sess *h2, return (0); } XXXAZ(Pool_Task(wrk->pool, &req->task, TASK_QUEUE_REQ)); - HTC_RxPipeline(h2->htc, h2->htc->rxbuf_b + sizeof(H2_prism)); - HTC_RxInit(h2->htc, h2->ws); - VSLb(h2->vsl, SLT_Debug, "H2: Got PRISM"); return (1); } @@ -333,14 +305,17 @@ h2_new_session(struct worker *wrk, void *arg) wsp = WS_Snapshot(h2->ws); h2->req0 = h2_new_req(wrk, h2, 0, NULL); - if ((req->err_code == H2_PU_MARKER && !h2_pu_session(wrk, h2)) || - (req->err_code == H2_OU_MARKER && !h2_ou_session(wrk, h2, req))) { + if (req->err_code == H2_OU_MARKER && !h2_ou_session(wrk, h2, req)) { CNT_AcctLogCharge(wrk->stats, req); VCL_Rel(&req->vcl); Req_Release(req); SES_Delete(h2->sess, SC_RX_JUNK, NAN); return; } + assert(HTC_S_COMPLETE == H2_prism_complete(h2->htc)); + HTC_RxPipeline(h2->htc, h2->htc->rxbuf_b + sizeof(H2_prism)); + HTC_RxInit(h2->htc, h2->ws); + VSLb(h2->vsl, SLT_Debug, "H2: Got pu PRISM"); THR_SetRequest(h2->srq); From geoff at uplex.de Fri Mar 10 11:09:06 2017 From: geoff at uplex.de (Geoff Simmons) Date: Fri, 10 Mar 2017 12:09:06 +0100 Subject: [master] aac0281 Start filling out "Upgrading to Varnish 5.1". Message-ID: commit aac0281b6fa3fa1e51861e1e4bf6715934454ac0 Author: Geoff Simmons Date: Fri Mar 10 12:04:43 2017 +0100 Start filling out "Upgrading to Varnish 5.1". So far this what I find in the commit log from varnish-5.0.0 until the beginning of 2017. Some "biggies" still to be mentioned are: * varnishd command-line options * VCl type conversions, stringification etc. * ranges? diff --git a/doc/sphinx/whats-new/changes-5.1.rst b/doc/sphinx/whats-new/changes-5.1.rst index 2e4e877..b1bf6ad 100644 --- a/doc/sphinx/whats-new/changes-5.1.rst +++ b/doc/sphinx/whats-new/changes-5.1.rst @@ -203,6 +203,8 @@ removing the ``ETag`` or ``Last-Modified`` headers in ``vcl_backend_response``, or by removing the If-* client request headers in ``vcl_pass``. +.. _whatsnew_changes_5.1_vtest: + Project tool improvements ~~~~~~~~~~~~~~~~~~~~~~~~~ diff --git a/doc/sphinx/whats-new/upgrading-5.1.rst b/doc/sphinx/whats-new/upgrading-5.1.rst index 7291736..c6186f6 100644 --- a/doc/sphinx/whats-new/upgrading-5.1.rst +++ b/doc/sphinx/whats-new/upgrading-5.1.rst @@ -4,15 +4,143 @@ Upgrading to Varnish 5.1 %%%%%%%%%%%%%%%%%%%%%%%% +varnishd command-line options +============================= + +* Added the ``workuser`` parameter to the ``-j`` option. + +varnishd parameters +=================== + +* The size of the shared memory log is now limited to 4G-1b + (4294967295 bytes). This places upper bounds on the ``-l`` + command-line option and on the ``vsl_space`` and ``vsm_space`` + parameters. + +* Added ``clock_step`` and ``thread_pool_reserve`` (see + :ref:`ref_param_clock_step`, :ref:`ref_param_thread_pool_reserve`). + +* ``thread_pool_stack`` is no longer considered experimental, and is + more extensively documented, see :ref:`ref_param_thread_pool_stack`. + +* ``thread_queue_limit`` only applies to queued client requests, see + :ref:`ref_param_thread_queue_limit`. + +* All parameters are defined on every platform, including those that + that are not functional on every platform. Most of these involve + features of the TCP stack, such as ``tcp_keepalive_intvl``, + ``tcp_keepalive_probes``, ``accept_filter`` and ``tcp_fastopen``. + The unavailability of a parameter is documented in the output of the + ``param.show`` command. Setting such a parameter is not an error, + but has no effect. + + Changes to VCL ============== +Type conversions +~~~~~~~~~~~~~~~~ + +* When ``bereq.backend`` and ``beresp.backend`` are set to a director, + then they return an actual backend on subsequent reads if the + director resolves to a backend immediately, or the director otherwise. + When used in string context, they return the name of the director + or of the resolved backend. + +* DURATION types may be used in boolean contexts, and are evaluated as + false when the duration is less than or equal to zero, true + otherwise. + +Response codes +~~~~~~~~~~~~~~ + +Response codes 1000 or greater may now be set in VCL internally. +``resp.status`` is delivered modulo 1000 in client responses. + +IP address comparison +~~~~~~~~~~~~~~~~~~~~~ + +IP addresses can now be compared for equality:: + + if (client.ip == remote.ip) { + call do_if_equal; + } + +The objects are equal if they designate equal socket addresses, not +including the port number. IPv6 addresses are always unequal to IPv4 +addresses (the comparison cannot consider v4-mapped IPv6 addresses). + +The STEVEDORE type and storage objects +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +The data type STEVEDORE for storage backends is now available in VCL +and for VMODs. Storage objects with names of the form +``storage.SNAME`` will exist in a VCL instance, where ``SNAME`` is the +name of a storage backend provided with the ``varnishd`` command-line +option ``-s``. If no ``-s`` option is given, then ``storage.s0`` +denotes the default storage. The object ``storage.Transient`` always +exists, designating transient storage. See :ref:`guide-storage`, and +the notes about ``beresp.storage`` and ``req.storage`` below. + +All VCL subroutines (except ``vcl_fini``) +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +* Added ``return(fail)`` to immediately terminate VCL processing. In + all cases but ``vcl_synth``, control is directed to ``vcl_synth`` + with ``resp.status`` and ``resp.reason`` set to 503 and "VCL + failed", respectively. ``vcl_synth`` is aborted on ``return(fail)``. + ``vcl_fini`` is executed whan a VCL instance in unloaded (enters the + COLD state) and has no failure condition. + +Client-side VCL subroutines +~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +* ``req.ttl`` is deprecated, see :ref:`vcl(7)`. + +vcl_recv +~~~~~~~~ + +* Added ``req.storage``, which tells Varnish which storage backend to + use if you choose to save the request body (see + :ref:`func_cache_req_body`). + vcl_backend_response ~~~~~~~~~~~~~~~~~~~~ * Added ``return(pass(DURATION))`` to set an object to hit-for-pass, see :ref:`whatsnew_changes_5.1_hitpass`. +* The object ``beresp.storage`` of type STEVEDORE should now be used + to set a storage backend; ``beresp.storage_hint`` is deprecated and + will be removed in a future release. Setting ``beresp.storage_hint`` + to a valid storage will set ``beresp.storage`` as well. If the + storage is invalid, ``beresp.storage`` is left untouched. + +When multiple storage backends have been defined with the ``-s`` +command-line option for varnishd, but none is explicitly set in +``vcl_backend_response``, storage selection and the use of the nuke +limit has been reworked (see :ref:`ref_param_nuke_limit`). Previously, +a storage backend was tried first with a nuke limit of 0, and retried +on failure with the limit configured as the ``-p`` parameter +``nuke_limit``. When no storage was specfied, Varnish went through +every one in round-robin order with a nuke limit of 0 before retrying. + +Now ``beresp.storage`` is initialized with a storage backend before +``vcl_backend_response`` executes, and the storage set in +``beresp.storage`` after its execution will be used. The configured +nuke limit is used in all cases. + +vcl_backend_error +~~~~~~~~~~~~~~~~~ + +* ``beresp.backend.ip`` is only available when the backend connection + is open, and hence not in ``vcl_backend_error``. + +VMOD std +~~~~~~~~ + +* Added ``std.getenv()``, see :ref:`func_getenv`. + Other changes ============= @@ -33,3 +161,25 @@ Other changes * An entry with the ``TTL`` tag and the prefix ``HFP`` is logged to record the duration set for hit-for-pass objects. + +* ``varnishncsa(1)``: + + * Clarified the meaning of the ``%r`` formatter, see NOTES in + :ref:`varnishncsa(1)`. + +* ``varnishtest(1)``: + + * Added the ``process`` and ``setenv`` commands, see :ref:`vtc(7)` . + + * ``-reason`` replaces ``-msg`` to set the reason string for a + response (default "OK"). + + * Added ``-cliexpect`` to match expected CLI responses to regular + expressions. + + * ``varnishtest`` can be stopped with the ``TERM``, ``INT`` of ``KILL`` + signals, but not with ``HUP``. These signals kill the process group, + so that processes started by running tests are stopped. + +* Added the ``vtest.sh`` tool to automate test builds, see + :ref:`whatsnew_changes_5.1_vtest`. From phk at FreeBSD.org Fri Mar 10 12:31:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Fri, 10 Mar 2017 13:31:05 +0100 Subject: [master] 28f4e1f Tweak a couple of -l options and drop an needless -s option Message-ID: commit 28f4e1f828365eda527375e9f80e8e59034d9059 Author: Poul-Henning Kamp Date: Fri Mar 10 12:10:44 2017 +0000 Tweak a couple of -l options and drop an needless -s option diff --git a/bin/varnishtest/tests/a00009.vtc b/bin/varnishtest/tests/a00009.vtc index ca0f299..f6e2a39 100644 --- a/bin/varnishtest/tests/a00009.vtc +++ b/bin/varnishtest/tests/a00009.vtc @@ -42,7 +42,7 @@ shell -err -expect {Neither -b nor -f given} { varnishd -n ${tmpdir}/v0 } # Test -F mode with no VCL loaded -process p1 "exec varnishd -n ${tmpdir}/v1 -F -f '' -a :0 -l2m,3m -s malloc,1m" -log -start +process p1 "exec varnishd -n ${tmpdir}/v1 -F -f '' -a :0 -l2m,1m" -log -start delay 2 diff --git a/bin/varnishtest/tests/a00016.vtc b/bin/varnishtest/tests/a00016.vtc index 963210f..354b01f 100644 --- a/bin/varnishtest/tests/a00016.vtc +++ b/bin/varnishtest/tests/a00016.vtc @@ -9,5 +9,5 @@ shell -err -expect {Error: -I file CLI command failed (104)} { echo "vcl.list" > foo echo "-foobar" >> foo echo "vcl.load" >> foo - varnishd -f '' -I foo -n ${tmpdir}/v0 -a :0 + varnishd -f '' -I foo -n ${tmpdir}/v0 -a :0 -l 2m,1m } From phk at FreeBSD.org Fri Mar 10 12:31:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Fri, 10 Mar 2017 13:31:05 +0100 Subject: [master] ae60839 Split this test in two, A9 was getting too many C-compiler invocations for the gcov vtester to finish in 60 seconds. Message-ID: commit ae60839616f099c80237720498bed4fa23ae0eba Author: Poul-Henning Kamp Date: Fri Mar 10 12:29:56 2017 +0000 Split this test in two, A9 was getting too many C-compiler invocations for the gcov vtester to finish in 60 seconds. diff --git a/bin/varnishtest/tests/a00009.vtc b/bin/varnishtest/tests/a00009.vtc index f6e2a39..abe4c85 100644 --- a/bin/varnishtest/tests/a00009.vtc +++ b/bin/varnishtest/tests/a00009.vtc @@ -5,101 +5,45 @@ shell -err -expect {VCL version declaration missing} { echo 'bad vcl' > ${tmpdir}/bad.vcl varnishd -f ${tmpdir}/bad.vcl -n ${tmpdir} } -shell -err -expect {VCL version declaration missing} { - echo 'bad vcl' > ${tmpdir}/bad.vcl - varnishd -C -f ${tmpdir}/bad.vcl -n ${tmpdir} -} -shell -err -expect {-spersistent has been deprecated} "varnishd -spersistent -f '' " -shell -err -expect {Unknown jail method "xyz"} "varnishd -jxyz -f '' " shell -err -expect {-x must be the first argument} "varnishd -d -x foo " +shell -err -expect {-V must be the first argument} "varnishd -d -V foo " + shell -err -expect {Too many arguments for -x} "varnishd -x foo bar" shell -err -expect {Invalid -x argument} "varnishd -x foo " +shell -err -expect {Option 'A' unknown.} "varnishd -A " +shell -err -expect {Usage: varnishd [options]} "varnishd -? " +shell -err -expect {Too many arguments} "varnishd foo " + shell "varnishd -x parameter > ${tmpdir}/_.param" shell "varnishd -x vsl > ${tmpdir}/_.vsl" shell "varnishd -x cli > ${tmpdir}/_.cli" shell "varnishd -x builtin > ${tmpdir}/_.builtin" -shell -err -expect {-V must be the first argument} "varnishd -d -V foo " -shell -err -expect {Too many arguments for -V} "varnishd -V -V" -shell -expect {Copyright (c) 2006} "varnishd -V" - -shell -err -expect {Too many arguments} "varnishd foo " -shell -err -expect {Only one of -d or -F can be specified} "varnishd -d -F " -shell -err -expect {Only one of -b or -f can be specified} "varnishd -b a -f b " -shell -err -expect {-C needs either -b or -f } \ - "varnishd -C " -shell -err -expect {-d makes no sense with -C} "varnishd -C -b 127.0.0.1:80 -d " -shell -err -expect {-F makes no sense with -C} "varnishd -C -b 127.0.0.1:80 -F " -shell -err -expect {Usage: varnishd [options]} "varnishd -? " -shell -err -expect {Invalid backslash sequence} {varnishd -l 'xyz\kk,xyz\foo' -f '' } -shell -err -expect {Invalid backslash sequence} {varnishd -l 'ab\8cd' -f '' } -shell -err -expect {Option 'A' unknown.} "varnishd -A " -shell -err -expect {Cannot open -S file} { - varnishd -S ${tmpdir}/nonexistent -n ${tmpdir}/v0 -f '' +shell -err -expect {-spersistent has been deprecated} { + varnishd -spersistent -f '' } -shell -err -expect {Neither -b nor -f given} { varnishd -n ${tmpdir}/v0 } -# Test -F mode with no VCL loaded - -process p1 "exec varnishd -n ${tmpdir}/v1 -F -f '' -a :0 -l2m,1m" -log -start - -delay 2 - -shell { - ( - echo 'vcl 4.0;' - echo 'backend default {' - echo ' .host="${bad_backend}";' - echo '}' - ) > ${tmpdir}/vcl +shell -err -expect {-C needs either -b or -f } { + varnishd -C } - -shell -expect {VCL compiled.} { - varnishadm -n ${tmpdir}/v1 vcl.load vcl1 ${tmpdir}/vcl +shell -err -expect {Cannot open -S file} { + varnishd -S ${tmpdir}/nonexistent -n ${tmpdir}/v0 -f '' } +shell -err -expect {Unknown jail method "xyz"} "varnishd -jxyz -f '' " -shell -expect {active auto/warm - vcl1} { - varnishadm -n ${tmpdir}/v1 vcl.list +shell -err -expect {Invalid backslash sequence} { + varnishd -l 'xyz\kk,xyz\foo' -f '' } - -shell {varnishadm -n ${tmpdir}/v1 start} - -shell {varnishadm -n ${tmpdir}/v1 debug.listen_address} - -process p1 -stop -wait - -# Test multiple -f options - -shell { - cat >${tmpdir}/ok1 <<-EOF - vcl 4.0; - backend ok1 { - .host="${bad_backend}"; - } - EOF - - cat >${tmpdir}/ok2 <<-EOF - vcl 4.0; - backend ok2 { - .host="${bad_backend}"; - } - EOF +shell -err -expect {Invalid backslash sequence} { + varnishd -l 'ab\8cd' -f '' } +shell -err -expect {Too many arguments for -V} "varnishd -V -V" +shell -expect {Copyright (c) 2006} "varnishd -V" -varnish v2 -arg "-f ${tmpdir}/ok1" -arg "-f ${tmpdir}/ok2" -start -varnish v2 -cliexpect {available *auto/warm *0 boot0} "vcl.list" -varnish v2 -cliexpect {active *auto/warm *0 boot} "vcl.list" -varnish v2 -stop -wait - -# Test multiple -f options with a bad VCL - -shell -err -expect {Cannot read -f file} { - exec varnishd -n ${tmpdir}/v0 -F -a :0 -l2m,3m -f ${tmpdir}/ok1 \ - -f ${tmpdir}/ok2 -f ${tmpdir}/bad -} +shell -err -expect {Only one of -d or -F can be specified} "varnishd -d -F " +shell -err -expect {Only one of -b or -f can be specified} "varnishd -b a -f b " +shell -err -expect {-d makes no sense with -C} "varnishd -C -b 127.0.0.1:80 -d " +shell -err -expect {-F makes no sense with -C} "varnishd -C -b 127.0.0.1:80 -F " +shell -err -expect {Neither -b nor -f given} { varnishd -n ${tmpdir}/v0 } -shell -err -expect {Cannot read -f file} { - exec varnishd -n ${tmpdir}/v0 -F -a :0 -l2m,3m -f ${tmpdir}/ok1 \ - -f ${tmpdir}/bad -f ${tmpdir}/ok2 -} diff --git a/bin/varnishtest/tests/a00017.vtc b/bin/varnishtest/tests/a00017.vtc new file mode 100644 index 0000000..1a3538b --- /dev/null +++ b/bin/varnishtest/tests/a00017.vtc @@ -0,0 +1,65 @@ +varnishtest "Code coverage of mgt_main, (VCL compiler and RSTdump etc)" + +# Test -F mode with no VCL loaded + +process p1 "exec varnishd -n ${tmpdir}/v1 -F -f '' -a :0 -l2m,1m" -log -start + +delay 2 + +shell { + ( + echo 'vcl 4.0;' + echo 'backend default {' + echo ' .host="${bad_backend}";' + echo '}' + ) > ${tmpdir}/vcl +} + +shell -expect {VCL compiled.} { + varnishadm -n ${tmpdir}/v1 vcl.load vcl1 ${tmpdir}/vcl +} + +shell -expect {active auto/warm - vcl1} { + varnishadm -n ${tmpdir}/v1 vcl.list +} + +shell {varnishadm -n ${tmpdir}/v1 start} + +shell {varnishadm -n ${tmpdir}/v1 debug.listen_address} + +process p1 -stop -wait + +# Test multiple -f options + +shell { + cat >${tmpdir}/ok1 <<-EOF + vcl 4.0; + backend ok1 { + .host="${bad_backend}"; + } + EOF + + cat >${tmpdir}/ok2 <<-EOF + vcl 4.0; + backend ok2 { + .host="${bad_backend}"; + } + EOF +} + +varnish v2 -arg "-f ${tmpdir}/ok1" -arg "-f ${tmpdir}/ok2" -start +varnish v2 -cliexpect {available *auto/warm *0 boot0} "vcl.list" +varnish v2 -cliexpect {active *auto/warm *0 boot} "vcl.list" +varnish v2 -stop -wait + +# Test multiple -f options with a bad VCL + +shell -err -expect {Cannot read -f file} { + exec varnishd -n ${tmpdir}/v0 -F -a :0 -l2m,3m -f ${tmpdir}/ok1 \ + -f ${tmpdir}/ok2 -f ${tmpdir}/bad +} + +shell -err -expect {Cannot read -f file} { + exec varnishd -n ${tmpdir}/v0 -F -a :0 -l2m,3m -f ${tmpdir}/ok1 \ + -f ${tmpdir}/bad -f ${tmpdir}/ok2 +} From geoff at uplex.de Fri Mar 10 16:14:06 2017 From: geoff at uplex.de (Geoff Simmons) Date: Fri, 10 Mar 2017 17:14:06 +0100 Subject: [master] 5e8953f Some minor additions to Upgrading to Varnish 5.1 Message-ID: commit 5e8953f060a0373a28103e06230f8d67c150d1bd Author: Geoff Simmons Date: Fri Mar 10 14:00:10 2017 +0100 Some minor additions to Upgrading to Varnish 5.1 diff --git a/doc/sphinx/whats-new/upgrading-5.1.rst b/doc/sphinx/whats-new/upgrading-5.1.rst index c6186f6..4c711dc 100644 --- a/doc/sphinx/whats-new/upgrading-5.1.rst +++ b/doc/sphinx/whats-new/upgrading-5.1.rst @@ -104,6 +104,9 @@ vcl_recv use if you choose to save the request body (see :ref:`func_cache_req_body`). +* ``return(vcl(LABEL))`` may not be called after a restart. It can + only be called from the active VCL instance. + vcl_backend_response ~~~~~~~~~~~~~~~~~~~~ @@ -169,7 +172,8 @@ Other changes * ``varnishtest(1)``: - * Added the ``process`` and ``setenv`` commands, see :ref:`vtc(7)` . + * Added the ``process``, ``setenv`` and ``write_body`` commands, see + :ref:`vtc(7)` . * ``-reason`` replaces ``-msg`` to set the reason string for a response (default "OK"). From geoff at uplex.de Fri Mar 10 16:14:06 2017 From: geoff at uplex.de (Geoff Simmons) Date: Fri, 10 Mar 2017 17:14:06 +0100 Subject: [master] 6dbe82e Typos Message-ID: commit 6dbe82e2525b449124a7ebbc27a115ecbdbdf3b6 Author: Geoff Simmons Date: Fri Mar 10 15:11:00 2017 +0100 Typos diff --git a/doc/sphinx/whats-new/changes-5.1.rst b/doc/sphinx/whats-new/changes-5.1.rst index b1bf6ad..f0c4015 100644 --- a/doc/sphinx/whats-new/changes-5.1.rst +++ b/doc/sphinx/whats-new/changes-5.1.rst @@ -39,9 +39,9 @@ process starts, so it could for instance contain:: vcl.load siteA0 /etc/varnish_siteA.vcl vcl.load siteB0 /etc/varnish_siteB.vcl vcl.load siteC0 /etc/varnish_siteC.vcl - vsl.label siteA siteA0 - vsl.label siteB siteB0 - vsl.label siteC siteC0 + vcl.label siteA siteA0 + vcl.label siteB siteB0 + vcl.label siteC siteC0 vcl.load main /etc/varnish_main.vcl vcl.use main From geoff at uplex.de Fri Mar 10 16:14:06 2017 From: geoff at uplex.de (Geoff Simmons) Date: Fri, 10 Mar 2017 17:14:06 +0100 Subject: [master] 1bc2479 Update the OPTIONS section in varnishd(3), and add a section about CLI files. Message-ID: commit 1bc2479c775c7569e02edced40ce68c8d392c7d2 Author: Geoff Simmons Date: Fri Mar 10 17:13:20 2017 +0100 Update the OPTIONS section in varnishd(3), and add a section about CLI files. diff --git a/doc/sphinx/reference/varnishd.rst b/doc/sphinx/reference/varnishd.rst index 22991aa..cf62b8d 100644 --- a/doc/sphinx/reference/varnishd.rst +++ b/doc/sphinx/reference/varnishd.rst @@ -15,7 +15,7 @@ HTTP accelerator daemon SYNOPSIS ======== -varnishd [-a address[:port][,PROTO]] [-b host[:port]] [-C] [-d] [-F] [-f config] [-h type[,options]] [-i identity] [-j jail[,jailoptions]] [-l vsl[,vsm]] [-M address:port] [-n name] [-P file] [-p param=value] [-r param[,param...]] [-S secret-file] [-s [name=]kind[,options]] [-T address[:port]] [-t TTL] [-V] [-W waiter] +varnishd [-a address[:port][,PROTO]] [-b host[:port]] [-C] [-d] [-F] [-f config] [-h type[,options]] [-I clifile] [-i identity] [-j jail[,jailoptions]] [-l vsl[,vsm]] [-M address:port] [-n name] [-P file] [-p param=value] [-r param[,param...]] [-S secret-file] [-s [name=]kind[,options]] [-T address[:port]] [-t TTL] [-V] [-W waiter] [-x parameter|vsl|cli|builtin] [-?] DESCRIPTION =========== @@ -29,6 +29,9 @@ satisfy future requests for the same document. OPTIONS ======= +Basic options +------------- + -a Listen for client requests on the specified address and port. The @@ -44,52 +47,76 @@ OPTIONS -b Use the specified host as backend server. If port is not specified, - the default is 8080. + the default is 8080. -b can be used only once, and not together with + -f. --C +-f config - Print VCL code compiled to C language and exit. Specify the VCL file - to compile with the -f option. + Use the specified VCL configuration file instead of the builtin + default. See :ref:`vcl(7)` for details on VCL syntax. --d + If a single -f option is used, then the VCL instance loaded from the + file is named "boot" and immediately becomes active. If more than + one -f option is used, the VCL instances are named "boot0", "boot1" + and so forth, in the order corresponding to the -f arguments, and + the last one is named "boot", which becomes active. - Enables debugging mode: The parent process runs in the foreground - with a CLI connection on stdin/stdout, and the child process must be - started explicitly with a CLI command. Terminating the parent - process will also terminate the child. + Either -b or one or more -f options must be specified, but not both, + and they cannot both be left out, unless -d is used to start + `varnishd` in debugging mode. If the empty string is specified as + the sole -f option, then `varnishd` starts without starting the + worker process, and the management process will accept CLI commands. --F +-n name - Do not fork, run in the foreground. + Specify the name for this instance. Amongst other things, this name + is used to construct the name of the directory in which `varnishd` + keeps temporary files and persistent state. If the specified name + begins with a forward slash, it is interpreted as the absolute path + to the directory which should be used for this purpose. --f config +Documentation options +--------------------- - Use the specified VCL configuration file instead of the builtin - default. See :ref:`vcl(7)` for details on VCL syntax. +For these options, `varnishd` prints information to standard output +and exits. When a -x option is used, it must be the only option. - When neither a -f nor a -b argument are given, `varnishd` will not - start the worker process but process cli commands. +-? --h + Print the usage message. - Specifies the hash algorithm. See `Hash Algorithm`_ section for a list - of supported algorithms. +-x parameter --i identity + Print documentation of the runtime parameters (-p options), see + `List of Parameters`_. - Specify the identity of the Varnish server. This can be accessed - using ``server.identity`` from VCL. +-x vsl --j + Print documentation of the tags used in the Varnish shared memory + log, see :ref:`vsl(7)`. - Specify the jailing mechanism to use. See `Jail`_ section. +-x cli --l + Print documentation of the command line interface, see + :ref:`varnish-cli(7)`. - Specifies size of shmlog file. vsl is the space for the VSL records - [80M] and vsm is the space for stats counters [1M]. Scaling suffixes - like 'K' and 'M' can be used up to (G)igabytes. - Default is 81 Megabytes. +-x builtin + + Print the contents of the default VCL program ``builtin.vcl``. + +Operations options +------------------ + +-F + + Do not fork, run in the foreground. Only one of -F or -d can be + specified, and -F cannot be used together with -C. + +-T + + Offer a management interface on the specified address and port. See + :ref:`varnish-cli(7)` for documentation of the management commands. + To disable the management interface use ``none``. -M @@ -97,24 +124,51 @@ OPTIONS it as a reverse shell. When running with -M and there is no backend defined the child process (the cache) will not start initially. --n name - - Specify the name for this instance. Amongst other things, this name - is used to construct the name of the directory in which `varnishd` - keeps temporary files and persistent state. If the specified name - begins with a forward slash, it is interpreted as the absolute path - to the directory which should be used for this purpose. - -P file Write the PID of the process to the specified file. +-i identity + + Specify the identity of the Varnish server. This can be accessed + using ``server.identity`` from VCL. + +-I clifile + + Execute the management commands in the file given as ``clifile`` + before the the worker process starts, see `CLI Command File`_. + +Tuning options +-------------- + +-t TTL + + Specifies the default time to live (TTL) for cached objects. This is + a shortcut for specifying the *default_ttl* run-time parameter. + -p Set the parameter specified by param to the specified value, see `List of Parameters`_ for details. This option can be used multiple times to specify multiple parameters. +-s <[name=]type[,options]> + + Use the specified storage backend. See `Storage Backend`_ section. + + This option can be used multiple times to specify multiple storage + files. Names are referenced in logs, VCL, statistics, etc. + +-l + + Specifies size of shmlog file. vsl is the space for the VSL records + [80M] and vsm is the space for stats counters [1M]. Scaling suffixes + like 'K' and 'M' can be used up to (G)igabytes. + Default is 81 Megabytes. + +Security options +---------------- + -r Make the listed parameters read only. This gives the system @@ -129,27 +183,37 @@ OPTIONS the management port. If not provided a new secret will be drawn from the system PRNG. To disable authentication use ``none``. --s <[name=]type[,options]> +-j - Use the specified storage backend. See `Storage Backend`_ section. + Specify the jailing mechanism to use. See `Jail`_ section. - This option can be used multiple times to specify multiple storage - files. Names are referenced in logs, VCL, statistics, etc. +Advanced, development and debugging options +------------------------------------------- --T +-d - Offer a management interface on the specified address and port. See - `Management Interface`_ for a list of management commands. To disable - the management interface use ``none``. + Enables debugging mode: The parent process runs in the foreground + with a CLI connection on stdin/stdout, and the child process must be + started explicitly with a CLI command. Terminating the parent + process will also terminate the child. --t TTL + Only one of -d or -F can be specified, and -d cannot be used together + with -C. - Specifies the default time to live (TTL) for cached objects. This is - a shortcut for specifying the *default_ttl* run-time parameter. +-C + + Print VCL code compiled to C language and exit. Specify the VCL file + to compile with the -f option. Either -f or -b must be used with -C, + and -C cannot be used with -F. -V - Display the version number and exit. + Display the version number and exit. This must be the only option. + +-h + + Specifies the hash algorithm. See `Hash Algorithm`_ section for a list + of supported algorithms. -W waiter @@ -271,9 +335,31 @@ Management Interface If the -T option was specified, `varnishd` will offer a command-line management interface on the specified address and port. The recommended way of connecting to the command-line management interface -is through varnishadm(1). - -The commands available are documented in varnish(7). +is through :ref:`varnishadm(1)`. + +The commands available are documented in :ref:`varnish-cli(7)`. + +CLI Command File +---------------- + +The -I option makes it possible to run arbitrary management commands +when `varnishd` is launched, before the worker process is started. In +particular, this is the way to load configurations, apply labels to +them, and make a VCL instance active that uses those labels on +startup:: + + vcl.load panic /etc/varnish_panic.vcl + vcl.load siteA0 /etc/varnish_siteA.vcl + vcl.load siteB0 /etc/varnish_siteB.vcl + vcl.load siteC0 /etc/varnish_siteC.vcl + vcl.label siteA siteA0 + vcl.label siteB siteB0 + vcl.label siteC siteC0 + vcl.load main /etc/varnish_main.vcl + vcl.use main + +If a command in the file is prefixed with '-', failure will not abort +the startup. .. _ref-varnishd-params: From fgsch at lodoss.net Fri Mar 10 17:01:06 2017 From: fgsch at lodoss.net (Federico G. Schwindt) Date: Fri, 10 Mar 2017 18:01:06 +0100 Subject: [master] 520442b This never really worked so not a change per se Message-ID: commit 520442bb440d40af1437c599df8c40a98a442f5a Author: Federico G. Schwindt Date: Fri Mar 10 16:50:37 2017 +0000 This never really worked so not a change per se diff --git a/doc/sphinx/whats-new/upgrading-5.1.rst b/doc/sphinx/whats-new/upgrading-5.1.rst index 4c711dc..ab6104f 100644 --- a/doc/sphinx/whats-new/upgrading-5.1.rst +++ b/doc/sphinx/whats-new/upgrading-5.1.rst @@ -133,12 +133,6 @@ Now ``beresp.storage`` is initialized with a storage backend before ``beresp.storage`` after its execution will be used. The configured nuke limit is used in all cases. -vcl_backend_error -~~~~~~~~~~~~~~~~~ - -* ``beresp.backend.ip`` is only available when the backend connection - is open, and hence not in ``vcl_backend_error``. - VMOD std ~~~~~~~~ From fgsch at lodoss.net Fri Mar 10 17:01:06 2017 From: fgsch at lodoss.net (Federico G. Schwindt) Date: Fri, 10 Mar 2017 18:01:06 +0100 Subject: [master] 7841984 Spelling Message-ID: commit 78419843f4286748ca6fd0d15a227c738d0fb27a Author: Federico G. Schwindt Date: Fri Mar 10 16:58:47 2017 +0000 Spelling diff --git a/doc/sphinx/whats-new/changes-5.1.rst b/doc/sphinx/whats-new/changes-5.1.rst index f0c4015..efdddb8 100644 --- a/doc/sphinx/whats-new/changes-5.1.rst +++ b/doc/sphinx/whats-new/changes-5.1.rst @@ -13,7 +13,7 @@ significant contributors to Varnish have changed jobs, and therefore stopped being active contributors to the Varnish Project. Per Buer was one of the first people who realized that Varnish was -not just "Some program for a couple of nordic newspapers", and he +not just "Some program for a couple of Nordic newspapers", and he started the company Varnish Software, which is one of the major sponsors of the Varnish Project. @@ -30,7 +30,7 @@ Startup CLI command file ~~~~~~~~~~~~~~~~~~~~~~~~ The new '-I cli_file' option to varnishd will make it much more -practical to use the vcl labels introduced in Varnish 5.0. +practical to use the VCL labels introduced in Varnish 5.0. The cli commands in the file will be executed before the worker process starts, so it could for instance contain:: @@ -51,7 +51,7 @@ the startup. Related to this change we have reordered the argument checking so that argument problems are reported more consistently. -In case you didn't hear about them yet, labeling VCL programs +In case you didn't hear about them yet, labelling VCL programs allows you to branch out to other VCLs in the main::vcl_recv{}, which in the above example could look like:: @@ -113,7 +113,7 @@ state in the argument to ``pass``. For example: ``return(pass(120s))``. To recap: when ``beresp.uncacheable`` is set to ``true`` in -``vcl_backend_response``, Varnish makes a note of it with a mininal +``vcl_backend_response``, Varnish makes a note of it with a minimal object in the cache, and finds that information again on the next lookup for the same object. In essence, the cache is used to remember that the last backend response was not cacheable. In that case, diff --git a/doc/sphinx/whats-new/upgrading-5.1.rst b/doc/sphinx/whats-new/upgrading-5.1.rst index ab6104f..a7180fa 100644 --- a/doc/sphinx/whats-new/upgrading-5.1.rst +++ b/doc/sphinx/whats-new/upgrading-5.1.rst @@ -89,7 +89,7 @@ All VCL subroutines (except ``vcl_fini``) all cases but ``vcl_synth``, control is directed to ``vcl_synth`` with ``resp.status`` and ``resp.reason`` set to 503 and "VCL failed", respectively. ``vcl_synth`` is aborted on ``return(fail)``. - ``vcl_fini`` is executed whan a VCL instance in unloaded (enters the + ``vcl_fini`` is executed when a VCL instance in unloaded (enters the COLD state) and has no failure condition. Client-side VCL subroutines @@ -125,7 +125,7 @@ command-line option for varnishd, but none is explicitly set in limit has been reworked (see :ref:`ref_param_nuke_limit`). Previously, a storage backend was tried first with a nuke limit of 0, and retried on failure with the limit configured as the ``-p`` parameter -``nuke_limit``. When no storage was specfied, Varnish went through +``nuke_limit``. When no storage was specified, Varnish went through every one in round-robin order with a nuke limit of 0 before retrying. Now ``beresp.storage`` is initialized with a storage backend before From geoff at uplex.de Fri Mar 10 17:20:07 2017 From: geoff at uplex.de (Geoff Simmons) Date: Fri, 10 Mar 2017 18:20:07 +0100 Subject: [master] 5679cc7 Summarize changes in varnishd command-line options in Upgrading to 5.1 Message-ID: commit 5679cc705b818452808f43dd883a33041cb6a104 Author: Geoff Simmons Date: Fri Mar 10 18:19:29 2017 +0100 Summarize changes in varnishd command-line options in Upgrading to 5.1 diff --git a/doc/sphinx/reference/varnishd.rst b/doc/sphinx/reference/varnishd.rst index cf62b8d..ada8875 100644 --- a/doc/sphinx/reference/varnishd.rst +++ b/doc/sphinx/reference/varnishd.rst @@ -204,7 +204,7 @@ Advanced, development and debugging options Print VCL code compiled to C language and exit. Specify the VCL file to compile with the -f option. Either -f or -b must be used with -C, - and -C cannot be used with -F. + and -C cannot be used with -F or -d. -V diff --git a/doc/sphinx/whats-new/changes-5.1.rst b/doc/sphinx/whats-new/changes-5.1.rst index efdddb8..6092091 100644 --- a/doc/sphinx/whats-new/changes-5.1.rst +++ b/doc/sphinx/whats-new/changes-5.1.rst @@ -25,6 +25,7 @@ years we have been around now. Guys, "Thanks" doesn't even start to cover it and we wish you all the best for the future! +.. _whatsnew_clifile: Startup CLI command file ~~~~~~~~~~~~~~~~~~~~~~~~ diff --git a/doc/sphinx/whats-new/upgrading-5.1.rst b/doc/sphinx/whats-new/upgrading-5.1.rst index a7180fa..f4ea684 100644 --- a/doc/sphinx/whats-new/upgrading-5.1.rst +++ b/doc/sphinx/whats-new/upgrading-5.1.rst @@ -7,6 +7,38 @@ Upgrading to Varnish 5.1 varnishd command-line options ============================= +If you have to change anything at all for version 5.1, then most +likely the command-line options for `varnishd` in your start scripts, +because we have tightened restrictions on which options may be used +together. This has served mainly to clarify the use of options for +testing purposes, for example using ``varnishd -C`` to check a VCL +source for syntactic correctness. We have also added some new options. + +The details are given in :ref:`varnishd(1)`, but here's a summary: + +* Added ``-I clifile`` to run CLI commands at startup, before the + worker process starts. See :ref:`whatsnew_clifile`. + +* More than one ``-f`` option is now permitted, to pre-load VCL + instances at startup. The last of these becomes the "boot" instance + that is is active at startup. + +* Either ``-b`` or one or more ``-f`` options must be specified, but + not both, and they cannot both be left out, unless ``-d`` is used to + start `varnishd` in debugging mode. If the empty string is specified + as the sole ``-f`` option, then `varnishd` starts without starting + the worker process, and the management process will accept CLI + commands. + +* Added ``-?`` to print the usage message, which is only printed for + this option. + +* Added the ``-x`` option to print certain kinds of documentation and + exit. When ``-x`` is used, it must be the only option. + +* Only one of ``-F`` or ``-d`` may be used, and neither of these can + be used with ``-C``. + * Added the ``workuser`` parameter to the ``-j`` option. varnishd parameters From geoff at uplex.de Fri Mar 10 17:26:05 2017 From: geoff at uplex.de (Geoff Simmons) Date: Fri, 10 Mar 2017 18:26:05 +0100 Subject: [master] 9379ac9 Correct the notes on bereq. and beresp.backend in Upgrading to 5.1. Message-ID: commit 9379ac943bceabbfc125756c5207a8fe74d55827 Author: Geoff Simmons Date: Fri Mar 10 18:24:33 2017 +0100 Correct the notes on bereq. and beresp.backend in Upgrading to 5.1. diff --git a/doc/sphinx/whats-new/upgrading-5.1.rst b/doc/sphinx/whats-new/upgrading-5.1.rst index f4ea684..e518b42 100644 --- a/doc/sphinx/whats-new/upgrading-5.1.rst +++ b/doc/sphinx/whats-new/upgrading-5.1.rst @@ -73,11 +73,13 @@ Changes to VCL Type conversions ~~~~~~~~~~~~~~~~ -* When ``bereq.backend`` and ``beresp.backend`` are set to a director, - then they return an actual backend on subsequent reads if the - director resolves to a backend immediately, or the director otherwise. - When used in string context, they return the name of the director - or of the resolved backend. +* When ``bereq.backend`` is set to a director, then it returns an + actual backend on subsequent reads if the director resolves to a + backend immediately, or the director otherwise. If ``bereq.backend`` + was set to a director, then ``beresp.backend`` returns the backend + to which it was set for the fetch. When either of these is used in + string context, it returns the name of the director or of the + resolved backend. * DURATION types may be used in boolean contexts, and are evaluated as false when the duration is less than or equal to zero, true From fgsch at lodoss.net Fri Mar 10 19:08:06 2017 From: fgsch at lodoss.net (Federico G. Schwindt) Date: Fri, 10 Mar 2017 20:08:06 +0100 Subject: [master] f4faa6e Fold r00936.vtc into vcc_action.c tests Message-ID: commit f4faa6e3c431d6ccf581f5683af56008e4d4be10 Author: Federico G. Schwindt Date: Fri Mar 10 18:59:14 2017 +0000 Fold r00936.vtc into vcc_action.c tests diff --git a/bin/varnishtest/tests/r00936.vtc b/bin/varnishtest/tests/r00936.vtc deleted file mode 100644 index ddb2f79..0000000 --- a/bin/varnishtest/tests/r00936.vtc +++ /dev/null @@ -1,16 +0,0 @@ -varnishtest "synthetic is only allowed in error" - -server s1 { - rxreq - txresp -} -start - -varnish v1 -errvcl {'synthetic': not a valid action in method 'vcl_recv'} { - backend foo { .host = "127.0.0.1"; } - - sub vcl_recv { - synthetic("HELLOO"); - return (synth(503)); - } -} - diff --git a/bin/varnishtest/tests/v00018.vtc b/bin/varnishtest/tests/v00018.vtc index 53d96c9..a0bbf02 100644 --- a/bin/varnishtest/tests/v00018.vtc +++ b/bin/varnishtest/tests/v00018.vtc @@ -117,3 +117,12 @@ varnish v1 -errvcl {Expected return action name.} { backend b { .host = "127.0.0.1"; } sub vcl_recv { return(foobar); } } + +# issue #936 +varnish v1 -errvcl {'synthetic': not a valid action in method 'vcl_recv'} { + backend foo { .host = "127.0.0.1"; } + sub vcl_recv { + synthetic("XXX"); + return (synth(503)); + } +} From dridi.boukelmoune at gmail.com Fri Mar 10 19:15:06 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Fri, 10 Mar 2017 20:15:06 +0100 Subject: [master] 5c8b790 Feed automake a pkgdatadir Message-ID: commit 5c8b790fb18130dcdb532913d34bf2343d43ed1b Author: Dridi Boukelmoune Date: Fri Mar 10 20:13:03 2017 +0100 Feed automake a pkgdatadir While at it, get rid of the hard-coded package name. Refs #2251 diff --git a/bin/varnishd/Makefile.am b/bin/varnishd/Makefile.am index b07e9f0..fabcff8 100644 --- a/bin/varnishd/Makefile.am +++ b/bin/varnishd/Makefile.am @@ -140,13 +140,15 @@ nobase_pkginclude_HEADERS = \ common/com_params.h \ waiter/waiter.h +pkgdatadir = ${datarootdir}/${PACKAGE}/vcl + varnishd_CFLAGS = \ @PCRE_CFLAGS@ \ @SAN_CFLAGS@ \ -DVARNISHD_IS_NOT_A_VMOD \ -DVARNISH_STATE_DIR='"${VARNISH_STATE_DIR}"' \ -DVARNISH_VMOD_DIR='"${pkglibdir}/vmods"' \ - -DVARNISH_VCL_DIR='"${varnishconfdir}:${datarootdir}/varnish/vcl"' + -DVARNISH_VCL_DIR='"${varnishconfdir}:${pkgdatadir}"' varnishd_LDFLAGS = -export-dynamic From phk at FreeBSD.org Fri Mar 10 21:46:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Fri, 10 Mar 2017 22:46:05 +0100 Subject: [master] f9e4d9c Tighten up the Session pulldown sequence and let GOWAY do it. Message-ID: commit f9e4d9c5b2ed8605f1183dc80e2422de2ff961f5 Author: Poul-Henning Kamp Date: Fri Mar 10 21:44:48 2017 +0000 Tighten up the Session pulldown sequence and let GOWAY do it. diff --git a/bin/varnishd/http2/cache_http2.h b/bin/varnishd/http2/cache_http2.h index ff49237..5599172 100644 --- a/bin/varnishd/http2/cache_http2.h +++ b/bin/varnishd/http2/cache_http2.h @@ -220,5 +220,3 @@ void h2_del_req(struct worker *, struct h2_req *); int h2_rxframe(struct worker *, struct h2_sess *); h2_error h2_set_setting(struct h2_sess *, const uint8_t *); void h2_req_body(struct req*); -h2_error H2_StreamError(uint32_t); -h2_error H2_ConnectionError(uint32_t); diff --git a/bin/varnishd/http2/cache_http2_deliver.c b/bin/varnishd/http2/cache_http2_deliver.c index f9a6fa1..920e0fa 100644 --- a/bin/varnishd/http2/cache_http2_deliver.c +++ b/bin/varnishd/http2/cache_http2_deliver.c @@ -81,15 +81,17 @@ h2_bytes(struct req *req, enum vdp_action act, void **priv, CHECK_OBJ_NOTNULL(req, REQ_MAGIC); CAST_OBJ_NOTNULL(r2, req->transport_priv, H2_REQ_MAGIC); (void)priv; + if (act == VDP_INIT) return (0); + if (r2->error) + return (-1); H2_Send_Get(req->wrk, r2->h2sess, r2); H2_Send(req->wrk, r2, H2_F_DATA, act == VDP_FINI ? H2FF_DATA_END_STREAM : H2FF_NONE, len, ptr); H2_Send_Rel(r2->h2sess, r2); - return (0); } diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index e22a1c9..f4e7fc9 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -95,8 +95,8 @@ static const h2_error stream_errors[] = { #define NSTREAMERRORS (sizeof(stream_errors)/sizeof(stream_errors[0])) -h2_error -H2_StreamError(uint32_t u) +static h2_error +h2_streamerror(uint32_t u) { if (u < NSTREAMERRORS && stream_errors[u] != NULL) return (stream_errors[u]); @@ -120,8 +120,8 @@ static const h2_error conn_errors[] = { #define NCONNERRORS (sizeof(conn_errors)/sizeof(conn_errors[0])) -h2_error -H2_ConnectionError(uint32_t u) +static h2_error +h2_connectionerror(uint32_t u) { if (u < NCONNERRORS && conn_errors[u] != NULL) return (conn_errors[u]); @@ -150,7 +150,6 @@ h2_new_req(const struct worker *wrk, struct h2_sess *h2, r2->stream = stream; r2->req = req; req->transport_priv = r2; - // XXX: ordering ? Lck_Lock(&h2->sess->mtx); VTAILQ_INSERT_TAIL(&h2->streams, r2, list); Lck_Unlock(&h2->sess->mtx); @@ -276,9 +275,10 @@ h2_rx_rst_stream(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) if (r2 == NULL) return (0); Lck_Lock(&h2->sess->mtx); - r2->error = H2_StreamError(vbe32dec(h2->rxf_data)); + r2->error = h2_streamerror(vbe32dec(h2->rxf_data)); if (r2->wrk != NULL) AZ(pthread_cond_signal(&r2->wrk->cond)); + Lck_Unlock(&h2->sess->mtx); return (0); } @@ -292,8 +292,9 @@ h2_rx_goaway(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) (void)wrk; (void)r2; h2->goaway_last_stream = vbe32dec(h2->rxf_data); - h2->error = H2_ConnectionError(vbe32dec(h2->rxf_data + 4)); - return (0); + h2->error = h2_connectionerror(vbe32dec(h2->rxf_data + 4)); + VSLb(h2->vsl, SLT_Debug, "GOAWAY %s", h2->error->name); + return (h2->error); } /********************************************************************** @@ -562,7 +563,7 @@ h2_rx_data(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) h2->mailcall = r2; Lck_Lock(&h2->sess->mtx); AZ(pthread_cond_broadcast(h2->cond)); - while (h2->mailcall != NULL) + while (h2->mailcall != NULL && h2->error == 0 && r2->error == 0) AZ(Lck_CondWait(h2->cond, &h2->sess->mtx, 0)); Lck_Unlock(&h2->sess->mtx); return (0); @@ -587,21 +588,26 @@ h2_vfp_body(struct vfp_ctx *vc, struct vfp_entry *vfe, void *ptr, ssize_t *lp) *lp = 0; Lck_Lock(&h2->sess->mtx); - while (h2->mailcall != r2) + while (h2->mailcall != r2 && h2->error == 0 && r2->error == 0) AZ(Lck_CondWait(h2->cond, &h2->sess->mtx, 0)); - if (l > h2->rxf_len) - l = h2->rxf_len; - if (l > 0) { - memcpy(ptr, h2->rxf_data, l); - h2->rxf_data += l; - h2->rxf_len -= l; - } - *lp = l; - if (h2->rxf_len == 0) { - if (h2->rxf_flags & H2FF_DATA_END_STREAM) - retval = VFP_END; + if (h2->mailcall == r2) { + assert(h2->mailcall == r2); + if (l > h2->rxf_len) + l = h2->rxf_len; + if (l > 0) { + memcpy(ptr, h2->rxf_data, l); + h2->rxf_data += l; + h2->rxf_len -= l; + } + *lp = l; + if (h2->rxf_len == 0) { + if (h2->rxf_flags & H2FF_DATA_END_STREAM) + retval = VFP_END; + } h2->mailcall = NULL; AZ(pthread_cond_broadcast(h2->cond)); + } else { + retval = VFP_ERROR; } Lck_Unlock(&h2->sess->mtx); return (retval); @@ -734,6 +740,7 @@ h2_rxframe(struct worker *wrk, struct h2_sess *h2) if (hs != HTC_S_COMPLETE) { Lck_Lock(&h2->sess->mtx); VSLb(h2->vsl, SLT_Debug, "H2: No frame (hs=%d)", hs); + h2->error = H2CE_NO_ERROR; Lck_Unlock(&h2->sess->mtx); return (0); } @@ -786,7 +793,8 @@ h2_rxframe(struct worker *wrk, struct h2_sess *h2) } h2e = h2_procframe(wrk, h2, h2f); - if (h2e) { + if (h2->error == 0 && h2e) { + h2->error = h2e; vbe32enc(b, h2->highest_stream); vbe32enc(b + 4, h2e->val); H2_Send_Get(wrk, h2, h2->req0); diff --git a/bin/varnishd/http2/cache_http2_session.c b/bin/varnishd/http2/cache_http2_session.c index e6c6973..073d04f 100644 --- a/bin/varnishd/http2/cache_http2_session.c +++ b/bin/varnishd/http2/cache_http2_session.c @@ -289,7 +289,7 @@ h2_new_session(struct worker *wrk, void *arg) struct req *req; struct sess *sp; struct h2_sess *h2; - struct h2_req *r2, *r22; + struct h2_req *r2; uintptr_t wsp; CHECK_OBJ_NOTNULL(wrk, WORKER_MAGIC); @@ -332,12 +332,30 @@ h2_new_session(struct worker *wrk, void *arg) HTC_RxInit(h2->htc, h2->ws); } + AN(h2->error); /* Delete all idle streams */ - VTAILQ_FOREACH_SAFE(r2, &h2->streams, list, r22) { - if (r2->state == H2_S_IDLE) - h2_del_req(wrk, r2); + Lck_Lock(&sp->mtx); + VSLb(h2->vsl, SLT_Debug, "H2 CLEANUP %p", h2->error); + VTAILQ_FOREACH(r2, &h2->streams, list) { + if (r2->error == 0) + r2->error = h2->error; + if (r2->wrk != NULL) + AZ(pthread_cond_signal(&r2->wrk->cond)); + } + while (1) { + VTAILQ_FOREACH(r2, &h2->streams, list) + if (r2->state == H2_S_IDLE && r2 != h2->req0) + break; + if (r2 == NULL) + break; + Lck_Unlock(&sp->mtx); + h2_del_req(wrk, r2); + Lck_Lock(&sp->mtx); } + VSLb(h2->vsl, SLT_Debug, "H2CLEAN done"); + Lck_Unlock(&sp->mtx); h2->cond = NULL; + h2_del_req(wrk, h2->req0); } struct transport H2_transport = { diff --git a/bin/varnishtest/tests/t02008.vtc b/bin/varnishtest/tests/t02008.vtc new file mode 100644 index 0000000..a1bccba --- /dev/null +++ b/bin/varnishtest/tests/t02008.vtc @@ -0,0 +1,49 @@ +varnishtest "Test GOAWAY/session cleanup" + +server s1 { + rxreq + txresp -hdr "Content-Type: text/plain" -body response +} -start + +varnish v1 -vcl+backend {} -start +varnish v1 -cliok {param.set feature +http2} +varnish v1 -cliok "param.set debug +syncvsl" + +client c1 { + stream 1 { + txprio + } -run + stream 3 { + txreq + + # First, HTTP checks + rxresp + expect resp.http.content-Type == "text/plain" + + # Then, payload checks + expect resp.body == response + } -run + stream 5 { + txprio + } -run + stream 0 { + txgoaway -err 7 + } -run + expect_close +} -run + +delay .1 + +client c1 { + stream 1 { + txreq + + # First, HTTP checks + rxresp + expect resp.http.content-Type == "text/plain" + + # Then, payload checks + expect resp.body == response + } -run +} -run + From fgsch at lodoss.net Sat Mar 11 10:45:06 2017 From: fgsch at lodoss.net (Federico G. Schwindt) Date: Sat, 11 Mar 2017 11:45:06 +0100 Subject: [master] 0ce6f9b Fix build on OSX Message-ID: commit 0ce6f9b33b77f9b56f2364dafd24397dda576d33 Author: Federico G. Schwindt Date: Sat Mar 11 10:42:55 2017 +0000 Fix build on OSX diff --git a/lib/libvarnishapi/daemon.c b/lib/libvarnishapi/daemon.c index 2ac2697..33b8552 100644 --- a/lib/libvarnishapi/daemon.c +++ b/lib/libvarnishapi/daemon.c @@ -39,6 +39,7 @@ #include #include "compat/daemon.h" +#include "vdef.h" #include "vas.h" /* From fgsch at lodoss.net Sat Mar 11 10:54:05 2017 From: fgsch at lodoss.net (Federico G. Schwindt) Date: Sat, 11 Mar 2017 11:54:05 +0100 Subject: [master] 6c4e164 First stab at osx on travis-ci Message-ID: commit 6c4e16495017e284feb4d25ec94531bd72553528 Author: Federico G. Schwindt Date: Sat Mar 11 10:52:07 2017 +0000 First stab at osx on travis-ci diff --git a/.travis.yml b/.travis.yml index 164ba4b..a8aae1f 100644 --- a/.travis.yml +++ b/.travis.yml @@ -3,11 +3,16 @@ language: c compiler: - clang - gcc +os: + - linux + - osx addons: apt: packages: - python-docutils before_install: + - if [[ "$TRAVIS_OS_NAME" == "osx" ]]; then brew update ; fi + - if [[ "$TRAVIS_OS_NAME" == "osx" ]]; then brew install docutils; fi - ./autogen.sh - ./configure sudo: false From fgsch at lodoss.net Sat Mar 11 11:39:05 2017 From: fgsch at lodoss.net (Federico G. Schwindt) Date: Sat, 11 Mar 2017 12:39:05 +0100 Subject: [master] 8ac8115 Switch to more recent linux and osx versions Message-ID: commit 8ac8115e159b75930064abcac13b8b476361962b Author: Federico G. Schwindt Date: Sat Mar 11 11:32:09 2017 +0000 Switch to more recent linux and osx versions Also install nghttp2 so a02022.vtc has a chance to run. diff --git a/.travis.yml b/.travis.yml index a8aae1f..845154f 100644 --- a/.travis.yml +++ b/.travis.yml @@ -3,17 +3,22 @@ language: c compiler: - clang - gcc -os: - - linux - - osx +matrix: + include: + - os: linux + dist: trusty + sudo: false + - os: osx + osx_image: xcode8.2 addons: apt: packages: - python-docutils + - nghttp2 before_install: - if [[ "$TRAVIS_OS_NAME" == "osx" ]]; then brew update ; fi - if [[ "$TRAVIS_OS_NAME" == "osx" ]]; then brew install docutils; fi + - if [[ "$TRAVIS_OS_NAME" == "osx" ]]; then brew install nghttp2 ; fi - ./autogen.sh - ./configure -sudo: false -script: 'make -j3 check VERBOSE=1' +script: make -j3 check VERBOSE=1 From fgsch at lodoss.net Sat Mar 11 11:49:06 2017 From: fgsch at lodoss.net (Federico G. Schwindt) Date: Sat, 11 Mar 2017 12:49:06 +0100 Subject: [master] a14e514 Cosmetic change to kick travis-ci Message-ID: commit a14e514f00b97026ac91bebaa820bab016ddb941 Author: Federico G. Schwindt Date: Sat Mar 11 11:47:43 2017 +0000 Cosmetic change to kick travis-ci diff --git a/bin/varnishtest/tests/t02006.vtc b/bin/varnishtest/tests/t02006.vtc index 0160090..44a9c89 100644 --- a/bin/varnishtest/tests/t02006.vtc +++ b/bin/varnishtest/tests/t02006.vtc @@ -32,8 +32,7 @@ client c1 { expect resp.http.content-Type == "text/plain" # Then, payload checks - write_body resp.txt - shell {grep -q response resp.txt} + expect resp.body == response } -run } -run From fgsch at lodoss.net Sat Mar 11 12:25:05 2017 From: fgsch at lodoss.net (Federico G. Schwindt) Date: Sat, 11 Mar 2017 13:25:05 +0100 Subject: [master] 4abdd29 Add these back - they are needed Message-ID: commit 4abdd29e519a830747372c09a07d21898e222b48 Author: Federico G. Schwindt Date: Sat Mar 11 12:17:52 2017 +0000 Add these back - they are needed diff --git a/.travis.yml b/.travis.yml index 845154f..a60d116 100644 --- a/.travis.yml +++ b/.travis.yml @@ -3,6 +3,9 @@ language: c compiler: - clang - gcc +os: + - linux + - osx matrix: include: - os: linux From fgsch at lodoss.net Sat Mar 11 12:45:06 2017 From: fgsch at lodoss.net (Federico G. Schwindt) Date: Sat, 11 Mar 2017 13:45:06 +0100 Subject: [master] f4bd388 Switch approach while I speak with the travis guys Message-ID: commit f4bd388bf02963173493f2d366aa67e4edaf201c Author: Federico G. Schwindt Date: Sat Mar 11 12:41:57 2017 +0000 Switch approach while I speak with the travis guys diff --git a/.travis.yml b/.travis.yml index a60d116..a25e823 100644 --- a/.travis.yml +++ b/.travis.yml @@ -6,13 +6,6 @@ compiler: os: - linux - osx -matrix: - include: - - os: linux - dist: trusty - sudo: false - - os: osx - osx_image: xcode8.2 addons: apt: packages: @@ -24,4 +17,7 @@ before_install: - if [[ "$TRAVIS_OS_NAME" == "osx" ]]; then brew install nghttp2 ; fi - ./autogen.sh - ./configure +dist: trusty +sudo: false +osx_image: xcode8.2 script: make -j3 check VERBOSE=1 From fgsch at lodoss.net Sat Mar 11 12:56:05 2017 From: fgsch at lodoss.net (Federico G. Schwindt) Date: Sat, 11 Mar 2017 13:56:05 +0100 Subject: [master] ffa620d bah, trusty does not have nghttp2 Message-ID: commit ffa620dec2a1e9d7b21d086863eb2c6084bc644f Author: Federico G. Schwindt Date: Sat Mar 11 12:51:19 2017 +0000 bah, trusty does not have nghttp2 diff --git a/.travis.yml b/.travis.yml index a25e823..bf6a001 100644 --- a/.travis.yml +++ b/.travis.yml @@ -10,7 +10,6 @@ addons: apt: packages: - python-docutils - - nghttp2 before_install: - if [[ "$TRAVIS_OS_NAME" == "osx" ]]; then brew update ; fi - if [[ "$TRAVIS_OS_NAME" == "osx" ]]; then brew install docutils; fi From dridi at varni.sh Sat Mar 11 13:10:29 2017 From: dridi at varni.sh (Dridi Boukelmoune) Date: Sat, 11 Mar 2017 14:10:29 +0100 Subject: [master] ffa620d bah, trusty does not have nghttp2 In-Reply-To: References: Message-ID: On Sat, Mar 11, 2017 at 1:56 PM, Federico G. Schwindt wrote: > > commit ffa620dec2a1e9d7b21d086863eb2c6084bc644f > Author: Federico G. Schwindt > Date: Sat Mar 11 12:51:19 2017 +0000 > > bah, trusty does not have nghttp2 I have it when my vtest instance is running ;) Cheers From fgsch at lodoss.net Sat Mar 11 16:41:05 2017 From: fgsch at lodoss.net (Federico G. Schwindt) Date: Sat, 11 Mar 2017 17:41:05 +0100 Subject: [master] dcedbd2 Try to fix the annoying osx setup Message-ID: commit dcedbd2592f59e28be2a8eeb14e439bb854d21c5 Author: Federico G. Schwindt Date: Sat Mar 11 16:37:17 2017 +0000 Try to fix the annoying osx setup diff --git a/.travis.yml b/.travis.yml index bf6a001..953d203 100644 --- a/.travis.yml +++ b/.travis.yml @@ -9,7 +9,7 @@ os: addons: apt: packages: - - python-docutils + - python-docutils before_install: - if [[ "$TRAVIS_OS_NAME" == "osx" ]]; then brew update ; fi - if [[ "$TRAVIS_OS_NAME" == "osx" ]]; then brew install docutils; fi @@ -19,4 +19,7 @@ before_install: dist: trusty sudo: false osx_image: xcode8.2 -script: make -j3 check VERBOSE=1 +script: + - if [[ "$TRAVIS_OS_NAME" == "osx" ]]; then + export PYTHONPATH=`brew --prefix`/lib/python2.7/site-packages; fi + - make -j3 check VERBOSE=1 From phk at FreeBSD.org Sat Mar 11 20:55:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Sat, 11 Mar 2017 21:55:05 +0100 Subject: [master] c011ffb VDP_FINI is not allowed to return failure. Message-ID: commit c011ffbacecca9748a103fe488a398bea977c994 Author: Poul-Henning Kamp Date: Sat Mar 11 20:54:00 2017 +0000 VDP_FINI is not allowed to return failure. diff --git a/bin/varnishd/http2/cache_http2_deliver.c b/bin/varnishd/http2/cache_http2_deliver.c index 920e0fa..3ef75a3 100644 --- a/bin/varnishd/http2/cache_http2_deliver.c +++ b/bin/varnishd/http2/cache_http2_deliver.c @@ -84,7 +84,7 @@ h2_bytes(struct req *req, enum vdp_action act, void **priv, if (act == VDP_INIT) return (0); - if (r2->error) + if (r2->error && act != VDP_FINI) return (-1); H2_Send_Get(req->wrk, r2->h2sess, r2); H2_Send(req->wrk, r2, From geoff at uplex.de Sun Mar 12 14:40:05 2017 From: geoff at uplex.de (Geoff Simmons) Date: Sun, 12 Mar 2017 15:40:05 +0100 Subject: [master] 4b2db5c Added some miscellaneous notes to Upgrading to 5.1. Message-ID: commit 4b2db5c633ffad78fb87a0decc916784cd4312d0 Author: Geoff Simmons Date: Sun Mar 12 15:38:43 2017 +0100 Added some miscellaneous notes to Upgrading to 5.1. diff --git a/doc/sphinx/whats-new/upgrading-5.1.rst b/doc/sphinx/whats-new/upgrading-5.1.rst index e518b42..5c2b27b 100644 --- a/doc/sphinx/whats-new/upgrading-5.1.rst +++ b/doc/sphinx/whats-new/upgrading-5.1.rst @@ -175,6 +175,8 @@ VMOD std Other changes ============= +* The storage backend type umem, long in disuse, has been retired. + * ``varnishstat(1)``: * Added the ``cache_hitmiss`` stat to to count hits on @@ -198,6 +200,10 @@ Other changes * Clarified the meaning of the ``%r`` formatter, see NOTES in :ref:`varnishncsa(1)`. + * Clarified the meaning of the ``%{X}i`` and ``%{X}o`` formatters + when the header X appears more than once (the last occurrence is + is used). + * ``varnishtest(1)``: * Added the ``process``, ``setenv`` and ``write_body`` commands, see @@ -209,6 +215,11 @@ Other changes * Added ``-cliexpect`` to match expected CLI responses to regular expressions. + * Added the ``-match`` operator for the ``shell`` command. + + * The ``err_shell`` command is deprecated, use ``shell -err + -expect`` instead. + * ``varnishtest`` can be stopped with the ``TERM``, ``INT`` of ``KILL`` signals, but not with ``HUP``. These signals kill the process group, so that processes started by running tests are stopped. From geoff at uplex.de Sun Mar 12 15:50:06 2017 From: geoff at uplex.de (Geoff Simmons) Date: Sun, 12 Mar 2017 16:50:06 +0100 Subject: [master] e8f004d Summarize the interpretation of + and - with the various data types in "Upgrading to 5.1". Message-ID: commit e8f004daa6e8b940c79e42eb2a3467a54a7fb806 Author: Geoff Simmons Date: Sun Mar 12 16:48:19 2017 +0100 Summarize the interpretation of + and - with the various data types in "Upgrading to 5.1". Also make an optimistic statement about the compatibility of VCL written for 5.0 with 5.1. diff --git a/doc/sphinx/whats-new/upgrading-5.1.rst b/doc/sphinx/whats-new/upgrading-5.1.rst index 5c2b27b..167aff1 100644 --- a/doc/sphinx/whats-new/upgrading-5.1.rst +++ b/doc/sphinx/whats-new/upgrading-5.1.rst @@ -70,9 +70,50 @@ varnishd parameters Changes to VCL ============== +VCL written for Varnish 5.0 will very likely work without changes in +version 5.1. We have added some new elements and capabilities to the +language (which you might like to start using), clarified some +matters, and deprecated some little-used language elements. + Type conversions ~~~~~~~~~~~~~~~~ +We have put some thought to the interpretation of the ``+`` and ``-`` +operators for various combinations of operands with differing data +types, many of which count as corner cases (what does it mean, for +example, to subtract a string from an IP address?). Recall that ``+`` +denotes addition for numeric operands, and string concatenation for +string operands; operands may be converted to strings and +concatenated, if a string is expected and there is no sensible numeric +interpretation. + +The semantics have not changed in nearly all cases, but the error +messages for illegal combinations of operands have improved. Most +importantly, we have taken the time to review these cases, so this +will be the way VCL works going forward. + +To summarize: + +* If both operands of ``+`` or ``-`` are one of BYTES, DURATION, INT + or REAL, then the result has the same data type, with the obvious + numeric interpretation. + +* INTs and REALs can be added or subtracted to yield a REAL. + +* A DURATION can be added to or subtracted from a TIME to yield a + TIME. + +* No other combinations of operand types are legal with ``-``. + +* If an expression with ``+`` is evaluated in a context where a STRING + is expected, then for all other combinations of operand data types, + the operands are converted to STRINGs and concatenated. + +* If a STRING is not expected for the ``+`` expression, then no other + combination of data types is legal. + +Other notes on data types: + * When ``bereq.backend`` is set to a director, then it returns an actual backend on subsequent reads if the director resolves to a backend immediately, or the director otherwise. If ``bereq.backend`` From geoff at uplex.de Sun Mar 12 15:56:05 2017 From: geoff at uplex.de (Geoff Simmons) Date: Sun, 12 Mar 2017 16:56:05 +0100 Subject: [master] 8f3ce04 Fix a double double word word. Message-ID: commit 8f3ce041214eb490b0d35951c362b3fac8537d4a Author: Geoff Simmons Date: Sun Mar 12 16:55:37 2017 +0100 Fix a double double word word. diff --git a/doc/sphinx/whats-new/upgrading-5.1.rst b/doc/sphinx/whats-new/upgrading-5.1.rst index 167aff1..1f02878 100644 --- a/doc/sphinx/whats-new/upgrading-5.1.rst +++ b/doc/sphinx/whats-new/upgrading-5.1.rst @@ -220,8 +220,8 @@ Other changes * ``varnishstat(1)``: - * Added the ``cache_hitmiss`` stat to to count hits on - hit-for-miss objects. + * Added the ``cache_hitmiss`` stat to count hits on hit-for-miss + objects. * The ``cache_hitpass`` stat now only counts hits on hit-for-pass objects. From phk at FreeBSD.org Sun Mar 12 19:36:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Sun, 12 Mar 2017 20:36:05 +0100 Subject: [master] 255b99a Add a new Req State to handle Expect & Connection, use it for H2. Message-ID: commit 255b99a90f82c5a3c41c9cd8b02524adf3d995a6 Author: Poul-Henning Kamp Date: Sun Mar 12 19:34:46 2017 +0000 Add a new Req State to handle Expect & Connection, use it for H2. diff --git a/bin/varnishd/cache/cache_req_fsm.c b/bin/varnishd/cache/cache_req_fsm.c index b8c4d20..733e45b 100644 --- a/bin/varnishd/cache/cache_req_fsm.c +++ b/bin/varnishd/cache/cache_req_fsm.c @@ -94,6 +94,17 @@ CNT_GotReq(struct worker *wrk, struct req *req) return (0); } +static enum req_fsm_nxt +cnt_transport(struct worker *wrk, struct req *req) +{ + + if (CNT_GotReq(wrk, req)) + return (REQ_FSM_DONE); + + req->req_step = R_STP_RECV; + return (REQ_FSM_MORE); +} + /*-------------------------------------------------------------------- * Deliver an object to client */ @@ -961,6 +972,7 @@ CNT_Request(struct worker *wrk, struct req *req) */ assert( req->req_step == R_STP_LOOKUP || + req->req_step == R_STP_TRANSPORT || req->req_step == R_STP_RECV); AN(req->vsl->wid & VSL_CLIENTMARKER); diff --git a/bin/varnishd/http2/cache_http2.h b/bin/varnishd/http2/cache_http2.h index 5599172..a3862e5 100644 --- a/bin/varnishd/http2/cache_http2.h +++ b/bin/varnishd/http2/cache_http2.h @@ -220,3 +220,4 @@ void h2_del_req(struct worker *, struct h2_req *); int h2_rxframe(struct worker *, struct h2_sess *); h2_error h2_set_setting(struct h2_sess *, const uint8_t *); void h2_req_body(struct req*); +task_func_t h2_do_req; diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index f4e7fc9..f6287b8 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -427,7 +427,7 @@ h2_rx_settings(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) * Incoming HEADERS, this is where the partys at... */ -static void __match_proto__(task_func_t) +void __match_proto__(task_func_t) h2_do_req(struct worker *wrk, void *priv) { struct req *req; @@ -436,8 +436,8 @@ h2_do_req(struct worker *wrk, void *priv) CAST_OBJ_NOTNULL(req, priv, REQ_MAGIC); CAST_OBJ_NOTNULL(r2, req->transport_priv, H2_REQ_MAGIC); THR_SetRequest(req); - if (!CNT_GotReq(wrk, req)) - assert(CNT_Request(wrk, req) != REQ_FSM_DISEMBARK); + req->req_step = R_STP_TRANSPORT; + assert(CNT_Request(wrk, req) != REQ_FSM_DISEMBARK); THR_SetRequest(NULL); VSL(SLT_Debug, 0, "H2REQ CNT done"); /* XXX clean up req */ @@ -491,7 +491,6 @@ h2_rx_headers(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) h2->new_req = req; req->sp = h2->sess; - req->req_step = R_STP_RECV; req->transport = &H2_transport; req->t_first = VTIM_real(); diff --git a/bin/varnishd/http2/cache_http2_session.c b/bin/varnishd/http2/cache_http2_session.c index 073d04f..6836f52 100644 --- a/bin/varnishd/http2/cache_http2_session.c +++ b/bin/varnishd/http2/cache_http2_session.c @@ -115,28 +115,6 @@ h2_new_sess(const struct worker *wrk, struct sess *sp, struct req *srq) return (h2); } -/********************************************************************** - * Incoming HEADERS, this is where the partys at... - */ - -static void __match_proto__(task_func_t) -h2_do_req(struct worker *wrk, void *priv) -{ - struct req *req; - struct h2_req *r2; - - CAST_OBJ_NOTNULL(req, priv, REQ_MAGIC); - CAST_OBJ_NOTNULL(r2, req->transport_priv, H2_REQ_MAGIC); - THR_SetRequest(req); - if (!CNT_GotReq(wrk, req)) - assert(CNT_Request(wrk, req) != REQ_FSM_DISEMBARK); - THR_SetRequest(NULL); - VSL(SLT_Debug, 0, "H2REQ CNT done"); - /* XXX clean up req */ - r2->state = H2_S_CLOSED; - h2_del_req(wrk, r2); -} - /**********************************************************************/ enum htc_status_e __match_proto__(htc_complete_f) diff --git a/include/tbl/steps.h b/include/tbl/steps.h index ab8d742..12deb9c 100644 --- a/include/tbl/steps.h +++ b/include/tbl/steps.h @@ -31,6 +31,7 @@ /*lint -save -e525 -e539 */ #ifdef REQ_STEP + REQ_STEP(transport, TRANSPORT, (wrk, req)) REQ_STEP(restart, RESTART, (wrk, req)) REQ_STEP(recv, RECV, (wrk, req)) REQ_STEP(pipe, PIPE, (wrk, req)) From phk at FreeBSD.org Sun Mar 12 20:24:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Sun, 12 Mar 2017 21:24:06 +0100 Subject: [master] 9a267ba Have HTTP1 use the new R_STP_TRANSPORT as well. Message-ID: commit 9a267ba2886e2b2240ad136551a36ad0e6f5a91b Author: Poul-Henning Kamp Date: Sun Mar 12 20:22:51 2017 +0000 Have HTTP1 use the new R_STP_TRANSPORT as well. diff --git a/bin/varnishd/cache/cache.h b/bin/varnishd/cache/cache.h index fba8763..7db4280 100644 --- a/bin/varnishd/cache/cache.h +++ b/bin/varnishd/cache/cache.h @@ -942,7 +942,6 @@ void VRB_Free(struct req *); /* cache_req_fsm.c [CNT] */ enum req_fsm_nxt CNT_Request(struct worker *, struct req *); void CNT_AcctLogCharge(struct dstat *, struct req *); -int CNT_GotReq(struct worker *, struct req *); /* cache_session.c [SES] */ struct sess *SES_New(struct pool *); diff --git a/bin/varnishd/cache/cache_req_fsm.c b/bin/varnishd/cache/cache_req_fsm.c index 733e45b..fa77dd8 100644 --- a/bin/varnishd/cache/cache_req_fsm.c +++ b/bin/varnishd/cache/cache_req_fsm.c @@ -53,8 +53,8 @@ * Handle "Expect:" and "Connection:" on incoming request */ -int -CNT_GotReq(struct worker *wrk, struct req *req) +static enum req_fsm_nxt +cnt_transport(struct worker *wrk, struct req *req) { const char *p; @@ -70,7 +70,7 @@ CNT_GotReq(struct worker *wrk, struct req *req) req->doclose = SC_RX_JUNK; (void)req->transport->minimal_response(req, 417); wrk->stats->client_req_417++; - return (-1); + return (REQ_FSM_DONE); } if (req->http->protover >= 11 && req->htc->pipeline_b == NULL) // XXX: HTTP1 vs 2 ? @@ -87,20 +87,10 @@ CNT_GotReq(struct worker *wrk, struct req *req) req->doclose = http_DoConnection(req->http); if (req->doclose == SC_RX_BAD) { (void)req->transport->minimal_response(req, 400); - return (-1); + return (REQ_FSM_DONE); } HTTP_Copy(req->http0, req->http); // For ESI & restart - return (0); -} - -static enum req_fsm_nxt -cnt_transport(struct worker *wrk, struct req *req) -{ - - if (CNT_GotReq(wrk, req)) - return (REQ_FSM_DONE); - req->req_step = R_STP_RECV; return (REQ_FSM_MORE); } diff --git a/bin/varnishd/http1/cache_http1_fsm.c b/bin/varnishd/http1/cache_http1_fsm.c index 5e8d42e..4b238c3 100644 --- a/bin/varnishd/http1/cache_http1_fsm.c +++ b/bin/varnishd/http1/cache_http1_fsm.c @@ -319,8 +319,7 @@ http1_dissect(struct worker *wrk, struct req *req) default: WRONG("Unknown req_body_status situation"); } - - return (CNT_GotReq(wrk, req)); + return (0); } /*---------------------------------------------------------------------- @@ -436,7 +435,7 @@ HTTP1_Session(struct worker *wrk, struct req *req) return; } } - req->req_step = R_STP_RECV; + req->req_step = R_STP_TRANSPORT; http1_setstate(sp, H1PROC); } else if (st == H1BUSY) { CHECK_OBJ_NOTNULL(req->transport, TRANSPORT_MAGIC); From phk at FreeBSD.org Sun Mar 12 20:52:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Sun, 12 Mar 2017 21:52:06 +0100 Subject: [master] 9d51cf7 Make H2 handle the waiting list. Message-ID: commit 9d51cf7e382cbbdf007a3d54ff506de145d6963d Author: Poul-Henning Kamp Date: Sun Mar 12 20:51:02 2017 +0000 Make H2 handle the waiting list. diff --git a/bin/varnishd/http1/cache_http1.h b/bin/varnishd/http1/cache_http1.h index bd74ed4..f3591127 100644 --- a/bin/varnishd/http1/cache_http1.h +++ b/bin/varnishd/http1/cache_http1.h @@ -34,7 +34,6 @@ int V1F_FetchRespHdr(struct busyobj *); int V1F_Setup_Fetch(struct vfp_ctx *vfc, struct http_conn *htc); /* cache_http1_fsm.c [HTTP1] */ -void HTTP1_Session(struct worker *, struct req *); extern const int HTTP1_Req[3]; extern const int HTTP1_Resp[3]; diff --git a/bin/varnishd/http1/cache_http1_fsm.c b/bin/varnishd/http1/cache_http1_fsm.c index 4b238c3..7ebee6b 100644 --- a/bin/varnishd/http1/cache_http1_fsm.c +++ b/bin/varnishd/http1/cache_http1_fsm.c @@ -51,6 +51,8 @@ static const char H1PROC[] = "HTTP1::Proc"; static const char H1BUSY[] = "HTTP1::Busy"; static const char H1CLEANUP[] = "HTTP1::Cleanup"; +static void HTTP1_Session(struct worker *, struct req *); + static void http1_setstate(const struct sess *sp, const char *s) { @@ -325,7 +327,7 @@ http1_dissect(struct worker *wrk, struct req *req) /*---------------------------------------------------------------------- */ -void +static void HTTP1_Session(struct worker *wrk, struct req *req) { enum htc_status_e hs; diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index f6287b8..0add0f9 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -436,13 +436,12 @@ h2_do_req(struct worker *wrk, void *priv) CAST_OBJ_NOTNULL(req, priv, REQ_MAGIC); CAST_OBJ_NOTNULL(r2, req->transport_priv, H2_REQ_MAGIC); THR_SetRequest(req); - req->req_step = R_STP_TRANSPORT; - assert(CNT_Request(wrk, req) != REQ_FSM_DISEMBARK); + if (CNT_Request(wrk, req) != REQ_FSM_DISEMBARK) { + VSL(SLT_Debug, 0, "H2REQ CNT done"); + r2->state = H2_S_CLOSED; + h2_del_req(wrk, r2); + } THR_SetRequest(NULL); - VSL(SLT_Debug, 0, "H2REQ CNT done"); - /* XXX clean up req */ - r2->state = H2_S_CLOSED; - h2_del_req(wrk, r2); } static h2_error @@ -464,6 +463,7 @@ h2_end_headers(const struct worker *wrk, const struct h2_sess *h2, else req->req_body_status = REQ_BODY_WITHOUT_LEN; + req->req_step = R_STP_TRANSPORT; req->task.func = h2_do_req; req->task.priv = req; XXXAZ(Pool_Task(wrk->pool, &req->task, TASK_QUEUE_REQ)); diff --git a/bin/varnishd/http2/cache_http2_session.c b/bin/varnishd/http2/cache_http2_session.c index 6836f52..6922166 100644 --- a/bin/varnishd/http2/cache_http2_session.c +++ b/bin/varnishd/http2/cache_http2_session.c @@ -223,6 +223,7 @@ h2_ou_session(const struct worker *wrk, struct h2_sess *h2, (void)h2_new_req(wrk, h2, 1, req); req->req_step = R_STP_RECV; req->transport = &H2_transport; + req->req_step = R_STP_TRANSPORT; req->task.func = h2_do_req; req->task.priv = req; req->err_code = 0; @@ -336,6 +337,30 @@ h2_new_session(struct worker *wrk, void *arg) h2_del_req(wrk, h2->req0); } +static void __match_proto__(vtr_reembark_f) +h2_reembark(struct worker *wrk, struct req *req) +{ + struct sess *sp; + + sp = req->sp; + CHECK_OBJ_NOTNULL(sp, SESS_MAGIC); + assert(req->transport == &H2_transport); + + if (!SES_Reschedule_Req(req)) + return; + + /* Couldn't schedule, ditch */ + wrk->stats->busy_wakeup--; + wrk->stats->busy_killed++; + AN (req->vcl); + VCL_Rel(&req->vcl); + CNT_AcctLogCharge(wrk->stats, req); + Req_Release(req); + DSL(DBG_WAITINGLIST, req->vsl->wid, "kill from waiting list"); + usleep(10000); +} + + struct transport H2_transport = { .name = "H2", .magic = TRANSPORT_MAGIC, @@ -344,4 +369,5 @@ struct transport H2_transport = { .deliver = h2_deliver, .req_body = h2_req_body, .minimal_response = h2_minimal_response, + .reembark = h2_reembark, }; diff --git a/bin/varnishtest/tests/t02009.vtc b/bin/varnishtest/tests/t02009.vtc new file mode 100644 index 0000000..2dc1cde --- /dev/null +++ b/bin/varnishtest/tests/t02009.vtc @@ -0,0 +1,31 @@ +varnishtest "H2 on waiting list" + +barrier b1 cond 2 + +server s1 { + rxreq + barrier b1 sync + delay 1 + txresp -hdr "Content-Type: text/plain" -body response +} -start + +varnish v1 -vcl+backend {} -start +varnish v1 -cliok {param.set feature +http2} +varnish v1 -cliok "param.set debug +syncvsl" + +client c1 { + stream 1 { + txreq + rxresp + expect resp.http.content-Type == "text/plain" + expect resp.body == response + } -start + stream 5 { + barrier b1 sync + txreq + rxresp + expect resp.http.content-Type == "text/plain" + expect resp.body == response + } -run + stream 1 -wait +} -run From geoff at uplex.de Sun Mar 12 21:03:05 2017 From: geoff at uplex.de (Geoff Simmons) Date: Sun, 12 Mar 2017 22:03:05 +0100 Subject: [master] 65c6290 Add miscellaneous notes to Upgrading to Varnish 5.1. Message-ID: commit 65c6290bd221953a6f91b5521698dd6b66d71656 Author: Geoff Simmons Date: Sun Mar 12 22:01:06 2017 +0100 Add miscellaneous notes to Upgrading to Varnish 5.1. diff --git a/doc/sphinx/whats-new/upgrading-5.1.rst b/doc/sphinx/whats-new/upgrading-5.1.rst index 1f02878..604b6c1 100644 --- a/doc/sphinx/whats-new/upgrading-5.1.rst +++ b/doc/sphinx/whats-new/upgrading-5.1.rst @@ -49,8 +49,9 @@ varnishd parameters command-line option and on the ``vsl_space`` and ``vsm_space`` parameters. -* Added ``clock_step`` and ``thread_pool_reserve`` (see - :ref:`ref_param_clock_step`, :ref:`ref_param_thread_pool_reserve`). +* Added ``clock_step``, ``thread_pool_reserve`` and ``ban_cutoff`` (see + :ref:`ref_param_clock_step`, :ref:`ref_param_thread_pool_reserve`, + :ref:`ref_param_ban_cutoff`). * ``thread_pool_stack`` is no longer considered experimental, and is more extensively documented, see :ref:`ref_param_thread_pool_stack`. @@ -167,6 +168,10 @@ All VCL subroutines (except ``vcl_fini``) ``vcl_fini`` is executed when a VCL instance in unloaded (enters the COLD state) and has no failure condition. +* VCL failure is invoked on any attempt to set one of the fields in the + the first line of a request or response to the empty string, such + as ``req.url``, ``req.proto``, ``req.reason`` and so forth. + Client-side VCL subroutines ~~~~~~~~~~~~~~~~~~~~~~~~~~~ @@ -213,6 +218,8 @@ VMOD std * Added ``std.getenv()``, see :ref:`func_getenv`. +* Added ``std.late_100_continue(BOOL)``, see :ref:`func_late_100_continue`. + Other changes ============= @@ -226,6 +233,19 @@ Other changes * The ``cache_hitpass`` stat now only counts hits on hit-for-pass objects. + * ``fetch_failed`` is incremented for any kind of fetch failure -- + when there is a failure after ``return(deliver)`` from + ``vcl_backend_response``, or when control is diverted to + ``vcl_backend_error``. + + * Added the ``n_test_gunzip`` stat, which is incremented when + Varnish verifies a compressed response from a backend -- this + operation was previously counted together with ``n_gunzip``. + + * Added the ``bans_lurker_obj_killed_cutoff`` to count the number of + objects killed by the ban lurker to keep the number of bans below + ``ban_cutoff``. + * ``varnishlog(1)``: * Hits on hit-for-miss and hit-for-pass objects are logged with @@ -236,6 +256,10 @@ Other changes * An entry with the ``TTL`` tag and the prefix ``HFP`` is logged to record the duration set for hit-for-pass objects. + * Added ``vxid`` as a lefthand side token for VSL queries, allowing + for queries that search for transaction IDs in the log. See + :ref:`vsl-query(7)`. + * ``varnishncsa(1)``: * Clarified the meaning of the ``%r`` formatter, see NOTES in @@ -258,9 +282,16 @@ Other changes * Added the ``-match`` operator for the ``shell`` command. + * Added the ``-hdrlen`` operator to generate a header with a + given name and length. + * The ``err_shell`` command is deprecated, use ``shell -err -expect`` instead. + * The ``${bad_backend}`` macro can now be used for a backend that + is always down, which does not require a port definition (as does + ``${bad_ip}`` in a backend definition). + * ``varnishtest`` can be stopped with the ``TERM``, ``INT`` of ``KILL`` signals, but not with ``HUP``. These signals kill the process group, so that processes started by running tests are stopped. From geoff at uplex.de Sun Mar 12 21:03:05 2017 From: geoff at uplex.de (Geoff Simmons) Date: Sun, 12 Mar 2017 22:03:05 +0100 Subject: [master] 91047a9 Grammar OCD Message-ID: commit 91047a9e4b1d6f8cfba3a8e65c05e9b409aa8a84 Author: Geoff Simmons Date: Sun Mar 12 22:02:45 2017 +0100 Grammar OCD diff --git a/doc/sphinx/whats-new/upgrading-5.1.rst b/doc/sphinx/whats-new/upgrading-5.1.rst index 604b6c1..98e4425 100644 --- a/doc/sphinx/whats-new/upgrading-5.1.rst +++ b/doc/sphinx/whats-new/upgrading-5.1.rst @@ -199,14 +199,15 @@ vcl_backend_response to a valid storage will set ``beresp.storage`` as well. If the storage is invalid, ``beresp.storage`` is left untouched. -When multiple storage backends have been defined with the ``-s`` -command-line option for varnishd, but none is explicitly set in -``vcl_backend_response``, storage selection and the use of the nuke -limit has been reworked (see :ref:`ref_param_nuke_limit`). Previously, -a storage backend was tried first with a nuke limit of 0, and retried -on failure with the limit configured as the ``-p`` parameter -``nuke_limit``. When no storage was specified, Varnish went through -every one in round-robin order with a nuke limit of 0 before retrying. +For the case where multiple storage backends have been defined with +the ``-s`` command-line option for varnishd, but none is explicitly +set in ``vcl_backend_response``, storage selection and the use of the +nuke limit has been reworked (see +:ref:`ref_param_nuke_limit`). Previously, a storage backend was tried +first with a nuke limit of 0, and retried on failure with the limit +configured as the ``-p`` parameter ``nuke_limit``. When no storage was +specified, Varnish went through every one in round-robin order with a +nuke limit of 0 before retrying. Now ``beresp.storage`` is initialized with a storage backend before ``vcl_backend_response`` executes, and the storage set in From fgsch at lodoss.net Sun Mar 12 21:24:05 2017 From: fgsch at lodoss.net (Federico G. Schwindt) Date: Sun, 12 Mar 2017 22:24:05 +0100 Subject: [master] cc2af9e When using -C remove temporary directories on exit Message-ID: commit cc2af9ead027fc4c501d2e894911af848fc57cfe Author: Federico G. Schwindt Date: Sun Mar 12 21:14:52 2017 +0000 When using -C remove temporary directories on exit OK phk. diff --git a/bin/varnishd/mgt/mgt_main.c b/bin/varnishd/mgt/mgt_main.c index edc89df..79bb3ed 100644 --- a/bin/varnishd/mgt/mgt_main.c +++ b/bin/varnishd/mgt/mgt_main.c @@ -68,6 +68,7 @@ struct vsb *vident; struct VSC_C_mgt static_VSC_C_mgt; struct VSC_C_mgt *VSC_C_mgt; static int I_fd = -1; +char Cn_arg[] = "/tmp/varnishd_C_XXXXXXX"; static struct vpf_fh *pfh = NULL; @@ -230,6 +231,17 @@ make_secret(const char *dirname) return (fn); } +static void +mgt_Cflag_atexit(void) +{ + + /* Only master process */ + if (getpid() != mgt_pid) + return; + (void)rmdir("vmod_cache"); + (void)rmdir(Cn_arg); +} + /*--------------------------------------------------------------------*/ static void @@ -481,7 +493,6 @@ main(int argc, char * const *argv) struct cli cli[1]; char *dirname; char **av; - char Cn_arg[] = "/tmp/varnishd_C_XXXXXXX"; unsigned u; struct sigaction sac; struct vev *e; @@ -728,14 +739,6 @@ main(int argc, char * const *argv) } assert(argc == optind); - if (C_flag) { - if (n_arg == NULL) { - AN(mkdtemp(Cn_arg)); - AZ(chmod(Cn_arg, 0755)); - n_arg = Cn_arg; - } - } - /* XXX: we can have multiple CLI actions above, is this enough ? */ if (cli[0].result != CLIS_OK) { AZ(VSB_finish(cli[0].sb)); @@ -745,6 +748,15 @@ main(int argc, char * const *argv) assert(d_flag == 0 || F_flag == 0); + if (C_flag) { + if (n_arg == NULL) { + AN(mkdtemp(Cn_arg)); + AZ(chmod(Cn_arg, 0755)); + AZ(atexit(mgt_Cflag_atexit)); + n_arg = Cn_arg; + } + } + if (S_arg != NULL && !strcmp(S_arg, "none")) { fprintf(stderr, "Warning: CLI authentication disabled.\n"); @@ -801,7 +813,6 @@ main(int argc, char * const *argv) fprintf(stderr, "%s\n", VSB_data(cli->sb)); VSB_clear(cli->sb); } - (void)rmdir(Cn_arg); exit(cli->result == CLIS_OK ? 0 : 2); } else { while (!VTAILQ_EMPTY(&f_args)) { From geoff at uplex.de Sun Mar 12 22:01:05 2017 From: geoff at uplex.de (Geoff Simmons) Date: Sun, 12 Mar 2017 23:01:05 +0100 Subject: [master] b72f755 Add some bugfixes to changes.rst. Message-ID: commit b72f755afbacc3c9f80bd47c1ba70cbf75fca0c9 Author: Geoff Simmons Date: Sun Mar 12 22:11:29 2017 +0100 Add some bugfixes to changes.rst. diff --git a/doc/changes.rst b/doc/changes.rst index 1dbba2a..0e2228f 100644 --- a/doc/changes.rst +++ b/doc/changes.rst @@ -8,6 +8,8 @@ Varnish Cache 5.1.0 (unreleased) Bugs fixed ---------- +* 2250_ - vrt.h now depends on vdef.h making current vmod fail. +* 2249_ - "logexpect -wait" doesn't fail * 2245_ - Varnish doesn't start, if use vmod (vmod_cache dir was permission denied) * 2241_ - VSL fails to get hold of SHM * 2233_ - Crash on "Assert error in WS_Assert(), cache/cache_ws.c line 59" @@ -65,6 +67,8 @@ Bugs fixed * 1750_ - Fail more gracefully on -l >= 4GB * 1704_ - fetch_failed not incremented +.. _2250: https://github.com/varnishcache/varnish-cache/issues/2250 +.. _2249: https://github.com/varnishcache/varnish-cache/issues/2249 .. _2245: https://github.com/varnishcache/varnish-cache/issues/2245 .. _2241: https://github.com/varnishcache/varnish-cache/issues/2241 .. _2233: https://github.com/varnishcache/varnish-cache/issues/2233 From geoff at uplex.de Sun Mar 12 22:01:05 2017 From: geoff at uplex.de (Geoff Simmons) Date: Sun, 12 Mar 2017 23:01:05 +0100 Subject: [master] a009f79 Update changes.rst for version 5.1. Message-ID: commit a009f79275f61d1c95476893be9cc2f2d2fe3755 Author: Geoff Simmons Date: Sun Mar 12 23:00:35 2017 +0100 Update changes.rst for version 5.1. diff --git a/doc/changes.rst b/doc/changes.rst index 0e2228f..dcc5cd2 100644 --- a/doc/changes.rst +++ b/doc/changes.rst @@ -2,8 +2,83 @@ Varnish Cache 5.1.0 (unreleased) ================================ -* The fallback director has now an extra, optional parameter to keep using the - current backend until it falls sick. +* Added varnishd command-line options -I, -x and -?, and tightened + restrictions on permitted combinations of options. + +* More progess on support for HTTP/2. + +* Add ``return(fail)`` to almost all VCL subroutines. + +* Restored the old hit-for-pass, invoked with + ``return(pass(DURATION))`` from + ``vcl_backend_response``. hit-for-miss remains the default. Added + the cache_hitmiss stat, and cache_hitpass only counts the new/old + hit-for-pass cases. Restored HitPass to the Varnish log, and added + HitMiss. Added the HFP prefix to TTL log entries to log a + hit-for-pass duration. + +* Rolled back the fix for #1206. Client delivery decides solely whether + to send a 304 client response, based on client request and response + headers. + +* Added vtest.sh. + +* Added vxid as a lefthand side for VSL queries. + +* Added the process, setenv and write_body commands for Varnish test + cases (vtc's). err_shell is deprecated. Also added the operators + -cliexpect, -match and -hdrlen, and -reason replaces -msg. Added the + ${bad_backend} macro. + +* varnishtest can be stopped with the TERM, INT and KILL signals, but + not with HUP. + +* The fallback director has now an extra, optional parameter to keep + using the current backend until it falls sick. + +* VMOD shared libraries are now copied to the workdir, to avoid problems + when VMODs are updated via packaging systems. + +* Bump the VRT version to 6.0. + +* Export more symbols from libvarnishapi.so. + +* The size of the VSL log is limited to 4G-1b, placing upper bounds on + the -l option and the vsl_space and vsm_space parameters. + +* Added parameters clock_step, thread_pool_reserve and ban_cutoff. + +* All parameters are defined, even on platforms that don't support + them. An unsupported parameter is documented as such in + param.show. Setting such a parameter is not an error, but has no + effect. + +* Clarified the interpretations of the + and - operators in VCL with + operands of the various data types. + +* DURATION types may be used in boolean contexts. + +* Response codes 1000 or greater may now be set in VCL internally. + resp.status is delivered modulo 1000 in client responses. + +* IP addresses can be compared for equality in VCL. + +* Introduce the STEVEDORE data type, and the objects storage.SNAME + in VCL. Added req.storage and beresp.storage; beresp.storage_hint + is deprecated. + +* Retired the umem stevedore. + +* req.ttl is deprecated. + +* Added std.getenv() and std.late_100_continue(BOOL). + +* The fetch_failed stat is incremented for any kind of fetch failure. + +* Added the stats n_test_gunzip and bans_lurker_obj_killed_cutoff. + +* Clarified the meanings of the %r, %{X}i and %{X}o formatters in + varnishncsa. Bugs fixed ---------- From phk at FreeBSD.org Sun Mar 12 22:11:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Sun, 12 Mar 2017 23:11:05 +0100 Subject: [master] 055f33d Start the worker (after -I processing) if we have a VCL and are not in -d mode. Message-ID: commit 055f33d743fbbb9a416eb233f74b0387c4b2e49a Author: Poul-Henning Kamp Date: Sun Mar 12 21:41:52 2017 +0000 Start the worker (after -I processing) if we have a VCL and are not in -d mode. diff --git a/bin/varnishd/mgt/mgt.h b/bin/varnishd/mgt/mgt.h index 02c58fe..f38ddd6 100644 --- a/bin/varnishd/mgt/mgt.h +++ b/bin/varnishd/mgt/mgt.h @@ -53,9 +53,10 @@ void MAC_Arg(const char *); void MAC_reopen_sockets(struct cli *); /* mgt_child.c */ -int MCH_Init(int launch); +void MCH_Init(void); int MCH_Running(void); void MCH_Stop_Child(void); +int MCH_Start_Child(void); void MCH_TrackHighFd(int fd); void MCH_Cli_Fail(void); diff --git a/bin/varnishd/mgt/mgt_child.c b/bin/varnishd/mgt/mgt_child.c index 8a6acf7..338ca53 100644 --- a/bin/varnishd/mgt/mgt_child.c +++ b/bin/varnishd/mgt/mgt_child.c @@ -597,6 +597,18 @@ MCH_Stop_Child(void) mgt_reap_child(); } +/*===================================================================== + */ + +int +MCH_Start_Child(void) +{ + mgt_launch_child(NULL); + if (child_state != CH_RUNNING) + return (2); + return(0); +} + /*==================================================================== * Query if the child is running */ @@ -668,17 +680,9 @@ static struct cli_proto cli_mch[] = { * and to reincarnate it in case of trouble. */ -int -MCH_Init(int launch) +void +MCH_Init(void) { VCLS_AddFunc(mgt_cls, MCF_AUTH, cli_mch); - - if (launch) { - mgt_launch_child(NULL); - if (child_state != CH_RUNNING) - return (2); - } - - return(0); } diff --git a/bin/varnishd/mgt/mgt_main.c b/bin/varnishd/mgt/mgt_main.c index 79bb3ed..cf8dbd9 100644 --- a/bin/varnishd/mgt/mgt_main.c +++ b/bin/varnishd/mgt/mgt_main.c @@ -862,9 +862,6 @@ main(int argc, char * const *argv) mgt_SHM_Create(); - if (!d_flag && !mgt_has_vcl() && !novcl) - MGT_Complain(C_ERR, "No VCL loaded yet"); - memset(&sac, 0, sizeof sac); sac.sa_handler = SIG_IGN; sac.sa_flags = SA_RESTART; @@ -872,7 +869,7 @@ main(int argc, char * const *argv) AZ(sigaction(SIGPIPE, &sac, NULL)); AZ(sigaction(SIGHUP, &sac, NULL)); - u = MCH_Init(d_flag || novcl ? 0 : 1); + MCH_Init(); if (I_fd >= 0) { fprintf(stderr, "BEGIN of -I file processing\n"); @@ -885,6 +882,14 @@ main(int argc, char * const *argv) } } + if (!d_flag && !mgt_has_vcl() && !novcl) + MGT_Complain(C_ERR, "No VCL loaded yet"); + + if (mgt_has_vcl() && ! d_flag) + u = MCH_Start_Child(); + else + u = 0; + if (eric_fd >= 0) mgt_eric_im_done(eric_fd, u); From phk at FreeBSD.org Sun Mar 12 22:11:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Sun, 12 Mar 2017 23:11:05 +0100 Subject: [master] 8649ed1 Add HTTP/2 status, minor tweaks. Message-ID: commit 8649ed1f80c746c1b6a5fce14f6dd34399cd6db0 Author: Poul-Henning Kamp Date: Sun Mar 12 21:44:24 2017 +0000 Add HTTP/2 status, minor tweaks. diff --git a/doc/sphinx/whats-new/changes-5.1.rst b/doc/sphinx/whats-new/changes-5.1.rst index 6092091..25cedbe 100644 --- a/doc/sphinx/whats-new/changes-5.1.rst +++ b/doc/sphinx/whats-new/changes-5.1.rst @@ -4,7 +4,7 @@ Changes in Varnish 5.1 ====================== We have a couple of new and interesting features in Varnish 5.1, -and we have a lot of smaller improvements and bugfixes all all over +and we have a lot of smaller improvements and bugfixes all over the place, in total we have made about 750 commits since Varnish 5.0, so this is just some of the highlights. @@ -22,8 +22,8 @@ addition to his other duties, he has taken care of the projects system administration and release engineering for most of the 11 years we have been around now. -Guys, "Thanks" doesn't even start to cover it and we wish you all -the best for the future! +Per & Lasse: "Thanks" doesn't even start to cover it, and we wish +you all the best for the future! .. _whatsnew_clifile: @@ -46,8 +46,8 @@ process starts, so it could for instance contain:: vcl.load main /etc/varnish_main.vcl vcl.use main -If the command is prefixed with '-', failure will not abort -the startup. +If a command in the file is prefixed with '-', failure will not +abort the startup. Related to this change we have reordered the argument checking so that argument problems are reported more consistently. @@ -79,7 +79,8 @@ to terminate forthright. In addition to ``return(fail)``, this mechanism will be used to handle all failure conditions without a safe fallback, for instance workspace exhaustion, too many -headers etc. +headers etc. (This is a work in progress, there is a +lot of code to review before we are done.) In ``vcl_init{}`` failing causes the ``vcl.load`` to fail. @@ -97,7 +98,23 @@ function which logs a SLT_VCL_Error record.) Progress on HTTP/2 support ~~~~~~~~~~~~~~~~~~~~~~~~~~ -XXX +HTTP/2 support is better than in 5.0, and is now enabled and survives +pretty well on our own varnish-cache.org website, but there are +still things missing, most notably windows and priority, which may +be fatal to more complex websites. + +We expect HTTP/2 support to be production ready in the autumn 2017 +release of Varnish-Cache, but that requires a testing and feedback +from real-world applications. + +So if you have a chance to test our HTTP/2 code, by all means do +so, please report any crashes, bugs or other trouble back to us. + +To enable HTTP/2 you need to ``param.set feature +http2`` but due +to internet-politics, you will only see HTTP/2 traffic if you have +an SSL proxy in front of Varnish which advertises HTTP2 with ALPN. + +For the hitch SSL proxy, add the argument ``--alpn-protos="h2,http/1.1"`` .. _whatsnew_changes_5.1_hitpass: @@ -274,5 +291,5 @@ News for authors of VMODs and Varnish API client applications name inside the workdir, from which the running VCL access it. This ensures that Varnishd can always restart the worker process, no matter what happened to the original VMOD file. - - + +*EOF* From phk at FreeBSD.org Mon Mar 13 07:48:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Mon, 13 Mar 2017 08:48:05 +0100 Subject: [master] fd186d9 Fix conditional requests in H2. Message-ID: commit fd186d9718f2651c13f8e8c278e4ed2c4e61510a Author: Poul-Henning Kamp Date: Mon Mar 13 07:45:57 2017 +0000 Fix conditional requests in H2. Fail vtc if -hdr doesn't have two args in H2 context. diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index 0add0f9..d1070b3 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -436,6 +436,7 @@ h2_do_req(struct worker *wrk, void *priv) CAST_OBJ_NOTNULL(req, priv, REQ_MAGIC); CAST_OBJ_NOTNULL(r2, req->transport_priv, H2_REQ_MAGIC); THR_SetRequest(req); + req->http->conds = 1; if (CNT_Request(wrk, req) != REQ_FSM_DISEMBARK) { VSL(SLT_Debug, 0, "H2REQ CNT done"); r2->state = H2_S_CLOSED; diff --git a/bin/varnishtest/tests/t02010.vtc b/bin/varnishtest/tests/t02010.vtc new file mode 100644 index 0000000..b6f24c9 --- /dev/null +++ b/bin/varnishtest/tests/t02010.vtc @@ -0,0 +1,80 @@ +varnishtest "Test H2 Client IMS" + +server s1 { + rxreq + expect req.url == "/foo" + txresp -hdr "Last-Modified: Thu, 26 Jun 2008 12:00:01 GMT" \ + -hdr {ETag: "foo"} \ + -body "11111\n" + rxreq + expect req.url == "/bar" + txresp -hdr "Last-Modified: Thu, 26 Jun 2008 12:00:01 GMT" \ + -hdr {ETag: "bar"} +} -start + +varnish v1 -vcl+backend { } -start +varnish v1 -cliok "param.set feature +http2" + +client c1 { + stream 1 { + txreq -url "/foo" + rxresp + expect resp.status == 200 + expect resp.http.etag == {"foo"} + expect resp.http.content-length == "6" + expect resp.bodylen == 6 + } -run + delay .1 + stream 3 { + txreq -url "/foo" \ + -hdr "if-modified-since" "Thu, 26 Jun 2008 12:00:00 GMT" + rxresp + expect resp.status == 200 + expect resp.http.content-length == "6" + expect resp.http.etag == {"foo"} + expect resp.bodylen == 6 + } -run + delay .1 + stream 5 { + txreq -url "/foo" \ + -hdr "if-modified-since" "Thu, 26 Jun 2008 12:00:01 GMT" + rxresp -no_obj + expect resp.status == 304 + expect resp.http.etag == {"foo"} + expect resp.http.content-length == "" + expect resp.bodylen == 0 + } -run + delay .1 + stream 7 { + txreq -url "/foo" \ + -hdr "if-modified-since" "Thu, 26 Jun 2008 12:00:02 GMT" + rxresp -no_obj + expect resp.status == 304 + expect resp.http.etag == {"foo"} + expect resp.http.content-length == "" + expect resp.bodylen == 0 + } -run + delay .1 + stream 9 { + txreq -url "/bar" + rxresp + expect resp.status == 200 + expect resp.http.etag == {"bar"} + expect resp.http.content-length == "0" + expect resp.bodylen == 0 + } -run + delay .1 + stream 11 { + txreq -url "/bar" \ + -hdr "if-modified-since" "Thu, 26 Jun 2008 12:00:01 GMT" + rxresp -no_obj + expect resp.status == 304 + expect resp.http.etag == {"bar"} + expect resp.http.content-length == + expect resp.bodylen == 0 + } -run +} + +client c1 -run + +# client c1 -run diff --git a/bin/varnishtest/vtc_http2.c b/bin/varnishtest/vtc_http2.c index 420a4db..b472d81 100644 --- a/bin/varnishtest/vtc_http2.c +++ b/bin/varnishtest/vtc_http2.c @@ -1452,6 +1452,8 @@ cmd_tx11obj(CMD_ARGS) scheme_done = 1; } else if (AV_IS("-hdr")) { + if (av[2] == NULL) + vtc_fatal(vl, "-hdr takes two arguments in http2"); ENC(hdr, av[1], av[2]); av += 2; } From dridi.boukelmoune at gmail.com Mon Mar 13 10:33:05 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Mon, 13 Mar 2017 11:33:05 +0100 Subject: [master] ef4dc6e Lck_ operations are limited to varnishd Message-ID: commit ef4dc6eaeaaeaa4e1c16c39ad25c11cd8dbe1930 Author: Dridi Boukelmoune Date: Mon Mar 13 11:28:10 2017 +0100 Lck_ operations are limited to varnishd diff --git a/bin/varnishhist/varnishhist.c b/bin/varnishhist/varnishhist.c index edb9044..19cbc33 100644 --- a/bin/varnishhist/varnishhist.c +++ b/bin/varnishhist/varnishhist.c @@ -357,7 +357,6 @@ accumulate(struct VSL_data *vsl, struct VSL_transaction * const pt[], if (vsl_ts > vsl_to) { double when = VTIM_real() + vsl_ts - vsl_to; struct timespec ts; - // Lck_CondWait ts.tv_nsec = (long)(modf(when, &t) * 1e9); ts.tv_sec = (long)t; i = pthread_cond_timedwait(&timebend_cv, &mtx, &ts); From phk at FreeBSD.org Mon Mar 13 10:38:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Mon, 13 Mar 2017 11:38:05 +0100 Subject: [master] 18e425b Keep the H2 rx window open. Message-ID: commit 18e425b49888bd23dcea7998d07bb8737f9d7396 Author: Poul-Henning Kamp Date: Mon Mar 13 10:37:03 2017 +0000 Keep the H2 rx window open. diff --git a/bin/varnishd/http2/cache_http2.h b/bin/varnishd/http2/cache_http2.h index a3862e5..89b85df 100644 --- a/bin/varnishd/http2/cache_http2.h +++ b/bin/varnishd/http2/cache_http2.h @@ -120,7 +120,8 @@ struct h2_req { struct h2_sess *h2sess; struct req *req; VTAILQ_ENTRY(h2_req) list; - int64_t window; + int64_t t_window; + int64_t r_window; struct h2h_decode *decode; /* Where to wake this stream up */ @@ -139,6 +140,9 @@ struct h2_sess { struct h2_req *mailcall; pthread_cond_t *cond; + int64_t r_window; + int64_t t_window; + struct sess *sess; int refcnt; uint32_t highest_stream; diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index d1070b3..fb7bfd1 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -149,6 +149,8 @@ h2_new_req(const struct worker *wrk, struct h2_sess *h2, r2->h2sess = h2; r2->stream = stream; r2->req = req; + r2->r_window = h2->local_settings.initial_window_size; + r2->t_window = h2->remote_settings.initial_window_size; req->transport_priv = r2; Lck_Lock(&h2->sess->mtx); VTAILQ_INSERT_TAIL(&h2->streams, r2, list); @@ -314,9 +316,9 @@ h2_rx_window_update(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) if (r2 == NULL) return (0); Lck_Lock(&h2->sess->mtx); - r2->window += wu; + r2->t_window += wu; Lck_Unlock(&h2->sess->mtx); - if (r2->window >= (1LLU << 31)) + if (r2->t_window >= (1LLU << 31)) return (H2SE_FLOW_CONTROL_ERROR); return (0); } @@ -558,14 +560,40 @@ h2_rx_continuation(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) static h2_error __match_proto__(h2_frame_f) h2_rx_data(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) { + int w1 = 0, w2 = 0; + char buf[4]; + unsigned wi; + (void)wrk; AZ(h2->mailcall); h2->mailcall = r2; Lck_Lock(&h2->sess->mtx); + h2->r_window -= h2->rxf_len; + r2->r_window -= h2->rxf_len; AZ(pthread_cond_broadcast(h2->cond)); while (h2->mailcall != NULL && h2->error == 0 && r2->error == 0) AZ(Lck_CondWait(h2->cond, &h2->sess->mtx, 0)); + wi = cache_param->h2_rx_window_increment; + if (h2->r_window < cache_param->h2_rx_window_low_water) { + h2->r_window += wi; + w1 = 1; + } + if (r2->r_window < cache_param->h2_rx_window_low_water) { + r2->r_window += wi; + w2 = 1; + } Lck_Unlock(&h2->sess->mtx); + if (w1 || w2) { + vbe32enc(buf, wi); + H2_Send_Get(wrk, h2, r2); + if (w1) + H2_Send_Frame(wrk, h2, H2_F_WINDOW_UPDATE, 0, + 4, 0, buf); + if (w2) + H2_Send_Frame(wrk, h2, H2_F_WINDOW_UPDATE, 0, + 4, r2->stream, buf); + H2_Send_Rel(h2, r2); + } return (0); } diff --git a/bin/varnishtest/tests/t02005.vtc b/bin/varnishtest/tests/t02005.vtc index 55647ff..2cf31ee 100644 --- a/bin/varnishtest/tests/t02005.vtc +++ b/bin/varnishtest/tests/t02005.vtc @@ -12,6 +12,7 @@ client c1 { stream 1 { txreq -req POST -hdr content-type text/plain -hdr content-length 7 -body request + rxwinup # First, HTTP checks rxresp expect resp.http.content-Type == "text/plain" diff --git a/bin/varnishtest/tests/t02006.vtc b/bin/varnishtest/tests/t02006.vtc index 44a9c89..c95feb0 100644 --- a/bin/varnishtest/tests/t02006.vtc +++ b/bin/varnishtest/tests/t02006.vtc @@ -27,6 +27,7 @@ client c1 { rxhdrs expect resp.status == 100 + rxwinup rxresp expect resp.status == 200 expect resp.http.content-Type == "text/plain" diff --git a/bin/varnishtest/tests/t02007.vtc b/bin/varnishtest/tests/t02007.vtc index b0e329e..e9068da 100644 --- a/bin/varnishtest/tests/t02007.vtc +++ b/bin/varnishtest/tests/t02007.vtc @@ -32,6 +32,7 @@ client c1 { rxhdrs expect resp.status == 100 + rxwinup rxresp expect resp.status == 200 expect resp.http.content-Type == "text/plain" diff --git a/bin/varnishtest/tests/t02009.vtc b/bin/varnishtest/tests/t02009.vtc index 2dc1cde..511f54f 100644 --- a/bin/varnishtest/tests/t02009.vtc +++ b/bin/varnishtest/tests/t02009.vtc @@ -15,14 +15,14 @@ varnish v1 -cliok "param.set debug +syncvsl" client c1 { stream 1 { - txreq + txreq rxresp expect resp.http.content-Type == "text/plain" expect resp.body == response } -start stream 5 { barrier b1 sync - txreq + txreq rxresp expect resp.http.content-Type == "text/plain" expect resp.body == response diff --git a/include/tbl/h2_settings.h b/include/tbl/h2_settings.h index 765ee18..7214bef 100644 --- a/include/tbl/h2_settings.h +++ b/include/tbl/h2_settings.h @@ -42,7 +42,7 @@ H2_SETTING( // rfc7540,l,2097,2103 HEADER_TABLE_SIZE, header_table_size, 0x1, - 4096, + 4096, // rfc7540,l,4224,4224 0, 0xffffffff, 0 @@ -51,7 +51,7 @@ H2_SETTING( // rfc7540,l,2105,2114 ENABLE_PUSH, enable_push, 0x2, - 1, + 1, // rfc7540,l,4225,4225 0, 1, H2CE_PROTOCOL_ERROR @@ -60,7 +60,7 @@ H2_SETTING( // rfc7540,l,2116,2121 MAX_CONCURRENT_STREAMS, max_concurrent_streams, 0x3, - 0xffffffff, + 0xffffffff, // rfc7540,l,4226,4226 0, 0xffffffff, 0 @@ -69,7 +69,7 @@ H2_SETTING( // rfc7540,l,2139,2148 INITIAL_WINDOW_SIZE, initial_window_size, 0x4, - 65535, + 65535, // rfc7540,l,4227,4227 0, 0x7fffffff, H2CE_FLOW_CONTROL_ERROR @@ -78,7 +78,7 @@ H2_SETTING( // rfc7540,l,2150,2157 MAX_FRAME_SIZE, max_frame_size, 0x5, - 16384, + 16384, // rfc7540,l,4228,4228 16384, 0x00ffffff, H2CE_PROTOCOL_ERROR @@ -87,7 +87,7 @@ H2_SETTING( // rfc7540,l,2159,2167 MAX_HEADER_LIST_SIZE, max_header_list_size, 0x6, - 0xffffffff, + 0xffffffff, // rfc7540,l,4229,4229 0, 0xffffffff, 0 diff --git a/include/tbl/params.h b/include/tbl/params.h index 49f77ac..cc12632 100644 --- a/include/tbl/params.h +++ b/include/tbl/params.h @@ -1651,6 +1651,38 @@ PARAM( /* func */ NULL ) +PARAM( + /* name */ h2_rx_window_low_water, + /* typ */ bytes_u, + /* min */ "65535", + /* max */ "1G", + /* default */ "10M", + /* units */ "bytes", + /* flags */ WIZARD, + /* s-text */ + "HTTP2 Receive Window low water mark.\n" + "We try to keep the window at least this big\n" + "Only affects incoming request bodies (ie: POST, PUT etc.)", + /* l-text */ "", + /* func */ NULL +) + +PARAM( + /* name */ h2_rx_window_increment, + /* typ */ bytes_u, + /* min */ "1M", + /* max */ "1G", + /* default */ "1M", + /* units */ "bytes", + /* flags */ WIZARD, + /* s-text */ + "HTTP2 Receive Window Increments.\n" + "How big credits we send in WINDOW_UPDATE frames\n" + "Only affects incoming request bodies (ie: POST, PUT etc.)", + /* l-text */ "", + /* func */ NULL +) + #undef PARAM /*lint -restore */ diff --git a/include/vrt.h b/include/vrt.h index 34da0ac..2a0f6f2 100644 --- a/include/vrt.h +++ b/include/vrt.h @@ -68,7 +68,7 @@ #ifdef __v_printflike # define __vrt_printflike(a,b) __v_printflike(a,b) #else -# define __vrt_printflike(a,b) +# define __vrt_printflike(a,b) #endif struct VCL_conf; From phk at FreeBSD.org Mon Mar 13 10:43:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Mon, 13 Mar 2017 11:43:05 +0100 Subject: [master] 2f40990 Staticize Message-ID: commit 2f40990e48602e807b3392829f19732cfbcc4899 Author: Poul-Henning Kamp Date: Mon Mar 13 10:42:25 2017 +0000 Staticize diff --git a/bin/varnishd/mgt/mgt_main.c b/bin/varnishd/mgt/mgt_main.c index cf8dbd9..896d6e0 100644 --- a/bin/varnishd/mgt/mgt_main.c +++ b/bin/varnishd/mgt/mgt_main.c @@ -68,7 +68,7 @@ struct vsb *vident; struct VSC_C_mgt static_VSC_C_mgt; struct VSC_C_mgt *VSC_C_mgt; static int I_fd = -1; -char Cn_arg[] = "/tmp/varnishd_C_XXXXXXX"; +static char Cn_arg[] = "/tmp/varnishd_C_XXXXXXX"; static struct vpf_fh *pfh = NULL; From fgsch at lodoss.net Mon Mar 13 11:12:06 2017 From: fgsch at lodoss.net (Federico G. Schwindt) Date: Mon, 13 Mar 2017 12:12:06 +0100 Subject: [master] 2adcd88 Update Message-ID: commit 2adcd88f214c0735dfb91f241bb02c532bc5e473 Author: Federico G. Schwindt Date: Mon Mar 13 11:10:49 2017 +0000 Update diff --git a/doc/changes.rst b/doc/changes.rst index dcc5cd2..1406c17 100644 --- a/doc/changes.rst +++ b/doc/changes.rst @@ -5,7 +5,7 @@ Varnish Cache 5.1.0 (unreleased) * Added varnishd command-line options -I, -x and -?, and tightened restrictions on permitted combinations of options. -* More progess on support for HTTP/2. +* More progress on support for HTTP/2. * Add ``return(fail)`` to almost all VCL subroutines. @@ -58,6 +58,8 @@ Varnish Cache 5.1.0 (unreleased) * DURATION types may be used in boolean contexts. +* INT, DURATION and REAL values can now be negative. + * Response codes 1000 or greater may now be set in VCL internally. resp.status is delivered modulo 1000 in client responses. @@ -71,7 +73,7 @@ Varnish Cache 5.1.0 (unreleased) * req.ttl is deprecated. -* Added std.getenv() and std.late_100_continue(BOOL). +* Added std.getenv() and std.late_100_continue(). * The fetch_failed stat is incremented for any kind of fetch failure. diff --git a/doc/sphinx/whats-new/upgrading-5.1.rst b/doc/sphinx/whats-new/upgrading-5.1.rst index 98e4425..2accfdc 100644 --- a/doc/sphinx/whats-new/upgrading-5.1.rst +++ b/doc/sphinx/whats-new/upgrading-5.1.rst @@ -127,6 +127,8 @@ Other notes on data types: false when the duration is less than or equal to zero, true otherwise. +* INT, DURATION and REAL values can now be negative. + Response codes ~~~~~~~~~~~~~~ @@ -214,12 +216,12 @@ Now ``beresp.storage`` is initialized with a storage backend before ``beresp.storage`` after its execution will be used. The configured nuke limit is used in all cases. -VMOD std +vmod_std ~~~~~~~~ * Added ``std.getenv()``, see :ref:`func_getenv`. -* Added ``std.late_100_continue(BOOL)``, see :ref:`func_late_100_continue`. +* Added ``std.late_100_continue()``, see :ref:`func_late_100_continue`. Other changes ============= diff --git a/include/tbl/vsc_f_main.h b/include/tbl/vsc_f_main.h index fd26c19..206cd03 100644 --- a/include/tbl/vsc_f_main.h +++ b/include/tbl/vsc_f_main.h @@ -574,7 +574,7 @@ VSC_FF(bans_lurker_tests_tested, uint64_t, 0, 'c', 'i', diag, "Ban tests tested against objects (lurker)", "Count of how many tests and objects have been tested against" " each other by the ban-lurker." - " 'ban req.url == foo && req.http.host == bar'" + " 'ban req.url == foo && req.http.host == bar'" " counts as one in 'bans_tested' and as two in 'bans_tests_tested'" ) From phk at FreeBSD.org Mon Mar 13 12:34:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Mon, 13 Mar 2017 13:34:06 +0100 Subject: [master] 4042ed2 Use the right h2req for sending window updates Message-ID: commit 4042ed234bf3b14a89436851971833bd7f08bf07 Author: Poul-Henning Kamp Date: Mon Mar 13 12:32:34 2017 +0000 Use the right h2req for sending window updates diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index fb7bfd1..cbb3c52 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -585,14 +585,14 @@ h2_rx_data(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) Lck_Unlock(&h2->sess->mtx); if (w1 || w2) { vbe32enc(buf, wi); - H2_Send_Get(wrk, h2, r2); + H2_Send_Get(wrk, h2, h2->req0); if (w1) H2_Send_Frame(wrk, h2, H2_F_WINDOW_UPDATE, 0, 4, 0, buf); if (w2) H2_Send_Frame(wrk, h2, H2_F_WINDOW_UPDATE, 0, 4, r2->stream, buf); - H2_Send_Rel(h2, r2); + H2_Send_Rel(h2, h2->req0); } return (0); } From dridi.boukelmoune at gmail.com Mon Mar 13 12:45:07 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Mon, 13 Mar 2017 13:45:07 +0100 Subject: [master] 7c328f9 Make miniobj work downstream Message-ID: commit 7c328f916d870d3a54bcdb91e08e30acbee0af9b Author: Dridi Boukelmoune Date: Sat Mar 11 13:50:34 2017 +0100 Make miniobj work downstream diff --git a/configure.ac b/configure.ac index b9463f6..a85b19a 100644 --- a/configure.ac +++ b/configure.ac @@ -194,7 +194,7 @@ AC_CHECK_HEADERS([pthread_np.h], [], [], [#include ]) AC_CHECK_HEADERS([priv.h]) # Checks for library functions. -AC_CHECK_FUNCS([explicit_bzero]) +_VARNISH_CHECK_EXPLICIT_BZERO AC_CHECK_FUNCS([nanosleep]) AC_CHECK_FUNCS([setppriv]) AC_CHECK_FUNCS([fallocate]) diff --git a/include/miniobj.h b/include/miniobj.h index 952a068..8186b9b 100644 --- a/include/miniobj.h +++ b/include/miniobj.h @@ -5,7 +5,7 @@ * */ -#if HAVE_EXPLICIT_BZERO +#ifdef HAVE_EXPLICIT_BZERO # define ZERO_OBJ(to, sz) explicit_bzero(to, sz) #else # define ZERO_OBJ(to, sz) (void)memset(to, 0, sz) diff --git a/varnish.m4 b/varnish.m4 index efb3c3b..b2157ce 100644 --- a/varnish.m4 +++ b/varnish.m4 @@ -62,6 +62,12 @@ AC_DEFUN([_VARNISH_SEARCH_LIBS], [ LIBS="${save_LIBS}" ]) +# _VARNISH_CHECK_EXPLICIT_BZERO() +# ------------------------------- +AC_DEFUN([_VARNISH_CHECK_EXPLICIT_BZERO], [ + AC_CHECK_FUNCS([explicit_bzero]) +]) + # _VARNISH_PKG_CONFIG # -------------------- AC_DEFUN([_VARNISH_PKG_CONFIG], [ @@ -91,6 +97,7 @@ AC_DEFUN([_VARNISH_PKG_CONFIG], [ AC_DEFUN([_VARNISH_CHECK_DEVEL], [ AC_REQUIRE([_VARNISH_PKG_CONFIG]) + AC_REQUIRE([_VARNISH_CHECK_EXPLICIT_BZERO]) [_orig_cppflags=$CPPFLAGS] [CPPFLAGS=$VARNISHAPI_CFLAGS] @@ -358,6 +365,7 @@ AC_DEFUN([VARNISH_VMODS], [ # AC_DEFUN([VARNISH_PREREQ], [ AC_REQUIRE([_VARNISH_PKG_CONFIG]) + AC_REQUIRE([_VARNISH_CHECK_EXPLICIT_BZERO]) AC_MSG_CHECKING([for Varnish]) AC_MSG_RESULT([$VARNISH_VERSION]) From fgsch at lodoss.net Mon Mar 13 15:46:05 2017 From: fgsch at lodoss.net (Federico G. Schwindt) Date: Mon, 13 Mar 2017 16:46:05 +0100 Subject: [master] ee5b896 Update config as per travis' support suggestion Message-ID: commit ee5b896bdcee4faf042423694f264fa382a6910d Author: Federico G. Schwindt Date: Mon Mar 13 15:43:57 2017 +0000 Update config as per travis' support suggestion Remove gcc from osx - by default it is actually clang with a different name. diff --git a/.travis.yml b/.travis.yml index 953d203..c339f55 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,11 +1,18 @@ --- language: c -compiler: - - clang - - gcc -os: - - linux - - osx +matrix: + include: + - os: linux + dist: trusty + sudo: false + compiler: gcc + - os: linux + dist: trusty + sudo: false + compiler: clang + - os: osx + osx_image: xcode8.2 + compiler: clang addons: apt: packages: @@ -16,9 +23,6 @@ before_install: - if [[ "$TRAVIS_OS_NAME" == "osx" ]]; then brew install nghttp2 ; fi - ./autogen.sh - ./configure -dist: trusty -sudo: false -osx_image: xcode8.2 script: - if [[ "$TRAVIS_OS_NAME" == "osx" ]]; then export PYTHONPATH=`brew --prefix`/lib/python2.7/site-packages; fi From dridi.boukelmoune at gmail.com Mon Mar 13 16:40:07 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Mon, 13 Mar 2017 17:40:07 +0100 Subject: [master] 35ac814 Update fetch FSM with return(pass) Message-ID: commit 35ac814e7cc3c6944c1e460db33589e84a45acc1 Author: Dridi Boukelmoune Date: Mon Mar 13 14:24:37 2017 +0100 Update fetch FSM with return(pass) diff --git a/doc/graphviz/cache_fetch.dot b/doc/graphviz/cache_fetch.dot index f6fc959..5e65495 100644 --- a/doc/graphviz/cache_fetch.dot +++ b/doc/graphviz/cache_fetch.dot @@ -47,7 +47,7 @@ digraph cache_fetch { v_b_hdrs -> v_b_e v_b_r [ shape=record - label="{vbf_stp_startfetch:|{vcl_backend_response\{\}|{bereq.*|beresp.*}}|{{retry|{max?|ok?}}|abandon|{deliver|{304?|other?}}}}" + label="{vbf_stp_startfetch:|{vcl_backend_response\{\}|{bereq.*|beresp.*}}|{{retry|{max?|ok?}}|abandon|{deliver or pass|{304?|other?}}}}" ] v_b_r:retry -> v_b_r_retry [color=purple] v_b_r:max -> v_b_e diff --git a/doc/graphviz/cache_fetch.svg b/doc/graphviz/cache_fetch.svg index a79dea9..f329e59 100644 --- a/doc/graphviz/cache_fetch.svg +++ b/doc/graphviz/cache_fetch.svg @@ -14,91 +14,91 @@ RETRY -RETRY +RETRY v_b_f - -vbf_stp_startfetch: - -vcl_backend_fetch{} - -bereq.* - -abandon - -fetch + +vbf_stp_startfetch: + +vcl_backend_fetch{} + +bereq.* + +abandon + +fetch RETRY->v_b_f - - + + v_b_f_BGFETCH - -BGFETCH + +BGFETCH v_b_f_BGFETCH->v_b_f - - + + v_b_f_FETCH - -FETCH + +FETCH v_b_f_FETCH->v_b_f - - + + v_b_f_FETCH->v_b_f - - + + v_b_hdrs - -send bereq, -read beresp (headers) + +send bereq, +read beresp (headers) v_b_f:fetch:s->v_b_hdrs - - + + v_b_r - -vbf_stp_startfetch: - + +vbf_stp_startfetch: + vcl_backend_response{} - -bereq.* - -beresp.* - -retry - -max? - -ok? - -abandon - -deliver - + +bereq.* + +beresp.* + +retry + +max? + +ok? + +abandon + +deliver or pass + 304? - -other? + +other? v_b_hdrs->v_b_r - - + + v_b_e @@ -123,13 +123,13 @@ v_b_hdrs->v_b_e - - + + v_b_r:max->v_b_e - - + + v_b_r_retry @@ -137,26 +137,26 @@ v_b_r:retry->v_b_r_retry - - + + vbf_stp_condfetch - -vbf_stp_condfetch: - -copy obj attr - -steal body - -fetch_fail? - -ok? + +vbf_stp_condfetch: + +copy obj attr + +steal body + +fetch_fail? + +ok? v_b_r:fetch_304:s->vbf_stp_condfetch - - + + vbf_stp_fetch @@ -173,19 +173,19 @@ v_b_r:non_304:s->vbf_stp_fetch - - + + FETCH_DONE - -FETCH_DONE + +FETCH_DONE v_b_e:deliver->FETCH_DONE - - -"backend synth" + + +"backend synth" FETCH_FAIL @@ -208,52 +208,52 @@ vbf_stp_fetchend - -vbf_stp_fetchend: - -finalize object and director - -done + +vbf_stp_fetchend: + +finalize object and director + +done vbf_stp_condfetch:ok:s->vbf_stp_fetchend - - + + vbf_stp_fetchbody - -vbf_stp_fetchbody: - -get storage - -read body, run VFPs - -fetch_fail? - -error? - -ok? + +vbf_stp_fetchbody: + +get storage + +read body, run VFPs + +fetch_fail? + +error? + +ok? vbf_stp_fetch:body:s->vbf_stp_fetchbody - - + + vbf_stp_fetch:body:s->vbf_stp_fetchend - - + + vbf_stp_fetchbody:ok:s->vbf_stp_fetchend - - + + vbf_stp_fetchend:done:s->FETCH_DONE - - + + error From dridi.boukelmoune at gmail.com Mon Mar 13 16:40:07 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Mon, 13 Mar 2017 17:40:07 +0100 Subject: [master] 89705bd Warn about global state in VMODs Message-ID: commit 89705bd2b1be138d002bb5dd56f9a35597f9efbd Author: Dridi Boukelmoune Date: Mon Mar 13 14:25:05 2017 +0100 Warn about global state in VMODs diff --git a/doc/sphinx/whats-new/changes-5.1.rst b/doc/sphinx/whats-new/changes-5.1.rst index 25cedbe..a0c2297 100644 --- a/doc/sphinx/whats-new/changes-5.1.rst +++ b/doc/sphinx/whats-new/changes-5.1.rst @@ -291,5 +291,10 @@ News for authors of VMODs and Varnish API client applications name inside the workdir, from which the running VCL access it. This ensures that Varnishd can always restart the worker process, no matter what happened to the original VMOD file. + + It also means that VMODs maintaining state spanning VCL reloads might + break. It is still possible to maintain global state in a VMOD despite + VMOD caching: one solution is to move the global state into separate + shared library that won't be cached by Varnish. *EOF* From dridi.boukelmoune at gmail.com Mon Mar 13 16:40:07 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Mon, 13 Mar 2017 17:40:07 +0100 Subject: [master] 752a002 Clarify Message-ID: commit 752a00269b7cdf268a1555d1f033c4919698772c Author: Dridi Boukelmoune Date: Mon Mar 13 14:28:36 2017 +0100 Clarify diff --git a/doc/sphinx/whats-new/changes-5.1.rst b/doc/sphinx/whats-new/changes-5.1.rst index a0c2297..3a81cde 100644 --- a/doc/sphinx/whats-new/changes-5.1.rst +++ b/doc/sphinx/whats-new/changes-5.1.rst @@ -82,7 +82,8 @@ fallback, for instance workspace exhaustion, too many headers etc. (This is a work in progress, there is a lot of code to review before we are done.) -In ``vcl_init{}`` failing causes the ``vcl.load`` to fail. +In ``vcl_init{}`` failing causes the ``vcl.load`` to fail, +this is nothing new for this sub-routine. A failure in any of the client side VCL methods (``vcl_recv{}``, ``vcl_hash{}`` ...) *except* ``vcl_synth{}``, sends the request From dridi.boukelmoune at gmail.com Mon Mar 13 16:40:07 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Mon, 13 Mar 2017 17:40:07 +0100 Subject: [master] 70d37c5 Breaking change Message-ID: commit 70d37c569442ec531fa15f10008224dbe66f5f96 Author: Dridi Boukelmoune Date: Mon Mar 13 14:30:35 2017 +0100 Breaking change diff --git a/doc/sphinx/whats-new/changes-5.1.rst b/doc/sphinx/whats-new/changes-5.1.rst index 3a81cde..1a56bbf 100644 --- a/doc/sphinx/whats-new/changes-5.1.rst +++ b/doc/sphinx/whats-new/changes-5.1.rst @@ -233,7 +233,8 @@ in the project. The ``varnishtest`` program has been improved in many small ways, in particular it is now much easier to execute and examine results from other programs with the ``shell`` and ``process`` -commands. +commands. It might break existing test cases if you were already +using ``varnishtest``. The project now has *KISS* web-backend which summarizes ``make distcheck`` results from various platforms: From dridi.boukelmoune at gmail.com Mon Mar 13 16:40:07 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Mon, 13 Mar 2017 17:40:07 +0100 Subject: [master] 44f9423 Remove euphemism Message-ID: commit 44f9423493dffd89877737d4cf91f27a1add788b Author: Dridi Boukelmoune Date: Mon Mar 13 14:31:40 2017 +0100 Remove euphemism diff --git a/doc/sphinx/whats-new/changes-5.1.rst b/doc/sphinx/whats-new/changes-5.1.rst index 1a56bbf..28a77af 100644 --- a/doc/sphinx/whats-new/changes-5.1.rst +++ b/doc/sphinx/whats-new/changes-5.1.rst @@ -250,7 +250,7 @@ We also publish our code-coverage status now: http://varnish-cache.org/gcov/ -Our goal is 90+% coverage, but we need to finish implementing +Our goal is 90+% coverage, but we need to start implementing terminal emulation in ``varnishtest`` before we can test the curses(1) based programs (top/stat/hist) comprehensively, so they currently drag us down. From dridi.boukelmoune at gmail.com Mon Mar 13 16:40:07 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Mon, 13 Mar 2017 17:40:07 +0100 Subject: [master] 3857621 Mention BACKEND comparison now fully working Message-ID: commit 3857621bfe0ebe22f77a3f6def7239d620ccf02c Author: Dridi Boukelmoune Date: Mon Mar 13 15:39:47 2017 +0100 Mention BACKEND comparison now fully working diff --git a/doc/sphinx/whats-new/upgrading-5.1.rst b/doc/sphinx/whats-new/upgrading-5.1.rst index 2accfdc..1e7747d 100644 --- a/doc/sphinx/whats-new/upgrading-5.1.rst +++ b/doc/sphinx/whats-new/upgrading-5.1.rst @@ -118,11 +118,17 @@ Other notes on data types: * When ``bereq.backend`` is set to a director, then it returns an actual backend on subsequent reads if the director resolves to a backend immediately, or the director otherwise. If ``bereq.backend`` - was set to a director, then ``beresp.backend`` returns the backend + was set to a director, then ``beresp.backend`` references the backend to which it was set for the fetch. When either of these is used in string context, it returns the name of the director or of the resolved backend. +* Comparisons between symbols of type BACKEND now work properly:: + + if (bereq.backend == foo.backend()) { + # do something specific to the foo backends + } + * DURATION types may be used in boolean contexts, and are evaluated as false when the duration is less than or equal to zero, true otherwise. From dridi.boukelmoune at gmail.com Mon Mar 13 16:40:07 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Mon, 13 Mar 2017 17:40:07 +0100 Subject: [master] c31390c The `process` command was introduced in 5.0 Message-ID: commit c31390c0dc54f0a764af7674144349c4c464e012 Author: Dridi Boukelmoune Date: Mon Mar 13 15:51:13 2017 +0100 The `process` command was introduced in 5.0 diff --git a/doc/changes.rst b/doc/changes.rst index 1406c17..9515b5b 100644 --- a/doc/changes.rst +++ b/doc/changes.rst @@ -25,10 +25,9 @@ Varnish Cache 5.1.0 (unreleased) * Added vxid as a lefthand side for VSL queries. -* Added the process, setenv and write_body commands for Varnish test - cases (vtc's). err_shell is deprecated. Also added the operators - -cliexpect, -match and -hdrlen, and -reason replaces -msg. Added the - ${bad_backend} macro. +* Added the setenv and write_body commands for Varnish test cases (VTCs). + err_shell is deprecated. Also added the operators -cliexpect, -match and + -hdrlen, and -reason replaces -msg. Added the ${bad_backend} macro. * varnishtest can be stopped with the TERM, INT and KILL signals, but not with HUP. diff --git a/doc/sphinx/whats-new/upgrading-5.1.rst b/doc/sphinx/whats-new/upgrading-5.1.rst index 1e7747d..ab99260 100644 --- a/doc/sphinx/whats-new/upgrading-5.1.rst +++ b/doc/sphinx/whats-new/upgrading-5.1.rst @@ -280,8 +280,7 @@ Other changes * ``varnishtest(1)``: - * Added the ``process``, ``setenv`` and ``write_body`` commands, see - :ref:`vtc(7)` . + * Added the ``setenv`` and ``write_body`` commands, see :ref:`vtc(7)`. * ``-reason`` replaces ``-msg`` to set the reason string for a response (default "OK"). From dridi.boukelmoune at gmail.com Mon Mar 13 16:40:07 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Mon, 13 Mar 2017 17:40:07 +0100 Subject: [master] 8be1d6b Suggest -f '' with -I in varnishd(1) Message-ID: commit 8be1d6bdaf202fdcb23fe44939f96ddb5332e357 Author: Dridi Boukelmoune Date: Mon Mar 13 16:30:00 2017 +0100 Suggest -f '' with -I in varnishd(1) diff --git a/doc/sphinx/reference/varnishd.rst b/doc/sphinx/reference/varnishd.rst index ada8875..73d0c97 100644 --- a/doc/sphinx/reference/varnishd.rst +++ b/doc/sphinx/reference/varnishd.rst @@ -66,6 +66,9 @@ Basic options `varnishd` in debugging mode. If the empty string is specified as the sole -f option, then `varnishd` starts without starting the worker process, and the management process will accept CLI commands. + You can also combine an empty -f option with an initialization + script (-I option) and the child process will be started if there + is an active VCL at the end of the initialization. -n name From dridi.boukelmoune at gmail.com Mon Mar 13 16:40:07 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Mon, 13 Mar 2017 17:40:07 +0100 Subject: [master] a96e465 Whitespace OCD Message-ID: commit a96e465904beb9e193d55d55be3247d4a3255b9d Author: Dridi Boukelmoune Date: Mon Mar 13 17:37:11 2017 +0100 Whitespace OCD diff --git a/doc/sphinx/whats-new/changes-5.1.rst b/doc/sphinx/whats-new/changes-5.1.rst index 28a77af..6093e09 100644 --- a/doc/sphinx/whats-new/changes-5.1.rst +++ b/doc/sphinx/whats-new/changes-5.1.rst @@ -298,5 +298,5 @@ News for authors of VMODs and Varnish API client applications break. It is still possible to maintain global state in a VMOD despite VMOD caching: one solution is to move the global state into separate shared library that won't be cached by Varnish. - -*EOF* + +*EOF* From dridi.boukelmoune at gmail.com Mon Mar 13 16:45:06 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Mon, 13 Mar 2017 17:45:06 +0100 Subject: [master] 7ef9b11 Mention that varnishd -x outputs RST Message-ID: commit 7ef9b110ed70d4ff2bea54010d8f756216052772 Author: Dridi Boukelmoune Date: Mon Mar 13 17:44:18 2017 +0100 Mention that varnishd -x outputs RST diff --git a/doc/sphinx/reference/varnishd.rst b/doc/sphinx/reference/varnishd.rst index 73d0c97..3b34004 100644 --- a/doc/sphinx/reference/varnishd.rst +++ b/doc/sphinx/reference/varnishd.rst @@ -82,7 +82,8 @@ Documentation options --------------------- For these options, `varnishd` prints information to standard output -and exits. When a -x option is used, it must be the only option. +and exits. When a -x option is used, it must be the only option (it +outputs documentation in reStructuredText, aka RST). -? From dridi.boukelmoune at gmail.com Mon Mar 13 17:31:05 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Mon, 13 Mar 2017 18:31:05 +0100 Subject: [master] 4c9f9e0 Fix rendering of varnishd -? in sphinx Message-ID: commit 4c9f9e08295ef86bc79ed389cf9ee85e24258e56 Author: Dridi Boukelmoune Date: Mon Mar 13 18:23:59 2017 +0100 Fix rendering of varnishd -? in sphinx Apparently rst2man and sphinx don't have the same opinion on what an option is or isn't. Looking at the RST spec it doesn't seem to allow a question mark [1] in an option list. Among the various kind of options we can see: Short POSIX options consist of one dash and an option letter. To work around that I introduced a crude hack using sed. It satisfies my OCD but I'm not even remotely proud of that. [1] http://docutils.sourceforge.net/docs/ref/rst/restructuredtext.html#option-lists diff --git a/doc/sphinx/Makefile.am b/doc/sphinx/Makefile.am index 255ce4e..a4303be 100644 --- a/doc/sphinx/Makefile.am +++ b/doc/sphinx/Makefile.am @@ -46,6 +46,8 @@ all: link_srcdir html: sphinx_prereq $(SPHINXBUILD) -b html $(ALLSPHINXOPTS) $(BUILDDIR)/html + @sed -i 's/Q.*UESTION_MARK_HACK/?/' \ + $(BUILDDIR)/html/reference/varnishd.html @echo @echo "Build finished. The HTML pages are in $(BUILDDIR)/html." diff --git a/doc/sphinx/reference/varnishd.rst b/doc/sphinx/reference/varnishd.rst index 3b34004..7bb27e9 100644 --- a/doc/sphinx/reference/varnishd.rst +++ b/doc/sphinx/reference/varnishd.rst @@ -85,7 +85,7 @@ For these options, `varnishd` prints information to standard output and exits. When a -x option is used, it must be the only option (it outputs documentation in reStructuredText, aka RST). --? +-QUESTION_MARK_HACK Print the usage message. diff --git a/man/Makefile.am b/man/Makefile.am index 2b61fbb..312d0b3 100644 --- a/man/Makefile.am +++ b/man/Makefile.am @@ -46,6 +46,7 @@ varnishd.1: \ $(top_builddir)/doc/sphinx/reference/varnishd.rst \ $(top_builddir)/doc/sphinx/include/params.rst ${RST2MAN} $(RST2ANY_FLAGS) $(top_builddir)/doc/sphinx/reference/varnishd.rst $@ + @sed -i 's/Q.*UESTION_MARK_HACK/?/' $@ varnishncsa.1: \ $(top_builddir)/doc/sphinx/reference/varnishncsa.rst \ From dridi.boukelmoune at gmail.com Mon Mar 13 18:00:08 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Mon, 13 Mar 2017 19:00:08 +0100 Subject: [master] 100adab Help sed understand what the expression is Message-ID: commit 100adab299e146a2fea849e5fb6786397c09c577 Author: Dridi Boukelmoune Date: Mon Mar 13 18:58:16 2017 +0100 Help sed understand what the expression is According to vtest the hack fails on FreeBSD i386, so either it fixes it or I revert the whole thing. diff --git a/doc/sphinx/Makefile.am b/doc/sphinx/Makefile.am index a4303be..be5a677 100644 --- a/doc/sphinx/Makefile.am +++ b/doc/sphinx/Makefile.am @@ -46,7 +46,7 @@ all: link_srcdir html: sphinx_prereq $(SPHINXBUILD) -b html $(ALLSPHINXOPTS) $(BUILDDIR)/html - @sed -i 's/Q.*UESTION_MARK_HACK/?/' \ + @sed -i -e 's/Q.*UESTION_MARK_HACK/?/' \ $(BUILDDIR)/html/reference/varnishd.html @echo @echo "Build finished. The HTML pages are in $(BUILDDIR)/html." diff --git a/man/Makefile.am b/man/Makefile.am index 312d0b3..15ce81f 100644 --- a/man/Makefile.am +++ b/man/Makefile.am @@ -46,7 +46,7 @@ varnishd.1: \ $(top_builddir)/doc/sphinx/reference/varnishd.rst \ $(top_builddir)/doc/sphinx/include/params.rst ${RST2MAN} $(RST2ANY_FLAGS) $(top_builddir)/doc/sphinx/reference/varnishd.rst $@ - @sed -i 's/Q.*UESTION_MARK_HACK/?/' $@ + @sed -i -e 's/Q.*UESTION_MARK_HACK/?/' $@ varnishncsa.1: \ $(top_builddir)/doc/sphinx/reference/varnishncsa.rst \ From dridi.boukelmoune at gmail.com Mon Mar 13 18:41:05 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Mon, 13 Mar 2017 19:41:05 +0100 Subject: [master] fc25bb5 Revert "Help sed understand what the expression is" Message-ID: commit fc25bb598a3cb7424badc08684172e6b7f33e755 Author: Dridi Boukelmoune Date: Mon Mar 13 19:35:08 2017 +0100 Revert "Help sed understand what the expression is" This reverts commit 100adab299e146a2fea849e5fb6786397c09c577. In-place sed on FreeBSD isn't compatible with GNU sed. It could be fixed with a temp file, but meh. diff --git a/doc/sphinx/Makefile.am b/doc/sphinx/Makefile.am index be5a677..a4303be 100644 --- a/doc/sphinx/Makefile.am +++ b/doc/sphinx/Makefile.am @@ -46,7 +46,7 @@ all: link_srcdir html: sphinx_prereq $(SPHINXBUILD) -b html $(ALLSPHINXOPTS) $(BUILDDIR)/html - @sed -i -e 's/Q.*UESTION_MARK_HACK/?/' \ + @sed -i 's/Q.*UESTION_MARK_HACK/?/' \ $(BUILDDIR)/html/reference/varnishd.html @echo @echo "Build finished. The HTML pages are in $(BUILDDIR)/html." diff --git a/man/Makefile.am b/man/Makefile.am index 15ce81f..312d0b3 100644 --- a/man/Makefile.am +++ b/man/Makefile.am @@ -46,7 +46,7 @@ varnishd.1: \ $(top_builddir)/doc/sphinx/reference/varnishd.rst \ $(top_builddir)/doc/sphinx/include/params.rst ${RST2MAN} $(RST2ANY_FLAGS) $(top_builddir)/doc/sphinx/reference/varnishd.rst $@ - @sed -i -e 's/Q.*UESTION_MARK_HACK/?/' $@ + @sed -i 's/Q.*UESTION_MARK_HACK/?/' $@ varnishncsa.1: \ $(top_builddir)/doc/sphinx/reference/varnishncsa.rst \ From dridi.boukelmoune at gmail.com Mon Mar 13 18:41:05 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Mon, 13 Mar 2017 19:41:05 +0100 Subject: [master] 85658ab Revert "Fix rendering of varnishd -? in sphinx" Message-ID: commit 85658ab59e1391365fbcf2cb6db5f787e289b4ae Author: Dridi Boukelmoune Date: Mon Mar 13 19:36:36 2017 +0100 Revert "Fix rendering of varnishd -? in sphinx" This reverts commit 4c9f9e08295ef86bc79ed389cf9ee85e24258e56. The generated HTML and troff code wasn't valid anyway. That would ruffle another OCD of mine. diff --git a/doc/sphinx/Makefile.am b/doc/sphinx/Makefile.am index a4303be..255ce4e 100644 --- a/doc/sphinx/Makefile.am +++ b/doc/sphinx/Makefile.am @@ -46,8 +46,6 @@ all: link_srcdir html: sphinx_prereq $(SPHINXBUILD) -b html $(ALLSPHINXOPTS) $(BUILDDIR)/html - @sed -i 's/Q.*UESTION_MARK_HACK/?/' \ - $(BUILDDIR)/html/reference/varnishd.html @echo @echo "Build finished. The HTML pages are in $(BUILDDIR)/html." diff --git a/doc/sphinx/reference/varnishd.rst b/doc/sphinx/reference/varnishd.rst index 7bb27e9..3b34004 100644 --- a/doc/sphinx/reference/varnishd.rst +++ b/doc/sphinx/reference/varnishd.rst @@ -85,7 +85,7 @@ For these options, `varnishd` prints information to standard output and exits. When a -x option is used, it must be the only option (it outputs documentation in reStructuredText, aka RST). --QUESTION_MARK_HACK +-? Print the usage message. diff --git a/man/Makefile.am b/man/Makefile.am index 312d0b3..2b61fbb 100644 --- a/man/Makefile.am +++ b/man/Makefile.am @@ -46,7 +46,6 @@ varnishd.1: \ $(top_builddir)/doc/sphinx/reference/varnishd.rst \ $(top_builddir)/doc/sphinx/include/params.rst ${RST2MAN} $(RST2ANY_FLAGS) $(top_builddir)/doc/sphinx/reference/varnishd.rst $@ - @sed -i 's/Q.*UESTION_MARK_HACK/?/' $@ varnishncsa.1: \ $(top_builddir)/doc/sphinx/reference/varnishncsa.rst \ From phk at FreeBSD.org Tue Mar 14 08:00:08 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Tue, 14 Mar 2017 09:00:08 +0100 Subject: [master] e3ef3cf Make sure the VSM overflow code has at least been executed once. Message-ID: commit e3ef3cf0a931874062307569e46bc0082f86254e Author: Poul-Henning Kamp Date: Tue Mar 14 07:59:15 2017 +0000 Make sure the VSM overflow code has at least been executed once. diff --git a/bin/varnishtest/tests/c00083.vtc b/bin/varnishtest/tests/c00083.vtc new file mode 100644 index 0000000..9b80321 --- /dev/null +++ b/bin/varnishtest/tests/c00083.vtc @@ -0,0 +1,30 @@ +varnishtest "VSM overflow allocation" + +server s1 { + rxreq + txresp +} -start + +varnish v1 -arg "-pvcc_allow_inline_c=true" -vcl+backend { + + C{ + void *VSM_Alloc(unsigned size, const char *class, const char *type, + const char *ident); + void VSM_Free(void *ptr); + }C + + sub vcl_recv { + C{ + void *p; + p = VSM_Alloc(3 * 1024 * 1024, "TEST", "TYPE", "0"); + VSM_Free(p); + }C + } + +} -start + +client c1 { + txreq + rxresp +} -run + From dridi.boukelmoune at gmail.com Tue Mar 14 09:59:06 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Tue, 14 Mar 2017 10:59:06 +0100 Subject: [master] 0ae899d Make a bigger deal of VXID in VSL queries Message-ID: commit 0ae899d2f30f3fd3834b67600fda9c5f1a89892a Author: Dridi Boukelmoune Date: Tue Mar 14 10:52:50 2017 +0100 Make a bigger deal of VXID in VSL queries As suggested by Geoff, it probably deserves a short description. diff --git a/doc/sphinx/whats-new/changes-5.1.rst b/doc/sphinx/whats-new/changes-5.1.rst index 6093e09..a35b599 100644 --- a/doc/sphinx/whats-new/changes-5.1.rst +++ b/doc/sphinx/whats-new/changes-5.1.rst @@ -222,6 +222,63 @@ removing the ``ETag`` or ``Last-Modified`` headers in ``vcl_backend_response``, or by removing the If-* client request headers in ``vcl_pass``. +VXID in VSL queries +~~~~~~~~~~~~~~~~~~~ + +The Varnish Shared Log (VSL) became much more powerful starting Varnish +4.0 and hasn't changed much since. Changes usually consist in adding new +log records when new feature are introduced, or when we realize that some +missing piece of information could really help troubleshooting. + +Varnish UTilities (VUT) relying on the VSL usually share the same ``-q`` +option for querying, which allows to filter transactions based on log +records. For example you could be looking for figures on a specific +domain:: + + varnishtop -i ReqURL -q 'ReqHeader:Host eq www.example.com' + +While options like ``-i`` and ``-q`` were until now both limited to log +records, it also meant you could only query a specific transaction using +the ``X-Varnish`` header. Depending on the nature of the transaction +(client or backend side) the syntax is not the same and you can't match +a session. + +For instance, we are looking for the transaction 1234 that occurred very +recently and we would like to collect everything from the same session. +We have two options:: + + # client side + varnishlog -d -g session -q 'RespHeader:X-Varnish[1] == 1234' + + # backend side + varnishlog -d -g session -q 'BereqHeader:X-Varnish == 1234' + +There was no simple way to match any transaction using its id until the +introduction of ``vxid`` as a possible left-hand side of a ``-q`` query +expression:: + + # client side + varnishlog -d -g session -q 'vxid == 1234' + + # backend side + varnishlog -d -g session -q 'vxid == 1234' + + # session + varnishlog -d -g session -q 'vxid == 1234' + +Another use case is the collection of non-transactional logs. With raw +grouping the output is organized differently and each record starts with +its transaction id or zero for non-transactional logs:: + + # before 5.1 + varnishlog -g raw | awk '$1 == 0' + + # from now on + varnishlog -g raw -q 'vxid == 0' + +This should offer you a more concise, and more consistent means to filter +transactions with ``varnishlog`` and other VUTs. + .. _whatsnew_changes_5.1_vtest: Project tool improvements @@ -236,7 +293,7 @@ results from other programs with the ``shell`` and ``process`` commands. It might break existing test cases if you were already using ``varnishtest``. -The project now has *KISS* web-backend which summarizes +The project now has *KISS* web-backend which summarizes ``make distcheck`` results from various platforms: http://varnish-cache.org/vtest/ From dridi.boukelmoune at gmail.com Tue Mar 14 10:46:06 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Tue, 14 Mar 2017 11:46:06 +0100 Subject: [master] c207078 Describe VMODs as VCL modules Message-ID: commit c2070784e2de3c75a1949599aed74c8fa01a1a65 Author: Dridi Boukelmoune Date: Tue Mar 14 11:43:54 2017 +0100 Describe VMODs as VCL modules diff --git a/doc/sphinx/reference/vcl.rst b/doc/sphinx/reference/vcl.rst index 075c345..a53e543 100644 --- a/doc/sphinx/reference/vcl.rst +++ b/doc/sphinx/reference/vcl.rst @@ -174,7 +174,7 @@ To include a VCL file in another file use the include keyword:: Import statement ---------------- -The ``import`` statement is used to load Varnish Modules (VMODs.) +The ``import`` statement is used to load VCL modules (VMODs.) Example:: diff --git a/doc/sphinx/reference/vmod.rst b/doc/sphinx/reference/vmod.rst index 910d613..1b8b0cf 100644 --- a/doc/sphinx/reference/vmod.rst +++ b/doc/sphinx/reference/vmod.rst @@ -1,8 +1,8 @@ .. _ref-vmod: -%%%%%%%%%%%%%%%%%%%%%% -VMOD - Varnish Modules -%%%%%%%%%%%%%%%%%%%%%% +%%%%%%%%%%%%%%%%%% +VMOD - VCL Modules +%%%%%%%%%%%%%%%%%% For all you can do in VCL, there are things you can not do. Look an IP number up in a database file for instance. diff --git a/doc/sphinx/users-guide/vcl-backends.rst b/doc/sphinx/users-guide/vcl-backends.rst index 5844891..6da1855 100644 --- a/doc/sphinx/users-guide/vcl-backends.rst +++ b/doc/sphinx/users-guide/vcl-backends.rst @@ -120,9 +120,9 @@ You can also group several backend into a group of backends. These groups are called directors. This will give you increased performance and resilience. -You can define several backends and group them together in a -director. This requires you to load a VMOD, a Varnish module, and then to -call certain actions in `vcl_init`.:: +You can define several backends and group them together in a director. +This requires you to load a VMOD, a VCL module, and then to call certain +actions in `vcl_init`.:: import directors; # load the directors From dridi.boukelmoune at gmail.com Tue Mar 14 14:34:05 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Tue, 14 Mar 2017 15:34:05 +0100 Subject: [master] fca8307 More VRT changes Message-ID: commit fca8307dea81b5db48557b2dd4fc1c43cb09064c Author: Dridi Boukelmoune Date: Tue Mar 14 15:31:16 2017 +0100 More VRT changes For future reference, I browsed the changes for this development cycle easily with: git log --patch --reverse varnish-5.0.0.. -- include/vrt.h diff --git a/include/vrt.h b/include/vrt.h index 2a0f6f2..bb56e00 100644 --- a/include/vrt.h +++ b/include/vrt.h @@ -42,6 +42,11 @@ * 6.0 (unreleased): * VRT_hit_for_pass added * VRT_ipcmp added + * VRT_Vmod_Init signature changed + * VRT_vcl_lookup removed + * VRT_vcl_get added + * VRT_vcl_rel added + * VRT_fail added * WS_Reset and WS_Snapshot signatures changed * WS_Front added * WS_ReserveLumps added From geoff at uplex.de Tue Mar 14 14:41:06 2017 From: geoff at uplex.de (Geoff Simmons) Date: Tue, 14 Mar 2017 15:41:06 +0100 Subject: [master] 1b80bb8 Document "math first, then string conversion" Message-ID: commit 1b80bb8589bbe60f47272bf1ad15d9f3e47f49fa Author: Geoff Simmons Date: Tue Mar 14 15:39:50 2017 +0100 Document "math first, then string conversion" diff --git a/doc/sphinx/whats-new/upgrading-5.1.rst b/doc/sphinx/whats-new/upgrading-5.1.rst index ab99260..e3bc039 100644 --- a/doc/sphinx/whats-new/upgrading-5.1.rst +++ b/doc/sphinx/whats-new/upgrading-5.1.rst @@ -97,7 +97,10 @@ To summarize: * If both operands of ``+`` or ``-`` are one of BYTES, DURATION, INT or REAL, then the result has the same data type, with the obvious - numeric interpretation. + numeric interpretation. If such an expression is evaluated in a + context that expects a STRING (for example for assignment to a + header), then the arithmetic is done first, and the result it + converted to a STRING. * INTs and REALs can be added or subtracted to yield a REAL. @@ -106,9 +109,9 @@ To summarize: * No other combinations of operand types are legal with ``-``. -* If an expression with ``+`` is evaluated in a context where a STRING - is expected, then for all other combinations of operand data types, - the operands are converted to STRINGs and concatenated. +* When a ``+`` expression is evaluated in a STRING context, then for + all other combinations of operand data types, the operands are + converted to STRINGs and concatenated. * If a STRING is not expected for the ``+`` expression, then no other combination of data types is legal. From geoff at uplex.de Tue Mar 14 14:45:07 2017 From: geoff at uplex.de (Geoff Simmons) Date: Tue, 14 Mar 2017 15:45:07 +0100 Subject: [master] 6324d39 It's resp.reason, not req.reason Message-ID: commit 6324d396262eea7ed172a7d2007753302f5850ad Author: Geoff Simmons Date: Tue Mar 14 15:44:33 2017 +0100 It's resp.reason, not req.reason diff --git a/doc/sphinx/whats-new/upgrading-5.1.rst b/doc/sphinx/whats-new/upgrading-5.1.rst index e3bc039..4d15c88 100644 --- a/doc/sphinx/whats-new/upgrading-5.1.rst +++ b/doc/sphinx/whats-new/upgrading-5.1.rst @@ -181,7 +181,7 @@ All VCL subroutines (except ``vcl_fini``) * VCL failure is invoked on any attempt to set one of the fields in the the first line of a request or response to the empty string, such - as ``req.url``, ``req.proto``, ``req.reason`` and so forth. + as ``req.url``, ``req.proto``, ``resp.reason`` and so forth. Client-side VCL subroutines ~~~~~~~~~~~~~~~~~~~~~~~~~~~ From geoff at uplex.de Tue Mar 14 14:48:05 2017 From: geoff at uplex.de (Geoff Simmons) Date: Tue, 14 Mar 2017 15:48:05 +0100 Subject: [master] cfce68d Grammar Message-ID: commit cfce68d64556f579394ead658baa4aaf5798bf2a Author: Geoff Simmons Date: Tue Mar 14 15:47:50 2017 +0100 Grammar diff --git a/doc/sphinx/whats-new/upgrading-5.1.rst b/doc/sphinx/whats-new/upgrading-5.1.rst index 4d15c88..528c2d1 100644 --- a/doc/sphinx/whats-new/upgrading-5.1.rst +++ b/doc/sphinx/whats-new/upgrading-5.1.rst @@ -254,9 +254,9 @@ Other changes Varnish verifies a compressed response from a backend -- this operation was previously counted together with ``n_gunzip``. - * Added the ``bans_lurker_obj_killed_cutoff`` to count the number of - objects killed by the ban lurker to keep the number of bans below - ``ban_cutoff``. + * Added the ``bans_lurker_obj_killed_cutoff`` stat to count the + number of objects killed by the ban lurker to keep the number of + bans below ``ban_cutoff``. * ``varnishlog(1)``: From dridi.boukelmoune at gmail.com Tue Mar 14 14:59:06 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Tue, 14 Mar 2017 15:59:06 +0100 Subject: [master] 0b84709 Avoid platform-dependent documentation Message-ID: commit 0b84709c238fe9c00371a21832ccb58db3b13d92 Author: Dridi Boukelmoune Date: Tue Mar 14 15:53:33 2017 +0100 Avoid platform-dependent documentation The varnish-cli will however still report when a parameter is not available. Spotted by Geoff. diff --git a/bin/varnishd/mgt/mgt_param.c b/bin/varnishd/mgt/mgt_param.c index e74cc57..7615228 100644 --- a/bin/varnishd/mgt/mgt_param.c +++ b/bin/varnishd/mgt/mgt_param.c @@ -100,6 +100,10 @@ static const char NOT_IMPLEMENTED_TEXT[] = "This parameter depends on a feature which is not available" " on this platform."; +static const char NOT_IMPLEMENTED_DOC[] = + "NB: This parameter depends on a feature which is not available" + " on all platforms."; + /*--------------------------------------------------------------------*/ static struct parspec * @@ -561,11 +565,8 @@ MCF_DumpRstParam(void) printf("~"); printf("\n"); - if (pp->flags && pp->flags & NOT_IMPLEMENTED) { - printf("\nNot Available: %s\n\n", - NOT_IMPLEMENTED_TEXT); - continue; - } + if (pp->flags && pp->flags & NOT_IMPLEMENTED) + printf("\n%s\n\n", NOT_IMPLEMENTED_DOC); if (pp->units != NULL && *pp->units != '\0') printf("\t* Units: %s\n", pp->units); @@ -583,8 +584,6 @@ MCF_DumpRstParam(void) printf("\t* Flags: "); q = ""; - AZ(pp->flags & NOT_IMPLEMENTED); - if (pp->flags & DELAYED_EFFECT) { printf("%sdelayed", q); q = ", "; From dridi.boukelmoune at gmail.com Tue Mar 14 15:26:06 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Tue, 14 Mar 2017 16:26:06 +0100 Subject: [master] 0c1408c Revert "Describe VMODs as VCL modules" Message-ID: commit 0c1408cb2fbabcdfccd81281f6fcded4a2eed309 Author: Dridi Boukelmoune Date: Tue Mar 14 16:19:30 2017 +0100 Revert "Describe VMODs as VCL modules" This reverts commit c2070784e2de3c75a1949599aed74c8fa01a1a65, we'll stick to varnish modules. I also updated a commented-out occurrence of "VCL modules" in params.h, we can probably get rid of these comments. diff --git a/doc/sphinx/reference/vcl.rst b/doc/sphinx/reference/vcl.rst index a53e543..075c345 100644 --- a/doc/sphinx/reference/vcl.rst +++ b/doc/sphinx/reference/vcl.rst @@ -174,7 +174,7 @@ To include a VCL file in another file use the include keyword:: Import statement ---------------- -The ``import`` statement is used to load VCL modules (VMODs.) +The ``import`` statement is used to load Varnish Modules (VMODs.) Example:: diff --git a/doc/sphinx/reference/vmod.rst b/doc/sphinx/reference/vmod.rst index 1b8b0cf..910d613 100644 --- a/doc/sphinx/reference/vmod.rst +++ b/doc/sphinx/reference/vmod.rst @@ -1,8 +1,8 @@ .. _ref-vmod: -%%%%%%%%%%%%%%%%%% -VMOD - VCL Modules -%%%%%%%%%%%%%%%%%% +%%%%%%%%%%%%%%%%%%%%%% +VMOD - Varnish Modules +%%%%%%%%%%%%%%%%%%%%%% For all you can do in VCL, there are things you can not do. Look an IP number up in a database file for instance. diff --git a/doc/sphinx/users-guide/vcl-backends.rst b/doc/sphinx/users-guide/vcl-backends.rst index 6da1855..5844891 100644 --- a/doc/sphinx/users-guide/vcl-backends.rst +++ b/doc/sphinx/users-guide/vcl-backends.rst @@ -120,9 +120,9 @@ You can also group several backend into a group of backends. These groups are called directors. This will give you increased performance and resilience. -You can define several backends and group them together in a director. -This requires you to load a VMOD, a VCL module, and then to call certain -actions in `vcl_init`.:: +You can define several backends and group them together in a +director. This requires you to load a VMOD, a Varnish module, and then to +call certain actions in `vcl_init`.:: import directors; # load the directors diff --git a/include/tbl/params.h b/include/tbl/params.h index cc12632..f66ffd1 100644 --- a/include/tbl/params.h +++ b/include/tbl/params.h @@ -1473,7 +1473,7 @@ PARAM( /* units */ NULL, /* flags */ 0, /* s-text */ - "Directory where VCL modules are to be found.", + "Directory where Varnish modules are to be found.", /* l-text */ "", /* func */ NULL ) From dridi.boukelmoune at gmail.com Tue Mar 14 15:31:05 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Tue, 14 Mar 2017 16:31:05 +0100 Subject: [master] b0190d0 Ignore failures from the osx job on Travis CI Message-ID: commit b0190d0f835030d473b35b25f96facc897235c17 Author: Dridi Boukelmoune Date: Tue Mar 14 16:29:04 2017 +0100 Ignore failures from the osx job on Travis CI This is not a supported platform, and we can still collect test logs for failing jobs. diff --git a/.travis.yml b/.travis.yml index c339f55..732d895 100644 --- a/.travis.yml +++ b/.travis.yml @@ -13,6 +13,8 @@ matrix: - os: osx osx_image: xcode8.2 compiler: clang + allow_failures: + - os: osx addons: apt: packages: From geoff at uplex.de Tue Mar 14 16:08:06 2017 From: geoff at uplex.de (Geoff Simmons) Date: Tue, 14 Mar 2017 17:08:06 +0100 Subject: [master] 444a622 Document that params vcl_dir and vmod_dir are deprecated. Message-ID: commit 444a6228b7761d879c7a6aee63ed98324f2f98b6 Author: Geoff Simmons Date: Tue Mar 14 17:06:27 2017 +0100 Document that params vcl_dir and vmod_dir are deprecated. diff --git a/doc/changes.rst b/doc/changes.rst index 9515b5b..55feb13 100644 --- a/doc/changes.rst +++ b/doc/changes.rst @@ -47,6 +47,9 @@ Varnish Cache 5.1.0 (unreleased) * Added parameters clock_step, thread_pool_reserve and ban_cutoff. +* Parameters vcl_dir and vmod_dir are deprecated, use vcl_path and + vmod_path instead. + * All parameters are defined, even on platforms that don't support them. An unsupported parameter is documented as such in param.show. Setting such a parameter is not an error, but has no diff --git a/doc/sphinx/whats-new/upgrading-5.1.rst b/doc/sphinx/whats-new/upgrading-5.1.rst index 528c2d1..f350c58 100644 --- a/doc/sphinx/whats-new/upgrading-5.1.rst +++ b/doc/sphinx/whats-new/upgrading-5.1.rst @@ -59,6 +59,10 @@ varnishd parameters * ``thread_queue_limit`` only applies to queued client requests, see :ref:`ref_param_thread_queue_limit`. +* ``vcl_dir`` and ``vmod_dir`` are deprecated and will be removed from + a future release, use ``vcl_path`` and ``vmod_path`` instead (see + :ref:`ref_param_vcl_path`, :ref:`ref_param_vmod_path`). + * All parameters are defined on every platform, including those that that are not functional on every platform. Most of these involve features of the TCP stack, such as ``tcp_keepalive_intvl``, From phk at FreeBSD.org Tue Mar 14 19:08:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Tue, 14 Mar 2017 20:08:06 +0100 Subject: [master] 7abd9d3 Try to make these two tests more predictable. Message-ID: commit 7abd9d3310b67c3e05b226d8ebefa9606d6b6bc9 Author: Poul-Henning Kamp Date: Tue Mar 14 19:06:07 2017 +0000 Try to make these two tests more predictable. diff --git a/bin/varnishtest/tests/t02006.vtc b/bin/varnishtest/tests/t02006.vtc index c95feb0..58b33e3 100644 --- a/bin/varnishtest/tests/t02006.vtc +++ b/bin/varnishtest/tests/t02006.vtc @@ -21,12 +21,12 @@ client c1 { -hdr content-length 7 \ -nostrend - txdata \ - -data request - rxhdrs expect resp.status == 100 + txdata \ + -data request + rxwinup rxresp expect resp.status == 200 diff --git a/bin/varnishtest/tests/t02007.vtc b/bin/varnishtest/tests/t02007.vtc index e9068da..a3d44be 100644 --- a/bin/varnishtest/tests/t02007.vtc +++ b/bin/varnishtest/tests/t02007.vtc @@ -26,12 +26,12 @@ client c1 { -hdr content-length 7 \ -nostrend - txdata \ - -data request - rxhdrs expect resp.status == 100 + txdata \ + -data request + rxwinup rxresp expect resp.status == 200 From phk at FreeBSD.org Tue Mar 14 19:08:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Tue, 14 Mar 2017 20:08:06 +0100 Subject: [master] 7fd78ac Add a VARNISHTEST_DURATION environment variable to allow setting the test timeout (-t) through a layer of makefiles (aka: make check). Message-ID: commit 7fd78ac491087d453c7613e98b896524be9173f3 Author: Poul-Henning Kamp Date: Tue Mar 14 19:06:18 2017 +0000 Add a VARNISHTEST_DURATION environment variable to allow setting the test timeout (-t) through a layer of makefiles (aka: make check). diff --git a/bin/varnishtest/vtc_main.c b/bin/varnishtest/vtc_main.c index f8057f5..0158a6d 100644 --- a/bin/varnishtest/vtc_main.c +++ b/bin/varnishtest/vtc_main.c @@ -580,6 +580,8 @@ main(int argc, char * const *argv) params_vsb = VSB_new_auto(); AN(params_vsb); + if (getenv("VARNISHTEST_DURATION")) + vtc_maxdur = atoi(getenv("VARNISHTEST_DURATION")); setbuf(stdout, NULL); setbuf(stderr, NULL); From phk at FreeBSD.org Tue Mar 14 19:19:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Tue, 14 Mar 2017 20:19:05 +0100 Subject: [master] d431018 Start saying Via 5.1 Message-ID: commit d431018453f7592fee2f896270d8f8c6ca54de9d Author: Poul-Henning Kamp Date: Tue Mar 14 19:18:23 2017 +0000 Start saying Via 5.1 diff --git a/bin/varnishd/cache/cache_req_fsm.c b/bin/varnishd/cache/cache_req_fsm.c index fa77dd8..ee135e7 100644 --- a/bin/varnishd/cache/cache_req_fsm.c +++ b/bin/varnishd/cache/cache_req_fsm.c @@ -141,7 +141,7 @@ cnt_deliver(struct worker *wrk, struct req *req) http_PrintfHeader(req->resp, "Age: %.0f", floor(fmax(0., req->t_prev - req->objcore->t_origin))); - http_SetHeader(req->resp, "Via: 1.1 varnish (Varnish/5.0)"); + http_SetHeader(req->resp, "Via: 1.1 varnish (Varnish/5.1)"); if (cache_param->http_gzip_support && ObjCheckFlag(req->wrk, req->objcore, OF_GZIPED) && From phk at FreeBSD.org Wed Mar 15 07:51:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Wed, 15 Mar 2017 08:51:06 +0100 Subject: [master] a806b0c Final H2 bugfix before 5.1: Don't accidentally rip the session out because of a H1 assumption in transport-independent code. Message-ID: commit a806b0c7f16b0f26c2b0b3812e7c936bf24ec9d2 Author: Poul-Henning Kamp Date: Wed Mar 15 07:49:42 2017 +0000 Final H2 bugfix before 5.1: Don't accidentally rip the session out because of a H1 assumption in transport-independent code. diff --git a/bin/varnishd/cache/cache.h b/bin/varnishd/cache/cache.h index 7db4280..c45cc5e 100644 --- a/bin/varnishd/cache/cache.h +++ b/bin/varnishd/cache/cache.h @@ -930,7 +930,7 @@ void VRG_dorange(struct req *req, const char *r); /* cache_req.c */ struct req *Req_New(const struct worker *, struct sess *); void Req_Release(struct req *); -int Req_Cleanup(struct sess *sp, struct worker *wrk, struct req *req); +void Req_Cleanup(struct sess *sp, struct worker *wrk, struct req *req); void Req_Fail(struct req *req, enum sess_close reason); /* cache_req_body.c */ diff --git a/bin/varnishd/cache/cache_req.c b/bin/varnishd/cache/cache_req.c index d0b4c3a..1899bb0 100644 --- a/bin/varnishd/cache/cache_req.c +++ b/bin/varnishd/cache/cache_req.c @@ -143,7 +143,7 @@ Req_Release(struct req *req) /*---------------------------------------------------------------------- */ -int +void Req_Cleanup(struct sess *sp, struct worker *wrk, struct req *req) { @@ -189,20 +189,8 @@ Req_Cleanup(struct sess *sp, struct worker *wrk, struct req *req) req->hash_ignore_busy = 0; req->is_hit = 0; - if (sp->fd >= 0 && req->doclose != SC_NULL) - SES_Close(sp, req->doclose); - - if (sp->fd < 0) { - wrk->stats->sess_closed++; - AZ(req->vcl); - Req_Release(req); - SES_Delete(sp, SC_NULL, NAN); - return (1); - } - WS_Reset(req->ws, 0); WS_Reset(wrk->aws, 0); - return (0); } /*---------------------------------------------------------------------- diff --git a/bin/varnishd/http1/cache_http1_fsm.c b/bin/varnishd/http1/cache_http1_fsm.c index 7ebee6b..3a8b08f 100644 --- a/bin/varnishd/http1/cache_http1_fsm.c +++ b/bin/varnishd/http1/cache_http1_fsm.c @@ -327,6 +327,28 @@ http1_dissect(struct worker *wrk, struct req *req) /*---------------------------------------------------------------------- */ +static int +http1_req_cleanup(struct sess *sp, struct worker *wrk, struct req *req) +{ + Req_Cleanup(sp, wrk, req); + + if (sp->fd >= 0 && req->doclose != SC_NULL) + SES_Close(sp, req->doclose); + + if (sp->fd < 0) { + wrk->stats->sess_closed++; + AZ(req->vcl); + Req_Release(req); + SES_Delete(sp, SC_NULL, NAN); + return (1); + } + + return (0); +} + +/*---------------------------------------------------------------------- + */ + static void HTTP1_Session(struct worker *wrk, struct req *req) { @@ -351,7 +373,7 @@ HTTP1_Session(struct worker *wrk, struct req *req) SES_Close(sp, SC_REM_CLOSE); else SES_Close(sp, SC_TX_ERROR); - AN(Req_Cleanup(sp, wrk, req)); + AN(http1_req_cleanup(sp, wrk, req)); return; } @@ -451,7 +473,7 @@ HTTP1_Session(struct worker *wrk, struct req *req) &req->hash_objhead); AZ(req->hash_objhead); SES_Close(sp, SC_REM_CLOSE); - AN(Req_Cleanup(sp, wrk, req)); + AN(http1_req_cleanup(sp, wrk, req)); return; } http1_setstate(sp, H1PROC); @@ -464,7 +486,7 @@ HTTP1_Session(struct worker *wrk, struct req *req) req->task.priv = NULL; http1_setstate(sp, H1CLEANUP); } else if (st == H1CLEANUP) { - if (Req_Cleanup(sp, wrk, req)) + if (http1_req_cleanup(sp, wrk, req)) return; HTC_RxInit(req->htc, req->ws); if (req->htc->rxbuf_e != req->htc->rxbuf_b) diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index cbb3c52..3ab643e 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -453,6 +453,8 @@ h2_end_headers(const struct worker *wrk, const struct h2_sess *h2, { h2_error h2e; + assert(r2->state == H2_S_OPEN); + r2->state = H2_S_CLOS_REM; h2e = h2h_decode_fini(h2, r2->decode); FREE_OBJ(r2->decode); if (h2e != NULL) { From dridi.boukelmoune at gmail.com Wed Mar 15 12:55:07 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Wed, 15 Mar 2017 13:55:07 +0100 Subject: [master] 5cc2916 Add ${pkgsysconfdir} and ${vcldir} to varnishapi.pc Message-ID: commit 5cc29168d24702c78ae9fb70b19e7a68fdfe28ea Author: Dridi Boukelmoune Date: Sat Mar 11 10:26:23 2017 +0100 Add ${pkgsysconfdir} and ${vcldir} to varnishapi.pc Fixes #2251 diff --git a/varnishapi.pc.in b/varnishapi.pc.in index b2a6e93..b452f6b 100644 --- a/varnishapi.pc.in +++ b/varnishapi.pc.in @@ -3,11 +3,14 @@ exec_prefix=@exec_prefix@ bindir=@bindir@ sbindir=@sbindir@ libdir=@libdir@ +sysconfdir=@sysconfdir@ +pkgsysconfdir=${sysconfdir}/@PACKAGE@ includedir=@includedir@ pkgincludedir=${includedir}/@PACKAGE@ datarootdir=@datarootdir@ datadir=@datadir@ pkgdatadir=${datadir}/@PACKAGE@ +vcldir=${pkgdatadir}/vcl vmoddir=${libdir}/@PACKAGE@/vmods vmodtool=${pkgdatadir}/vmodtool.py From dridi.boukelmoune at gmail.com Wed Mar 15 12:55:07 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Wed, 15 Mar 2017 13:55:07 +0100 Subject: [master] f62e60d Polish: s/varnishconfdir/pkgsysconfdir/ Message-ID: commit f62e60dc8c2eeeff6e2aea6a5638a3265bc52ecf Author: Dridi Boukelmoune Date: Sat Mar 11 10:29:40 2017 +0100 Polish: s/varnishconfdir/pkgsysconfdir/ For consistency. diff --git a/bin/varnishd/Makefile.am b/bin/varnishd/Makefile.am index fabcff8..1034c51 100644 --- a/bin/varnishd/Makefile.am +++ b/bin/varnishd/Makefile.am @@ -148,7 +148,7 @@ varnishd_CFLAGS = \ -DVARNISHD_IS_NOT_A_VMOD \ -DVARNISH_STATE_DIR='"${VARNISH_STATE_DIR}"' \ -DVARNISH_VMOD_DIR='"${pkglibdir}/vmods"' \ - -DVARNISH_VCL_DIR='"${varnishconfdir}:${pkgdatadir}"' + -DVARNISH_VCL_DIR='"${pkgsysconfdir}:${pkgdatadir}"' varnishd_LDFLAGS = -export-dynamic diff --git a/configure.ac b/configure.ac index a85b19a..5ea261e 100644 --- a/configure.ac +++ b/configure.ac @@ -505,8 +505,8 @@ VARNISH_STATE_DIR='${localstatedir}/varnish' AC_SUBST(VARNISH_STATE_DIR) # Default configuration directory. -varnishconfdir='${sysconfdir}/varnish' -AC_SUBST(varnishconfdir) +pkgsysconfdir='${sysconfdir}/varnish' +AC_SUBST(pkgsysconfdir) # Check for linker script support gl_LD_VERSION_SCRIPT From dridi.boukelmoune at gmail.com Wed Mar 15 12:55:07 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Wed, 15 Mar 2017 13:55:07 +0100 Subject: [master] 94c9a54 Package-wide and per-VMOD vcldir support in varnish.m4 Message-ID: commit 94c9a54ace34125d3fab6925651d192e5cb9e160 Author: Dridi Boukelmoune Date: Sat Mar 11 11:21:12 2017 +0100 Package-wide and per-VMOD vcldir support in varnish.m4 Refs #2251 diff --git a/varnish.m4 b/varnish.m4 index b2157ce..31a5c8f 100644 --- a/varnish.m4 +++ b/varnish.m4 @@ -81,6 +81,7 @@ AC_DEFUN([_VARNISH_PKG_CONFIG], [ PKG_CHECK_VAR([VARNISHAPI_LIBDIR], [varnishapi], [libdir]) PKG_CHECK_VAR([VARNISHAPI_BINDIR], [varnishapi], [bindir]) PKG_CHECK_VAR([VARNISHAPI_SBINDIR], [varnishapi], [sbindir]) + PKG_CHECK_VAR([VARNISHAPI_VCLDIR], [varnishapi], [vcldir]) PKG_CHECK_VAR([VARNISHAPI_VMODDIR], [varnishapi], [vmoddir]) PKG_CHECK_VAR([VMODTOOL], [varnishapi], [vmodtool]) @@ -90,6 +91,19 @@ AC_DEFUN([_VARNISH_PKG_CONFIG], [ AC_SUBST([VARNISH_TEST_PATH], [$VARNISHAPI_SBINDIR:$VARNISHAPI_BINDIR:$PATH]) + + dnl Define the VCL directory for automake + AS_CASE([$prefix], + [NONE], [ + vcldir=$VARNISHAPI_VCLDIR + ac_default_prefix=$VARNISHAPI_PREFIX], + [vcldir=$($PKG_CONFIG --define-variable=datadir=$datadir \ + --variable=vcldir varnishapi)] + ) + AC_SUBST([vcldir]) + + dnl Define the VCL directory for this package + AC_SUBST([pkgvcldir], [\${vcldir}/\${PACKAGE}]) ]) # _VARNISH_CHECK_DEVEL @@ -183,6 +197,9 @@ AC_DEFUN([_VARNISH_VMOD], [ VMOD_IMPORT="$1 from \\\"$VMOD_FILE\\\"" AC_SUBST(m4_toupper(VMOD_$1), [$VMOD_IMPORT]) + dnl Define the VCL directory for automake + AC_SUBST([vmod_$1_vcldir], [\${vcldir}/$1]) + VMOD_RULES=" vmod_$1.lo: vcc_$1_if.c vcc_$1_if.h @@ -214,6 +231,9 @@ clean-vmod-$1: # -------------------- # Since: Varnish 4.1.4 # +# Since Varnish 5.1.0: +# - vmod_*_vcldir added +# # Set up the VMOD tool-chain to build the collection of NAMES modules. The # definition of key variables is made available for use in Makefile rules # to build the modules: @@ -222,6 +242,7 @@ clean-vmod-$1: # - VMOD_TEST_PATH (an alias for VARNISH_TEST_PATH) # - VMODTOOL (to generate a VMOD's interface) # - vmoddir (the install prefix for VMODs) +# - vmod_*_vcldir (the install prefix for the VMODs VCL files) # # Configuring your VMOD build with libtool can be as simple as: # @@ -267,7 +288,8 @@ clean-vmod-$1: # hand python detection is done and the resulting PYTHON variable to use # the VMODTOOL. Since nothing requires RST2MAN to be written in python, it # is left outside of the scope. You may even define a phony RST2MAN to -# skip man page generation as it is often the case from a dist archive. +# skip man page generation as it is often the case from a dist archive +# (usually /bin/true when the manual is distributed). # # Two notable variables are exposed from Varnish's pkg-config: # @@ -322,6 +344,22 @@ clean-vmod-$1: # # EXTRA_DIST = vmod_foo.vcc vmod_bar.vcc $(TESTS) # +# If a VMOD is actually a combination of both a library and VCL sub-routines, +# automake directories are available for installation: +# +# vmod_foo_vcl_DATA = some_addition.vcl +# +# This way the end-user's VCL only needs few lines of code to start using both +# VMODs and VCLs assuming Varnish's default vmod_path and vcl_path were not +# changed: +# +# vcl 4.0; +# +# import foo; +# import bar; +# +# include "foo/some_addition.vcl"; +# # Now, you can focus on writing this VMOD of yours. # AC_DEFUN([VARNISH_VMODS], [ @@ -338,6 +376,9 @@ AC_DEFUN([VARNISH_VMODS], [ # - VARNISH_TEST_PATH added # - VARNISH_LIBRARY_PATH added # - VARNISHAPI_LIBDIR added +# - VARNISHAPI_VCLDIR added +# - vcldir added +# - pkgvcldir added # # Verify that the version of Varnish Cache found by pkg-config is at least # MINIMUM-VERSION. If MAXIMUM-VERSION is specified, verify that the version @@ -360,9 +401,23 @@ AC_DEFUN([VARNISH_VMODS], [ # - VARNISHAPI_LIBDIR # - VARNISHAPI_BINDIR # - VARNISHAPI_SBINDIR +# - VARNISHAPI_VCLDIR # - VARNISHAPI_VMODDIR # - VMODTOOL # +# In addition, two directories are set up for installation in automake: +# +# - vcldir +# - pkgvcldir +# +# The vcldir is where Varnish will by default look up VCL files using relative +# paths not found in its sysconfdir (by default /etc/varnish). The pkgvcldir on +# the other hand is a recommended location for your package's VCL files, it +# defaults to "${vcldir}/${PACKAGE}". +# +# This provides a namespace facility for installed VCL files needing including +# other VCL files, which can be overridden if the package name is not desired. +# AC_DEFUN([VARNISH_PREREQ], [ AC_REQUIRE([_VARNISH_PKG_CONFIG]) AC_REQUIRE([_VARNISH_CHECK_EXPLICIT_BZERO]) From dridi.boukelmoune at gmail.com Wed Mar 15 12:55:07 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Wed, 15 Mar 2017 13:55:07 +0100 Subject: [master] 39e65f1 Polish: maintain PATH in the doc example Message-ID: commit 39e65f1d0d78c472f7c3776a9a119ff6ffcf9670 Author: Dridi Boukelmoune Date: Sat Mar 11 11:21:53 2017 +0100 Polish: maintain PATH in the doc example diff --git a/varnish.m4 b/varnish.m4 index 31a5c8f..3bfeb0e 100644 --- a/varnish.m4 +++ b/varnish.m4 @@ -310,7 +310,7 @@ clean-vmod-$1: # is a minimal setup: # # AM_TESTS_ENVIRONMENT = \ -# PATH="$(VARNISH_TEST_PATH)" \ +# PATH="$(VARNISH_TEST_PATH):$(PATH)" \ # LD_LIBRARY_PATH="$(VARNISH_LIBRARY_PATH)" # TEST_EXTENSIONS = .vtc # VTC_LOG_COMPILER = varnishtest -v @@ -319,7 +319,7 @@ clean-vmod-$1: # Setting up the different paths is mostly relevant when you aren't building # against the system installation of Varnish. In the case of the PATH, you # may also need to preserve the original PATH if you run commands outside of -# the Varnish distribution in your test cases. +# the Varnish distribution in your test cases (as shown above). # # The $(VMOD_*) variables contain a proper import statement if the relevant # VMOD was built in the same directory as the test runner. With the example From dridi.boukelmoune at gmail.com Wed Mar 15 12:55:07 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Wed, 15 Mar 2017 13:55:07 +0100 Subject: [master] 3fbeda7 Polish: do the --prefix inheritance in one place Message-ID: commit 3fbeda74ab1c79104134793f7a339b486b8dd087 Author: Dridi Boukelmoune Date: Sat Mar 11 11:31:10 2017 +0100 Polish: do the --prefix inheritance in one place Closes #2252 diff --git a/varnish.m4 b/varnish.m4 index 3bfeb0e..58248fb 100644 --- a/varnish.m4 +++ b/varnish.m4 @@ -92,14 +92,12 @@ AC_DEFUN([_VARNISH_PKG_CONFIG], [ AC_SUBST([VARNISH_TEST_PATH], [$VARNISHAPI_SBINDIR:$VARNISHAPI_BINDIR:$PATH]) + dnl Inherit Varnish's prefix if undefined + test "$prefix" = NONE && ac_default_prefix=$VARNISHAPI_PREFIX + dnl Define the VCL directory for automake - AS_CASE([$prefix], - [NONE], [ - vcldir=$VARNISHAPI_VCLDIR - ac_default_prefix=$VARNISHAPI_PREFIX], - [vcldir=$($PKG_CONFIG --define-variable=datadir=$datadir \ - --variable=vcldir varnishapi)] - ) + vcldir=$($PKG_CONFIG --define-variable=datadir=$datadir \ + --variable=vcldir varnishapi) AC_SUBST([vcldir]) dnl Define the VCL directory for this package @@ -158,13 +156,8 @@ AC_DEFUN([_VARNISH_VMOD_CONFIG], [ AC_SUBST([VARNISHAPI_DATAROOTDIR]) dnl Define the VMOD directory for libtool - AS_CASE([$prefix], - [NONE], [ - vmoddir=$VARNISHAPI_VMODDIR - ac_default_prefix=$VARNISHAPI_PREFIX], - [vmoddir=$($PKG_CONFIG --define-variable=libdir=$libdir \ - --variable=vmoddir varnishapi)] - ) + vmoddir=$($PKG_CONFIG --define-variable=libdir=$libdir \ + --variable=vmoddir varnishapi) AC_SUBST([vmoddir]) dnl Define an automake silent execution for vmodtool From dridi.boukelmoune at gmail.com Wed Mar 15 13:28:06 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Wed, 15 Mar 2017 14:28:06 +0100 Subject: [master] a04a489 Changelog update for #2251 Message-ID: commit a04a48952a927482271c7933f7411de0e46bba00 Author: Dridi Boukelmoune Date: Wed Mar 15 14:27:22 2017 +0100 Changelog update for #2251 diff --git a/doc/changes.rst b/doc/changes.rst index 55feb13..bbc16d4 100644 --- a/doc/changes.rst +++ b/doc/changes.rst @@ -87,6 +87,7 @@ Varnish Cache 5.1.0 (unreleased) Bugs fixed ---------- +* 2251_ - varnishapi.pc and varnishconfdir * 2250_ - vrt.h now depends on vdef.h making current vmod fail. * 2249_ - "logexpect -wait" doesn't fail * 2245_ - Varnish doesn't start, if use vmod (vmod_cache dir was permission denied) @@ -146,6 +147,7 @@ Bugs fixed * 1750_ - Fail more gracefully on -l >= 4GB * 1704_ - fetch_failed not incremented +.. _2251: https://github.com/varnishcache/varnish-cache/issues/2251 .. _2250: https://github.com/varnishcache/varnish-cache/issues/2250 .. _2249: https://github.com/varnishcache/varnish-cache/issues/2249 .. _2245: https://github.com/varnishcache/varnish-cache/issues/2245 diff --git a/doc/sphinx/whats-new/changes-5.1.rst b/doc/sphinx/whats-new/changes-5.1.rst index a35b599..654e4dc 100644 --- a/doc/sphinx/whats-new/changes-5.1.rst +++ b/doc/sphinx/whats-new/changes-5.1.rst @@ -339,6 +339,9 @@ News for authors of VMODs and Varnish API client applications * All of the ``VSB_*`` functions for working with safe string buffers. +* ``varnish.m4`` and ``varnishapi.pc`` now expose more information about + the Varnish installation. See "Since 5.1.0" comments for a comprehensive + list of what was added. * VMOD version coexistence improvements: In difference from executable files, shared libraries are not protected against overwriting under From hermunn at varnish-software.com Wed Mar 15 13:38:05 2017 From: hermunn at varnish-software.com (Pål Hermunn Johansen) Date: Wed, 15 Mar 2017 14:38:05 +0100 Subject: [master] 51ba68f Prepare for 5.1.0 final Message-ID: commit 51ba68f304a3c65140b6a506c7c6fd19aa245e71 Author: P?l Hermunn Johansen Date: Wed Mar 15 14:05:41 2017 +0100 Prepare for 5.1.0 final diff --git a/configure.ac b/configure.ac index 5ea261e..9aa8b2f 100644 --- a/configure.ac +++ b/configure.ac @@ -1,8 +1,8 @@ AC_PREREQ(2.59) AC_COPYRIGHT([Copyright (c) 2006 Verdens Gang AS -Copyright (c) 2006-2016 Varnish Software]) +Copyright (c) 2006-2017 Varnish Software]) AC_REVISION([$Id$]) -AC_INIT([Varnish], [trunk], [varnish-dev at varnish-cache.org]) +AC_INIT([Varnish], [5.1.0], [varnish-dev at varnish-cache.org]) AC_CONFIG_SRCDIR(include/miniobj.h) AC_CONFIG_HEADERS([config.h]) AC_CONFIG_MACRO_DIR([m4]) diff --git a/doc/changes.rst b/doc/changes.rst index bbc16d4..596072e 100644 --- a/doc/changes.rst +++ b/doc/changes.rst @@ -1,5 +1,5 @@ ================================ -Varnish Cache 5.1.0 (unreleased) +Varnish Cache 5.1.0 (2017-03-15) ================================ * Added varnishd command-line options -I, -x and -?, and tightened diff --git a/include/vrt.h b/include/vrt.h index bb56e00..d8e4b4e 100644 --- a/include/vrt.h +++ b/include/vrt.h @@ -39,7 +39,7 @@ * binary/load-time compatible, increment MAJOR version * * - * 6.0 (unreleased): + * 6.0 (2017-03-15): * VRT_hit_for_pass added * VRT_ipcmp added * VRT_Vmod_Init signature changed From fgsch at lodoss.net Wed Mar 15 16:18:06 2017 From: fgsch at lodoss.net (Federico G. Schwindt) Date: Wed, 15 Mar 2017 17:18:06 +0100 Subject: [master] bd4a8ca Back to trunk Message-ID: commit bd4a8cad80e98a64362513d3c89de1048dc4588d Author: Federico G. Schwindt Date: Wed Mar 15 16:16:17 2017 +0000 Back to trunk diff --git a/configure.ac b/configure.ac index 9aa8b2f..d556c23 100644 --- a/configure.ac +++ b/configure.ac @@ -2,7 +2,7 @@ AC_PREREQ(2.59) AC_COPYRIGHT([Copyright (c) 2006 Verdens Gang AS Copyright (c) 2006-2017 Varnish Software]) AC_REVISION([$Id$]) -AC_INIT([Varnish], [5.1.0], [varnish-dev at varnish-cache.org]) +AC_INIT([Varnish], [trunk], [varnish-dev at varnish-cache.org]) AC_CONFIG_SRCDIR(include/miniobj.h) AC_CONFIG_HEADERS([config.h]) AC_CONFIG_MACRO_DIR([m4]) diff --git a/doc/changes.rst b/doc/changes.rst index 596072e..376ac19 100644 --- a/doc/changes.rst +++ b/doc/changes.rst @@ -1,4 +1,10 @@ ================================ +Varnish Cache trunk (unreleased) +================================ + +* No changes. + +================================ Varnish Cache 5.1.0 (2017-03-15) ================================ From phk at FreeBSD.org Wed Mar 15 22:24:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Wed, 15 Mar 2017 23:24:05 +0100 Subject: [master] fca21c7 Fix bug in H1 session cleanup. Message-ID: commit fca21c77189ce058d4185c40e0372f04708297e7 Author: Poul-Henning Kamp Date: Wed Mar 15 22:22:36 2017 +0000 Fix bug in H1 session cleanup. (Yes, obviously I managed to break 5.1 with my last commit before the tag...) diff --git a/bin/varnishd/http1/cache_http1_fsm.c b/bin/varnishd/http1/cache_http1_fsm.c index 3a8b08f..95b23f0 100644 --- a/bin/varnishd/http1/cache_http1_fsm.c +++ b/bin/varnishd/http1/cache_http1_fsm.c @@ -330,6 +330,8 @@ http1_dissect(struct worker *wrk, struct req *req) static int http1_req_cleanup(struct sess *sp, struct worker *wrk, struct req *req) { + AZ(wrk->aws->r); + AZ(req->ws->r); Req_Cleanup(sp, wrk, req); if (sp->fd >= 0 && req->doclose != SC_NULL) @@ -369,10 +371,12 @@ HTTP1_Session(struct worker *wrk, struct req *req) * On systems which return errors for ioctl, we close early */ if (http1_getstate(sp) == H1NEWREQ && VTCP_blocking(sp->fd)) { + AN(req->htc->ws->r); if (errno == ECONNRESET) SES_Close(sp, SC_REM_CLOSE); else SES_Close(sp, SC_TX_ERROR); + WS_Release(req->htc->ws, 0); AN(http1_req_cleanup(sp, wrk, req)); return; } @@ -387,13 +391,14 @@ HTTP1_Session(struct worker *wrk, struct req *req) assert(isnan(req->t_req)); AZ(req->vcl); AZ(req->esi_level); + AN(req->htc->ws->r); hs = HTC_RxStuff(req->htc, HTTP1_Complete, &req->t_first, &req->t_req, sp->t_idle + cache_param->timeout_linger, sp->t_idle + cache_param->timeout_idle, cache_param->http_req_size); - XXXAZ(req->htc->ws->r); + AZ(req->htc->ws->r); if (hs < HTC_S_EMPTY) { req->acct.req_hdrbytes += req->htc->rxbuf_e - req->htc->rxbuf_b; From phk at FreeBSD.org Thu Mar 16 06:58:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Thu, 16 Mar 2017 07:58:05 +0100 Subject: [master] 7b70617 One more H1 session cleanup fix and a lot more asserts. Message-ID: commit 7b70617fdbf0f19585ca33b19c03e9ab54fbb4ee Author: Poul-Henning Kamp Date: Thu Mar 16 06:57:22 2017 +0000 One more H1 session cleanup fix and a lot more asserts. diff --git a/bin/varnishd/http1/cache_http1_fsm.c b/bin/varnishd/http1/cache_http1_fsm.c index 95b23f0..4b00488 100644 --- a/bin/varnishd/http1/cache_http1_fsm.c +++ b/bin/varnishd/http1/cache_http1_fsm.c @@ -433,6 +433,8 @@ HTTP1_Session(struct worker *wrk, struct req *req) if (H2_prism_complete(req->htc) == HTC_S_COMPLETE) { if (!FEATURE(FEATURE_HTTP2)) { SES_Close(req->sp, SC_REQ_HTTP20); + AZ(req->ws->r); + AZ(wrk->aws->r); http1_setstate(sp, H1CLEANUP); continue; } @@ -447,6 +449,8 @@ HTTP1_Session(struct worker *wrk, struct req *req) if (i) { assert(req->doclose > 0); SES_Close(req->sp, req->doclose); + AZ(req->ws->r); + AZ(wrk->aws->r); http1_setstate(sp, H1CLEANUP); continue; } @@ -473,9 +477,10 @@ HTTP1_Session(struct worker *wrk, struct req *req) * Check to see if the remote has left. */ if (VTCP_check_hup(sp->fd)) { + AN(req->ws->r); + WS_Release(req->ws, 0); AN(req->hash_objhead); - (void)HSH_DerefObjHead(wrk, - &req->hash_objhead); + (void)HSH_DerefObjHead(wrk, &req->hash_objhead); AZ(req->hash_objhead); SES_Close(sp, SC_REM_CLOSE); AN(http1_req_cleanup(sp, wrk, req)); @@ -489,6 +494,8 @@ HTTP1_Session(struct worker *wrk, struct req *req) return; req->task.func = NULL; req->task.priv = NULL; + AZ(req->ws->r); + AZ(wrk->aws->r); http1_setstate(sp, H1CLEANUP); } else if (st == H1CLEANUP) { if (http1_req_cleanup(sp, wrk, req)) From phk at FreeBSD.org Thu Mar 16 13:02:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Thu, 16 Mar 2017 14:02:06 +0100 Subject: [master] b40e69b Explain why 5.1.1 is necessary Message-ID: commit b40e69be88ee0e5ec16ef2dcd865153987279fac Author: Poul-Henning Kamp Date: Thu Mar 16 13:00:50 2017 +0000 Explain why 5.1.1 is necessary diff --git a/doc/changes.rst b/doc/changes.rst index 376ac19..5d57de4 100644 --- a/doc/changes.rst +++ b/doc/changes.rst @@ -2,7 +2,8 @@ Varnish Cache trunk (unreleased) ================================ -* No changes. +* Fix bug introduced by stubborn old bugger right before release + 5.1.0 was cut. ================================ Varnish Cache 5.1.0 (2017-03-15) From hermunn at varnish-software.com Thu Mar 16 13:16:06 2017 From: hermunn at varnish-software.com (Pål Hermunn Johansen) Date: Thu, 16 Mar 2017 14:16:06 +0100 Subject: [master] de38712 Prepare for 5.1.1 final Message-ID: commit de38712a7c8be1ea26caf4e7392814f34c44275e Author: P?l Hermunn Johansen Date: Thu Mar 16 14:02:24 2017 +0100 Prepare for 5.1.1 final diff --git a/configure.ac b/configure.ac index d556c23..7aaf658 100644 --- a/configure.ac +++ b/configure.ac @@ -2,7 +2,7 @@ AC_PREREQ(2.59) AC_COPYRIGHT([Copyright (c) 2006 Verdens Gang AS Copyright (c) 2006-2017 Varnish Software]) AC_REVISION([$Id$]) -AC_INIT([Varnish], [trunk], [varnish-dev at varnish-cache.org]) +AC_INIT([Varnish], [5.1.1], [varnish-dev at varnish-cache.org]) AC_CONFIG_SRCDIR(include/miniobj.h) AC_CONFIG_HEADERS([config.h]) AC_CONFIG_MACRO_DIR([m4]) diff --git a/doc/changes.rst b/doc/changes.rst index 5d57de4..2546c4d 100644 --- a/doc/changes.rst +++ b/doc/changes.rst @@ -1,5 +1,5 @@ ================================ -Varnish Cache trunk (unreleased) +Varnish Cache 5.1.1 (2017-03-16) ================================ * Fix bug introduced by stubborn old bugger right before release From phk at FreeBSD.org Mon Mar 20 08:42:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Mon, 20 Mar 2017 09:42:06 +0100 Subject: [master] d87dcf1 This assert will not hold in all error situations. Message-ID: commit d87dcf17d367c3db62c7ee56f61c57b45dce8fc8 Author: Poul-Henning Kamp Date: Mon Mar 20 08:41:03 2017 +0000 This assert will not hold in all error situations. diff --git a/bin/varnishtest/vtc_http2.c b/bin/varnishtest/vtc_http2.c index b472d81..bef8689 100644 --- a/bin/varnishtest/vtc_http2.c +++ b/bin/varnishtest/vtc_http2.c @@ -836,7 +836,7 @@ receive_frame(void *priv) continue; } AZ(pthread_mutex_unlock(&hp->mtx)); - AZ(vsb); + assert(vtc_error || vsb == NULL); return (NULL); } From phk at FreeBSD.org Tue Mar 21 12:26:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Tue, 21 Mar 2017 13:26:06 +0100 Subject: [master] 29db5c9 Add a H1 testcase which exercises the single like of code which triggers this bug for H2. (H2 will be added to the testcase as part of the fix.) Message-ID: commit 29db5c9a92493ae6553f5cce37c04a2a625e96cd Author: Poul-Henning Kamp Date: Tue Mar 21 12:24:48 2017 +0000 Add a H1 testcase which exercises the single like of code which triggers this bug for H2. (H2 will be added to the testcase as part of the fix.) diff --git a/bin/varnishtest/tests/r02258.vtc b/bin/varnishtest/tests/r02258.vtc new file mode 100644 index 0000000..ab2fac3 --- /dev/null +++ b/bin/varnishtest/tests/r02258.vtc @@ -0,0 +1,24 @@ +varnishtest "Streaming range premature finish" + +server s1 { + non_fatal + rxreq + txresp -nolen -hdr "Content-length: 9" + delay 1 + send "BLA" + delay .4 + send "BLA" + delay .3 + send "BL" +} -start + +varnish v1 -vcl+backend { } -start + +client c1 { + txreq -hdr "range: bytes=0-16" + rxresp -no_obj + expect resp.status == 206 + expect resp.http.content-length == 9 + recv 8 + expect_close +} -run From nils.goroll at uplex.de Tue Mar 21 12:47:05 2017 From: nils.goroll at uplex.de (Nils Goroll) Date: Tue, 21 Mar 2017 13:47:05 +0100 Subject: [master] a8b453c Allow EPIPE in VTCP_Check() Message-ID: commit a8b453cb432e9717e1a8afab91433aa4294ba27e Author: Nils Goroll Date: Tue Mar 21 13:41:25 2017 +0100 Allow EPIPE in VTCP_Check() We may see it after a write on a socket which has been closed by the remote end. Fixes #2267 diff --git a/lib/libvarnish/vtcp.c b/lib/libvarnish/vtcp.c index 67be8a0..9122f3e 100644 --- a/lib/libvarnish/vtcp.c +++ b/lib/libvarnish/vtcp.c @@ -577,7 +577,7 @@ VTCP_Check(int a) * connection. * This is a bug in Solaris and documented behaviour on NetBSD. */ - if (errno == EINVAL || errno == ETIMEDOUT) + if (errno == EINVAL || errno == ETIMEDOUT || errno == EPIPE) return (1); #endif return (0); From phk at FreeBSD.org Tue Mar 21 13:39:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Tue, 21 Mar 2017 14:39:05 +0100 Subject: [master] 5fd8055 Add a xport->req_fail() for H2 Message-ID: commit 5fd805510aaf960b613ead15add444786b083647 Author: Poul-Henning Kamp Date: Tue Mar 21 13:37:46 2017 +0000 Add a xport->req_fail() for H2 Fixes: #2258 diff --git a/bin/varnishd/http1/cache_http1_fsm.c b/bin/varnishd/http1/cache_http1_fsm.c index 4b00488..5a7c958 100644 --- a/bin/varnishd/http1/cache_http1_fsm.c +++ b/bin/varnishd/http1/cache_http1_fsm.c @@ -243,14 +243,14 @@ struct transport HTTP1_transport = { .name = "HTTP/1", .magic = TRANSPORT_MAGIC, .deliver = V1D_Deliver, - .unwait = http1_unwait, + .minimal_response = http1_minimal_response, + .new_session = http1_new_session, + .reembark = http1_reembark, .req_body = http1_req_body, .req_fail = http1_req_fail, - .new_session = http1_new_session, - .sess_panic = http1_sess_panic, .req_panic = http1_req_panic, - .reembark = http1_reembark, - .minimal_response = http1_minimal_response, + .sess_panic = http1_sess_panic, + .unwait = http1_unwait, }; /*---------------------------------------------------------------------- diff --git a/bin/varnishd/http2/cache_http2.h b/bin/varnishd/http2/cache_http2.h index 89b85df..bd9e778 100644 --- a/bin/varnishd/http2/cache_http2.h +++ b/bin/varnishd/http2/cache_http2.h @@ -225,3 +225,6 @@ int h2_rxframe(struct worker *, struct h2_sess *); h2_error h2_set_setting(struct h2_sess *, const uint8_t *); void h2_req_body(struct req*); task_func_t h2_do_req; +#ifdef TRANSPORT_MAGIC +vtr_req_fail_f h2_req_fail; +#endif diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index 3ab643e..117690c 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -663,6 +663,15 @@ h2_req_body(struct req *req) /**********************************************************************/ +void __match_proto__(vtr_req_fail_f) +h2_req_fail(struct req *req, enum sess_close reason) +{ + assert(reason > 0); + assert(req->sp->fd != 0); +} + +/**********************************************************************/ + static enum htc_status_e __match_proto__(htc_complete_f) h2_frame_complete(struct http_conn *htc) { diff --git a/bin/varnishd/http2/cache_http2_session.c b/bin/varnishd/http2/cache_http2_session.c index 6922166..ce28251 100644 --- a/bin/varnishd/http2/cache_http2_session.c +++ b/bin/varnishd/http2/cache_http2_session.c @@ -364,10 +364,11 @@ h2_reembark(struct worker *wrk, struct req *req) struct transport H2_transport = { .name = "H2", .magic = TRANSPORT_MAGIC, - .new_session = h2_new_session, - .sess_panic = h2_sess_panic, .deliver = h2_deliver, - .req_body = h2_req_body, .minimal_response = h2_minimal_response, + .new_session = h2_new_session, .reembark = h2_reembark, + .req_body = h2_req_body, + .req_fail = h2_req_fail, + .sess_panic = h2_sess_panic, }; diff --git a/bin/varnishtest/tests/r02258.vtc b/bin/varnishtest/tests/r02258.vtc index ab2fac3..707d4b6 100644 --- a/bin/varnishtest/tests/r02258.vtc +++ b/bin/varnishtest/tests/r02258.vtc @@ -1,7 +1,6 @@ varnishtest "Streaming range premature finish" server s1 { - non_fatal rxreq txresp -nolen -hdr "Content-length: 9" delay 1 @@ -10,6 +9,7 @@ server s1 { send "BLA" delay .3 send "BL" + delay .3 } -start varnish v1 -vcl+backend { } -start @@ -22,3 +22,30 @@ client c1 { recv 8 expect_close } -run + +delay .3 + +server s1 { + rxreq + txresp -nolen -hdr "Content-length: 9" + delay 1 + send "BLA" + delay .4 + send "BLA" + delay .3 + send "BL" +} -start + +varnish v1 -cliok "param.set feature +http2" + +client c1 { + stream 1 { + txreq -hdr "range" "bytes=0-16" + rxhdrs + expect resp.status == 206 + expect resp.http.content-length == 9 + rxdata -all + } -run +} -run + + From nils.goroll at uplex.de Tue Mar 21 19:32:05 2017 From: nils.goroll at uplex.de (Nils Goroll) Date: Tue, 21 Mar 2017 20:32:05 +0100 Subject: [master] 528fd74 sync VRB_Ignore() comment with reality Message-ID: commit 528fd74b0d886a90cc23babe6b977ada4f3d7329 Author: Nils Goroll Date: Tue Mar 21 19:20:07 2017 +0100 sync VRB_Ignore() comment with reality diff --git a/bin/varnishd/cache/cache_req_body.c b/bin/varnishd/cache/cache_req_body.c index 935a9fc..a27e4b4 100644 --- a/bin/varnishd/cache/cache_req_body.c +++ b/bin/varnishd/cache/cache_req_body.c @@ -218,7 +218,9 @@ VRB_Iterate(struct req *req, objiterate_f *func, void *priv) /*---------------------------------------------------------------------- * VRB_Ignore() is a dedicated function, because we might * be able to disuade or terminate its transmission in some protocols. - * For HTTP1 we have no such luck, and we just iterate it into oblivion. + * + * For HTTP1, we do nothing if we are going to close the connection anyway or + * just iterate it into oblivion. */ static int __match_proto__(objiterate_f) From phk at FreeBSD.org Wed Mar 22 00:00:09 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Wed, 22 Mar 2017 01:00:09 +0100 Subject: [master] 3da40ca Add panic function for {vrt|vmod}_privs Message-ID: commit 3da40ca9eb539046e0db1134062538208a772619 Author: Poul-Henning Kamp Date: Tue Mar 21 23:27:54 2017 +0000 Add panic function for {vrt|vmod}_privs diff --git a/bin/varnishd/cache/cache_panic.c b/bin/varnishd/cache/cache_panic.c index 84c78ea..d261c2d 100644 --- a/bin/varnishd/cache/cache_panic.c +++ b/bin/varnishd/cache/cache_panic.c @@ -122,8 +122,8 @@ sess_close_2str(enum sess_close sc, int want_desc) static const void *already_list[N_ALREADY]; static int already_idx; -static int -pan_already(struct vsb *vsb, const void *ptr) +int +PAN_already(struct vsb *vsb, const void *ptr) { int i; @@ -143,7 +143,6 @@ pan_already(struct vsb *vsb, const void *ptr) return (0); } - /*--------------------------------------------------------------------*/ static void @@ -151,7 +150,7 @@ pan_ws(struct vsb *vsb, const struct ws *ws) { VSB_printf(vsb, "ws = %p {\n", ws); - if (pan_already(vsb, ws)) + if (PAN_already(vsb, ws)) return; VSB_indent(vsb, 2); PAN_CheckMagic(vsb, ws, WS_MAGIC); @@ -183,7 +182,7 @@ pan_htc(struct vsb *vsb, const struct http_conn *htc) { VSB_printf(vsb, "http_conn = %p {\n", htc); - if (pan_already(vsb, htc)) + if (PAN_already(vsb, htc)) return; VSB_indent(vsb, 2); PAN_CheckMagic(vsb, htc, HTTP_CONN_MAGIC); @@ -215,7 +214,7 @@ pan_http(struct vsb *vsb, const char *id, const struct http *h) int i; VSB_printf(vsb, "http[%s] = %p {\n", id, h); - if (pan_already(vsb, h)) + if (PAN_already(vsb, h)) return; VSB_indent(vsb, 2); PAN_CheckMagic(vsb, h, HTTP_MAGIC); @@ -239,7 +238,7 @@ static void pan_boc(struct vsb *vsb, const struct boc *boc) { VSB_printf(vsb, "boc = %p {\n", boc); - if (pan_already(vsb, boc)) + if (PAN_already(vsb, boc)) return; VSB_indent(vsb, 2); PAN_CheckMagic(vsb, boc, BOC_MAGIC); @@ -259,7 +258,7 @@ pan_objcore(struct vsb *vsb, const char *typ, const struct objcore *oc) const char *p; VSB_printf(vsb, "objcore[%s] = %p {\n", typ, oc); - if (pan_already(vsb, oc)) + if (PAN_already(vsb, oc)) return; VSB_indent(vsb, 2); PAN_CheckMagic(vsb, oc, OBJCORE_MAGIC); @@ -314,7 +313,7 @@ pan_wrk(struct vsb *vsb, const struct worker *wrk) const char *p; VSB_printf(vsb, "worker = %p {\n", wrk); - if (pan_already(vsb, wrk)) + if (PAN_already(vsb, wrk)) return; VSB_indent(vsb, 2); PAN_CheckMagic(vsb, wrk, WORKER_MAGIC); @@ -364,7 +363,7 @@ pan_busyobj(struct vsb *vsb, const struct busyobj *bo) const char *p; VSB_printf(vsb, "busyobj = %p {\n", bo); - if (pan_already(vsb, bo)) + if (PAN_already(vsb, bo)) return; VSB_indent(vsb, 2); PAN_CheckMagic(vsb, bo, BUSYOBJ_MAGIC); @@ -419,7 +418,7 @@ pan_req(struct vsb *vsb, const struct req *req) const struct transport *xp; VSB_printf(vsb, "req = %p {\n", req); - if (pan_already(vsb, req)) + if (PAN_already(vsb, req)) return; VSB_indent(vsb, 2); PAN_CheckMagic(vsb, req, REQ_MAGIC); @@ -498,7 +497,7 @@ pan_sess(struct vsb *vsb, const struct sess *sp) const struct transport *xp; VSB_printf(vsb, "sp = %p {\n", sp); - if (pan_already(vsb, sp)) + if (PAN_already(vsb, sp)) return; VSB_indent(vsb, 2); PAN_CheckMagic(vsb, sp, SESS_MAGIC); @@ -521,6 +520,8 @@ pan_sess(struct vsb *vsb, const struct sess *sp) cp = SES_Get_String_Attr(sp, SA_CLIENT_PORT); VSB_printf(vsb, "client = %s %s,\n", ci, cp); + pan_privs(vsb, sp->privs); + VSB_indent(vsb, -2); VSB_printf(vsb, "},\n"); } diff --git a/bin/varnishd/cache/cache_priv.h b/bin/varnishd/cache/cache_priv.h index abf5e7f..0ff51eb 100644 --- a/bin/varnishd/cache/cache_priv.h +++ b/bin/varnishd/cache/cache_priv.h @@ -90,6 +90,7 @@ void ObjInit(void); /* cache_panic.c */ void PAN_Init(void); +int PAN_already(struct vsb *, const void *); /* cache_pool.c */ void Pool_Init(void); @@ -118,6 +119,7 @@ void VCL_Poll(void); /* cache_vrt.c */ void VRTPRIV_init(struct vrt_privs *privs); void VRTPRIV_dynamic_kill(struct vrt_privs *privs, uintptr_t id); +void pan_privs(struct vsb *, const struct vrt_privs *); /* cache_vrt_vmod.c */ void VMOD_Init(void); diff --git a/bin/varnishd/cache/cache_vrt_priv.c b/bin/varnishd/cache/cache_vrt_priv.c index bc97995..baafa66 100644 --- a/bin/varnishd/cache/cache_vrt_priv.c +++ b/bin/varnishd/cache/cache_vrt_priv.c @@ -54,6 +54,38 @@ static struct vmod_priv cli_task_priv; */ void +pan_privs(struct vsb *vsb, const struct vrt_privs *privs) +{ + struct vrt_priv *vp; + + VSB_printf(vsb, "privs = %p {\n", privs); + if (PAN_already(vsb, privs)) + return; + VSB_indent(vsb, 2); + PAN_CheckMagic(vsb, privs, VRT_PRIVS_MAGIC); + if (privs->magic == VRT_PRIVS_MAGIC) { + VTAILQ_FOREACH(vp, &privs->privs, list) { + PAN_CheckMagic(vsb, vp, VRT_PRIV_MAGIC); + VSB_printf(vsb, + "priv {p %p l %d f %p} vcl %p id %jx vmod %jx\n", + vp->priv->priv, + vp->priv->len, + vp->priv->free, + vp->vcl, + (uintmax_t)vp->id, + (uintmax_t)vp->vmod_id + ); + } + } + VSB_indent(vsb, -2); + VSB_printf(vsb, "},\n"); +} + + +/*-------------------------------------------------------------------- + */ + +void VRTPRIV_init(struct vrt_privs *privs) { From phk at FreeBSD.org Wed Mar 22 00:00:09 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Wed, 22 Mar 2017 01:00:09 +0100 Subject: [master] e94a5e4 Also release the req0. Message-ID: commit e94a5e4a88201cf73ff42a27bfcf497461d49c4e Author: Poul-Henning Kamp Date: Tue Mar 21 23:59:14 2017 +0000 Also release the req0. diff --git a/bin/varnishd/http2/cache_http2_session.c b/bin/varnishd/http2/cache_http2_session.c index ce28251..4c46a57 100644 --- a/bin/varnishd/http2/cache_http2_session.c +++ b/bin/varnishd/http2/cache_http2_session.c @@ -288,6 +288,7 @@ h2_new_session(struct worker *wrk, void *arg) CNT_AcctLogCharge(wrk->stats, req); VCL_Rel(&req->vcl); Req_Release(req); + h2_del_req(wrk, h2->req0); SES_Delete(h2->sess, SC_RX_JUNK, NAN); return; } From varnish-commit at varnish-cache.org Wed Mar 22 04:35:43 2017 From: varnish-commit at varnish-cache.org (fyrqopkma) Date: Wed, 22 Mar 2017 12:35:43 +0800 Subject: =?utf-8?B?dmFybmlzaC1jb21taXQ65ZCI5LyZ5Lq655qE5Lyw?= =?utf-8?B?5YC85qih5Z6LICAxMjozNTo1MA==?= Message-ID: <20170322123551210122@slsryuboi.org> varnish-commit???? 1????????????????????? 2???5?????????????? 3???????????4???? 4??????????????? ????????????????? 2017-3-2212:35:50 -------------- next part -------------- An HTML attachment was scrubbed... URL: -------------- next part -------------- A non-text attachment was scrubbed... Name: ?????--????? 2017.docx Type: application/vnd.openxmlformats-officedocument.wordprocessingml.document Size: 24915 bytes Desc: not available URL: From phk at FreeBSD.org Wed Mar 22 08:43:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Wed, 22 Mar 2017 09:43:06 +0100 Subject: [master] 4204414 Move a bunch of SES_ functions to cache_transport.h, they are not for casual calling. Message-ID: commit 4204414270572f997fb28625ae830b8363b63731 Author: Poul-Henning Kamp Date: Wed Mar 22 07:40:11 2017 +0000 Move a bunch of SES_ functions to cache_transport.h, they are not for casual calling. diff --git a/bin/varnishd/cache/cache.h b/bin/varnishd/cache/cache.h index c45cc5e..cfed8b4 100644 --- a/bin/varnishd/cache/cache.h +++ b/bin/varnishd/cache/cache.h @@ -944,15 +944,10 @@ enum req_fsm_nxt CNT_Request(struct worker *, struct req *); void CNT_AcctLogCharge(struct dstat *, struct req *); /* cache_session.c [SES] */ -struct sess *SES_New(struct pool *); -void SES_Close(struct sess *, enum sess_close reason); void SES_Wait(struct sess *, const struct transport *); -void SES_Delete(struct sess *, enum sess_close reason, double now); void SES_Ref(struct sess *sp); void SES_Rel(struct sess *sp); int SES_Reschedule_Req(struct req *); -void SES_SetTransport(struct worker *, struct sess *, struct req *, - const struct transport *); enum htc_status_e { HTC_S_JUNK = -5, diff --git a/bin/varnishd/cache/cache_transport.h b/bin/varnishd/cache/cache_transport.h index 22c10b2..3433959 100644 --- a/bin/varnishd/cache/cache_transport.h +++ b/bin/varnishd/cache/cache_transport.h @@ -75,3 +75,10 @@ void H2_OU_Sess(struct worker *, struct sess *, struct req *); const struct transport *XPORT_ByNumber(uint16_t no); void VPX_Send_Proxy(int fd, int version, const struct sess *); + +/* cache_session.c */ +struct sess *SES_New(struct pool *); +void SES_Delete(struct sess *, enum sess_close reason, double now); +void SES_Close(struct sess *, enum sess_close reason); +void SES_SetTransport(struct worker *, struct sess *, struct req *, + const struct transport *); diff --git a/bin/varnishd/http1/cache_http1_deliver.c b/bin/varnishd/http1/cache_http1_deliver.c index 0833f49..3f19bdf 100644 --- a/bin/varnishd/http1/cache_http1_deliver.c +++ b/bin/varnishd/http1/cache_http1_deliver.c @@ -136,7 +136,7 @@ V1D_Deliver(struct req *req, struct boc *boc, int sendbody) } if ((V1L_FlushRelease(req->wrk) || err) && req->sp->fd >= 0) - SES_Close(req->sp, SC_REM_CLOSE); + Req_Fail(req, SC_REM_CLOSE); AZ(req->wrk->v1l); VDP_close(req); } From phk at FreeBSD.org Wed Mar 22 08:43:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Wed, 22 Mar 2017 09:43:06 +0100 Subject: [master] 5b70451 Fixes to and better test-coverage of exception paths in H2 upgrade. Message-ID: commit 5b70451f629cfe80584e8ea9e63221b60256edfa Author: Poul-Henning Kamp Date: Wed Mar 22 08:41:51 2017 +0000 Fixes to and better test-coverage of exception paths in H2 upgrade. diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index 117690c..60b671c 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -181,7 +181,6 @@ h2_del_req(struct worker *wrk, struct h2_req *r2) Req_Release(r2->req); if (r) return; - /* All streams gone, including stream #0, clean up */ req = h2->srq; Req_Cleanup(sp, wrk, req); diff --git a/bin/varnishd/http2/cache_http2_session.c b/bin/varnishd/http2/cache_http2_session.c index 4c46a57..18b2adf 100644 --- a/bin/varnishd/http2/cache_http2_session.c +++ b/bin/varnishd/http2/cache_http2_session.c @@ -192,11 +192,12 @@ h2_b64url_settings(struct h2_sess *h2, struct req *req) /**********************************************************************/ static int -h2_ou_session(const struct worker *wrk, struct h2_sess *h2, +h2_ou_session(struct worker *wrk, struct h2_sess *h2, struct req *req) { ssize_t sz; enum htc_status_e hs; + struct h2_req *r2; if (h2_b64url_settings(h2, req)) { VSLb(h2->vsl, SLT_Debug, "H2: Bad HTTP-Settings"); @@ -220,7 +221,7 @@ h2_ou_session(const struct worker *wrk, struct h2_sess *h2, HTC_RxInit(h2->htc, h2->ws); /* Start req thread */ - (void)h2_new_req(wrk, h2, 1, req); + r2 = h2_new_req(wrk, h2, 1, req); req->req_step = R_STP_RECV; req->transport = &H2_transport; req->req_step = R_STP_TRANSPORT; @@ -233,7 +234,8 @@ h2_ou_session(const struct worker *wrk, struct h2_sess *h2, hs = HTC_RxStuff(h2->htc, H2_prism_complete, NULL, NULL, NAN, h2->sess->t_idle + cache_param->timeout_idle, 256); if (hs != HTC_S_COMPLETE) { - VSLb(h2->vsl, SLT_Debug, "H2: No OU PRISM (hs=%d)", hs); + VSLb(h2->vsl, SLT_Debug, "H2: No/Bad OU PRISM (hs=%d)", hs); + h2_del_req(wrk, r2); return (0); } XXXAZ(Pool_Task(wrk->pool, &req->task, TASK_QUEUE_REQ)); @@ -285,11 +287,7 @@ h2_new_session(struct worker *wrk, void *arg) h2->req0 = h2_new_req(wrk, h2, 0, NULL); if (req->err_code == H2_OU_MARKER && !h2_ou_session(wrk, h2, req)) { - CNT_AcctLogCharge(wrk->stats, req); - VCL_Rel(&req->vcl); - Req_Release(req); h2_del_req(wrk, h2->req0); - SES_Delete(h2->sess, SC_RX_JUNK, NAN); return; } assert(HTC_S_COMPLETE == H2_prism_complete(h2->htc)); diff --git a/bin/varnishtest/tests/t02000.vtc b/bin/varnishtest/tests/t02000.vtc index 2bdfac9..29fe3ba 100644 --- a/bin/varnishtest/tests/t02000.vtc +++ b/bin/varnishtest/tests/t02000.vtc @@ -8,9 +8,17 @@ server s1 { varnish v1 -vcl+backend {} -start -varnish v1 -cliok "param.set feature +http2" varnish v1 -cliok "param.set debug +syncvsl" +varnish v1 -cliok "param.set feature -http2" + +client c1 { + txpri + expect_close +} -run + +varnish v1 -cliok "param.set feature +http2" + client c1 { stream 1 { txprio -weight 10 -stream 0 diff --git a/bin/varnishtest/tests/t02001.vtc b/bin/varnishtest/tests/t02001.vtc index d461f53..a55920a 100644 --- a/bin/varnishtest/tests/t02001.vtc +++ b/bin/varnishtest/tests/t02001.vtc @@ -27,16 +27,41 @@ client c1 { server s1 { rxreq - expect req.url == /upgrade + expect req.url == /upgrade1 + expect req.http.host == foo.bar + expect req.bodylen == 4 + txresp -status 401 -bodylen 8 + + rxreq + expect req.url == /upgrade2 expect req.http.host == foo.bar barrier b1 sync - txresp -status 401 -bodylen 11 + txresp -status 402 -bodylen 11 } -start +delay .5 + varnish v1 -cliok "param.set feature +http2" +# We don't support upgrades with body + +client c1 { + send "POST /upgrade1 HTTP/1.1\r\n" + send "Host: foo.bar\r\n" + send "Upgrade: h2c\r\n" + send "HTTP2-Settings: AAMAAABkAAQAAP__\r\n" + send "Content-Length: 4\r\n" + send "\r\n" + send "FOO\n" + rxresp + expect resp.status == 401 + expect resp.bodylen == 8 +} -run + +delay .5 + client c1 { - send "GET /upgrade HTTP/1.1\r\n" + send "GET /upgrade2 HTTP/1.1\r\n" send "Host: foo.bar\r\n" send "Upgrade: h2c\r\n" send "HTTP2-Settings: AAMAAABkAAQAAP__\r\n" @@ -56,7 +81,7 @@ client c1 { barrier b1 sync stream 1 { rxresp - expect resp.status == 401 + expect resp.status == 402 expect resp.bodylen == 11 } -run } -run From phk at FreeBSD.org Wed Mar 22 09:28:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Wed, 22 Mar 2017 10:28:06 +0100 Subject: [master] 4d3037a Generalize HPACK length encoding Message-ID: commit 4d3037a13ea2fd253f3c575f8cd6d7ed9f0fc17f Author: Poul-Henning Kamp Date: Wed Mar 22 09:27:19 2017 +0000 Generalize HPACK length encoding Fixes #2260 diff --git a/bin/varnishd/http2/cache_http2_deliver.c b/bin/varnishd/http2/cache_http2_deliver.c index 3ef75a3..2d65033 100644 --- a/bin/varnishd/http2/cache_http2_deliver.c +++ b/bin/varnishd/http2/cache_http2_deliver.c @@ -154,6 +154,24 @@ h2_minimal_response(struct req *req, uint16_t status) return (0); } +static uint8_t * +h2_enc_len(uint8_t *p, unsigned bits, unsigned val) +{ + assert(bits < 8); + unsigned mask = (1U << bits) - 1U; + + if (val >= mask) { + *p++ |= (uint8_t)mask; + val -= mask; + while (val >= 128) { + *p++ = 0x80 | ((uint8_t)val & 0x7f); + val >>= 7; + } + } + *p++ = (uint8_t)val; + return (p); +} + void __match_proto__(vtr_deliver_f) h2_deliver(struct req *req, struct boc *boc, int sendbody) { @@ -205,23 +223,13 @@ h2_deliver(struct req *req, struct boc *boc, int sendbody) VSLb(req->vsl, SLT_Debug, "HP {%d, \"%s\", \"%s\"} <%s>", hps->idx, hps->name, hps->val, hp->hd[u].b); - if (hps->idx < 15) { - *p++ = 0x10 | hps->idx; - } else { - *p++ = 0x1f; - *p++ = hps->idx - 0x0f; - } + *p = 0x10; + p = h2_enc_len(p, 4, hps->idx); } else { *p++ = 0x10; sz--; - if (sz < 127) { - *p++ = (uint8_t)sz; - } else { - *p++ = 0x7f; - *p++ = (uint8_t)sz - 0x7f; - } - + p = h2_enc_len(p, 7, sz); for (sz1 = 0; sz1 < sz; sz1++) *p++ = (uint8_t)tolower(hp->hd[u].b[sz1]); @@ -230,14 +238,7 @@ h2_deliver(struct req *req, struct boc *boc, int sendbody) while (vct_islws(*++r)) continue; sz = hp->hd[u].e - r; - assert(sz <= 254); - if (sz < 127) { - *p++ = (uint8_t)sz; - } else if (sz < 127 * 2) { - *p++ = 0x7f; - *p++ = (uint8_t)sz - 0x7f; - } - + p = h2_enc_len(p, 7, sz); memcpy(p, r, sz); p += sz; assert(WS_Inside(req->ws, p, NULL)); diff --git a/bin/varnishtest/tests/t02000.vtc b/bin/varnishtest/tests/t02000.vtc index 29fe3ba..cb14e51 100644 --- a/bin/varnishtest/tests/t02000.vtc +++ b/bin/varnishtest/tests/t02000.vtc @@ -3,7 +3,10 @@ varnishtest "Direct H2 start" server s1 { rxreq expect req.http.host == foo.bar - txresp -bodylen 10 + txresp \ + -hdr "H234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789I: foo" \ + -hdr "Foo: H234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789I" \ + -bodylen 10 } -start varnish v1 -vcl+backend {} -start From phk at FreeBSD.org Wed Mar 22 11:40:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Wed, 22 Mar 2017 12:40:06 +0100 Subject: [master] 569dc01 Add a couple of commits to try to catch #2257 Message-ID: commit 569dc01257c7c5744ffc4e10b09156f4c3ea3912 Author: Poul-Henning Kamp Date: Wed Mar 22 11:38:52 2017 +0000 Add a couple of commits to try to catch #2257 diff --git a/bin/varnishd/cache/cache_req_fsm.c b/bin/varnishd/cache/cache_req_fsm.c index ee135e7..524a21e 100644 --- a/bin/varnishd/cache/cache_req_fsm.c +++ b/bin/varnishd/cache/cache_req_fsm.c @@ -1011,6 +1011,7 @@ CNT_Request(struct worker *wrk, struct req *req) VRB_Free(req); req->wrk = NULL; } + assert(nxt == REQ_FSM_DISEMBARK || req->ws->r == NULL); return (nxt); } diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index 60b671c..33aea63 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -440,6 +440,7 @@ h2_do_req(struct worker *wrk, void *priv) req->http->conds = 1; if (CNT_Request(wrk, req) != REQ_FSM_DISEMBARK) { VSL(SLT_Debug, 0, "H2REQ CNT done"); + AZ(req->ws->r); r2->state = H2_S_CLOSED; h2_del_req(wrk, r2); } From nils.goroll at uplex.de Wed Mar 22 14:07:05 2017 From: nils.goroll at uplex.de (Nils Goroll) Date: Wed, 22 Mar 2017 15:07:05 +0100 Subject: [master] 11fe8b0 I want to find this vtc when grepping for waitinglist Message-ID: commit 11fe8b0f70115414544e79fda2e85d57ac60101c Author: Nils Goroll Date: Wed Mar 22 14:06:11 2017 +0100 I want to find this vtc when grepping for waitinglist diff --git a/bin/varnishtest/tests/c00013.vtc b/bin/varnishtest/tests/c00013.vtc index b833296..e2bbedb 100644 --- a/bin/varnishtest/tests/c00013.vtc +++ b/bin/varnishtest/tests/c00013.vtc @@ -1,4 +1,4 @@ -varnishtest "Test parking second request on backend delay" +varnishtest "Test parking second request on backend delay (waitinglist)" barrier b1 cond 2 barrier b2 cond 2 From nils.goroll at uplex.de Wed Mar 22 14:07:05 2017 From: nils.goroll at uplex.de (Nils Goroll) Date: Wed, 22 Mar 2017 15:07:05 +0100 Subject: [master] 3e015a1 Do all of the vfc setup and init in one place and only when needed Message-ID: commit 3e015a1a8e256c65d4536390b6db098740ca9a5e Author: Nils Goroll Date: Wed Mar 22 14:17:55 2017 +0100 Do all of the vfc setup and init in one place and only when needed Previously, we would be left with a set up but uninitialized req->vfc when reembarking a request on the waitinglist because the set up was done in CNT_Request, but transport->req_body was only called in cnt_recv. Fixes #2266 diff --git a/bin/varnishd/cache/cache_req_fsm.c b/bin/varnishd/cache/cache_req_fsm.c index 524a21e..2086966 100644 --- a/bin/varnishd/cache/cache_req_fsm.c +++ b/bin/varnishd/cache/cache_req_fsm.c @@ -90,6 +90,14 @@ cnt_transport(struct worker *wrk, struct req *req) return (REQ_FSM_DONE); } + if (req->req_body_status < REQ_BODY_TAKEN) { + AN(req->transport->req_body != NULL); + VFP_Setup(req->vfc); + req->vfc->http = req->http; + req->vfc->wrk = wrk; + req->transport->req_body(req); + } + HTTP_Copy(req->http0, req->http); // For ESI & restart req->req_step = R_STP_RECV; return (REQ_FSM_MORE); @@ -791,13 +799,9 @@ cnt_recv(struct worker *wrk, struct req *req) http_CollectHdr(req->http, H_Cache_Control); - if (req->transport->req_body != NULL) { - req->transport->req_body(req); - - if (req->req_body_status == REQ_BODY_FAIL) { - req->doclose = SC_OVERLOAD; - return (REQ_FSM_DONE); - } + if (req->req_body_status == REQ_BODY_FAIL) { + req->doclose = SC_OVERLOAD; + return (REQ_FSM_DONE); } VCL_recv_method(req->vcl, wrk, req, NULL, NULL); @@ -967,13 +971,8 @@ CNT_Request(struct worker *wrk, struct req *req) AN(req->vsl->wid & VSL_CLIENTMARKER); - req->wrk = wrk; + req->vfc->wrk = req->wrk = wrk; wrk->vsl = req->vsl; - - VFP_Setup(req->vfc); - req->vfc->http = req->http; - req->vfc->wrk = wrk; - for (nxt = REQ_FSM_MORE; nxt == REQ_FSM_MORE; ) { /* * This is a good place to be paranoid about the various diff --git a/bin/varnishtest/tests/r02266.vtc b/bin/varnishtest/tests/r02266.vtc new file mode 100644 index 0000000..5fed4d6 --- /dev/null +++ b/bin/varnishtest/tests/r02266.vtc @@ -0,0 +1,50 @@ +varnishtest "request with body parked on waitinglist - almost identical to c00013.vtc" + +barrier b1 cond 2 +barrier b2 cond 2 + +server s1 { + rxreq + expect req.url == "/foo" + send "HTTP/1.0 200 OK\r\nConnection: close\r\n\r\n" + delay .2 + barrier b1 sync + delay .2 + send "line1\n" + delay .2 + barrier b2 sync + send "line2\n" +} -start + +varnish v1 -vcl+backend { + sub vcl_backend_response { + set beresp.do_stream = false; + } +} -start + +varnish v1 -cliok "param.set debug +syncvsl" + +client c1 { + txreq -url "/foo" -hdr "client: c1" + rxresp + expect resp.status == 200 + expect resp.bodylen == 12 + expect resp.http.x-varnish == "1001" +} -start + +barrier b1 sync + +client c2 { + txreq -url "/foo" -hdr "client: c2" -body 1 + delay .2 + barrier b2 sync + rxresp + expect resp.status == 200 + expect resp.bodylen == 12 + expect resp.http.x-varnish == "1004 1002" +} -run + +client c1 -wait + +varnish v1 -expect busy_sleep >= 1 +varnish v1 -expect busy_wakeup >= 1 diff --git a/include/tbl/req_body.h b/include/tbl/req_body.h index 9878e9c..5b4716a 100644 --- a/include/tbl/req_body.h +++ b/include/tbl/req_body.h @@ -32,6 +32,7 @@ REQ_BODY(INIT) REQ_BODY(WITHOUT_LEN) REQ_BODY(WITH_LEN) +/* states >= TAKEN imply that no body is to be read */ REQ_BODY(TAKEN) REQ_BODY(CACHED) REQ_BODY(FAIL) From phk at FreeBSD.org Thu Mar 23 08:10:07 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Thu, 23 Mar 2017 09:10:07 +0100 Subject: [master] 8e77985 If the client workspace is almost, but not quite exhaused, we may not be able to get enough iovec's to do Chunked transmission. Message-ID: commit 8e77985261fa4bef963a0e55b7d7392d75e93c2e Author: Poul-Henning Kamp Date: Thu Mar 23 08:08:29 2017 +0000 If the client workspace is almost, but not quite exhaused, we may not be able to get enough iovec's to do Chunked transmission. Fixes #2275 And #2207 was probably misdiagnosed, but the fix is correct anyhow. diff --git a/bin/varnishd/http1/cache_http1_line.c b/bin/varnishd/http1/cache_http1_line.c index 2565b05..5f102b0 100644 --- a/bin/varnishd/http1/cache_http1_line.c +++ b/bin/varnishd/http1/cache_http1_line.c @@ -89,7 +89,8 @@ V1L_Reserve(struct worker *wrk, struct ws *ws, int *fd, struct vsl_log *vsl, v1l->res = res; u = WS_ReserveLumps(ws, sizeof(struct iovec)); - if (u == 0) { + if (u < 3) { + /* Must have at least 3 in case of chunked encoding */ WS_Release(ws, 0); WS_MarkOverflow(ws); return; @@ -262,6 +263,7 @@ V1L_Chunked(const struct worker *wrk) CHECK_OBJ_NOTNULL(v1l, V1L_MAGIC); assert(v1l->ciov == v1l->siov); + assert(v1l->siov >= 3); /* * If there are not space for chunked header, a chunk of data and * a chunk tail, we might as well flush right away. diff --git a/bin/varnishtest/tests/c00071.vtc b/bin/varnishtest/tests/c00071.vtc index 50574df..a168eb8 100644 --- a/bin/varnishtest/tests/c00071.vtc +++ b/bin/varnishtest/tests/c00071.vtc @@ -14,7 +14,7 @@ server s1 { varnish v1 -vcl+backend { import debug; sub vcl_deliver { - debug.workspace_allocate(client, debug.workspace_free(client) - 160); + debug.workspace_allocate(client, debug.workspace_free(client) - 208); if (req.url ~ "/bar") { set resp.http.x-foo = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"; From martin at varnish-software.com Thu Mar 23 12:55:06 2017 From: martin at varnish-software.com (Martin Blix Grydeland) Date: Thu, 23 Mar 2017 13:55:06 +0100 Subject: [master] 6cb0c66 Add parenthesis to clearify code Message-ID: commit 6cb0c6664bb5ef53b6e2cd6fdc5e4b56567eca44 Author: Martin Blix Grydeland Date: Wed Mar 22 14:04:37 2017 +0100 Add parenthesis to clearify code diff --git a/bin/varnishd/mgt/mgt_vcl.c b/bin/varnishd/mgt/mgt_vcl.c index 9c1e412..9f6672c 100644 --- a/bin/varnishd/mgt/mgt_vcl.c +++ b/bin/varnishd/mgt/mgt_vcl.c @@ -387,14 +387,14 @@ mgt_vcl_setstate(struct cli *cli, struct vclprog *vp, const char *vs) } if (vs == VCL_STATE_AUTO) { now = VTIM_mono(); - vs = vp->warm ? VCL_STATE_WARM : VCL_STATE_COLD; + vs = (vp->warm ? VCL_STATE_WARM : VCL_STATE_COLD); if (vp->go_cold > 0 && vp->state == VCL_STATE_AUTO && vp->go_cold + mgt_param.vcl_cooldown < now) vs = VCL_STATE_COLD; } assert(vs != VCL_STATE_AUTO); - warm = vs == VCL_STATE_WARM ? 1 : 0; + warm = (vs == VCL_STATE_WARM ? 1 : 0); if (vp->warm == warm) return (0); From martin at varnish-software.com Thu Mar 23 12:55:06 2017 From: martin at varnish-software.com (Martin Blix Grydeland) Date: Thu, 23 Mar 2017 13:55:06 +0100 Subject: [master] ad8e8f8 Do not update mgt's mirrored VCL temp state on child temp state failures Message-ID: commit ad8e8f8e5ea4f14097825d4a4a23411e2ac222ae Author: Martin Blix Grydeland Date: Wed Mar 22 14:17:17 2017 +0100 Do not update mgt's mirrored VCL temp state on child temp state failures The child expects mgt to be consistent in its VCL state changes, e.g. not ask the child to 'use' a VCL that isn't warm. Not doing so will cause the child to assert (see asserts in cache_vcl.c:ccf_config_use). This could trigger because the mgt erranously would set its recorded temp regardless of the child's reply in mgt_vcl_setstate. This patch changes it to only record the new temp in mgt if the child replied success. If the child isn't running the new temp is always recorded. Slightly update v00044.vtc test case to reflect the need to update the state before restarting the child. diff --git a/bin/varnishd/mgt/mgt_vcl.c b/bin/varnishd/mgt/mgt_vcl.c index 9f6672c..8849752 100644 --- a/bin/varnishd/mgt/mgt_vcl.c +++ b/bin/varnishd/mgt/mgt_vcl.c @@ -399,16 +399,15 @@ mgt_vcl_setstate(struct cli *cli, struct vclprog *vp, const char *vs) if (vp->warm == warm) return (0); - vp->warm = warm; - - if (vp->warm == 0) - vp->go_cold = 0; - - if (!MCH_Running()) + if (!MCH_Running()) { + vp->warm = warm; + if (vp->warm == 0) + vp->go_cold = 0; return (0); + } i = mgt_cli_askchild(&status, &p, "vcl.state %s %d%s\n", - vp->name, vp->warm, vp->state); + vp->name, warm, vp->state); if (i && cli != NULL) { VCLI_SetResult(cli, status); VCLI_Out(cli, "%s", p); @@ -416,8 +415,15 @@ mgt_vcl_setstate(struct cli *cli, struct vclprog *vp, const char *vs) MGT_Complain(C_ERR, "Please file ticket: VCL poker problem: " "'vcl.state %s %d%s' -> %03d '%s'", - vp->name, vp->warm, vp->state, i, p); + vp->name, warm, vp->state, i, p); + } else { + /* Success, update mgt's VCL state to reflect child's + state */ + vp->warm = warm; + if (vp->warm == 0) + vp->go_cold = 0; } + free(p); return (i); } diff --git a/bin/varnishtest/tests/v00044.vtc b/bin/varnishtest/tests/v00044.vtc index 26feae3..ff218f2 100644 --- a/bin/varnishtest/tests/v00044.vtc +++ b/bin/varnishtest/tests/v00044.vtc @@ -90,4 +90,5 @@ varnish v1 -clierr 300 "vcl.state vcl1 warm" # A warm-up failure can also fail a child start varnish v1 -cliok stop +varnish v1 -cliok "vcl.state vcl1 warm" varnish v1 -clierr 300 start From martin at varnish-software.com Thu Mar 23 12:56:06 2017 From: martin at varnish-software.com (Martin Blix Grydeland) Date: Thu, 23 Mar 2017 13:56:06 +0100 Subject: [master] 744e55d Log VSM/VSL errors in varnishtest Message-ID: commit 744e55dc837c3be0a6761cfbc7406419a44d7cc0 Author: Martin Blix Grydeland Date: Wed Mar 22 17:58:28 2017 +0100 Log VSM/VSL errors in varnishtest This might be useful for debugging diff --git a/bin/varnishtest/vtc_varnish.c b/bin/varnishtest/vtc_varnish.c index 5941848..154952e 100644 --- a/bin/varnishtest/vtc_varnish.c +++ b/bin/varnishtest/vtc_varnish.c @@ -209,11 +209,15 @@ varnishlog_thread(void *priv) if (c == NULL) { VTIM_sleep(0.1); if (VSM_Open(vsm)) { + vtc_log(v->vl, 3, "vsm|%s", + VSM_Error(vsm)); VSM_ResetError(vsm); continue; } c = VSL_CursorVSM(vsl, vsm, opt); if (c == NULL) { + vtc_log(v->vl, 3, "vsl|%s", + VSL_Error(vsl)); VSL_ResetError(vsl); continue; } From martin at varnish-software.com Thu Mar 23 12:56:06 2017 From: martin at varnish-software.com (Martin Blix Grydeland) Date: Thu, 23 Mar 2017 13:56:06 +0100 Subject: [master] 110d073 Add a vsl_catchup varnishtest function Message-ID: commit 110d0732d4ba6a6bfb082994f632b837490a7e9b Author: Martin Blix Grydeland Date: Wed Mar 22 18:09:12 2017 +0100 Add a vsl_catchup varnishtest function This enables waiting for the logging thread to idle to make sure all generated log is caught. diff --git a/bin/varnishtest/vtc_varnish.c b/bin/varnishtest/vtc_varnish.c index 154952e..eb42078 100644 --- a/bin/varnishtest/vtc_varnish.c +++ b/bin/varnishtest/vtc_varnish.c @@ -82,6 +82,7 @@ struct varnish { unsigned vsl_tag_count[256]; volatile int vsl_rec; + volatile int vsl_idle; }; #define NONSENSE "%XJEIFLH|)Xspa8P" @@ -182,6 +183,16 @@ wait_running(const struct varnish *v) * Varnishlog gatherer thread */ +static void +vsl_catchup(const struct varnish *v) +{ + int vsl_idle; + + vsl_idle = v->vsl_idle; + while (vsl_idle == v->vsl_idle) + VTIM_sleep(0.1); +} + static void * varnishlog_thread(void *priv) { @@ -249,6 +260,7 @@ varnishlog_thread(void *priv) } if (i == 0) { /* Nothing to do but wait */ + v->vsl_idle++; VTIM_sleep(0.1); } else if (i == -2) { /* Abandoned - try reconnect */ @@ -1054,6 +1066,10 @@ varnish_expect(const struct varnish *v, char * const *av) * style pattern (ie: fnmatch(3)) as used in shell filename expansion. * To see all counters use pattern "*", to see all counters about * requests use "*req*". + * + * \-vsl_catchup + * Wait until the logging thread has idled to make sure that all + * the generated log is flushed */ void @@ -1209,6 +1225,10 @@ cmd_varnish(CMD_ARGS) varnish_wait(v); continue; } + if (!strcmp(*av, "-vsl_catchup")) { + vsl_catchup(v); + continue; + } vtc_fatal(v->vl, "Unknown varnish argument: %s", *av); } } From phk at FreeBSD.org Thu Mar 23 12:58:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Thu, 23 Mar 2017 13:58:06 +0100 Subject: [master] 3bb4641 FlexeLinting: Avoid cpp macro argument names inside strings Message-ID: commit 3bb4641bf1f6620d246c00cf88b2bf92b10ce3bd Author: Poul-Henning Kamp Date: Thu Mar 23 10:40:45 2017 +0000 FlexeLinting: Avoid cpp macro argument names inside strings diff --git a/bin/varnishtest/vtc.h b/bin/varnishtest/vtc.h index 0e09392..8ba61c2 100644 --- a/bin/varnishtest/vtc.h +++ b/bin/varnishtest/vtc.h @@ -41,13 +41,13 @@ #include "vqueue.h" #include "vsb.h" -#define VTC_CHECK_NAME(vl, name, type, chr) \ +#define VTC_CHECK_NAME(vl, nm, type, chr) \ do { \ - AN(name); \ - if (*(name) != chr) \ + AN(nm); \ + if (*(nm) != chr) \ vtc_fatal(vl, \ type " name must start with '%c' (got %s)", \ - chr, name); \ + chr, nm); \ } while (0) struct vtclog; diff --git a/bin/varnishtest/vtc_http2.c b/bin/varnishtest/vtc_http2.c index bef8689..1f6bfc3 100644 --- a/bin/varnishtest/vtc_http2.c +++ b/bin/varnishtest/vtc_http2.c @@ -840,12 +840,12 @@ receive_frame(void *priv) return (NULL); } -#define STRTOU32(n, s, p, v, c) \ +#define STRTOU32(n, ss, p, v, c) \ do { \ - n = strtoul(s, &p, 0); \ + n = strtoul(ss, &p, 0); \ if (*p != '\0') \ vtc_fatal(v, "%s takes an integer as argument" \ - "(found %s)", c, s); \ + "(found %s)", c, ss); \ } while (0) #define STRTOU32_CHECK(n, sp, p, v, c, l) \ @@ -2336,7 +2336,7 @@ cmd_rxpush(CMD_ARGS) if (s->frame->type != TYPE_ ## upctype) \ vtc_fatal(vl, "Received frame of type %d " \ "is invalid for %s", \ - s->frame->type, "rx ## lctype"); \ + s->frame->type, "rx" #lctype); \ } /* SECTION: stream.spec.prio_rxprio rxprio From phk at FreeBSD.org Thu Mar 23 12:58:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Thu, 23 Mar 2017 13:58:06 +0100 Subject: [master] d73a4e4 Flexelinting: initialize variable flexelint cannot see through. Message-ID: commit d73a4e4a42ad44ce6d79dab5f89d1bc9d5a41f0b Author: Poul-Henning Kamp Date: Thu Mar 23 11:21:40 2017 +0000 Flexelinting: initialize variable flexelint cannot see through. diff --git a/bin/varnishtest/vtc_process.c b/bin/varnishtest/vtc_process.c index 8960692..eaf8d02 100644 --- a/bin/varnishtest/vtc_process.c +++ b/bin/varnishtest/vtc_process.c @@ -220,7 +220,7 @@ process_start(struct process *p) struct vsb *cl; int out_fd, err_fd; int fds[2]; - int fdt[2]; + int fdt[2] = { -1, -1 }; CHECK_OBJ_NOTNULL(p, PROCESS_MAGIC); if (p->hasthread) From phk at FreeBSD.org Thu Mar 23 12:58:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Thu, 23 Mar 2017 13:58:06 +0100 Subject: [master] 30786d6 Tune for 32 bit machines also Message-ID: commit 30786d676a67adbbfc4ec174ab193171232f6ad5 Author: Poul-Henning Kamp Date: Thu Mar 23 12:57:36 2017 +0000 Tune for 32 bit machines also diff --git a/bin/varnishtest/tests/c00071.vtc b/bin/varnishtest/tests/c00071.vtc index a168eb8..77e39d3 100644 --- a/bin/varnishtest/tests/c00071.vtc +++ b/bin/varnishtest/tests/c00071.vtc @@ -14,7 +14,7 @@ server s1 { varnish v1 -vcl+backend { import debug; sub vcl_deliver { - debug.workspace_allocate(client, debug.workspace_free(client) - 208); + debug.workspace_allocate(client, debug.workspace_free(client) - 192); if (req.url ~ "/bar") { set resp.http.x-foo = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"; From phk at FreeBSD.org Thu Mar 23 12:58:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Thu, 23 Mar 2017 13:58:06 +0100 Subject: [master] 1ed2adc Merge branch 'master' of github.com:varnishcache/varnish-cache Message-ID: commit 1ed2adc1e1cd647b4cb21d397f3543cdff729813 Merge: 30786d6 110d073 Author: Poul-Henning Kamp Date: Thu Mar 23 12:57:49 2017 +0000 Merge branch 'master' of github.com:varnishcache/varnish-cache From phk at FreeBSD.org Thu Mar 23 13:36:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Thu, 23 Mar 2017 14:36:06 +0100 Subject: [master] ce9c09a Negative SIZE to debug.workspace_allocate() now means "leave this much free in workspace". Message-ID: commit ce9c09a297a7b15f9db28411a5cb712113f803d9 Author: Poul-Henning Kamp Date: Thu Mar 23 13:27:45 2017 +0000 Negative SIZE to debug.workspace_allocate() now means "leave this much free in workspace". Add debug.typesize() which can tell us the C-sizeof() various types. diff --git a/lib/libvmod_debug/vmod.vcc b/lib/libvmod_debug/vmod.vcc index 4fe903f..b33d3af 100644 --- a/lib/libvmod_debug/vmod.vcc +++ b/lib/libvmod_debug/vmod.vcc @@ -167,6 +167,8 @@ $Function VOID workspace_allocate(ENUM { client, backend, session, thread }, INT size) Allocate and zero out SIZE bytes from a workspace. +If SIZE is negative, all but that many bytes are allocated from the workspace. +(NB: Beware of the alignment imposed on workspace allocations.) $Function BOOL workspace_overflowed(ENUM { client, backend, session, thread }) @@ -203,3 +205,17 @@ Synchronize with a varnishtest shared barrier. $Function VOID test_probe(PROBE probe, PROBE same = 0) Only here to make sure probe definitions are passed properly. + +$Function INT typesize(STRING) + +Returns the size in bytes of a collection of C-datatypes. + +* 'p' = pointer +* 'i' = int +* 'd' = double +* 'f' = float +* 'l' = long +* 's' = short +* 'z' = size_t +* 'o' = off_t +* 'j' = intmax_t diff --git a/lib/libvmod_debug/vmod_debug.c b/lib/libvmod_debug/vmod_debug.c index fe07219..65bea1f 100644 --- a/lib/libvmod_debug/vmod_debug.c +++ b/lib/libvmod_debug/vmod_debug.c @@ -410,6 +410,10 @@ vmod_workspace_allocate(VRT_CTX, VCL_ENUM which, VCL_INT size) WS_Assert(ws); AZ(ws->r); + if (size < 0) { + size += WS_Reserve(ws, 0); + WS_Release(ws, 0); + } s = WS_Alloc(ws, size); if (!s) return; @@ -544,3 +548,27 @@ vmod_test_probe(VRT_CTX, VCL_PROBE probe, VCL_PROBE same) CHECK_OBJ_ORNULL(same, VRT_BACKEND_PROBE_MAGIC); AZ(same == NULL || probe == same); } + +VCL_INT +vmod_typesize(VRT_CTX, VCL_STRING s) +{ + int i = 0; + const char *p; + + (void)ctx; + for (p = s; *p; p++) { + switch (*p) { + case 'p': i += sizeof(void *); break; + case 'i': i += sizeof(int); break; + case 'd': i += sizeof(double); break; + case 'f': i += sizeof(float); break; + case 'l': i += sizeof(long); break; + case 's': i += sizeof(short); break; + case 'z': i += sizeof(size_t); break; + case 'o': i += sizeof(off_t); break; + case 'j': i += sizeof(intmax_t); break; + default: return(-1); + } + } + return (i); +} From phk at FreeBSD.org Thu Mar 23 13:36:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Thu, 23 Mar 2017 14:36:06 +0100 Subject: [master] 3ca71eb Add testcase for #2275 Message-ID: commit 3ca71ebe745f3806f3c0ec3cf5f749688de2c2ab Author: Poul-Henning Kamp Date: Thu Mar 23 13:29:28 2017 +0000 Add testcase for #2275 diff --git a/bin/varnishtest/tests/r02275.vtc b/bin/varnishtest/tests/r02275.vtc new file mode 100644 index 0000000..5458832 --- /dev/null +++ b/bin/varnishtest/tests/r02275.vtc @@ -0,0 +1,39 @@ +varnishtest "Chunked with no space for iov's on workspace" + +server s1 -repeat 2 { + rxreq + txresp -nolen -hdr "Transfer-encoding: chunked" + delay 1 + chunkedlen 10 + delay .1 + chunkedlen 10 + delay .1 + chunkedlen 0 +} -start + +varnish v1 -vcl+backend { + import debug; + + sub vcl_deliver { + if (req.url == "/1") { + debug.workspace_allocate(client, + -1 * (40 + debug.typesize("p") * 25)); + } else { + debug.workspace_allocate(client, + -1 * (48 + debug.typesize("p") * 25)); + } + set resp.http.foo = debug.workspace_free(client); + } +} -start + +client c1 { + txreq -url /1 + rxresp + expect resp.status == 500 +} -run +client c1 { + txreq -url /2 + rxresp + expect resp.status == 200 +} -run + From dridi.boukelmoune at gmail.com Thu Mar 23 14:38:06 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Thu, 23 Mar 2017 15:38:06 +0100 Subject: [master] 52099d4 Don't append newline for varnishtest -p Message-ID: commit 52099d46f7ac50b92be718d87bbfad32408d30c3 Author: Dridi Boukelmoune Date: Thu Mar 23 15:33:15 2017 +0100 Don't append newline for varnishtest -p Original patch from @joshuaspence. Closes #2262 diff --git a/bin/varnishtest/tests/r02262.vtc b/bin/varnishtest/tests/r02262.vtc new file mode 100644 index 0000000..15ffe26 --- /dev/null +++ b/bin/varnishtest/tests/r02262.vtc @@ -0,0 +1,10 @@ +varnishtest "varnishtest -p" + +shell { +cat >_.vtc < 0) From phk at FreeBSD.org Thu Mar 23 19:02:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Thu, 23 Mar 2017 20:02:06 +0100 Subject: [master] 97d8ef9 Change/simplify the V1L logic for chunked encoding. Message-ID: commit 97d8ef918f98ebf08f12e5e7f7a5f54ca7fe6067 Author: Poul-Henning Kamp Date: Thu Mar 23 19:00:55 2017 +0000 Change/simplify the V1L logic for chunked encoding. This reverts the patch for #2207, which as martin points out, is not a good idea after all. diff --git a/bin/varnishd/http1/cache_http1_line.c b/bin/varnishd/http1/cache_http1_line.c index 5f102b0..8215fab 100644 --- a/bin/varnishd/http1/cache_http1_line.c +++ b/bin/varnishd/http1/cache_http1_line.c @@ -161,9 +161,7 @@ V1L_Flush(const struct worker *wrk) CHECK_OBJ_NOTNULL(v1l, V1L_MAGIC); AN(v1l->wfd); - /* For chunked, there must be one slot reserved for the chunked tail */ - if (v1l->ciov < v1l->siov) - assert(v1l->niov < v1l->siov); + assert(v1l->niov <= v1l->siov); if (*v1l->wfd >= 0 && v1l->liov > 0 && v1l->werr == 0) { if (v1l->ciov < v1l->siov && v1l->cliov > 0) { @@ -174,6 +172,7 @@ V1L_Flush(const struct worker *wrk) v1l->iov[v1l->ciov].iov_len = i; v1l->liov += i; + /* This is OK, because siov was --'ed */ v1l->iov[v1l->niov].iov_base = cbuf + i - 2; v1l->iov[v1l->niov++].iov_len = 2; v1l->liov += 2; @@ -240,16 +239,14 @@ V1L_Write(const struct worker *wrk, const void *ptr, ssize_t len) return (0); if (len == -1) len = strlen(ptr); - if (v1l->niov >= v1l->siov - (v1l->ciov < v1l->siov ? 2 : 0)) - (void)V1L_Flush(wrk); + assert(v1l->niov < v1l->siov); v1l->iov[v1l->niov].iov_base = TRUST_ME(ptr); v1l->iov[v1l->niov].iov_len = len; v1l->liov += len; v1l->niov++; - if (v1l->ciov < v1l->siov) { - assert(v1l->niov < v1l->siov); - v1l->cliov += len; - } + v1l->cliov += len; + if (v1l->niov >= v1l->siov) + (void)V1L_Flush(wrk); return (len); } @@ -270,6 +267,7 @@ V1L_Chunked(const struct worker *wrk) */ if (v1l->niov + 3 >= v1l->siov) (void)V1L_Flush(wrk); + v1l->siov--; v1l->ciov = v1l->niov++; v1l->cliov = 0; assert(v1l->ciov < v1l->siov); @@ -294,6 +292,7 @@ V1L_EndChunk(const struct worker *wrk) assert(v1l->ciov < v1l->siov); (void)V1L_Flush(wrk); + v1l->siov++; v1l->ciov = v1l->siov; v1l->niov = 0; v1l->cliov = 0; From phk at FreeBSD.org Thu Mar 23 19:02:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Thu, 23 Mar 2017 20:02:06 +0100 Subject: [master] 01d7080 Use the new "allocate all but" debug.workspace_allocate() feature Message-ID: commit 01d7080bf421c1f3cd57e7df8aca0d8ccc1ec588 Author: Poul-Henning Kamp Date: Thu Mar 23 17:45:19 2017 +0000 Use the new "allocate all but" debug.workspace_allocate() feature diff --git a/bin/varnishtest/tests/c00071.vtc b/bin/varnishtest/tests/c00071.vtc index 77e39d3..befa08d 100644 --- a/bin/varnishtest/tests/c00071.vtc +++ b/bin/varnishtest/tests/c00071.vtc @@ -14,7 +14,7 @@ server s1 { varnish v1 -vcl+backend { import debug; sub vcl_deliver { - debug.workspace_allocate(client, debug.workspace_free(client) - 192); + debug.workspace_allocate(client, -192); if (req.url ~ "/bar") { set resp.http.x-foo = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"; diff --git a/bin/varnishtest/tests/r01834.vtc b/bin/varnishtest/tests/r01834.vtc index 1937da1..e5e1dbc 100644 --- a/bin/varnishtest/tests/r01834.vtc +++ b/bin/varnishtest/tests/r01834.vtc @@ -18,7 +18,7 @@ varnish v1 -vcl+backend { } sub vcl_backend_fetch { - debug.workspace_allocate(backend, debug.workspace_free(backend) - std.integer(bereq.http.WS, 256)); + debug.workspace_allocate(backend, -1 * std.integer(bereq.http.WS, 256)); } } -start From phk at FreeBSD.org Thu Mar 23 21:21:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Thu, 23 Mar 2017 22:21:06 +0100 Subject: [master] b335c0e Put a priority block in a HEADERS frame Message-ID: commit b335c0eee4fa15218aee417308c6bcb50bcd6dc0 Author: Poul-Henning Kamp Date: Thu Mar 23 19:22:45 2017 +0000 Put a priority block in a HEADERS frame diff --git a/bin/varnishtest/tests/t02000.vtc b/bin/varnishtest/tests/t02000.vtc index cb14e51..16b79b8 100644 --- a/bin/varnishtest/tests/t02000.vtc +++ b/bin/varnishtest/tests/t02000.vtc @@ -33,7 +33,7 @@ client c1 { txprio -weight 10 -stream 2 } -run stream 7 { - txreq -hdr :authority foo.bar -pad cotton + txreq -dep 3 -hdr :authority foo.bar -pad cotton rxresp expect resp.status == 200 } -start From phk at FreeBSD.org Thu Mar 23 21:21:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Thu, 23 Mar 2017 22:21:06 +0100 Subject: [master] 2e5da22 Make -vsl_catchup bail on test-failure or child death Message-ID: commit 2e5da2264069121e6001b8da9d1f16ec7430b7cc Author: Poul-Henning Kamp Date: Thu Mar 23 20:08:51 2017 +0000 Make -vsl_catchup bail on test-failure or child death diff --git a/bin/varnishtest/vtc_varnish.c b/bin/varnishtest/vtc_varnish.c index eb42078..2079943 100644 --- a/bin/varnishtest/vtc_varnish.c +++ b/bin/varnishtest/vtc_varnish.c @@ -189,7 +189,7 @@ vsl_catchup(const struct varnish *v) int vsl_idle; vsl_idle = v->vsl_idle; - while (vsl_idle == v->vsl_idle) + while (!vtc_error && v->pid && vsl_idle == v->vsl_idle) VTIM_sleep(0.1); } From phk at FreeBSD.org Thu Mar 23 21:21:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Thu, 23 Mar 2017 22:21:06 +0100 Subject: [master] 6358f4a Try to push H2 into even weirder corners. Message-ID: commit 6358f4a81edec4065b3bfeaeea54583d70336eb5 Author: Poul-Henning Kamp Date: Thu Mar 23 21:19:46 2017 +0000 Try to push H2 into even weirder corners. diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index 33aea63..6683752 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -177,12 +177,14 @@ h2_del_req(struct worker *wrk, struct h2_req *r2) /* XXX: PRIORITY reshuffle */ VTAILQ_REMOVE(&h2->streams, r2, list); Lck_Unlock(&sp->mtx); + AZ(r2->req->ws->r); Req_Cleanup(sp, wrk, r2->req); Req_Release(r2->req); if (r) return; /* All streams gone, including stream #0, clean up */ req = h2->srq; + AZ(req->ws->r); Req_Cleanup(sp, wrk, req); Req_Release(req); SES_Delete(sp, SC_RX_JUNK, NAN); @@ -271,15 +273,21 @@ h2_rx_rst_stream(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) { (void)wrk; + AN(r2); if (h2->rxf_len != 4) // rfc7540,l,2003,2004 return (H2CE_FRAME_SIZE_ERROR); - if (r2 == NULL) - return (0); Lck_Lock(&h2->sess->mtx); r2->error = h2_streamerror(vbe32dec(h2->rxf_data)); +VSLb(h2->vsl, SLT_Debug, "H2RST %u %d %s", r2->stream, r2->state, r2->error->name); if (r2->wrk != NULL) - AZ(pthread_cond_signal(&r2->wrk->cond)); + AZ(pthread_cond_signal(h2->cond)); + if (r2->state != H2_S_IDLE) { + r2->state = H2_S_CLOSED; + r2 = NULL; + } Lck_Unlock(&h2->sess->mtx); + if (r2 != NULL) + h2_del_req(wrk, r2); return (0); } @@ -620,7 +628,9 @@ h2_vfp_body(struct vfp_ctx *vc, struct vfp_entry *vfe, void *ptr, ssize_t *lp) Lck_Lock(&h2->sess->mtx); while (h2->mailcall != r2 && h2->error == 0 && r2->error == 0) AZ(Lck_CondWait(h2->cond, &h2->sess->mtx, 0)); - if (h2->mailcall == r2) { + if (h2->error || r2->error) { + retval = VFP_ERROR; + } else { assert(h2->mailcall == r2); if (l > h2->rxf_len) l = h2->rxf_len; @@ -636,8 +646,6 @@ h2_vfp_body(struct vfp_ctx *vc, struct vfp_entry *vfe, void *ptr, ssize_t *lp) } h2->mailcall = NULL; AZ(pthread_cond_broadcast(h2->cond)); - } else { - retval = VFP_ERROR; } Lck_Unlock(&h2->sess->mtx); return (retval); diff --git a/bin/varnishd/http2/cache_http2_session.c b/bin/varnishd/http2/cache_http2_session.c index 18b2adf..69fc12f 100644 --- a/bin/varnishd/http2/cache_http2_session.c +++ b/bin/varnishd/http2/cache_http2_session.c @@ -313,7 +313,7 @@ h2_new_session(struct worker *wrk, void *arg) AN(h2->error); /* Delete all idle streams */ Lck_Lock(&sp->mtx); - VSLb(h2->vsl, SLT_Debug, "H2 CLEANUP %p", h2->error); + VSLb(h2->vsl, SLT_Debug, "H2 CLEANUP %s", h2->error->name); VTAILQ_FOREACH(r2, &h2->streams, list) { if (r2->error == 0) r2->error = h2->error; diff --git a/bin/varnishtest/tests/t02007.vtc b/bin/varnishtest/tests/t02007.vtc index a3d44be..b168535 100644 --- a/bin/varnishtest/tests/t02007.vtc +++ b/bin/varnishtest/tests/t02007.vtc @@ -4,6 +4,19 @@ server s1 { rxreq expect req.proto == HTTP/1.1 txresp -hdr "Content-Type: text/plain" -hdrlen Foo 100 -bodylen 100 + + non_fatal + close + accept + rxreq + expect req.url == /3 + expect req.proto == HTTP/1.1 + txresp -hdr "Content-Type: text/plain" -hdrlen Foo 50 -bodylen 50 + + close + accept + rxreq + expect req.url == /5 } -start varnish v1 -vcl+backend {} -cliok "param.set feature +http2" -start @@ -40,3 +53,36 @@ client c1 { } -run } -run +varnish v1 -vsl_catchup + +client c1 { + stream 3 { + txreq \ + -req POST \ + -url /3 \ + -hdr content-type text/plain \ + -nostrend + delay .2 + txdata \ + -nostrend \ + -data request + delay .2 + txrst -err 0x333 + } -run + delay 2 + + stream 5 { + txreq \ + -req POST \ + -url /5 \ + -hdr content-type text/plain \ + -nostrend + delay .2 + txdata \ + -nostrend \ + -data request + delay .2 + } -run +} -run + +varnish v1 -vsl_catchup From phk at FreeBSD.org Thu Mar 23 22:08:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Thu, 23 Mar 2017 23:08:06 +0100 Subject: [master] cc5c71b Handle RST_STREAM on completed streams Message-ID: commit cc5c71b733c63de72e1ddc3114e0cf569753e19c Author: Poul-Henning Kamp Date: Thu Mar 23 22:07:10 2017 +0000 Handle RST_STREAM on completed streams diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index 6683752..b5f07a2 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -273,9 +273,10 @@ h2_rx_rst_stream(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) { (void)wrk; - AN(r2); if (h2->rxf_len != 4) // rfc7540,l,2003,2004 return (H2CE_FRAME_SIZE_ERROR); + if (r2 == NULL) + return (0); Lck_Lock(&h2->sess->mtx); r2->error = h2_streamerror(vbe32dec(h2->rxf_data)); VSLb(h2->vsl, SLT_Debug, "H2RST %u %d %s", r2->stream, r2->state, r2->error->name); diff --git a/bin/varnishtest/tests/t02000.vtc b/bin/varnishtest/tests/t02000.vtc index 16b79b8..6eb9ff8 100644 --- a/bin/varnishtest/tests/t02000.vtc +++ b/bin/varnishtest/tests/t02000.vtc @@ -36,6 +36,8 @@ client c1 { txreq -dep 3 -hdr :authority foo.bar -pad cotton rxresp expect resp.status == 200 + delay 1 + txrst -err 0x1111 } -start stream 0 { txping -data "_-__-_-_" From phk at FreeBSD.org Thu Mar 23 22:51:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Thu, 23 Mar 2017 23:51:05 +0100 Subject: [master] e8bb7ec Give this test 8 bytes more to succeed in. Message-ID: commit e8bb7ec58b893a138b1c1d782b2b2e40d69cc97c Author: Poul-Henning Kamp Date: Thu Mar 23 22:50:38 2017 +0000 Give this test 8 bytes more to succeed in. diff --git a/bin/varnishtest/tests/r02275.vtc b/bin/varnishtest/tests/r02275.vtc index 5458832..a5b2e27 100644 --- a/bin/varnishtest/tests/r02275.vtc +++ b/bin/varnishtest/tests/r02275.vtc @@ -20,7 +20,7 @@ varnish v1 -vcl+backend { -1 * (40 + debug.typesize("p") * 25)); } else { debug.workspace_allocate(client, - -1 * (48 + debug.typesize("p") * 25)); + -1 * (56 + debug.typesize("p") * 25)); } set resp.http.foo = debug.workspace_free(client); } From varnish-commit at varnish-cache.org Fri Mar 24 01:40:07 2017 From: varnish-commit at varnish-cache.org (eiyo) Date: Fri, 24 Mar 2017 09:40:07 +0800 Subject: =?utf-8?B?dmFybmlzaC1jb21taXTvvJroh7TmiYDmnIlIUg==?= =?utf-8?B?55qE5LiA5bCB5L+hICA5OjQwOjEx?= Message-ID: <20170324094012844604@twjpjxsiy.net> ????????? ?????? 2017? 4?14-15??? ??????4980?/???????????????? ?????? HR????????????????????????????? ?????? ???? + ???? + ???? +???? + ???? + ???? ?????? 021-31006787, 13381601000 (???) ?QQ/???320588808 ?????? 1??????HR?????????? 2?????????????????? 3??????HR??????HR??????HR?????? 4??????HR?????????? 5??????????HR????????????? ?????? 1?HR????????????????????????????????? 2?HR????????????????????????????? 3?HR????????????????????????????????? 4?HR??????????????????????????KPI????? 5?HR????????????????????????? ????? ??1?HR????? ??2?????????? ??3???????HR???? ??4?HR??????? ??5?????? ??6? HR??? ?????? ??1????????HR?????? ??2????????HR?????? ??3??????????HR?????? ??4??????????HR??? ??5????????HR?????? ??6????????????? ?????? ???? ?????HR?????????????0.5??? ??????HR???? ??????HR???? ??1?HR????? ???? HR??? ??????? 2.5??+?????2??? ????? ???HR?????????-??1????????????? ??2?????????? ????1????????HR?????? ???HR???????? ????2????????HR?????? ??2???????????????? ????? ???????????HR?????????? ????????HR???????????? 1?HR?????????? ????3??????????HR?????? 2????HR?????????????? ????4??????????HR??? ?????????HR???????????????????? ??3????ROE?28.6%???9.82%???????????????HR????????? ??5????????HR?????? ???? HR??????????2??+?????2??? ????? ???HR??????HR??????? ?IT??????????39%???8%???????55%? ??4????????????????3?? ???HR??????HR??????? 1?HR???????????????????????? ??5?????????8.3%????9.2%??????????????????????? 2?????????? ??4? HR??????? ????? ???HR???? 1????????????????5?---??????????? 2?KPI????????????? 3???????????????? ???HR???? ???? HR??????????1.5??????????????? ????? ???HR?? ??6?HR?????????? ??????? ??5?????? ????? ??7??????????????????50%????????80%????????20%? ???? HR"?"?????????1.5??? ?????HR??? ??6? HR??? ???????? ????????????? ????????????????? ???????????????? ????????????? ?????????????? ????Bel Fuse Inc.?????????????? ????500???????????? ??????????????? ???? ???20??HR??????????????????????????500????????500?????????????????????????????????????????????????????? ??????????????????????????????????????IPO???????????????????????? ?????????????????????HR??????????????????HR????????????????????????????????????????????????????????????????????????????? ???? ???????????????????HR???????????????????????????????????? ?????????????????????????smart?????????? -------------- next part -------------- An HTML attachment was scrubbed... URL: From phk at FreeBSD.org Fri Mar 24 11:02:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Fri, 24 Mar 2017 12:02:06 +0100 Subject: [master] 35d1e51 Avoid sign-extension in hexdump Message-ID: commit 35d1e519ec717f10a1e274423eb1666d7ed965e2 Author: Poul-Henning Kamp Date: Fri Mar 24 06:58:19 2017 +0000 Avoid sign-extension in hexdump diff --git a/bin/varnishtest/vtc.h b/bin/varnishtest/vtc.h index 8ba61c2..ba0fb1c 100644 --- a/bin/varnishtest/vtc.h +++ b/bin/varnishtest/vtc.h @@ -107,8 +107,7 @@ void vtc_fatal(struct vtclog *vl, const char *, ...) __attribute__((__noreturn__)) __v_printflike(2,3); void vtc_dump(struct vtclog *vl, int lvl, const char *pfx, const char *str, int len); -void vtc_hexdump(struct vtclog *vl, int lvl, const char *pfx, - const char *str, int len); +void vtc_hexdump(struct vtclog *, int , const char *, const void *, int ); int vtc_send_proxy(int fd, int version, const struct suckaddr *sac, const struct suckaddr *sas); diff --git a/bin/varnishtest/vtc_log.c b/bin/varnishtest/vtc_log.c index 7f31744..df786e8 100644 --- a/bin/varnishtest/vtc_log.c +++ b/bin/varnishtest/vtc_log.c @@ -231,17 +231,18 @@ vtc_dump(struct vtclog *vl, int lvl, const char *pfx, const char *str, int len) void vtc_hexdump(struct vtclog *vl, int lvl, const char *pfx, - const char *str, int len) + const void *ptr, int len) { int nl = 1; unsigned l; + const uint8_t *ss = ptr; AN(pfx); GET_VL(vl); - if (str == NULL) + if (ss == NULL) vtc_leadin(vl, lvl, "%s(null)\n", pfx); else { - for (l = 0; l < len; l++, str++) { + for (l = 0; l < len; l++, ss++) { if (l > 512) { VSB_printf(vl->vsb, "..."); break; @@ -250,7 +251,7 @@ vtc_hexdump(struct vtclog *vl, int lvl, const char *pfx, vtc_leadin(vl, lvl, "%s| ", pfx); nl = 0; } - VSB_printf(vl->vsb, " %02x", *str); + VSB_printf(vl->vsb, " %02x", *ss); if ((l & 0xf) == 0xf) { VSB_printf(vl->vsb, "\n"); nl = 1; From phk at FreeBSD.org Fri Mar 24 11:02:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Fri, 24 Mar 2017 12:02:06 +0100 Subject: [master] 1ad7006 A LOT more H2 plumbing. Message-ID: commit 1ad7006dd182e33b06fa60816adf3b4f5a761452 Author: Poul-Henning Kamp Date: Fri Mar 24 11:00:33 2017 +0000 A LOT more H2 plumbing. diff --git a/bin/varnishd/http2/cache_http2.h b/bin/varnishd/http2/cache_http2.h index bd9e778..b95ac67 100644 --- a/bin/varnishd/http2/cache_http2.h +++ b/bin/varnishd/http2/cache_http2.h @@ -221,6 +221,8 @@ h2_error H2_Send(struct worker *, const struct h2_req *, struct h2_req * h2_new_req(const struct worker *, struct h2_sess *, unsigned stream, struct req *); void h2_del_req(struct worker *, struct h2_req *); +void h2_kill_req(struct worker *, const struct h2_sess *, + struct h2_req *, h2_error); int h2_rxframe(struct worker *, struct h2_sess *); h2_error h2_set_setting(struct h2_sess *, const uint8_t *); void h2_req_body(struct req*); diff --git a/bin/varnishd/http2/cache_http2_deliver.c b/bin/varnishd/http2/cache_http2_deliver.c index 2d65033..be422e6 100644 --- a/bin/varnishd/http2/cache_http2_deliver.c +++ b/bin/varnishd/http2/cache_http2_deliver.c @@ -260,7 +260,6 @@ h2_deliver(struct req *req, struct boc *boc, int sendbody) WS_Release(req->ws, 0); - if (sendbody) { VDP_push(req, h2_bytes, NULL, 1, "H2"); err = VDP_DeliverObj(req); diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index b5f07a2..146754f 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -190,6 +190,31 @@ h2_del_req(struct worker *wrk, struct h2_req *r2) SES_Delete(sp, SC_RX_JUNK, NAN); } +void +h2_kill_req(struct worker *wrk, const struct h2_sess *h2, + struct h2_req *r2, h2_error h2e) +{ + + VSLb(h2->vsl, SLT_Debug, "KILL st=%u state=%d", r2->stream, r2->state); + Lck_Lock(&h2->sess->mtx); + r2->error = h2e; + switch (r2->state) { + case H2_S_CLOS_REM: + if (r2->wrk != NULL) + AZ(pthread_cond_signal(h2->cond)); + r2 = NULL; + break; + case H2_S_OPEN: + (void)h2h_decode_fini(h2, r2->decode); + break; + default: + break; + } + Lck_Unlock(&h2->sess->mtx); + if (r2 != NULL) + h2_del_req(wrk, r2); +} + /**********************************************************************/ static void @@ -241,8 +266,7 @@ h2_rx_ping(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) (void)r2; if (h2->rxf_len != 8) // rfc7540,l,2364,2366 return (H2CE_FRAME_SIZE_ERROR); - if (h2->rxf_stream != 0) // rfc7540,l,2359,2362 - return (H2CE_PROTOCOL_ERROR); + AZ(h2->rxf_stream); // rfc7540,l,2359,2362 if (h2->rxf_flags != 0) // We never send pings return (H2SE_PROTOCOL_ERROR); H2_Send_Get(wrk, h2, r2); @@ -275,20 +299,9 @@ h2_rx_rst_stream(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) if (h2->rxf_len != 4) // rfc7540,l,2003,2004 return (H2CE_FRAME_SIZE_ERROR); - if (r2 == NULL) - return (0); - Lck_Lock(&h2->sess->mtx); - r2->error = h2_streamerror(vbe32dec(h2->rxf_data)); -VSLb(h2->vsl, SLT_Debug, "H2RST %u %d %s", r2->stream, r2->state, r2->error->name); - if (r2->wrk != NULL) - AZ(pthread_cond_signal(h2->cond)); - if (r2->state != H2_S_IDLE) { - r2->state = H2_S_CLOSED; - r2 = NULL; - } - Lck_Unlock(&h2->sess->mtx); if (r2 != NULL) - h2_del_req(wrk, r2); + h2_kill_req(wrk, h2, r2, + h2_streamerror(vbe32dec(h2->rxf_data))); return (0); } @@ -463,7 +476,6 @@ h2_end_headers(const struct worker *wrk, const struct h2_sess *h2, h2_error h2e; assert(r2->state == H2_S_OPEN); - r2->state = H2_S_CLOS_REM; h2e = h2h_decode_fini(h2, r2->decode); FREE_OBJ(r2->decode); if (h2e != NULL) { @@ -480,6 +492,7 @@ h2_end_headers(const struct worker *wrk, const struct h2_sess *h2, req->req_step = R_STP_TRANSPORT; req->task.func = h2_do_req; req->task.priv = req; + r2->state = H2_S_CLOS_REM; // XXX: not _quite_ true XXXAZ(Pool_Task(wrk->pool, &req->task, TASK_QUEUE_REQ)); return (0); } @@ -535,7 +548,10 @@ h2_rx_headers(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) } h2e = h2h_decode_bytes(h2, r2->decode, p, l); if (h2e != NULL) { - VSL(SLT_Debug, 0, "H2H_DECODE_BYTES %s", h2e->name); + VSL(SLT_Debug, 0, "H2H_DECODE_BYTES(hdr) %s", h2e->name); + (void)h2h_decode_fini(h2, r2->decode); + AZ(r2->req->ws->r); + h2_del_req(wrk, r2); return (h2e); } if (h2->rxf_flags & H2FF_HEADERS_END_HEADERS) @@ -558,7 +574,10 @@ h2_rx_continuation(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) req = r2->req; h2e = h2h_decode_bytes(h2, r2->decode, h2->rxf_data, h2->rxf_len); if (h2e != NULL) { - VSL(SLT_Debug, 0, "H2H_DECODE_BYTES %s", h2e->name); + VSL(SLT_Debug, 0, "H2H_DECODE_BYTES(cont) %s", h2e->name); + (void)h2h_decode_fini(h2, r2->decode); + AZ(r2->req->ws->r); + h2_del_req(wrk, r2); return (h2e); } if (h2->rxf_flags & H2FF_HEADERS_END_HEADERS) @@ -677,6 +696,7 @@ h2_req_fail(struct req *req, enum sess_close reason) { assert(reason > 0); assert(req->sp->fd != 0); + VSLb(req->vsl, SLT_Debug, "H2FAILREQ"); } /**********************************************************************/ @@ -836,7 +856,7 @@ h2_rxframe(struct worker *wrk, struct h2_sess *h2) h2->bogosity++; VSLb(h2->vsl, SLT_Debug, "H2: Unknown flags 0x%02x on %s (ignored)", - (uint8_t)h2->rxf_flags, h2f->name); + (uint8_t)h2->rxf_flags & ~h2f->flags, h2f->name); h2->rxf_flags &= h2f->flags; } diff --git a/bin/varnishd/http2/cache_http2_session.c b/bin/varnishd/http2/cache_http2_session.c index 69fc12f..63732d2 100644 --- a/bin/varnishd/http2/cache_http2_session.c +++ b/bin/varnishd/http2/cache_http2_session.c @@ -201,6 +201,10 @@ h2_ou_session(struct worker *wrk, struct h2_sess *h2, if (h2_b64url_settings(h2, req)) { VSLb(h2->vsl, SLT_Debug, "H2: Bad HTTP-Settings"); + AN (req->vcl); + VCL_Rel(&req->vcl); + CNT_AcctLogCharge(wrk->stats, req); + Req_Release(req); return (0); } @@ -317,20 +321,25 @@ h2_new_session(struct worker *wrk, void *arg) VTAILQ_FOREACH(r2, &h2->streams, list) { if (r2->error == 0) r2->error = h2->error; +#if 0 if (r2->wrk != NULL) - AZ(pthread_cond_signal(&r2->wrk->cond)); + AZ(pthread_cond_signal(&r2->wrk->cond)); // XXX Why? +#endif } + AZ(pthread_cond_signal(h2->cond)); while (1) { VTAILQ_FOREACH(r2, &h2->streams, list) - if (r2->state == H2_S_IDLE && r2 != h2->req0) + if (r2->state != H2_S_CLOS_REM && r2 != h2->req0) break; if (r2 == NULL) break; Lck_Unlock(&sp->mtx); - h2_del_req(wrk, r2); + h2_kill_req(wrk, h2, r2, h2->error); Lck_Lock(&sp->mtx); } VSLb(h2->vsl, SLT_Debug, "H2CLEAN done"); + VTAILQ_FOREACH(r2, &h2->streams, list) + VSLb(h2->vsl, SLT_Debug, "ST %u %d", r2->stream, r2->state); Lck_Unlock(&sp->mtx); h2->cond = NULL; h2_del_req(wrk, h2->req0); diff --git a/bin/varnishtest/tests/t02001.vtc b/bin/varnishtest/tests/t02001.vtc index a55920a..d744822 100644 --- a/bin/varnishtest/tests/t02001.vtc +++ b/bin/varnishtest/tests/t02001.vtc @@ -39,7 +39,12 @@ server s1 { txresp -status 402 -bodylen 11 } -start -delay .5 +varnish v1 -vsl_catchup + +varnish v1 -expect MEMPOOL.req0.live == 0 +varnish v1 -expect MEMPOOL.req1.live == 0 +varnish v1 -expect MEMPOOL.sess0.live == 0 +varnish v1 -expect MEMPOOL.sess1.live == 0 varnish v1 -cliok "param.set feature +http2" @@ -58,7 +63,12 @@ client c1 { expect resp.bodylen == 8 } -run -delay .5 +varnish v1 -vsl_catchup + +varnish v1 -expect MEMPOOL.req0.live == 0 +varnish v1 -expect MEMPOOL.req1.live == 0 +varnish v1 -expect MEMPOOL.sess0.live == 0 +varnish v1 -expect MEMPOOL.sess1.live == 0 client c1 { send "GET /upgrade2 HTTP/1.1\r\n" @@ -86,6 +96,13 @@ client c1 { } -run } -run +varnish v1 -vsl_catchup + +varnish v1 -expect MEMPOOL.req0.live == 0 +varnish v1 -expect MEMPOOL.req1.live == 0 +varnish v1 -expect MEMPOOL.sess0.live == 0 +varnish v1 -expect MEMPOOL.sess1.live == 0 + client c1 { # Illegal HTTP2-Settings send "GET /noupgrade HTTP/1.1\r\n" @@ -96,6 +113,13 @@ client c1 { expect_close } -run +varnish v1 -vsl_catchup + +varnish v1 -expect MEMPOOL.req0.live == 0 +varnish v1 -expect MEMPOOL.req1.live == 0 +varnish v1 -expect MEMPOOL.sess0.live == 0 +varnish v1 -expect MEMPOOL.sess1.live == 0 + client c1 { # PRISM with error in last bit send "GET /noupgrade HTTP/1.1\r\n" @@ -111,8 +135,7 @@ client c1 { expect_close } -run -# XXX: Tests temporarily neutered, they are too flakey -#varnish v1 -expect MEMPOOL.req0.live == 0 -#varnish v1 -expect MEMPOOL.req1.live == 0 -#varnish v1 -expect MEMPOOL.sess0.live == 0 -#varnish v1 -expect MEMPOOL.sess1.live == 0 +varnish v1 -expect MEMPOOL.req0.live == 0 +varnish v1 -expect MEMPOOL.req1.live == 0 +varnish v1 -expect MEMPOOL.sess0.live == 0 +varnish v1 -expect MEMPOOL.sess1.live == 0 diff --git a/bin/varnishtest/tests/t02003.vtc b/bin/varnishtest/tests/t02003.vtc index 62b0fe7..a3b99e3 100644 --- a/bin/varnishtest/tests/t02003.vtc +++ b/bin/varnishtest/tests/t02003.vtc @@ -1,4 +1,4 @@ -varnishtest "H2 Stream error conditions" +varnishtest "H2 Frame coverage/error conditions" server s1 { rxreq @@ -26,6 +26,13 @@ client c1 { stream 0 -wait } -run +varnish v1 -vsl_catchup + +varnish v1 -expect MEMPOOL.req0.live == 0 +varnish v1 -expect MEMPOOL.req1.live == 0 +varnish v1 -expect MEMPOOL.sess0.live == 0 +varnish v1 -expect MEMPOOL.sess1.live == 0 + ####################################################################### # Test reverse order stream numbers @@ -44,6 +51,13 @@ client c1 { stream 0 -wait } -run +varnish v1 -vsl_catchup + +varnish v1 -expect MEMPOOL.req0.live == 0 +varnish v1 -expect MEMPOOL.req1.live == 0 +varnish v1 -expect MEMPOOL.sess0.live == 0 +varnish v1 -expect MEMPOOL.sess1.live == 0 + ####################################################################### # Test WINDOW_UPDATE error conditions @@ -68,7 +82,13 @@ client c1 { } -start stream 5 { txprio - sendhex "000003 08 00 00000005 010203" + sendhex "000003 08 00 00000005" + delay .1 + sendhex 01 + delay .1 + sendhex 02 + delay .1 + sendhex 03 } -run stream 0 -wait } -run @@ -93,6 +113,13 @@ client c1 { } -run } -run +varnish v1 -vsl_catchup + +varnish v1 -expect MEMPOOL.req0.live == 0 +varnish v1 -expect MEMPOOL.req1.live == 0 +varnish v1 -expect MEMPOOL.sess0.live == 0 +varnish v1 -expect MEMPOOL.sess1.live == 0 + ####################################################################### # Test PING error conditions @@ -114,6 +141,22 @@ client c1 { } -run } -run +client c1 { + stream 0 { + sendhex "000007 06 80 00000000 01020304050607" + rxgoaway + expect goaway.laststream == 0 + expect goaway.err == FRAME_SIZE_ERROR + } -run +} -run + +varnish v1 -vsl_catchup + +varnish v1 -expect MEMPOOL.req0.live == 0 +varnish v1 -expect MEMPOOL.req1.live == 0 +varnish v1 -expect MEMPOOL.sess0.live == 0 +varnish v1 -expect MEMPOOL.sess1.live == 0 + ####################################################################### # Test PUSH_PROMISE error conditions @@ -130,6 +173,14 @@ client c1 { stream 0 -wait } -run +varnish v1 -vsl_catchup + +varnish v1 -expect MEMPOOL.req0.live == 0 +varnish v1 -expect MEMPOOL.req1.live == 0 +varnish v1 -expect MEMPOOL.sess0.live == 0 +varnish v1 -expect MEMPOOL.sess1.live == 0 + +####################################################################### # Test RST_STREAM error conditions client c1 { @@ -166,6 +217,20 @@ client c1 { } -run } -run +client c1 { + stream 1 { + txreq -nohdrend + txrst -err 0x666 + } -run +} -run + +varnish v1 -vsl_catchup + +varnish v1 -expect MEMPOOL.req0.live == 0 +varnish v1 -expect MEMPOOL.req1.live == 0 +varnish v1 -expect MEMPOOL.sess0.live == 0 +varnish v1 -expect MEMPOOL.sess1.live == 0 + ####################################################################### # Test SETTING error conditions @@ -186,8 +251,7 @@ client c1 { rxgoaway expect goaway.err == PROTOCOL_ERROR expect goaway.laststream == 0 - } -run -} -run + } -run } -run client c1 { stream 0 { @@ -207,3 +271,112 @@ client c1 { rxping } -run } -run + +varnish v1 -vsl_catchup + +varnish v1 -expect MEMPOOL.req0.live == 0 +varnish v1 -expect MEMPOOL.req1.live == 0 +varnish v1 -expect MEMPOOL.sess0.live == 0 +varnish v1 -expect MEMPOOL.sess1.live == 0 + +####################################################################### +# Test GOAWAY error conditions + +client c1 { + stream 0 { + txgoaway -err 2 + } -run + expect_close +} -run + +client c1 { + stream 0 { + txgoaway -err 2222 + } -run + expect_close +} -run + + +varnish v1 -vsl_catchup + +varnish v1 -expect MEMPOOL.req0.live == 0 +varnish v1 -expect MEMPOOL.req1.live == 0 +varnish v1 -expect MEMPOOL.sess0.live == 0 +varnish v1 -expect MEMPOOL.sess1.live == 0 + +####################################################################### +# Test HEADERS error conditions + +client c1 { + stream 1 { + txreq -nostrend + txreq -nostrend + } -run + stream 0 { + rxgoaway + } -run + expect_close +} -run + +client c1 { + stream 0 { + sendhex 00000c + sendhex 01 + sendhex 05 + sendhex 00000001 + sendhex ffffffff + sendhex ffffffff + sendhex ffffffff + rxgoaway + expect goaway.err == COMPRESSION_ERROR + } -run +} -run + +varnish v1 -vsl_catchup + +varnish v1 -expect MEMPOOL.req0.live == 0 +varnish v1 -expect MEMPOOL.req1.live == 0 +varnish v1 -expect MEMPOOL.sess0.live == 0 +varnish v1 -expect MEMPOOL.sess1.live == 0 + +####################################################################### +# Test CONTINUATION error conditions + +client c1 { + stream 1 { + txreq -nostrend + txcont -hdr "foo" "bar" + } -run + stream 0 { + rxgoaway + } -run + expect_close +} -run + +client c1 { + stream 0 { + sendhex 000014 + sendhex 01 + sendhex 01 + sendhex 00000001 + sendhex {8286 8441 0f77 7777 2e65 7861 6d70 6c65 2e63 6f6d} + + sendhex 00000c + sendhex 09 + sendhex 04 + sendhex 00000001 + sendhex ffffffff + sendhex ffffffff + sendhex ffffffff + rxgoaway + expect goaway.err == COMPRESSION_ERROR + } -run +} -run + +varnish v1 -vsl_catchup + +varnish v1 -expect MEMPOOL.req0.live == 0 +varnish v1 -expect MEMPOOL.req1.live == 0 +varnish v1 -expect MEMPOOL.sess0.live == 0 +varnish v1 -expect MEMPOOL.sess1.live == 0 + diff --git a/bin/varnishtest/tests/t02008.vtc b/bin/varnishtest/tests/t02008.vtc index a1bccba..75cee51 100644 --- a/bin/varnishtest/tests/t02008.vtc +++ b/bin/varnishtest/tests/t02008.vtc @@ -27,7 +27,7 @@ client c1 { txprio } -run stream 0 { - txgoaway -err 7 + txgoaway -err 2 } -run expect_close } -run From noreply at github.com Fri Mar 24 18:23:06 2017 From: noreply at github.com (GitHub) Date: Fri, 24 Mar 2017 19:23:06 +0100 Subject: [master] 3767269 How to report signal panics Message-ID: commit 37672695d84b1bed51d71be8c61c6719513502b2 Author: Dridi Boukelmoune Date: Fri Mar 24 19:22:47 2017 +0100 How to report signal panics diff --git a/.github/ISSUE_TEMPLATE.md b/.github/ISSUE_TEMPLATE.md index ca79ff0..3c29561 100644 --- a/.github/ISSUE_TEMPLATE.md +++ b/.github/ISSUE_TEMPLATE.md @@ -2,6 +2,11 @@ ## Expected Behavior + ## Expected Behavior @@ -42,3 +63,4 @@ * Version used: * Operating System and version: +* Source of binary packages used (if any) From nils.goroll at uplex.de Sun Mar 26 11:50:05 2017 From: nils.goroll at uplex.de (Nils Goroll) Date: Sun, 26 Mar 2017 13:50:05 +0200 Subject: [master] acd4c29 no debuginfo packages on packagecloud.io Message-ID: commit acd4c296d59bbc768a7189aab963222ce48088df Author: Nils Goroll Date: Sun Mar 26 13:48:54 2017 +0200 no debuginfo packages on packagecloud.io diff --git a/.github/ISSUE_TEMPLATE.md b/.github/ISSUE_TEMPLATE.md index 6bc9424..2e578a7 100644 --- a/.github/ISSUE_TEMPLATE.md +++ b/.github/ISSUE_TEMPLATE.md @@ -12,7 +12,10 @@ - but at least the latest release of a supported version - you got - - debuginfo packages installed when running binaries from packages + - debuginfo packages installed when running binaries from + packages if these are available from the package source + you are using + - or have compiled with debug information whenever possible (configure --enable-debugging-symbols) From dridi.boukelmoune at gmail.com Mon Mar 27 19:33:06 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Mon, 27 Mar 2017 21:33:06 +0200 Subject: [master] bc2ea2c Support multi-lib systems for out-of-tree builds Message-ID: commit bc2ea2c35ebd1dcf613b5b9ab2b3957d0b4b4839 Author: Dridi Boukelmoune Date: Mon Mar 27 21:26:15 2017 +0200 Support multi-lib systems for out-of-tree builds On systems where both 32 and 64-bit libraries can co-exist, simply inheriting Varnish's prefix is not enough because VMODs might land in the wrong directory. For instance, on rhel you will find both /usr/lib and /usr/lib64. This is usually not a problem with package managers, because they usually take care of everything at configure time, for example RPMs may use a %configure macro that defines all well-known directories. It can however be overlooked when a VMOD is manually built from source. diff --git a/varnish.m4 b/varnish.m4 index 58248fb..400e087 100644 --- a/varnish.m4 +++ b/varnish.m4 @@ -1,4 +1,4 @@ -# Copyright (c) 2016 Varnish Software AS +# Copyright (c) 2016-2017 Varnish Software AS # All rights reserved. # # Author: Dridi Boukelmoune @@ -29,7 +29,7 @@ # OF THE POSSIBILITY OF SUCH DAMAGE. # varnish.m4 - Macros to define VMOD builds. -*- Autoconf -*- -# serial 6 (varnish-5.1.0) +# serial 7 (varnish-5.1.2) # # This collection of macros helps create VMODs or tools interacting with # Varnish Cache using the GNU build system (autotools). In order to work @@ -93,7 +93,12 @@ AC_DEFUN([_VARNISH_PKG_CONFIG], [ [$VARNISHAPI_SBINDIR:$VARNISHAPI_BINDIR:$PATH]) dnl Inherit Varnish's prefix if undefined - test "$prefix" = NONE && ac_default_prefix=$VARNISHAPI_PREFIX + dnl Also the libdir for multi-lib systems + if test "$prefix" = NONE + then + ac_default_prefix=$VARNISHAPI_PREFIX + libdir=$VARNISHAPI_LIBDIR + fi dnl Define the VCL directory for automake vcldir=$($PKG_CONFIG --define-variable=datadir=$datadir \ From phk at FreeBSD.org Tue Mar 28 07:56:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Tue, 28 Mar 2017 09:56:06 +0200 Subject: [master] 581948c Log the remote address to make it easier to cross-ref to VSL Message-ID: commit 581948c49181751b935fff809d6a54cfcb4594b2 Author: Poul-Henning Kamp Date: Tue Mar 28 07:28:02 2017 +0000 Log the remote address to make it easier to cross-ref to VSL diff --git a/bin/varnishtest/vtc_server.c b/bin/varnishtest/vtc_server.c index 773e7fb..13dd336 100644 --- a/bin/varnishtest/vtc_server.c +++ b/bin/varnishtest/vtc_server.c @@ -152,6 +152,8 @@ server_thread(void *priv) struct sockaddr_storage addr_s; struct sockaddr *addr; socklen_t l; + char abuf[VTCP_ADDRBUFSIZE]; + char pbuf[VTCP_PORTBUFSIZE]; CAST_OBJ_NOTNULL(s, priv, SERVER_MAGIC); assert(s->sock >= 0); @@ -167,7 +169,8 @@ server_thread(void *priv) fd = accept(s->sock, addr, &l); if (fd < 0) vtc_fatal(vl, "Accept failed: %s", strerror(errno)); - vtc_log(vl, 3, "accepted fd %d", fd); + VTCP_hisname(fd, abuf, sizeof abuf, pbuf, sizeof pbuf); + vtc_log(vl, 3, "accepted fd %d %s %s", fd, abuf, pbuf); fd = http_process(vl, s->spec, fd, &s->sock); vtc_log(vl, 3, "shutting fd %d", fd); j = shutdown(fd, SHUT_WR); From phk at FreeBSD.org Tue Mar 28 07:56:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Tue, 28 Mar 2017 09:56:06 +0200 Subject: [master] 15f5c12 When the client abandons a fetch we close the connection to the backend if still in mid-transfer. With sufficiently small -bodylen, as in this test, that might or might not happen. Message-ID: commit 15f5c12d9945263027fd7493205120054af3d22a Author: Poul-Henning Kamp Date: Tue Mar 28 07:36:22 2017 +0000 When the client abandons a fetch we close the connection to the backend if still in mid-transfer. With sufficiently small -bodylen, as in this test, that might or might not happen. Explicitly close from the server side, to stabilize this test. Fixes #2280 diff --git a/bin/varnishtest/tests/r02042.vtc b/bin/varnishtest/tests/r02042.vtc index fcb79a6..8e59926 100644 --- a/bin/varnishtest/tests/r02042.vtc +++ b/bin/varnishtest/tests/r02042.vtc @@ -20,6 +20,9 @@ server s1 { expect req.http.If-None-Match == txresp -hdr "ETag: foo" -bodylen 7 + close + accept + rxreq expect req.url == "/lm" txresp -hdr "Last-Modified: Thu, 26 Jun 2008 12:00:01 GMT" \ @@ -107,6 +110,8 @@ client c1 { expect resp.http.X-Cache == "MISS" } -run +varnish v1 -vsl_catchup + # The next two tests are adapted from the former r01206.vtc, reflecting # changes for the recv->pass and beresp.uncacheable (hit-for-miss) cases # after rolling back the fix for #1206, and verifying that they are @@ -125,6 +130,9 @@ server s1 { expect req.http.If-None-Match == "foo" txresp -hdr "ETag: foo" -bodylen 7 + close + accept + rxreq expect req.url == "/lm2" txresp -hdr "Last-Modified: Thu, 26 Jun 2008 12:00:01 GMT" \ @@ -201,6 +209,9 @@ server s1 { expect req.http.If-None-Match == txresp -hdr "ETag: foo" -bodylen 7 + close + accept + rxreq expect req.url == "/lm3" txresp -hdr "Last-Modified: Thu, 26 Jun 2008 12:00:01 GMT" \ From dridi.boukelmoune at gmail.com Tue Mar 28 08:49:06 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Tue, 28 Mar 2017 10:49:06 +0200 Subject: [master] 99b1a62 Check backend existence when reading proxy_header Message-ID: commit 99b1a625c400ce0751967f1a0b7552d60de9c144 Author: Dridi Boukelmoune Date: Tue Mar 28 10:43:56 2017 +0200 Check backend existence when reading proxy_header A probe may still be running when its backend is deleted. In that case it needs to read the proxy_header field under the lock and give up if the backend was already gone. Not sure how to write a test case for this one. Fixes #2278 diff --git a/bin/varnishd/cache/cache_backend_probe.c b/bin/varnishd/cache/cache_backend_probe.c index 4c18854..3d5bc15 100644 --- a/bin/varnishd/cache/cache_backend_probe.c +++ b/bin/varnishd/cache/cache_backend_probe.c @@ -267,7 +267,7 @@ vbp_write_proxy_v1(struct vbp_target *vt, int *sock) static void vbp_poke(struct vbp_target *vt) { - int s, tmo, i; + int s, tmo, i, proxy_header; double t_start, t_now, t_end; unsigned rlen, resp; char buf[8192], *p; @@ -299,12 +299,22 @@ vbp_poke(struct vbp_target *vt) return; } + Lck_Lock(&vbp_mtx); + if (vt->backend != NULL) + proxy_header = vt->backend->proxy_header; + else + proxy_header = -1; + Lck_Unlock(&vbp_mtx); + + if (proxy_header < 0) + return; + /* Send the PROXY header */ - assert(vt->backend->proxy_header <= 2); - if (vt->backend->proxy_header == 1) { + assert(proxy_header <= 2); + if (proxy_header == 1) { if (vbp_write_proxy_v1(vt, &s) != 0) return; - } else if (vt->backend->proxy_header == 2 && + } else if (proxy_header == 2 && vbp_write(vt, &s, vbp_proxy_local, sizeof vbp_proxy_local) != 0) return; From phk at FreeBSD.org Tue Mar 28 14:48:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Tue, 28 Mar 2017 16:48:06 +0200 Subject: [master] c022cc4 It is more robust to wait for the client connection to close than to delay a random-ish number of seconds Message-ID: commit c022cc4ce74118d78b62d78d3e84a071bc52cc8c Author: Poul-Henning Kamp Date: Tue Mar 28 14:47:09 2017 +0000 It is more robust to wait for the client connection to close than to delay a random-ish number of seconds diff --git a/bin/varnishtest/tests/c00057.vtc b/bin/varnishtest/tests/c00057.vtc index ba0ec1e..6ad74aa 100644 --- a/bin/varnishtest/tests/c00057.vtc +++ b/bin/varnishtest/tests/c00057.vtc @@ -16,8 +16,7 @@ varnish v1 -vcl+backend { client c1 { txreq + expect_close } -run -delay 7 - varnish v1 -cliok "panic.show" From phk at FreeBSD.org Tue Mar 28 18:45:07 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Tue, 28 Mar 2017 20:45:07 +0200 Subject: [master] 54b5a09 Try to confuse GCC to not doing FP brain-damage. Message-ID: commit 54b5a09f00c027da280361b30d32a4ff309ba3ab Author: Poul-Henning Kamp Date: Tue Mar 28 18:44:12 2017 +0000 Try to confuse GCC to not doing FP brain-damage. Fixes #1875 (maybe) diff --git a/bin/varnishd/mgt/mgt_param_tweak.c b/bin/varnishd/mgt/mgt_param_tweak.c index 12a7a52..b26581e 100644 --- a/bin/varnishd/mgt/mgt_param_tweak.c +++ b/bin/varnishd/mgt/mgt_param_tweak.c @@ -52,7 +52,7 @@ static int tweak_generic_double(struct vsb *vsb, volatile double *dest, const char *arg, const char *min, const char *max, const char *fmt) { - double u, minv = 0, maxv = 0; + volatile double u, minv = 0, maxv = 0; if (arg != NULL) { if (min != NULL) { From phk at FreeBSD.org Wed Mar 29 11:51:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Wed, 29 Mar 2017 13:51:05 +0200 Subject: [master] 89e4f96 Remove place_holder code. Message-ID: commit 89e4f9690e54564587f41767bf3b66f04a097f4e Author: Poul-Henning Kamp Date: Wed Mar 29 07:47:35 2017 +0000 Remove place_holder code. diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index fa59e28..d54453e 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -838,21 +838,10 @@ h2_rxframe(struct worker *wrk, struct h2_sess *h2) return (1); } h2f = h2flist[h2->rxf_type]; -#if 1 + AN(h2f->name); AN(h2f->rxfunc); -#else - /* If we ever get holes in the frame table... */ - if (h2f->name == NULL || h2f->func == NULL) { - // rfc7540,l,679,681 - // XXX: later, drain rest of frame - h2->bogosity++; - VSLb(h2->vsl, SLT_Debug, - "H2: Unimplemented frame type 0x%02x (ignored)", - h2->rxf_type); - return (0); - } -#endif + if (h2->rxf_flags & ~h2f->flags) { // rfc7540,l,687,688 h2->bogosity++; From phk at FreeBSD.org Wed Mar 29 11:51:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Wed, 29 Mar 2017 13:51:06 +0200 Subject: [master] 735b0ec Add a copy of the rxthread to h2_sess and create an assert so we can mark up functions where only it can go. Message-ID: commit 735b0ec916ea8a48258c2968c7d0f01d603f3b60 Author: Poul-Henning Kamp Date: Wed Mar 29 08:30:21 2017 +0000 Add a copy of the rxthread to h2_sess and create an assert so we can mark up functions where only it can go. Mark scheduled h2_req's. diff --git a/bin/varnishd/http2/cache_http2.h b/bin/varnishd/http2/cache_http2.h index b95ac67..3d761ed 100644 --- a/bin/varnishd/http2/cache_http2.h +++ b/bin/varnishd/http2/cache_http2.h @@ -116,6 +116,7 @@ struct h2_req { unsigned magic; #define H2_REQ_MAGIC 0x03411584 uint32_t stream; + int scheduled; enum h2_stream_e state; struct h2_sess *h2sess; struct req *req; @@ -137,6 +138,7 @@ struct h2_sess { unsigned magic; #define H2_SESS_MAGIC 0xa16f7e4b + pthread_t rxthr; struct h2_req *mailcall; pthread_cond_t *cond; @@ -175,6 +177,8 @@ struct h2_sess { h2_error error; }; +#define ASSERT_RXTHR(h2) do {assert(h2->rxthr == pthread_self());} while(0) + /* http2/cache_http2_panic.c */ #ifdef TRANSPORT_MAGIC vtr_sess_panic_f h2_sess_panic; diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index d54453e..b8b19aa 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -263,6 +263,7 @@ static h2_error __match_proto__(h2_frame_f) h2_rx_ping(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) { + ASSERT_RXTHR(h2); (void)r2; if (h2->rxf_len != 8) // rfc7540,l,2364,2366 return (H2CE_FRAME_SIZE_ERROR); @@ -282,9 +283,10 @@ h2_rx_ping(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) static h2_error __match_proto__(h2_frame_f) h2_rx_push_promise(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) { - // rfc7540,l,2262,2267 + (void)wrk; - (void)h2; + ASSERT_RXTHR(h2); + // rfc7540,l,2262,2267 (void)r2; return (H2CE_PROTOCOL_ERROR); } @@ -295,7 +297,9 @@ h2_rx_push_promise(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) static h2_error __match_proto__(h2_frame_f) h2_rx_rst_stream(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) { + (void)wrk; + ASSERT_RXTHR(h2); if (h2->rxf_len != 4) // rfc7540,l,2003,2004 return (H2CE_FRAME_SIZE_ERROR); @@ -313,6 +317,7 @@ h2_rx_goaway(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) { (void)wrk; + ASSERT_RXTHR(h2); (void)r2; h2->goaway_last_stream = vbe32dec(h2->rxf_data); h2->error = h2_connectionerror(vbe32dec(h2->rxf_data + 4)); @@ -329,6 +334,7 @@ h2_rx_window_update(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) uint32_t wu; (void)wrk; + ASSERT_RXTHR(h2); if (h2->rxf_len != 4) return (H2CE_FRAME_SIZE_ERROR); wu = vbe32dec(h2->rxf_data) & ~(1LU<<31); @@ -353,7 +359,7 @@ h2_rx_priority(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) { (void)wrk; - (void)h2; + ASSERT_RXTHR(h2); xxxassert(r2->stream & 1); return (0); } @@ -423,6 +429,7 @@ h2_rx_settings(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) h2_error retval = 0; AN(wrk); + ASSERT_RXTHR(h2); AN(r2); AZ(h2->rxf_stream); if (h2->rxf_flags == H2FF_SETTINGS_ACK) { @@ -463,6 +470,7 @@ h2_do_req(struct worker *wrk, void *priv) if (CNT_Request(wrk, req) != REQ_FSM_DISEMBARK) { VSL(SLT_Debug, 0, "H2REQ CNT done"); AZ(req->ws->r); + r2->scheduled = 0; r2->state = H2_S_CLOSED; h2_del_req(wrk, r2); } @@ -475,6 +483,7 @@ h2_end_headers(struct worker *wrk, const struct h2_sess *h2, { h2_error h2e; + ASSERT_RXTHR(h2); assert(r2->state == H2_S_OPEN); h2e = h2h_decode_fini(h2, r2->decode); FREE_OBJ(r2->decode); @@ -495,6 +504,7 @@ h2_end_headers(struct worker *wrk, const struct h2_sess *h2, req->req_step = R_STP_TRANSPORT; req->task.func = h2_do_req; req->task.priv = req; + r2->scheduled = 1; XXXAZ(Pool_Task(wrk->pool, &req->task, TASK_QUEUE_REQ)); return (0); } @@ -507,6 +517,7 @@ h2_rx_headers(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) const uint8_t *p; size_t l; + ASSERT_RXTHR(h2); if (r2->state != H2_S_IDLE) return (H2CE_PROTOCOL_ERROR); // XXX spec ? r2->state = H2_S_OPEN; @@ -571,6 +582,7 @@ h2_rx_continuation(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) struct req *req; h2_error h2e; + ASSERT_RXTHR(h2); if (r2->state != H2_S_OPEN) return (H2CE_PROTOCOL_ERROR); // XXX spec ? req = r2->req; @@ -597,6 +609,7 @@ h2_rx_data(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) unsigned wi; (void)wrk; + ASSERT_RXTHR(h2); AZ(h2->mailcall); h2->mailcall = r2; Lck_Lock(&h2->sess->mtx); @@ -730,6 +743,7 @@ h2_procframe(struct worker *wrk, struct h2_sess *h2, h2_error h2e; char b[4]; + ASSERT_RXTHR(h2); if (h2->rxf_stream == 0 && h2f->act_szero != 0) return (h2f->act_szero); @@ -801,6 +815,7 @@ h2_rxframe(struct worker *wrk, struct h2_sess *h2) h2_error h2e; char b[8]; + ASSERT_RXTHR(h2); (void)VTCP_blocking(*h2->htc->rfd); h2->sess->t_idle = VTIM_real(); hs = HTC_RxStuff(h2->htc, h2_frame_complete, diff --git a/bin/varnishd/http2/cache_http2_session.c b/bin/varnishd/http2/cache_http2_session.c index 63732d2..967dd1f 100644 --- a/bin/varnishd/http2/cache_http2_session.c +++ b/bin/varnishd/http2/cache_http2_session.c @@ -98,6 +98,7 @@ h2_new_sess(const struct worker *wrk, struct sess *sp, struct req *srq) h2->vsl->wid = sp->vxid; h2->htc->rfd = &sp->fd; h2->sess = sp; + h2->rxthr = pthread_self(); VTAILQ_INIT(&h2->streams); VTAILQ_INIT(&h2->txqueue); h2->local_settings = H2_proto_settings; From phk at FreeBSD.org Wed Mar 29 11:51:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Wed, 29 Mar 2017 13:51:06 +0200 Subject: [master] ec9c04d Stop nagging the VSM if we ran out of it after an error Message-ID: commit ec9c04d60ff0a6c7c87bc4d6d1c26c7ed40789b5 Author: Poul-Henning Kamp Date: Wed Mar 29 09:45:14 2017 +0000 Stop nagging the VSM if we ran out of it after an error diff --git a/bin/varnishtest/vtc_varnish.c b/bin/varnishtest/vtc_varnish.c index 2079943..31ab631 100644 --- a/bin/varnishtest/vtc_varnish.c +++ b/bin/varnishtest/vtc_varnish.c @@ -218,6 +218,8 @@ varnishlog_thread(void *priv) opt = 0; while (v->pid || c != NULL) { if (c == NULL) { + if (vtc_error) + break; VTIM_sleep(0.1); if (VSM_Open(vsm)) { vtc_log(v->vl, 3, "vsm|%s", From phk at FreeBSD.org Wed Mar 29 11:51:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Wed, 29 Mar 2017 13:51:06 +0200 Subject: [master] bf6ce0f Improve the handling of h2 frame-reception when the connection closes. Insist we get the frames we expect. Message-ID: commit bf6ce0f733856843fd4598d8216df7e437d20187 Author: Poul-Henning Kamp Date: Wed Mar 29 11:08:47 2017 +0000 Improve the handling of h2 frame-reception when the connection closes. Insist we get the frames we expect. diff --git a/bin/varnishtest/tests/t02003.vtc b/bin/varnishtest/tests/t02003.vtc index 5c6b30c..b2e964f 100644 --- a/bin/varnishtest/tests/t02003.vtc +++ b/bin/varnishtest/tests/t02003.vtc @@ -269,8 +269,9 @@ client c1 { client c1 { stream 0 { - # SETTING unknown vlaue + # SETTING unknown value sendhex "000006 04 00 00000000 ffff00000000" + rxsettings txping rxping } -run diff --git a/bin/varnishtest/vtc_http2.c b/bin/varnishtest/vtc_http2.c index 1f6bfc3..ead77a4 100644 --- a/bin/varnishtest/vtc_http2.c +++ b/bin/varnishtest/vtc_http2.c @@ -177,27 +177,30 @@ get_bytes(const struct http *hp, char *buf, int n) if (i < 0 && errno == EINTR) continue; if (i == 0) - vtc_log(hp->vl, hp->fatal, + vtc_log(hp->vl, 3, "HTTP2 rx timeout (fd:%d %u ms)", hp->fd, hp->timeout); if (i < 0) - vtc_log(hp->vl, hp->fatal, + vtc_log(hp->vl, 3, "HTTP2 rx failed (fd:%d poll: %s)", hp->fd, strerror(errno)); - assert(i > 0); + if (i <= 0) + return (i); i = read(hp->fd, buf, n); if (!(pfd[0].revents & POLLIN)) vtc_log(hp->vl, 4, "HTTP2 rx poll (fd:%d revents: %x n=%d, i=%d)", hp->fd, pfd[0].revents, n, i); if (i == 0) - vtc_log(hp->vl, hp->fatal, + vtc_log(hp->vl, 3, "HTTP2 rx EOF (fd:%d read: %s)", hp->fd, strerror(errno)); if (i < 0) - vtc_log(hp->vl, hp->fatal, + vtc_log(hp->vl, 3, "HTTP2 rx failed (fd:%d read: %s)", hp->fd, strerror(errno)); + if (i <= 0) + return (i); n -= i; } return (1); @@ -729,7 +732,12 @@ receive_frame(void *priv) AZ(pthread_mutex_unlock(&hp->mtx)); if (!get_bytes(hp, hdr, 9)) { - vtc_log(hp->vl, 1, "could not get header"); + AZ(pthread_mutex_lock(&hp->mtx)); + VTAILQ_FOREACH(s, &hp->streams, list) + AZ(pthread_cond_signal(&s->cond)); + AZ(pthread_mutex_unlock(&hp->mtx)); + vtc_log(hp->vl, hp->fatal, + "could not get frame header"); return (NULL); } ALLOC_OBJ(f, FRAME_MAGIC); @@ -747,7 +755,15 @@ receive_frame(void *priv) f->data = malloc(f->size + 1L); AN(f->data); f->data[f->size] = '\0'; - AN(get_bytes(hp, f->data, f->size)); + if (get_bytes(hp, f->data, f->size) <= 0) { + AZ(pthread_mutex_lock(&hp->mtx)); + VTAILQ_FOREACH(s, &hp->streams, list) + AZ(pthread_cond_signal(&s->cond)); + AZ(pthread_mutex_unlock(&hp->mtx)); + vtc_log(hp->vl, hp->fatal, + "could not get frame body"); + return (NULL); + } } /* is the corresponding stream waiting? */ @@ -2331,12 +2347,13 @@ cmd_rxpush(CMD_ARGS) (void)cmd; \ (void)av; \ CAST_OBJ_NOTNULL(s, priv, STREAM_MAGIC); \ - if ((s->frame = rxstuff(s))) \ - return; \ - if (s->frame->type != TYPE_ ## upctype) \ - vtc_fatal(vl, "Received frame of type %d " \ - "is invalid for %s", \ - s->frame->type, "rx" #lctype); \ + s->frame = rxstuff(s); \ + if (s->frame != NULL && s->frame->type != TYPE_ ## upctype) \ + vtc_fatal(vl, \ + "Wrong frame type %s (%d) wanted %s", \ + s->frame->type < TYPE_MAX ? \ + h2_types[s->frame->type] : "?", \ + s->frame->type, #upctype); \ } /* SECTION: stream.spec.prio_rxprio rxprio From phk at FreeBSD.org Wed Mar 29 11:51:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Wed, 29 Mar 2017 13:51:06 +0200 Subject: [master] d56a248 Use each streams workers condvar instead of broadcasting. Message-ID: commit d56a2481d2ae5703c9401692670d265154d6861c Author: Poul-Henning Kamp Date: Wed Mar 29 11:16:29 2017 +0000 Use each streams workers condvar instead of broadcasting. diff --git a/bin/varnishd/http2/cache_http2.h b/bin/varnishd/http2/cache_http2.h index 3d761ed..0550e15 100644 --- a/bin/varnishd/http2/cache_http2.h +++ b/bin/varnishd/http2/cache_http2.h @@ -120,6 +120,7 @@ struct h2_req { enum h2_stream_e state; struct h2_sess *h2sess; struct req *req; + pthread_cond_t *cond; VTAILQ_ENTRY(h2_req) list; int64_t t_window; int64_t r_window; diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index b8b19aa..bba57de 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -138,6 +138,7 @@ h2_new_req(const struct worker *wrk, struct h2_sess *h2, { struct h2_req *r2; + ASSERT_RXTHR(h2); if (req == NULL) req = Req_New(wrk, h2->sess); CHECK_OBJ_NOTNULL(req, REQ_MAGIC); @@ -200,8 +201,8 @@ h2_kill_req(struct worker *wrk, const struct h2_sess *h2, r2->error = h2e; switch (r2->state) { case H2_S_CLOS_REM: - if (r2->wrk != NULL) - AZ(pthread_cond_signal(h2->cond)); + if (r2->cond != NULL) + AZ(pthread_cond_signal(r2->cond)); r2 = NULL; break; case H2_S_OPEN: @@ -487,7 +488,7 @@ h2_end_headers(struct worker *wrk, const struct h2_sess *h2, assert(r2->state == H2_S_OPEN); h2e = h2h_decode_fini(h2, r2->decode); FREE_OBJ(r2->decode); - r2->state = H2_S_CLOS_REM; // XXX: not _quite_ true + r2->state = H2_S_CLOS_REM; if (h2e != NULL) { VSL(SLT_Debug, 0, "H2H_DECODE_FINI %s", h2e->name); AZ(r2->req->ws->r); @@ -610,12 +611,13 @@ h2_rx_data(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) (void)wrk; ASSERT_RXTHR(h2); + Lck_Lock(&h2->sess->mtx); AZ(h2->mailcall); h2->mailcall = r2; - Lck_Lock(&h2->sess->mtx); h2->r_window -= h2->rxf_len; r2->r_window -= h2->rxf_len; - AZ(pthread_cond_broadcast(h2->cond)); + if (r2->cond) + AZ(pthread_cond_signal(r2->cond)); while (h2->mailcall != NULL && h2->error == 0 && r2->error == 0) AZ(Lck_CondWait(h2->cond, &h2->sess->mtx, 0)); wi = cache_param->h2_rx_window_increment; @@ -628,6 +630,7 @@ h2_rx_data(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) w2 = 1; } Lck_Unlock(&h2->sess->mtx); + if (w1 || w2) { vbe32enc(buf, wi); H2_Send_Get(wrk, h2, h2->req0); @@ -661,8 +664,10 @@ h2_vfp_body(struct vfp_ctx *vc, struct vfp_entry *vfe, void *ptr, ssize_t *lp) *lp = 0; Lck_Lock(&h2->sess->mtx); + r2->cond = &vc->wrk->cond; while (h2->mailcall != r2 && h2->error == 0 && r2->error == 0) - AZ(Lck_CondWait(h2->cond, &h2->sess->mtx, 0)); + AZ(Lck_CondWait(r2->cond, &h2->sess->mtx, 0)); + r2->cond = NULL; if (h2->error || r2->error) { retval = VFP_ERROR; } else { @@ -680,7 +685,7 @@ h2_vfp_body(struct vfp_ctx *vc, struct vfp_entry *vfe, void *ptr, ssize_t *lp) retval = VFP_END; } h2->mailcall = NULL; - AZ(pthread_cond_broadcast(h2->cond)); + AZ(pthread_cond_signal(h2->cond)); } Lck_Unlock(&h2->sess->mtx); return (retval); From phk at FreeBSD.org Wed Mar 29 11:51:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Wed, 29 Mar 2017 13:51:06 +0200 Subject: [master] 49c58d7 Don't let stream threads muck around in the stream list. Message-ID: commit 49c58d726d98ce82d1e9d84d436436e268c8d36d Author: Poul-Henning Kamp Date: Wed Mar 29 11:50:13 2017 +0000 Don't let stream threads muck around in the stream list. This should fix some H2 tickets. diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index bba57de..1a85b1e 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -171,6 +171,7 @@ h2_del_req(struct worker *wrk, struct h2_req *r2) CHECK_OBJ_NOTNULL(r2, H2_REQ_MAGIC); h2 = r2->h2sess; CHECK_OBJ_NOTNULL(h2, H2_SESS_MAGIC); + ASSERT_RXTHR(h2); sp = h2->sess; Lck_Lock(&sp->mtx); assert(h2->refcnt > 0); @@ -196,20 +197,19 @@ h2_kill_req(struct worker *wrk, const struct h2_sess *h2, struct h2_req *r2, h2_error h2e) { + ASSERT_RXTHR(h2); + AN(h2e); VSLb(h2->vsl, SLT_Debug, "KILL st=%u state=%d", r2->stream, r2->state); Lck_Lock(&h2->sess->mtx); - r2->error = h2e; - switch (r2->state) { - case H2_S_CLOS_REM: + if (r2->error == NULL) + r2->error = h2e; + if (r2->scheduled) { if (r2->cond != NULL) AZ(pthread_cond_signal(r2->cond)); r2 = NULL; - break; - case H2_S_OPEN: - (void)h2h_decode_fini(h2, r2->decode); - break; - default: - break; + } else { + if (r2->state == H2_S_OPEN) + (void)h2h_decode_fini(h2, r2->decode); } Lck_Unlock(&h2->sess->mtx); if (r2 != NULL) @@ -304,9 +304,9 @@ h2_rx_rst_stream(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) if (h2->rxf_len != 4) // rfc7540,l,2003,2004 return (H2CE_FRAME_SIZE_ERROR); - if (r2 != NULL) - h2_kill_req(wrk, h2, r2, - h2_streamerror(vbe32dec(h2->rxf_data))); + if (r2 == NULL) + return (0); + h2_kill_req(wrk, h2, r2, h2_streamerror(vbe32dec(h2->rxf_data))); return (0); } @@ -473,7 +473,8 @@ h2_do_req(struct worker *wrk, void *priv) AZ(req->ws->r); r2->scheduled = 0; r2->state = H2_S_CLOSED; - h2_del_req(wrk, r2); + if (r2->h2sess->error) + AZ(pthread_cond_signal(r2->h2sess->cond)); } THR_SetRequest(NULL); } @@ -744,7 +745,7 @@ static h2_error h2_procframe(struct worker *wrk, struct h2_sess *h2, h2_frame h2f) { - struct h2_req *r2 = NULL; + struct h2_req *r2 = NULL, *r22; h2_error h2e; char b[4]; @@ -767,9 +768,12 @@ h2_procframe(struct worker *wrk, struct h2_sess *h2, return (H2CE_PROTOCOL_ERROR); } - VTAILQ_FOREACH(r2, &h2->streams, list) + VTAILQ_FOREACH_SAFE(r2, &h2->streams, list, r22) { if (r2->stream == h2->rxf_stream) break; + if (r2->state == H2_S_CLOSED && !r2->scheduled) + h2_del_req(wrk, r2); + } if (r2 == NULL && h2f->act_sidle == 0) { if (h2->rxf_stream <= h2->highest_stream) diff --git a/bin/varnishd/http2/cache_http2_session.c b/bin/varnishd/http2/cache_http2_session.c index 967dd1f..3725586 100644 --- a/bin/varnishd/http2/cache_http2_session.c +++ b/bin/varnishd/http2/cache_http2_session.c @@ -275,8 +275,9 @@ h2_new_session(struct worker *wrk, void *arg) struct req *req; struct sess *sp; struct h2_sess *h2; - struct h2_req *r2; + struct h2_req *r2, *r22; uintptr_t wsp; + int again; CHECK_OBJ_NOTNULL(wrk, WORKER_MAGIC); CAST_OBJ_NOTNULL(req, arg, REQ_MAGIC); @@ -316,32 +317,32 @@ h2_new_session(struct worker *wrk, void *arg) } AN(h2->error); + /* Delete all idle streams */ - Lck_Lock(&sp->mtx); VSLb(h2->vsl, SLT_Debug, "H2 CLEANUP %s", h2->error->name); VTAILQ_FOREACH(r2, &h2->streams, list) { if (r2->error == 0) r2->error = h2->error; -#if 0 - if (r2->wrk != NULL) - AZ(pthread_cond_signal(&r2->wrk->cond)); // XXX Why? -#endif + if (r2->cond != NULL) + AZ(pthread_cond_signal(r2->cond)); } AZ(pthread_cond_signal(h2->cond)); - while (1) { - VTAILQ_FOREACH(r2, &h2->streams, list) - if (r2->state != H2_S_CLOS_REM && r2 != h2->req0) - break; - if (r2 == NULL) + while(1) { + again = 0; + VTAILQ_FOREACH_SAFE(r2, &h2->streams, list, r22) { + if (r2 != h2->req0) { + h2_kill_req(wrk, h2, r2, h2->error); + again++; + } + } + if (!again) break; - Lck_Unlock(&sp->mtx); - h2_kill_req(wrk, h2, r2, h2->error); - Lck_Lock(&sp->mtx); + VTAILQ_FOREACH(r2, &h2->streams, list) + VSLb(h2->vsl, SLT_Debug, "ST %u %d", r2->stream, r2->state); + Lck_Lock(&h2->sess->mtx); + (void)Lck_CondWait(h2->cond, &h2->sess->mtx, .1); + Lck_Unlock(&h2->sess->mtx); } - VSLb(h2->vsl, SLT_Debug, "H2CLEAN done"); - VTAILQ_FOREACH(r2, &h2->streams, list) - VSLb(h2->vsl, SLT_Debug, "ST %u %d", r2->stream, r2->state); - Lck_Unlock(&sp->mtx); h2->cond = NULL; h2_del_req(wrk, h2->req0); } From phk at FreeBSD.org Wed Mar 29 17:47:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Wed, 29 Mar 2017 19:47:05 +0200 Subject: [master] ad75b0e Add an assert so silly buggers who are to busy to check the arguments Lck_CondWait() will stopped in the tracks. Message-ID: commit ad75b0e43077b4c0be78729abf126646a8b361a9 Author: Poul-Henning Kamp Date: Wed Mar 29 17:45:03 2017 +0000 Add an assert so silly buggers who are to busy to check the arguments Lck_CondWait() will stopped in the tracks. diff --git a/bin/varnishd/cache/cache_lck.c b/bin/varnishd/cache/cache_lck.c index 4081d60..609971a 100644 --- a/bin/varnishd/cache/cache_lck.c +++ b/bin/varnishd/cache/cache_lck.c @@ -199,6 +199,7 @@ Lck_CondWait(pthread_cond_t *cond, struct lock *lck, double when) if (when == 0) { AZ(pthread_cond_wait(cond, &ilck->mtx)); } else { + assert(when > 1e9); ts.tv_nsec = (long)(modf(when, &t) * 1e9); ts.tv_sec = (long)t; retval = pthread_cond_timedwait(cond, &ilck->mtx, &ts); From phk at FreeBSD.org Wed Mar 29 17:47:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Wed, 29 Mar 2017 19:47:05 +0200 Subject: [master] 9042625 This silly bugger has now checked the arguments to Lck_CondWait() Message-ID: commit 90426253ab8f9fe706bce4f3d3d7e3da52b40583 Author: Poul-Henning Kamp Date: Wed Mar 29 17:46:05 2017 +0000 This silly bugger has now checked the arguments to Lck_CondWait() diff --git a/bin/varnishd/http2/cache_http2_session.c b/bin/varnishd/http2/cache_http2_session.c index 3725586..c1dee52 100644 --- a/bin/varnishd/http2/cache_http2_session.c +++ b/bin/varnishd/http2/cache_http2_session.c @@ -38,6 +38,7 @@ #include "http2/cache_http2.h" #include "vend.h" +#include "vtim.h" static const char h2_resp_101[] = "HTTP/1.1 101 Switching Protocols\r\n" @@ -340,7 +341,7 @@ h2_new_session(struct worker *wrk, void *arg) VTAILQ_FOREACH(r2, &h2->streams, list) VSLb(h2->vsl, SLT_Debug, "ST %u %d", r2->stream, r2->state); Lck_Lock(&h2->sess->mtx); - (void)Lck_CondWait(h2->cond, &h2->sess->mtx, .1); + (void)Lck_CondWait(h2->cond, &h2->sess->mtx, VTIM_real() + .1); Lck_Unlock(&h2->sess->mtx); } h2->cond = NULL; From phk at FreeBSD.org Wed Mar 29 18:57:05 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Wed, 29 Mar 2017 20:57:05 +0200 Subject: [master] c737577 Straighten out the HPACK error path. Message-ID: commit c73757749d29af793f470c97d2846629256448a3 Author: Poul-Henning Kamp Date: Wed Mar 29 18:55:42 2017 +0000 Straighten out the HPACK error path. Fixes #2289 diff --git a/bin/varnishd/http2/cache_http2_hpack.c b/bin/varnishd/http2/cache_http2_hpack.c index 4b0a1ce..9bcc1dd 100644 --- a/bin/varnishd/http2/cache_http2_hpack.c +++ b/bin/varnishd/http2/cache_http2_hpack.c @@ -49,7 +49,7 @@ h2h_checkhdr(const struct http *hp, const char *b, size_t namelen, size_t len) if (namelen == 2) { VSLb(hp->vsl, SLT_BogoHeader, "Empty name"); - return (H2CE_PROTOCOL_ERROR); + return (H2SE_PROTOCOL_ERROR); } for (p = b; p < b + len; p++) { @@ -61,7 +61,7 @@ h2h_checkhdr(const struct http *hp, const char *b, size_t namelen, size_t len) VSLb(hp->vsl, SLT_BogoHeader, "Illegal header name (upper-case): %.*s", (int)(len > 20 ? 20 : len), b); - return (H2CE_PROTOCOL_ERROR); + return (H2SE_PROTOCOL_ERROR); } if (vct_istchar(*p)) { /* XXX: vct should have a proper class for @@ -71,7 +71,7 @@ h2h_checkhdr(const struct http *hp, const char *b, size_t namelen, size_t len) VSLb(hp->vsl, SLT_BogoHeader, "Illegal header name: %.*s", (int)(len > 20 ? 20 : len), b); - return (H2CE_PROTOCOL_ERROR); + return (H2SE_PROTOCOL_ERROR); } else if (p < b + namelen) { /* ': ' added by us */ assert(*p == ':' || *p == ' '); @@ -82,7 +82,7 @@ h2h_checkhdr(const struct http *hp, const char *b, size_t namelen, size_t len) VSLb(hp->vsl, SLT_BogoHeader, "Illegal header value: %.*s", (int)(len > 20 ? 20 : len), b); - return (H2CE_PROTOCOL_ERROR); + return (H2SE_PROTOCOL_ERROR); } } @@ -134,7 +134,7 @@ h2h_addhdr(struct http *hp, char *b, size_t namelen, size_t len) VSLb(hp->vsl, SLT_BogoHeader, "Unknown pseudo-header: %.*s", (int)(len > 20 ? 20 : len), b); - return (H2SE_PROTOCOL_ERROR); + return (H2SE_PROTOCOL_ERROR); // rfc7540,l,2990,2992 } } else n = hp->nhd; @@ -145,7 +145,7 @@ h2h_addhdr(struct http *hp, char *b, size_t namelen, size_t len) VSLb(hp->vsl, SLT_BogoHeader, "Duplicate pseudo-header: %.*s", (int)(len > 20 ? 20 : len), b); - return (H2SE_PROTOCOL_ERROR); + return (H2SE_PROTOCOL_ERROR); // rfc7540,l,3158,3162 } } else { /* Check for space in struct http */ diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index 1a85b1e..5e34543 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -469,7 +469,6 @@ h2_do_req(struct worker *wrk, void *priv) THR_SetRequest(req); req->http->conds = 1; if (CNT_Request(wrk, req) != REQ_FSM_DISEMBARK) { - VSL(SLT_Debug, 0, "H2REQ CNT done"); AZ(req->ws->r); r2->scheduled = 0; r2->state = H2_S_CLOSED; @@ -491,7 +490,7 @@ h2_end_headers(struct worker *wrk, const struct h2_sess *h2, FREE_OBJ(r2->decode); r2->state = H2_S_CLOS_REM; if (h2e != NULL) { - VSL(SLT_Debug, 0, "H2H_DECODE_FINI %s", h2e->name); + VSLb(h2->vsl, SLT_Debug, "HPACK/FINI %s", h2e->name); AZ(r2->req->ws->r); h2_del_req(wrk, r2); return (h2e); @@ -558,12 +557,12 @@ h2_rx_headers(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) p += 1; } if (h2->rxf_flags & H2FF_HEADERS_PRIORITY) { - p += 5; l -= 5; + p += 5; } h2e = h2h_decode_bytes(h2, r2->decode, p, l); if (h2e != NULL) { - VSL(SLT_Debug, 0, "H2H_DECODE_BYTES(hdr) %s", h2e->name); + VSLb(h2->vsl, SLT_Debug, "HPACK(hdr) %s", h2e->name); (void)h2h_decode_fini(h2, r2->decode); AZ(r2->req->ws->r); h2_del_req(wrk, r2); @@ -590,7 +589,7 @@ h2_rx_continuation(struct worker *wrk, struct h2_sess *h2, struct h2_req *r2) req = r2->req; h2e = h2h_decode_bytes(h2, r2->decode, h2->rxf_data, h2->rxf_len); if (h2e != NULL) { - VSL(SLT_Debug, 0, "H2H_DECODE_BYTES(cont) %s", h2e->name); + VSLb(h2->vsl, SLT_Debug, "HPACK(cont) %s", h2e->name); (void)h2h_decode_fini(h2, r2->decode); AZ(r2->req->ws->r); h2_del_req(wrk, r2); @@ -733,7 +732,6 @@ h2_frame_complete(struct http_conn *htc) if (l < 9) return (HTC_S_MORE); u = vbe32dec(htc->rxbuf_b) >> 8; - VSL(SLT_Debug, 0, "RX %p %d %u", htc->rxbuf_b, l, u); if (l < u + 9) // XXX: Only for !DATA frames return (HTC_S_MORE); return (HTC_S_COMPLETE); @@ -792,12 +790,11 @@ h2_procframe(struct worker *wrk, struct h2_sess *h2, VSLb(h2->vsl, SLT_Debug, "H2: stream %u: %s", h2->rxf_stream, h2e->txt); vbe32enc(b, h2e->val); - H2_Send_Get(wrk, h2, r2); + H2_Send_Get(wrk, h2, h2->req0); (void)H2_Send_Frame(wrk, h2, H2_F_RST_STREAM, 0, sizeof b, h2->rxf_stream, b); - H2_Send_Rel(h2, r2); + H2_Send_Rel(h2, h2->req0); - h2_del_req(wrk, r2); return (0); } diff --git a/bin/varnishtest/tests/t02003.vtc b/bin/varnishtest/tests/t02003.vtc index b2e964f..eef69e2 100644 --- a/bin/varnishtest/tests/t02003.vtc +++ b/bin/varnishtest/tests/t02003.vtc @@ -349,6 +349,14 @@ client c1 { } -run } -run +client c1 { + stream 1 { + txreq -hdr ":bla" "foo" + rxrst + expect rst.err == PROTOCOL_ERROR + } -run +} -run + varnish v1 -vsl_catchup varnish v1 -expect MEMPOOL.req0.live == 0 From phk at FreeBSD.org Thu Mar 30 07:34:06 2017 From: phk at FreeBSD.org (Poul-Henning Kamp) Date: Thu, 30 Mar 2017 09:34:06 +0200 Subject: [master] 3db481a A *little* bit more coverage Message-ID: commit 3db481a96f55ecff21983c09c644f578ac507b1f Author: Poul-Henning Kamp Date: Thu Mar 30 07:23:20 2017 +0000 A *little* bit more coverage diff --git a/bin/varnishd/http2/cache_http2_proto.c b/bin/varnishd/http2/cache_http2_proto.c index 5e34543..4441406 100644 --- a/bin/varnishd/http2/cache_http2_proto.c +++ b/bin/varnishd/http2/cache_http2_proto.c @@ -767,10 +767,10 @@ h2_procframe(struct worker *wrk, struct h2_sess *h2, } VTAILQ_FOREACH_SAFE(r2, &h2->streams, list, r22) { - if (r2->stream == h2->rxf_stream) - break; if (r2->state == H2_S_CLOSED && !r2->scheduled) h2_del_req(wrk, r2); + else if (r2->stream == h2->rxf_stream) + break; } if (r2 == NULL && h2f->act_sidle == 0) { diff --git a/bin/varnishtest/tests/t02003.vtc b/bin/varnishtest/tests/t02003.vtc index eef69e2..db5fb31 100644 --- a/bin/varnishtest/tests/t02003.vtc +++ b/bin/varnishtest/tests/t02003.vtc @@ -228,6 +228,18 @@ client c1 { } -run } -run +client c1 { + stream 1 { + txreq + rxresp + } -run + stream 1 { + # RST_STREAM on closed stream + txrst + } -run +} -run + + varnish v1 -vsl_catchup varnish v1 -expect MEMPOOL.req0.live == 0 From hermunn at varnish-software.com Thu Mar 30 14:42:06 2017 From: hermunn at varnish-software.com (Pål Hermunn Johansen) Date: Thu, 30 Mar 2017 16:42:06 +0200 Subject: [4.1] 5030448 add std.getenv() Message-ID: commit 503044881785d367854018d4a9f15339d6912d50 Author: Nils Goroll Date: Fri Dec 2 10:48:12 2016 +0100 add std.getenv() Merges #2152 diff --git a/bin/varnishtest/tests/m00026.vtc b/bin/varnishtest/tests/m00026.vtc new file mode 100644 index 0000000..17ca1ed --- /dev/null +++ b/bin/varnishtest/tests/m00026.vtc @@ -0,0 +1,21 @@ +varnishtest "Test std.getenv" + +varnish v1 -vcl { + import std; + + backend dummy { .host = "${bad_ip}"; .port = "9080"; } + + sub vcl_recv { + return(synth(200)); + } + + sub vcl_synth { + set resp.http.X-PATH = std.getenv("PATH"); + } +} -start + +client c1 { + txreq + rxresp + expect resp.http.X-PATH ~ "^/" +} -run diff --git a/lib/libvmod_std/vmod.vcc b/lib/libvmod_std/vmod.vcc index bb69945..97d3b5e 100644 --- a/lib/libvmod_std/vmod.vcc +++ b/lib/libvmod_std/vmod.vcc @@ -269,6 +269,14 @@ Example | ... | } +$Function STRING getenv(STRING name) + +Description + Return environment variable *name* or the empty string. + + See getenv(3) +Example + | set req.http.My-Env = getenv("MY_ENV"); SEE ALSO ======== diff --git a/lib/libvmod_std/vmod_std.c b/lib/libvmod_std/vmod_std.c index 6cd5b8a..685a348 100644 --- a/lib/libvmod_std/vmod_std.c +++ b/lib/libvmod_std/vmod_std.c @@ -253,3 +253,12 @@ vmod_strstr(VRT_CTX, VCL_STRING s1, VCL_STRING s2) return (NULL); return (strstr(s1, s2)); } + +VCL_STRING __match_proto__(td_std_getenv) +vmod_getenv(VRT_CTX, VCL_STRING name) +{ + CHECK_OBJ_NOTNULL(ctx, VRT_CTX_MAGIC); + if (name == NULL || *name == '\0') + return (NULL); + return (getenv(name)); +} From hrvarnish-commit at varnish-cache.org Thu Mar 30 15:29:11 2017 From: hrvarnish-commit at varnish-cache.org (varnish-commit) Date: Thu, 30 Mar 2017 23:29:11 +0800 Subject: =?utf-8?B?6L2s5Y+R77ya5ZCR5LiK566h55CG55qEOeS4quWGheWuueWSjDXkuKrmraXpqqQ=?= Message-ID: <20170330232918187451@chahospice.com> An HTML attachment was scrubbed... URL: -------------- next part -------------- A non-text attachment was scrubbed... Name: ?????9????5???.docx Type: application/octet-stream Size: 26201 bytes Desc: not available URL: From hermunn at varnish-software.com Thu Mar 30 17:01:06 2017 From: hermunn at varnish-software.com (Pål Hermunn Johansen) Date: Thu, 30 Mar 2017 19:01:06 +0200 Subject: [4.1] 2bc20ee Repair test case m00026.vtc Message-ID: commit 2bc20ee0d10b96760011d63b46c5de268225c145 Author: P?l Hermunn Johansen Date: Thu Mar 30 18:59:14 2017 +0200 Repair test case m00026.vtc Bad cherry-pick again from me. Fixing the test case that needs to be 4.1 compatible. diff --git a/bin/varnishtest/tests/m00026.vtc b/bin/varnishtest/tests/m00026.vtc index 17ca1ed..31e38fa 100644 --- a/bin/varnishtest/tests/m00026.vtc +++ b/bin/varnishtest/tests/m00026.vtc @@ -1,7 +1,7 @@ varnishtest "Test std.getenv" varnish v1 -vcl { - import std; + import ${vmod_std}; backend dummy { .host = "${bad_ip}"; .port = "9080"; } From martin at varnish-software.com Fri Mar 31 11:57:05 2017 From: martin at varnish-software.com (Martin Blix Grydeland) Date: Fri, 31 Mar 2017 13:57:05 +0200 Subject: [master] 5dd70af Set the go-cold timer on newly loaded warm auto VCLs Message-ID: commit 5dd70aff3e968f173d3b747b1d1a2bb805be5f6f Author: Martin Blix Grydeland Date: Wed Mar 22 10:59:54 2017 +0100 Set the go-cold timer on newly loaded warm auto VCLs Newly loaded VCLs didn't get their go cold timer set even when they were set to auto, causing them to never go cold automatically. Fixes: #2270 diff --git a/bin/varnishd/mgt/mgt_vcl.c b/bin/varnishd/mgt/mgt_vcl.c index 8849752..9a1a42b 100644 --- a/bin/varnishd/mgt/mgt_vcl.c +++ b/bin/varnishd/mgt/mgt_vcl.c @@ -481,8 +481,13 @@ mgt_new_vcl(struct cli *cli, const char *vclname, const char *vclsrc, mgt_vcl_del(vp); VCLI_Out(cli, "%s", p); VCLI_SetResult(cli, status); + free(p); + return; } free(p); + + if (vp->warm && !strcmp(vp->state, "auto")) + vp->go_cold = VTIM_mono(); } /*--------------------------------------------------------------------*/ diff --git a/bin/varnishtest/tests/r02270.vtc b/bin/varnishtest/tests/r02270.vtc new file mode 100644 index 0000000..8547ca5 --- /dev/null +++ b/bin/varnishtest/tests/r02270.vtc @@ -0,0 +1,19 @@ +varnishtest "Test that never used VCLs go cold automatically" + +server s1 { + rxreq + txresp +} -start + +varnish v1 -arg "-p vcl_cooldown=1" -vcl+backend { +} -start + +varnish v1 -expect VBE.vcl1.s1.happy >= 0 + +varnish v1 -cliok {vcl.inline vcl2 "vcl 4.0; backend s1 {.host = \"${s1_addr}\"; .port = \"${s1_port}\"; }"} + +varnish v1 -expect VBE.vcl2.s1.happy >= 0 + +delay 5 + +varnish v1 -expect !VBE.vcl2.s1.happy From dridi.boukelmoune at gmail.com Fri Mar 31 12:25:08 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Fri, 31 Mar 2017 14:25:08 +0200 Subject: [master] 5087989 Teach http_CollectHdr to use arbitrary separators Message-ID: commit 5087989e7bd1afa01d02552fcfe7284609d7d5fd Author: Dridi Boukelmoune Date: Thu Mar 30 14:53:43 2017 +0200 Teach http_CollectHdr to use arbitrary separators This done via a new http_CollectHdrSep function, implying a VRT minor bump. Refs #2291 diff --git a/bin/varnishd/cache/cache.h b/bin/varnishd/cache/cache.h index cfed8b4..5bc79d7 100644 --- a/bin/varnishd/cache/cache.h +++ b/bin/varnishd/cache/cache.h @@ -783,6 +783,7 @@ void http_CopyHome(const struct http *hp); void http_Unset(struct http *hp, const char *hdr); unsigned http_CountHdr(const struct http *hp, const char *hdr); void http_CollectHdr(struct http *hp, const char *hdr); +void http_CollectHdrSep(struct http *hp, const char *hdr, const char *sep); void http_VSL_log(const struct http *hp); void HTTP_Merge(struct worker *, struct objcore *, struct http *to); uint16_t HTTP_GetStatusPack(struct worker *, struct objcore *oc); diff --git a/bin/varnishd/cache/cache_http.c b/bin/varnishd/cache/cache_http.c index 0c1487d..8ad5ea8 100644 --- a/bin/varnishd/cache/cache_http.c +++ b/bin/varnishd/cache/cache_http.c @@ -1,6 +1,6 @@ /*- * Copyright (c) 2006 Verdens Gang AS - * Copyright (c) 2006-2015 Varnish Software AS + * Copyright (c) 2006-2017 Varnish Software AS * All rights reserved. * * Author: Poul-Henning Kamp @@ -328,12 +328,30 @@ http_CountHdr(const struct http *hp, const char *hdr) void http_CollectHdr(struct http *hp, const char *hdr) { - unsigned u, l, ml, f, x, d; + + http_CollectHdrSep(hp, hdr, NULL); +} + +/*-------------------------------------------------------------------- + * You may prefer to collapse header fields using a different separator. + * For Cookie headers, the separator is "; " for example. That's probably + * the only example too. + */ + +void +http_CollectHdrSep(struct http *hp, const char *hdr, const char *sep) +{ + unsigned u, l, lsep, ml, f, x, d; char *b = NULL, *e = NULL; CHECK_OBJ_NOTNULL(hp, HTTP_MAGIC); if (WS_Overflowed(hp->ws)) return; + + if (sep == NULL || *sep == '\0') + sep = ","; + lsep = strlen(sep); + l = hdr[0]; assert(l == strlen(hdr + 1)); assert(hdr[l] == ':'); @@ -371,15 +389,15 @@ http_CollectHdr(struct http *hp, const char *hdr) AN(e); /* Append the Nth header we found */ - if (b < e) - *b++ = ','; x = Tlen(hp->hd[u]) - l; - if (b + x >= e) { + if (b + lsep + x >= e) { http_fail(hp); VSLb(hp->vsl, SLT_LostHeader, "%s", hdr + 1); WS_Release(hp->ws, 0); return; } + memcpy(b, sep, lsep); + b += lsep; memcpy(b, hp->hd[u].b + *hdr, x); b += x; } diff --git a/include/vrt.h b/include/vrt.h index d8e4b4e..ef5204a 100644 --- a/include/vrt.h +++ b/include/vrt.h @@ -39,6 +39,8 @@ * binary/load-time compatible, increment MAJOR version * * + * 6.1 (unreleased): + * http_CollectHdrSep added * 6.0 (2017-03-15): * VRT_hit_for_pass added * VRT_ipcmp added From dridi.boukelmoune at gmail.com Fri Mar 31 12:25:08 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Fri, 31 Mar 2017 14:25:08 +0200 Subject: [master] d26a828 Collapse Cookie headers in HTTP/2 Message-ID: commit d26a828751ac8a49b04774a2014228de4e76205d Author: Dridi Boukelmoune Date: Thu Mar 30 14:58:58 2017 +0200 Collapse Cookie headers in HTTP/2 Fixes #2291 diff --git a/bin/varnishd/cache/cache_req_fsm.c b/bin/varnishd/cache/cache_req_fsm.c index 3963625..aa8e1d7 100644 --- a/bin/varnishd/cache/cache_req_fsm.c +++ b/bin/varnishd/cache/cache_req_fsm.c @@ -1,6 +1,6 @@ /*- * Copyright (c) 2006 Verdens Gang AS - * Copyright (c) 2006-2015 Varnish Software AS + * Copyright (c) 2006-2017 Varnish Software AS * All rights reserved. * * Author: Poul-Henning Kamp @@ -799,6 +799,9 @@ cnt_recv(struct worker *wrk, struct req *req) http_CollectHdr(req->http, H_Cache_Control); + if (req->http->protover == 20) // rfc7540,l,3114,3120 + http_CollectHdrSep(req->http, H_Cookie, "; "); + if (req->req_body_status == REQ_BODY_FAIL) { req->doclose = SC_OVERLOAD; return (REQ_FSM_DONE); diff --git a/bin/varnishtest/tests/r02291.vtc b/bin/varnishtest/tests/r02291.vtc new file mode 100644 index 0000000..25659dd --- /dev/null +++ b/bin/varnishtest/tests/r02291.vtc @@ -0,0 +1,33 @@ +varnishtest "Collect cookie headers in HTTP/2" + +server s1 -repeat 2 { + rxreq + txresp +} -start + +varnish v1 -vcl+backend { } -start +varnish v1 -cliok "param.set feature +http2" + +logexpect l1 -v v1 { + expect * * BereqProtocol HTTP/1.1 + expect * = BereqHeader "Cookie: user=alice" + expect * = BereqHeader "Cookie: peer=bob" + expect * * BereqProtocol HTTP/2.0 + expect * = BereqHeader "cookie: user=alice; peer=bob" +} -start + +client c1 { + txreq -hdr "Cookie: user=alice" -hdr "Cookie: peer=bob" + rxresp + expect resp.status == 200 +} -run + +client c2 { + stream 1 { + txreq -hdr cookie user=alice -hdr cookie peer=bob + rxresp + expect resp.status == 200 + } -run +} -run + +logexpect l1 -wait From dridi.boukelmoune at gmail.com Fri Mar 31 12:25:08 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Fri, 31 Mar 2017 14:25:08 +0200 Subject: [master] 58b2d30 Grow a separator argument in std.collect Message-ID: commit 58b2d3061bd2e2bc9a8f45729e4fb1c2e6dc6ccb Author: Dridi Boukelmoune Date: Thu Mar 30 15:56:36 2017 +0200 Grow a separator argument in std.collect Fixes #2292 diff --git a/lib/libvmod_std/vmod.vcc b/lib/libvmod_std/vmod.vcc index 61eed10..ab1741d 100644 --- a/lib/libvmod_std/vmod.vcc +++ b/lib/libvmod_std/vmod.vcc @@ -1,5 +1,5 @@ #- -# Copyright (c) 2010-2015 Varnish Software AS +# Copyright (c) 2010-2017 Varnish Software AS # All rights reserved. # # Author: Poul-Henning Kamp @@ -107,17 +107,19 @@ Description Example set beresp.http.served-by = std.fileread("/etc/hostname"); -$Function VOID collect(HEADER hdr) +$Function VOID collect(HEADER hdr, STRING sep=",") Description Collapses multiple *hdr* headers into one long header. - The header values are joined with a comma (","). + The header values are joined with a comma (",") unless a + different separator is specified. Care should be taken when collapsing headers. In particular collapsing Set-Cookie will lead to unexpected results on the browser side. -Example - std.collect(req.http.cookie); +Examples + std.collect(req.http.accept); + std.collect(req.http.cookie, "; "); $Function DURATION duration(STRING s, DURATION fallback) diff --git a/lib/libvmod_std/vmod_std.c b/lib/libvmod_std/vmod_std.c index 557e88d..601de8b 100644 --- a/lib/libvmod_std/vmod_std.c +++ b/lib/libvmod_std/vmod_std.c @@ -1,5 +1,5 @@ /*- - * Copyright (c) 2010-2015 Varnish Software AS + * Copyright (c) 2010-2017 Varnish Software AS * All rights reserved. * * Author: Poul-Henning Kamp @@ -174,13 +174,13 @@ vmod_syslog(VRT_CTX, VCL_INT fac, const char *fmt, ...) } VCL_VOID __match_proto__(td_std_collect) -vmod_collect(VRT_CTX, VCL_HEADER hdr) +vmod_collect(VRT_CTX, VCL_HEADER hdr, VCL_STRING sep) { struct http *hp; CHECK_OBJ_NOTNULL(ctx, VRT_CTX_MAGIC); hp = VRT_selecthttp(ctx, hdr->where); - http_CollectHdr(hp, hdr->what); + http_CollectHdrSep(hp, hdr->what, sep); } VCL_BOOL __match_proto__(td_std_healthy) From dridi.boukelmoune at gmail.com Fri Mar 31 12:25:08 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Fri, 31 Mar 2017 14:25:08 +0200 Subject: [master] eadcc45 Ignore leading spaces in http_CollectHdr Message-ID: commit eadcc45ee781f54bdd8e41e5cefea001132114da Author: Dridi Boukelmoune Date: Thu Mar 30 16:18:54 2017 +0200 Ignore leading spaces in http_CollectHdr The default separator is now ", " to maintain the "pretty collapsing" of the headers without risking an extra space with the "; " separator for cookies. Refs #2291 Refs #2292 diff --git a/bin/varnishd/cache/cache_http.c b/bin/varnishd/cache/cache_http.c index 8ad5ea8..5d900bf 100644 --- a/bin/varnishd/cache/cache_http.c +++ b/bin/varnishd/cache/cache_http.c @@ -343,13 +343,14 @@ http_CollectHdrSep(struct http *hp, const char *hdr, const char *sep) { unsigned u, l, lsep, ml, f, x, d; char *b = NULL, *e = NULL; + const char *v; CHECK_OBJ_NOTNULL(hp, HTTP_MAGIC); if (WS_Overflowed(hp->ws)) return; if (sep == NULL || *sep == '\0') - sep = ","; + sep = ", "; lsep = strlen(sep); l = hdr[0]; @@ -390,6 +391,13 @@ http_CollectHdrSep(struct http *hp, const char *hdr, const char *sep) /* Append the Nth header we found */ x = Tlen(hp->hd[u]) - l; + + v = hp->hd[u].b + *hdr; + while (vct_issp(*v)) { + v++; + x--; + } + if (b + lsep + x >= e) { http_fail(hp); VSLb(hp->vsl, SLT_LostHeader, "%s", hdr + 1); @@ -398,7 +406,7 @@ http_CollectHdrSep(struct http *hp, const char *hdr, const char *sep) } memcpy(b, sep, lsep); b += lsep; - memcpy(b, hp->hd[u].b + *hdr, x); + memcpy(b, v, x); b += x; } if (b == NULL) diff --git a/bin/varnishtest/tests/r02291.vtc b/bin/varnishtest/tests/r02291.vtc index 25659dd..3a02360 100644 --- a/bin/varnishtest/tests/r02291.vtc +++ b/bin/varnishtest/tests/r02291.vtc @@ -13,7 +13,7 @@ logexpect l1 -v v1 { expect * = BereqHeader "Cookie: user=alice" expect * = BereqHeader "Cookie: peer=bob" expect * * BereqProtocol HTTP/2.0 - expect * = BereqHeader "cookie: user=alice; peer=bob" + expect * = BereqHeader "cookie: user=alice; peer=bob" } -start client c1 { diff --git a/lib/libvmod_std/vmod.vcc b/lib/libvmod_std/vmod.vcc index ab1741d..d4a4381 100644 --- a/lib/libvmod_std/vmod.vcc +++ b/lib/libvmod_std/vmod.vcc @@ -107,7 +107,7 @@ Description Example set beresp.http.served-by = std.fileread("/etc/hostname"); -$Function VOID collect(HEADER hdr, STRING sep=",") +$Function VOID collect(HEADER hdr, STRING sep=", ") Description Collapses multiple *hdr* headers into one long header. From dridi.boukelmoune at gmail.com Fri Mar 31 12:25:08 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Fri, 31 Mar 2017 14:25:08 +0200 Subject: [master] 99efebb Coverage for std.collect Message-ID: commit 99efebb3c986aebf313c1f2ad43dddbfa4c07159 Author: Dridi Boukelmoune Date: Thu Mar 30 16:32:26 2017 +0200 Coverage for std.collect Refs #2291 Refs #2292 diff --git a/bin/varnishtest/tests/m00006.vtc b/bin/varnishtest/tests/m00006.vtc index 2afad24..24ad5f9 100644 --- a/bin/varnishtest/tests/m00006.vtc +++ b/bin/varnishtest/tests/m00006.vtc @@ -20,7 +20,7 @@ varnish v1 -vcl+backend { std.collect(beresp.http.bar); } sub vcl_deliver { - std.collect(resp.http.qux); + std.collect(resp.http.qux, "; "); } } -start @@ -28,5 +28,5 @@ client c1 { txreq -hdr "Foo: 1" -hdr "Foo: 2" -hdr "Baz: 3" -hdr "Baz: 4" rxresp expect resp.http.bar == "a, b" - expect resp.http.qux == "c, d" + expect resp.http.qux == "c; d" } -run From dridi.boukelmoune at gmail.com Fri Mar 31 12:25:08 2017 From: dridi.boukelmoune at gmail.com (Dridi Boukelmoune) Date: Fri, 31 Mar 2017 14:25:08 +0200 Subject: [master] 84e98d8 Improve documentation for std.collect Message-ID: commit 84e98d8d0d5c922805bcd47e29a48580d026fc22 Author: Dridi Boukelmoune Date: Fri Mar 31 09:12:27 2017 +0200 Improve documentation for std.collect diff --git a/lib/libvmod_std/vmod.vcc b/lib/libvmod_std/vmod.vcc index d4a4381..2ebfb45 100644 --- a/lib/libvmod_std/vmod.vcc +++ b/lib/libvmod_std/vmod.vcc @@ -110,16 +110,17 @@ Example $Function VOID collect(HEADER hdr, STRING sep=", ") Description - Collapses multiple *hdr* headers into one long header. - The header values are joined with a comma (",") unless a - different separator is specified. + Collapses multiple *hdr* headers into one long header. The + default separator *sep* is the standard comma separator to + use when collapsing headers, with an additional whitespace + for pretty printing. Care should be taken when collapsing headers. In particular collapsing Set-Cookie will lead to unexpected results on the browser side. Examples - std.collect(req.http.accept); - std.collect(req.http.cookie, "; "); + | std.collect(req.http.accept); + | std.collect(req.http.cookie, "; "); $Function DURATION duration(STRING s, DURATION fallback) From hermunn at varnish-software.com Fri Mar 31 14:27:06 2017 From: hermunn at varnish-software.com (Pål Hermunn Johansen) Date: Fri, 31 Mar 2017 16:27:06 +0200 Subject: [4.1] 3c1c970 Dramatically simplify VEV Message-ID: commit 3c1c9703b1c2b837b9b40eebe3753f53301a545c Author: Poul-Henning Kamp Date: Fri Jan 27 20:42:24 2017 +0000 Dramatically simplify VEV Fixes: #2200 diff --git a/bin/varnishtest/tests/c00057.vtc b/bin/varnishtest/tests/c00057.vtc index df4767b..ba0ec1e 100644 --- a/bin/varnishtest/tests/c00057.vtc +++ b/bin/varnishtest/tests/c00057.vtc @@ -18,6 +18,6 @@ client c1 { txreq } -run -delay 5 +delay 7 varnish v1 -cliok "panic.show" diff --git a/include/vev.h b/include/vev.h index 37db60f..47fd050 100644 --- a/include/vev.h +++ b/include/vev.h @@ -41,6 +41,7 @@ struct vev { const char *name; int fd; unsigned fd_flags; + unsigned fd_events; #define EV_RD POLLIN #define EV_WR POLLOUT #define EV_ERR POLLERR @@ -54,11 +55,9 @@ struct vev { /* priv */ double __when; - VTAILQ_ENTRY(vev) __list; unsigned __binheap_idx; unsigned __privflags; struct vev_base *__vevb; - int __poll_idx; }; struct vev_base *vev_new_base(void); diff --git a/lib/libvarnish/vev.c b/lib/libvarnish/vev.c index 0ceaaa9..760fbed 100644 --- a/lib/libvarnish/vev.c +++ b/lib/libvarnish/vev.c @@ -43,7 +43,6 @@ #include "vas.h" #include "binary_heap.h" -#include "vqueue.h" #include "vev.h" #include "vtim.h" @@ -67,13 +66,11 @@ static int vev_nsig; struct vev_base { unsigned magic; #define VEV_BASE_MAGIC 0x477bcf3d - VTAILQ_HEAD(,vev) events; struct pollfd *pfd; + struct vev **pev; unsigned npfd; unsigned lpfd; struct binheap *binheap; - unsigned char compact_pfd; - unsigned char disturbed; unsigned psig; pthread_t thread; #ifdef DEBUG_EVENTS @@ -90,6 +87,7 @@ struct vev_base { } while (0); #else #define DBG(evb, ...) /* ... */ +//#define DBG(evb, ...) fprintf(stderr, __VA_ARGS__); #endif /*--------------------------------------------------------------------*/ @@ -102,7 +100,14 @@ vev_bh_update(void *priv, void *a, unsigned u) CAST_OBJ_NOTNULL(evb, priv, VEV_BASE_MAGIC); CAST_OBJ_NOTNULL(e, a, VEV_MAGIC); + assert(u < evb->lpfd); e->__binheap_idx = u; + if (u != BINHEAP_NOIDX) { + evb->pev[u] = e; + evb->pfd[u].fd = e->fd; + evb->pfd[u].events = + e->fd_flags & (EV_RD|EV_WR|EV_ERR|EV_HUP); + } } static int __match_proto__(binheap_cmp_t) @@ -123,7 +128,6 @@ static int vev_get_pfd(struct vev_base *evb) { unsigned u; - void *p; if (evb->lpfd + 1 < evb->npfd) return (0); @@ -134,11 +138,11 @@ vev_get_pfd(struct vev_base *evb) u = evb->npfd + 256; else u = evb->npfd * 2; - p = realloc(evb->pfd, sizeof *evb->pfd * u); - if (p == NULL) - return (1); evb->npfd = u; - evb->pfd = p; + evb->pfd = realloc(evb->pfd, sizeof(*evb->pfd) * u); + AN(evb->pfd); + evb->pev = realloc(evb->pev, sizeof(*evb->pev) * u); + AN(evb->pev); return (0); } @@ -190,12 +194,12 @@ vev_new_base(void) evb = calloc(sizeof *evb, 1); if (evb == NULL) return (evb); + evb->lpfd = BINHEAP_NOIDX + 1; if (vev_get_pfd(evb)) { free(evb); return (NULL); } evb->magic = VEV_BASE_MAGIC; - VTAILQ_INIT(&evb->events); evb->binheap = binheap_new(evb, vev_bh_cmp, vev_bh_update); evb->thread = pthread_self(); #ifdef DEBUG_EVENTS @@ -248,13 +252,14 @@ vev_add(struct vev_base *evb, struct vev *e) assert(evb->thread == pthread_self()); DBG(evb, "ev_add(%p) fd = %d\n", e, e->fd); - if (e->sig > 0 && vev_get_sig(e->sig)) - return (ENOMEM); - - if (e->fd >= 0 && vev_get_pfd(evb)) + if (vev_get_pfd(evb)) return (ENOMEM); if (e->sig > 0) { + if (vev_get_sig(e->sig)) + return (ENOMEM); + + assert(e->fd < 0); es = &vev_sigs[e->sig]; if (es->vev != NULL) return (EBUSY); @@ -267,36 +272,19 @@ vev_add(struct vev_base *evb, struct vev *e) es = NULL; } - if (e->fd >= 0) { - assert(evb->lpfd < evb->npfd); - evb->pfd[evb->lpfd].fd = e->fd; - evb->pfd[evb->lpfd].events = - e->fd_flags & (EV_RD|EV_WR|EV_ERR|EV_HUP); - e->__poll_idx = evb->lpfd; - evb->lpfd++; - DBG(evb, "... pidx = %d lpfd = %d\n", - e->__poll_idx, evb->lpfd); - } else - e->__poll_idx = -1; - e->magic = VEV_MAGIC; /* before binheap_insert() */ - if (e->timeout != 0.0) { + if (e->timeout != 0.0) e->__when += VTIM_mono() + e->timeout; - binheap_insert(evb->binheap, e); - assert(e->__binheap_idx > 0); - DBG(evb, "... bidx = %d\n", e->__binheap_idx); - } else { - e->__when = 0.0; - e->__binheap_idx = 0; - } + else + e->__when = 9e99; + + evb->lpfd++; + binheap_insert(evb->binheap, e); + assert(e->__binheap_idx != BINHEAP_NOIDX); e->__vevb = evb; e->__privflags = 0; - if (e->fd < 0) - VTAILQ_INSERT_TAIL(&evb->events, e, __list); - else - VTAILQ_INSERT_HEAD(&evb->events, e, __list); if (e->sig > 0) { assert(es != NULL); @@ -315,24 +303,16 @@ vev_del(struct vev_base *evb, struct vev *e) CHECK_OBJ_NOTNULL(evb, VEV_BASE_MAGIC); CHECK_OBJ_NOTNULL(e, VEV_MAGIC); - DBG(evb, "ev_del(%p) fd = %d\n", e, e->fd); + DBG(evb, "ev_del(%p) fd = %d i=%u L=%d\n", e, e->fd, e->__binheap_idx, evb->lpfd); assert(evb == e->__vevb); assert(evb->thread == pthread_self()); + assert(evb->pev[e->__binheap_idx] == e); - if (e->__binheap_idx != 0) - binheap_delete(evb->binheap, e->__binheap_idx); - AZ(e->__binheap_idx); - - if (e->fd >= 0) { - DBG(evb, "... pidx = %d\n", e->__poll_idx); - evb->pfd[e->__poll_idx].fd = -1; - if (e->__poll_idx == evb->lpfd - 1) - evb->lpfd--; - else - evb->compact_pfd++; - e->fd = -1; - DBG(evb, "... lpfd = %d\n", evb->lpfd); - } + assert(e->__binheap_idx != BINHEAP_NOIDX); + e->fd = -1; + binheap_delete(evb->binheap, e->__binheap_idx); + assert(e->__binheap_idx == BINHEAP_NOIDX); + evb->lpfd--; if (e->sig > 0) { assert(e->sig < vev_nsig); @@ -346,12 +326,8 @@ vev_del(struct vev_base *evb, struct vev *e) es->happened = 0; } - VTAILQ_REMOVE(&evb->events, e, __list); - e->magic = 0; e->__vevb = NULL; - - evb->disturbed = 1; } /*--------------------------------------------------------------------*/ @@ -371,38 +347,6 @@ vev_schedule(struct vev_base *evb) /*--------------------------------------------------------------------*/ -static void -vev_compact_pfd(struct vev_base *evb) -{ - unsigned u; - struct pollfd *p; - struct vev *ep; - int lfd; - - DBG(evb, "compact_pfd() lpfd = %d\n", evb->lpfd); - p = evb->pfd; - for (u = 0; u < evb->lpfd; u++, p++) { - DBG(evb, "...[%d] fd = %d\n", u, p->fd); - if (p->fd >= 0) - continue; - if (u == evb->lpfd - 1) - break; - lfd = evb->pfd[evb->lpfd - 1].fd; - VTAILQ_FOREACH(ep, &evb->events, __list) - if (ep->fd == lfd) - break; - AN(ep); - DBG(evb, "...[%d] move %p pidx %d\n", u, ep, ep->__poll_idx); - *p = evb->pfd[--evb->lpfd]; - ep->__poll_idx = u; - } - evb->lpfd = u; - evb->compact_pfd = 0; - DBG(evb, "... lpfd = %d\n", evb->lpfd); -} - -/*--------------------------------------------------------------------*/ - static int vev_sched_timeout(struct vev_base *evb, struct vev *e, double t) { @@ -449,16 +393,20 @@ int vev_schedule_one(struct vev_base *evb) { double t; - struct vev *e, *e2, *e3; - int i, j, tmo; - struct pollfd *pfd; + struct vev *e; + int i, j, k, tmo; CHECK_OBJ_NOTNULL(evb, VEV_BASE_MAGIC); assert(evb->thread == pthread_self()); + assert(evb->lpfd < evb->npfd); + + if (evb->psig) + return (vev_sched_signal(evb)); + e = binheap_root(evb->binheap); if (e != NULL) { CHECK_OBJ_NOTNULL(e, VEV_MAGIC); - assert(e->__binheap_idx == 1); + assert(e->__binheap_idx == BINHEAP_NOIDX + 1); t = VTIM_mono(); if (e->__when <= t) return (vev_sched_timeout(evb, e, t)); @@ -468,54 +416,43 @@ vev_schedule_one(struct vev_base *evb) } else tmo = INFTIM; - if (evb->compact_pfd) - vev_compact_pfd(evb); - - if (tmo == INFTIM && evb->lpfd == 0) + if (tmo == INFTIM && evb->lpfd == BINHEAP_NOIDX + 1) return (0); - if (evb->psig) - return (vev_sched_signal(evb)); - assert(evb->lpfd < evb->npfd); - i = poll(evb->pfd, evb->lpfd, tmo); + i = poll(evb->pfd + 1, evb->lpfd - 1, tmo); if (i == -1 && errno == EINTR) return (vev_sched_signal(evb)); + if (i == 0) { assert(e != NULL); t = VTIM_mono(); if (e->__when <= t) return (vev_sched_timeout(evb, e, t)); } - evb->disturbed = 0; - VTAILQ_FOREACH_SAFE(e, &evb->events, __list, e2) { - if (i == 0) - break; - if (e->fd < 0) - continue; - assert(e->__poll_idx < evb->lpfd); - pfd = &evb->pfd[e->__poll_idx]; - assert(pfd->fd == e->fd); - if (!pfd->revents) - continue; - DBG(evb, "callback(%p) fd = %d what = 0x%x pidx = %d\n", - e, e->fd, pfd->revents, e->__poll_idx); - j = e->callback(e, pfd->revents); - i--; - if (evb->disturbed) { - VTAILQ_FOREACH(e3, &evb->events, __list) { - if (e3 == e) { - e3 = VTAILQ_NEXT(e, __list); - break; - } else if (e3 == e2) - break; + + k = 0; + for(j = 1; j < evb->lpfd; j++) { + evb->pev[j]->fd_events = evb->pfd[j].revents; + if (evb->pev[j]->fd_events) + k++; + } + assert(k == i); + + DBG(evb, "EVENTS %d\n", i); + while (i > 0) { + for(j = BINHEAP_NOIDX + 1; j < evb->lpfd; j++) { + e = evb->pev[j]; + if (e->fd_events == 0) + continue; + DBG(evb, "EVENT %p j=%d fd=%d ev=0x%x %d\n", + e, j, e->fd, e->fd_events, i); + k = e->callback(e, e->fd_events); + e->fd_events = 0; + i--; + if (k) { + vev_del(evb, e); + free(e); } - e2 = e3; - evb->disturbed = 0; - } - if (j) { - vev_del(evb, e); - evb->disturbed = 0; - free(e); } } AZ(i); From nils.goroll at uplex.de Fri Mar 31 15:14:06 2017 From: nils.goroll at uplex.de (Nils Goroll) Date: Fri, 31 Mar 2017 17:14:06 +0200 Subject: [master] b758894 try to stabilize this test for make -j80 check Message-ID: commit b758894297ec967f33fe9fd6af90fcd9ff342313 Author: Nils Goroll Date: Fri Mar 31 17:11:23 2017 +0200 try to stabilize this test for make -j80 check diff --git a/bin/varnishtest/tests/r01490.vtc b/bin/varnishtest/tests/r01490.vtc index 76b32be..88c2550 100644 --- a/bin/varnishtest/tests/r01490.vtc +++ b/bin/varnishtest/tests/r01490.vtc @@ -13,6 +13,8 @@ varnish v1 \ -vcl+backend {} varnish v1 -start +delay 2 + varnish v1 -expect threads == 2 logexpect l1 -v v1 -g raw {