[master] b335906 Make H2_F_* a self-describing object and ditch the enum.

Poul-Henning Kamp phk at FreeBSD.org
Mon Mar 6 16:07:06 CET 2017


commit b33590604e9982bc1a6c13ef9d955bf8ee3c0021
Author: Poul-Henning Kamp <phk at FreeBSD.org>
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;



More information about the varnish-commit mailing list