[master] ad6f672c1 filter: Pass a VRT_CTX to the init methods

Dridi Boukelmoune dridi.boukelmoune at gmail.com
Mon Jan 10 14:58:07 UTC 2022


commit ad6f672c17b3f36a02299c98cd29d9e9c5f6fff8
Author: Dridi Boukelmoune <dridi.boukelmoune at gmail.com>
Date:   Mon Jan 10 08:11:03 2022 +0100

    filter: Pass a VRT_CTX to the init methods
    
    This allows VDPs and VFPs to pass state from a PRIV_TASK to respectively
    a vdp_entry or a vfp_entry. When a filter is set up by a VMOD, there is
    otherwise no way to configure a filter on a per-task basis.

diff --git a/bin/varnishd/cache/cache_deliver_proc.c b/bin/varnishd/cache/cache_deliver_proc.c
index d4a074bdc..2749b798e 100644
--- a/bin/varnishd/cache/cache_deliver_proc.c
+++ b/bin/varnishd/cache/cache_deliver_proc.c
@@ -136,10 +136,12 @@ VDP_bytes(struct vdp_ctx *vdc, enum vdp_action act,
 }
 
 int
-VDP_Push(struct vdp_ctx *vdc, struct ws *ws, const struct vdp *vdp, void *priv)
+VDP_Push(VRT_CTX, struct vdp_ctx *vdc, struct ws *ws, const struct vdp *vdp,
+    void *priv)
 {
 	struct vdp_entry *vdpe;
 
+	CHECK_OBJ_NOTNULL(ctx, VRT_CTX_MAGIC);
 	CHECK_OBJ_NOTNULL(vdc, VDP_CTX_MAGIC);
 	AN(ws);
 	AN(vdp);
@@ -168,11 +170,9 @@ VDP_Push(struct vdp_ctx *vdc, struct ws *ws, const struct vdp *vdp, void *priv)
 	if (vdpe->vdp->init == NULL)
 		return (vdc->retval);
 
-	vdc->retval = vdpe->vdp->init(
-	    vdc,
-	    &vdpe->priv,
-	    vdpe == vdc->nxt ? vdc->req->objcore : NULL
-	);
+	vdc->retval = vdpe->vdp->init(ctx, vdc, &vdpe->priv,
+	    vdpe == vdc->nxt ? vdc->req->objcore : NULL);
+
 	if (vdc->retval > 0) {
 		VTAILQ_REMOVE(&vdc->vdp, vdpe, list);
 		vdc->nxt = VTAILQ_FIRST(&vdc->vdp);
diff --git a/bin/varnishd/cache/cache_esi_deliver.c b/bin/varnishd/cache/cache_esi_deliver.c
index c3c78fb91..d539807f7 100644
--- a/bin/varnishd/cache/cache_esi_deliver.c
+++ b/bin/varnishd/cache/cache_esi_deliver.c
@@ -255,11 +255,12 @@ ved_decode_len(struct vsl_log *vsl, const uint8_t **pp)
  */
 
 static int v_matchproto_(vdp_init_f)
-ved_vdp_esi_init(struct vdp_ctx *vdc, void **priv, struct objcore *oc)
+ved_vdp_esi_init(VRT_CTX, struct vdp_ctx *vdc, void **priv, struct objcore *oc)
 {
 	struct ecx *ecx;
 	struct req *req;
 
+	CHECK_OBJ_NOTNULL(ctx, VRT_CTX_MAGIC);
 	CHECK_OBJ_NOTNULL(vdc, VDP_CTX_MAGIC);
 	CHECK_OBJ_ORNULL(oc, OBJCORE_MAGIC);
 	if (oc == NULL || !ObjHasAttr(vdc->wrk, oc, OA_ESIDATA))
@@ -589,13 +590,14 @@ struct ved_foo {
 };
 
 static int v_matchproto_(vdp_fini_f)
-ved_gzgz_init(struct vdp_ctx *vdc, void **priv, struct objcore *oc)
+ved_gzgz_init(VRT_CTX, struct vdp_ctx *vdc, void **priv, struct objcore *oc)
 {
 	ssize_t l;
 	const char *p;
 	struct ved_foo *foo;
 	struct req *req;
 
+	CHECK_OBJ_NOTNULL(ctx, VRT_CTX_MAGIC);
 	CHECK_OBJ_NOTNULL(vdc, VDP_CTX_MAGIC);
 	(void)oc;
 	req = vdc->req;
@@ -844,6 +846,7 @@ ved_deliver(struct req *req, struct boc *boc, int wantbody)
 	const char *p;
 	struct ecx *ecx;
 	struct ved_foo foo[1];
+	struct vrt_ctx ctx[1];
 
 	CHECK_OBJ_NOTNULL(req, REQ_MAGIC);
 	CHECK_OBJ_ORNULL(boc, BOC_MAGIC);
@@ -862,6 +865,9 @@ ved_deliver(struct req *req, struct boc *boc, int wantbody)
 	if (i)
 		i = ObjCheckFlag(req->wrk, req->objcore, OF_GZIPED);
 
+	INIT_OBJ(ctx, VRT_CTX_MAGIC);
+	VCL_Req2Ctx(ctx, req);
+
 	if (ecx->isgzip && i && !(req->res_mode & RES_ESI)) {
 		/* A gzip'ed include which is not ESI processed */
 
@@ -878,14 +884,14 @@ ved_deliver(struct req *req, struct boc *boc, int wantbody)
 		INIT_OBJ(foo, VED_FOO_MAGIC);
 		foo->ecx = ecx;
 		foo->objcore = req->objcore;
-		i = VDP_Push(req->vdc, req->ws, &ved_gzgz, foo);
+		i = VDP_Push(ctx, req->vdc, req->ws, &ved_gzgz, foo);
 
 	} else if (ecx->isgzip && !i) {
 		/* Non-Gzip'ed include in gzip'ed parent */
-		i = VDP_Push(req->vdc, req->ws, &ved_pretend_gz, ecx);
+		i = VDP_Push(ctx, req->vdc, req->ws, &ved_pretend_gz, ecx);
 	} else {
 		/* Anything else goes straight through */
-		i = VDP_Push(req->vdc, req->ws, &ved_ved, ecx);
+		i = VDP_Push(ctx, req->vdc, req->ws, &ved_ved, ecx);
 	}
 
 	if (i == 0) {
diff --git a/bin/varnishd/cache/cache_esi_fetch.c b/bin/varnishd/cache/cache_esi_fetch.c
index 0b2d46339..c52b7ff84 100644
--- a/bin/varnishd/cache/cache_esi_fetch.c
+++ b/bin/varnishd/cache/cache_esi_fetch.c
@@ -157,10 +157,11 @@ vfp_esi_end(struct vfp_ctx *vc, struct vef_priv *vef,
 }
 
 static enum vfp_status v_matchproto_(vfp_init_f)
-vfp_esi_gzip_init(struct vfp_ctx *vc, struct vfp_entry *vfe)
+vfp_esi_gzip_init(VRT_CTX, struct vfp_ctx *vc, struct vfp_entry *vfe)
 {
 	struct vef_priv *vef;
 
+	CHECK_OBJ_NOTNULL(ctx, VRT_CTX_MAGIC);
 	CHECK_OBJ_NOTNULL(vc, VFP_CTX_MAGIC);
 	CHECK_OBJ_NOTNULL(vc->req, HTTP_MAGIC);
 	CHECK_OBJ_NOTNULL(vfe, VFP_ENTRY_MAGIC);
@@ -243,11 +244,12 @@ vfp_esi_gzip_pull(struct vfp_ctx *vc, struct vfp_entry *vfe, void *p,
 }
 
 static enum vfp_status v_matchproto_(vfp_init_f)
-vfp_esi_init(struct vfp_ctx *vc, struct vfp_entry *vfe)
+vfp_esi_init(VRT_CTX, struct vfp_ctx *vc, struct vfp_entry *vfe)
 {
 	struct vef_priv *vef;
 	struct vep_state *vep;
 
+	CHECK_OBJ_NOTNULL(ctx, VRT_CTX_MAGIC);
 	CHECK_OBJ_NOTNULL(vc, VFP_CTX_MAGIC);
 	CHECK_OBJ_NOTNULL(vc->req, HTTP_MAGIC);
 	if (http_GetStatus(vc->resp) == 206) {
diff --git a/bin/varnishd/cache/cache_fetch.c b/bin/varnishd/cache/cache_fetch.c
index e28c432f0..fde7e29a9 100644
--- a/bin/varnishd/cache/cache_fetch.c
+++ b/bin/varnishd/cache/cache_fetch.c
@@ -630,6 +630,7 @@ vbf_stp_fetchbody(struct worker *wrk, struct busyobj *bo)
 static const struct fetch_step * v_matchproto_(vbf_state_f)
 vbf_stp_fetch(struct worker *wrk, struct busyobj *bo)
 {
+	struct vrt_ctx ctx[1];
 	struct objcore *oc;
 
 	CHECK_OBJ_NOTNULL(wrk, WORKER_MAGIC);
@@ -667,7 +668,10 @@ vbf_stp_fetch(struct worker *wrk, struct busyobj *bo)
 
 	oc->boc->len_so_far = 0;
 
-	if (VFP_Open(bo->vfc)) {
+	INIT_OBJ(ctx, VRT_CTX_MAGIC);
+	VCL_Bo2Ctx(ctx, bo);
+
+	if (VFP_Open(ctx, bo->vfc)) {
 		(void)VFP_Error(bo->vfc, "Fetch pipeline failed to open");
 		bo->htc->doclose = SC_RX_BODY;
 		vbf_cleanup(bo);
diff --git a/bin/varnishd/cache/cache_fetch_proc.c b/bin/varnishd/cache/cache_fetch_proc.c
index 079279c30..ed7fbea59 100644
--- a/bin/varnishd/cache/cache_fetch_proc.c
+++ b/bin/varnishd/cache/cache_fetch_proc.c
@@ -136,10 +136,11 @@ VFP_Close(struct vfp_ctx *vc)
 }
 
 int
-VFP_Open(struct vfp_ctx *vc)
+VFP_Open(VRT_CTX, struct vfp_ctx *vc)
 {
 	struct vfp_entry *vfe;
 
+	CHECK_OBJ_NOTNULL(ctx, VRT_CTX_MAGIC);
 	CHECK_OBJ_NOTNULL(vc, VFP_CTX_MAGIC);
 	CHECK_OBJ_NOTNULL(vc->resp, HTTP_MAGIC);
 	CHECK_OBJ_NOTNULL(vc->wrk, WORKER_MAGIC);
@@ -151,7 +152,7 @@ VFP_Open(struct vfp_ctx *vc)
 		if (DO_DEBUG(DBG_PROCESSORS))
 			VSLb(vc->wrk->vsl, SLT_Debug, "VFP_Open(%s)",
 			     vfe->vfp->name);
-		vfe->closed = vfe->vfp->init(vc, vfe);
+		vfe->closed = vfe->vfp->init(ctx, vc, vfe);
 		if (vfe->closed != VFP_OK && vfe->closed != VFP_NULL) {
 			(void)VFP_Error(vc, "Fetch filter %s failed to open",
 			    vfe->vfp->name);
diff --git a/bin/varnishd/cache/cache_filter.h b/bin/varnishd/cache/cache_filter.h
index 5d910e9c6..ceee01310 100644
--- a/bin/varnishd/cache/cache_filter.h
+++ b/bin/varnishd/cache/cache_filter.h
@@ -43,7 +43,8 @@ enum vfp_status {
 	VFP_NULL = 2,
 };
 
-typedef enum vfp_status vfp_init_f(struct vfp_ctx *, struct vfp_entry *);
+typedef enum vfp_status vfp_init_f(VRT_CTX, struct vfp_ctx *,
+    struct vfp_entry *);
 typedef enum vfp_status
     vfp_pull_f(struct vfp_ctx *, struct vfp_entry *, void *ptr, ssize_t *len);
 typedef void vfp_fini_f(struct vfp_ctx *, struct vfp_entry *);
@@ -104,7 +105,8 @@ enum vdp_action {
 	VDP_END,		/* Last buffer or after, implies VDP_FLUSH */
 };
 
-typedef int vdp_init_f(struct vdp_ctx *, void **priv, struct objcore *);
+typedef int vdp_init_f(VRT_CTX, struct vdp_ctx *, void **priv,
+    struct objcore *);
 /*
  * Return value:
  *	negative:	Error - abandon delivery
diff --git a/bin/varnishd/cache/cache_gzip.c b/bin/varnishd/cache/cache_gzip.c
index e4d23de51..b73ca938e 100644
--- a/bin/varnishd/cache/cache_gzip.c
+++ b/bin/varnishd/cache/cache_gzip.c
@@ -288,7 +288,7 @@ VGZ_Gzip(struct vgz *vg, const void **pptr, ssize_t *plen, enum vgz_flag flags)
  */
 
 static int v_matchproto_(vdp_init_f)
-vdp_gunzip_init(struct vdp_ctx *vdp, void **priv, struct objcore *oc)
+vdp_gunzip_init(VRT_CTX, struct vdp_ctx *vdp, void **priv, struct objcore *oc)
 {
 	struct vgz *vg;
 	struct boc *boc;
@@ -298,6 +298,7 @@ vdp_gunzip_init(struct vdp_ctx *vdp, void **priv, struct objcore *oc)
 	ssize_t dl;
 	uint64_t u;
 
+	CHECK_OBJ_NOTNULL(ctx, VRT_CTX_MAGIC);
 	CHECK_OBJ_NOTNULL(vdp, VDP_CTX_MAGIC);
 	CHECK_OBJ_ORNULL(oc, OBJCORE_MAGIC);
 	req = vdp->req;
@@ -471,10 +472,11 @@ VGZ_Destroy(struct vgz **vgp)
 /*--------------------------------------------------------------------*/
 
 static enum vfp_status v_matchproto_(vfp_init_f)
-vfp_gzip_init(struct vfp_ctx *vc, struct vfp_entry *vfe)
+vfp_gzip_init(VRT_CTX, struct vfp_ctx *vc, struct vfp_entry *vfe)
 {
 	struct vgz *vg;
 
+	CHECK_OBJ_NOTNULL(ctx, VRT_CTX_MAGIC);
 	CHECK_OBJ_NOTNULL(vc, VFP_CTX_MAGIC);
 	CHECK_OBJ_NOTNULL(vfe, VFP_ENTRY_MAGIC);
 
diff --git a/bin/varnishd/cache/cache_range.c b/bin/varnishd/cache/cache_range.c
index e4ccbc7c6..b9aab9aed 100644
--- a/bin/varnishd/cache/cache_range.c
+++ b/bin/varnishd/cache/cache_range.c
@@ -217,11 +217,12 @@ vrg_ifrange(struct req *req)
 }
 
 static int v_matchproto_(vdp_init_f)
-vrg_range_init(struct vdp_ctx *vdc, void **priv, struct objcore *oc)
+vrg_range_init(VRT_CTX, struct vdp_ctx *vdc, void **priv, struct objcore *oc)
 {
 	const char *err;
 	struct req *req;
 
+	CHECK_OBJ_NOTNULL(ctx, VRT_CTX_MAGIC);
 	CHECK_OBJ_NOTNULL(vdc, VDP_CTX_MAGIC);
 	(void)oc;
 	req = vdc->req;
diff --git a/bin/varnishd/cache/cache_req_body.c b/bin/varnishd/cache/cache_req_body.c
index e5bd6beeb..6391f928d 100644
--- a/bin/varnishd/cache/cache_req_body.c
+++ b/bin/varnishd/cache/cache_req_body.c
@@ -54,6 +54,7 @@ static ssize_t
 vrb_pull(struct req *req, ssize_t maxsize, objiterate_f *func, void *priv)
 {
 	ssize_t l, r = 0, yet;
+	struct vrt_ctx ctx[1];
 	struct vfp_ctx *vfc;
 	uint8_t *ptr;
 	enum vfp_status vfps = VFP_ERROR;
@@ -87,7 +88,10 @@ vrb_pull(struct req *req, ssize_t maxsize, objiterate_f *func, void *priv)
 
 	vfc->oc = req->body_oc;
 
-	if (VFP_Open(vfc) < 0) {
+	INIT_OBJ(ctx, VRT_CTX_MAGIC);
+	VCL_Req2Ctx(ctx, req);
+
+	if (VFP_Open(ctx, vfc) < 0) {
 		req->req_body_status = BS_ERROR;
 		HSH_DerefBoc(req->wrk, req->body_oc);
 		AZ(HSH_DerefObjCore(req->wrk, &req->body_oc, 0));
diff --git a/bin/varnishd/cache/cache_varnishd.h b/bin/varnishd/cache/cache_varnishd.h
index 1827ae008..b3a4b5ad4 100644
--- a/bin/varnishd/cache/cache_varnishd.h
+++ b/bin/varnishd/cache/cache_varnishd.h
@@ -193,7 +193,8 @@ void VDP_Init(struct vdp_ctx *vdx, struct worker *wrk, struct vsl_log *vsl,
     struct req *req);
 uint64_t VDP_Close(struct vdp_ctx *);
 void VDP_Panic(struct vsb *vsb, const struct vdp_ctx *vdc);
-int VDP_Push(struct vdp_ctx *, struct ws *, const struct vdp *, void *priv);
+int VDP_Push(VRT_CTX, struct vdp_ctx *, struct ws *, const struct vdp *,
+    void *priv);
 int VDP_DeliverObj(struct vdp_ctx *vdc, struct objcore *oc);
 extern const struct vdp VDP_gunzip;
 extern const struct vdp VDP_esi;
@@ -281,7 +282,7 @@ struct vfp_entry *VFP_Push(struct vfp_ctx *, const struct vfp *);
 enum vfp_status VFP_GetStorage(struct vfp_ctx *, ssize_t *sz, uint8_t **ptr);
 void VFP_Extend(const struct vfp_ctx *, ssize_t sz, enum vfp_status);
 void VFP_Setup(struct vfp_ctx *vc, struct worker *wrk);
-int VFP_Open(struct vfp_ctx *);
+int VFP_Open(VRT_CTX, struct vfp_ctx *);
 uint64_t VFP_Close(struct vfp_ctx *);
 
 extern const struct vfp VFP_gunzip;
diff --git a/bin/varnishd/cache/cache_vrt_filter.c b/bin/varnishd/cache/cache_vrt_filter.c
index b8e3b7c9a..ac6e9a9b9 100644
--- a/bin/varnishd/cache/cache_vrt_filter.c
+++ b/bin/varnishd/cache/cache_vrt_filter.c
@@ -257,9 +257,13 @@ int
 VCL_StackVDP(struct req *req, const struct vcl *vcl, const char *fl)
 {
 	const struct vfilter *vp;
+	struct vrt_ctx ctx[1];
 
 	AN(fl);
 	VSLb(req->vsl, SLT_Filters, "%s", fl);
+	INIT_OBJ(ctx, VRT_CTX_MAGIC);
+	VCL_Req2Ctx(ctx, req);
+
 	while (1) {
 		vp = vcl_filter_list_iter(0, &vrt_filters, &vcl->filters, &fl);
 		if (vp == NULL)
@@ -269,7 +273,7 @@ VCL_StackVDP(struct req *req, const struct vcl *vcl, const char *fl)
 			    "Filter '...%s' not found", fl);
 			return (-1);
 		}
-		if (VDP_Push(req->vdc, req->ws, vp->vdp, NULL))
+		if (VDP_Push(ctx, req->vdc, req->ws, vp->vdp, NULL))
 			return (-1);
 	}
 }
diff --git a/bin/varnishd/http1/cache_http1_deliver.c b/bin/varnishd/http1/cache_http1_deliver.c
index e90d1d48e..2db4f8efa 100644
--- a/bin/varnishd/http1/cache_http1_deliver.c
+++ b/bin/varnishd/http1/cache_http1_deliver.c
@@ -88,6 +88,7 @@ v1d_error(struct req *req, const char *msg)
 void v_matchproto_(vtr_deliver_f)
 V1D_Deliver(struct req *req, struct boc *boc, int sendbody)
 {
+	struct vrt_ctx ctx[1];
 	int err = 0, chunked = 0;
 	stream_close_t sc;
 	uint64_t hdrbytes, bytes;
@@ -117,7 +118,9 @@ V1D_Deliver(struct req *req, struct boc *boc, int sendbody)
 				req->doclose = SC_TX_EOF;
 			}
 		}
-		if (VDP_Push(req->vdc, req->ws, &v1d_vdp, NULL)) {
+		INIT_OBJ(ctx, VRT_CTX_MAGIC);
+		VCL_Req2Ctx(ctx, req);
+		if (VDP_Push(ctx, req->vdc, req->ws, &v1d_vdp, NULL)) {
 			v1d_error(req, "workspace_thread overflow");
 			AZ(req->wrk->v1l);
 			return;
diff --git a/bin/varnishd/http2/cache_http2_deliver.c b/bin/varnishd/http2/cache_http2_deliver.c
index 8b0514228..f5e08b7da 100644
--- a/bin/varnishd/http2/cache_http2_deliver.c
+++ b/bin/varnishd/http2/cache_http2_deliver.c
@@ -73,9 +73,10 @@ V2D_Init(void)
 /**********************************************************************/
 
 static int v_matchproto_(vdp_init_f)
-h2_init(struct vdp_ctx *vdc, void **priv, struct objcore *oc)
+h2_init(VRT_CTX, struct vdp_ctx *vdc, void **priv, struct objcore *oc)
 {
 
+	CHECK_OBJ_NOTNULL(ctx, VRT_CTX_MAGIC);
 	CHECK_OBJ_NOTNULL(vdc, VDP_CTX_MAGIC);
 	(void)oc;
 	CHECK_OBJ_NOTNULL(vdc->req, REQ_MAGIC);
@@ -297,6 +298,7 @@ h2_deliver(struct req *req, struct boc *boc, int sendbody)
 	struct sess *sp;
 	struct h2_req *r2;
 	struct vsb resp[1];
+	struct vrt_ctx ctx[1];
 	uintptr_t ss;
 
 	CHECK_OBJ_NOTNULL(req, REQ_MAGIC);
@@ -341,7 +343,9 @@ h2_deliver(struct req *req, struct boc *boc, int sendbody)
 
 	/* XXX someone into H2 please add appropriate error handling */
 	if (sendbody) {
-		if (!VDP_Push(req->vdc, req->ws, &h2_vdp, NULL))
+		INIT_OBJ(ctx, VRT_CTX_MAGIC);
+		VCL_Req2Ctx(ctx, req);
+		if (!VDP_Push(ctx, req->vdc, req->ws, &h2_vdp, NULL))
 			(void)VDP_DeliverObj(req->vdc, req->objcore);
 	}
 
diff --git a/vmod/vmod_debug.c b/vmod/vmod_debug.c
index b1c272d7e..654b4f433 100644
--- a/vmod/vmod_debug.c
+++ b/vmod/vmod_debug.c
@@ -102,10 +102,12 @@ static const struct vfp xyzzy_vfp_rot13 = {
 #define ROT13_BUFSZ 8
 
 static int v_matchproto_(vdp_init_f)
-xyzzy_vfp_rot13_init(struct vdp_ctx *vdc, void **priv, struct objcore *oc)
+xyzzy_vfp_rot13_init(VRT_CTX, struct vdp_ctx *vdc, void **priv, struct objcore *oc)
 {
 	(void)vdc;
 	(void)oc;
+
+	CHECK_OBJ_NOTNULL(ctx, VRT_CTX_MAGIC);
 	AN(priv);
 	*priv = malloc(ROT13_BUFSZ);
 	if (*priv == NULL)


More information about the varnish-commit mailing list