MINOR: connection: make the last arg of subscribe() a struct wait_event*

The subscriber used to be passed as a "void *param" that was systematically
cast to a struct wait_event*. By now it appears clear that the subscribe()
call at every layer is well defined and always takes a pointer to an event
subscriber of type wait_event, so let's enforce this in the functions'
prototypes, remove the intermediary variables used to cast it and clean up
the comments to clarify what all these functions do in their context.
This commit is contained in:
Willy Tarreau 2020-01-17 07:52:13 +01:00
parent 8907e4ddb8
commit ee1a6fc943
10 changed files with 132 additions and 97 deletions

View File

@ -51,8 +51,8 @@ int make_proxy_line(char *buf, int buf_len, struct server *srv, struct connectio
int make_proxy_line_v1(char *buf, int buf_len, struct sockaddr_storage *src, struct sockaddr_storage *dst);
int make_proxy_line_v2(char *buf, int buf_len, struct server *srv, struct connection *remote);
int conn_subscribe(struct connection *conn, void *xprt_ctx, int event_type, void *param);
int conn_unsubscribe(struct connection *conn, void *xprt_ctx, int event_type, void *param);
int conn_subscribe(struct connection *conn, void *xprt_ctx, int event_type, struct wait_event *es);
int conn_unsubscribe(struct connection *conn, void *xprt_ctx, int event_type, struct wait_event *es);
/* receive a NetScaler Client IP insertion header over a connection */
int conn_recv_netscaler_cip(struct connection *conn, int flag);

View File

@ -326,8 +326,8 @@ struct xprt_ops {
void (*destroy_srv)(struct server *srv); /* destroy a server context */
int (*get_alpn)(const struct connection *conn, void *xprt_ctx, const char **str, int *len); /* get application layer name */
char name[8]; /* transport layer name, zero-terminated */
int (*subscribe)(struct connection *conn, void *xprt_ctx, int event_type, void *param); /* Subscribe to events, such as "being able to send" */
int (*unsubscribe)(struct connection *conn, void *xprt_ctx, int event_type, void *param); /* Unsubscribe to events */
int (*subscribe)(struct connection *conn, void *xprt_ctx, int event_type, struct wait_event *es); /* Subscribe <es> to events, such as "being able to send" */
int (*unsubscribe)(struct connection *conn, void *xprt_ctx, int event_type, struct wait_event *es); /* Unsubscribe <es> from events */
int (*remove_xprt)(struct connection *conn, void *xprt_ctx, void *toremove_ctx, const struct xprt_ops *newops, void *newctx); /* Remove an xprt from the connection, used by temporary xprt such as the handshake one */
int (*add_xprt)(struct connection *conn, void *xprt_ctx, void *toadd_ctx, const struct xprt_ops *toadd_ops, void **oldxprt_ctx, const struct xprt_ops **oldxprt_ops); /* Add a new XPRT as the new xprt, and return the old one */
};
@ -359,8 +359,8 @@ struct mux_ops {
const struct conn_stream *(*get_first_cs)(const struct connection *); /* retrieves any valid conn_stream from this connection */
void (*detach)(struct conn_stream *); /* Detach a conn_stream from an outgoing connection, when the request is done */
void (*show_fd)(struct buffer *, struct connection *); /* append some data about connection into chunk for "show fd" */
int (*subscribe)(struct conn_stream *cs, int event_type, void *param); /* Subscribe to events, such as "being able to send" */
int (*unsubscribe)(struct conn_stream *cs, int event_type, void *param); /* Unsubscribe to events */
int (*subscribe)(struct conn_stream *cs, int event_type, struct wait_event *es); /* Subscribe <es> to events, such as "being able to send" */
int (*unsubscribe)(struct conn_stream *cs, int event_type, struct wait_event *es); /* Unsubscribe <es> from events */
int (*avail_streams)(struct connection *conn); /* Returns the number of streams still available for a connection */
int (*used_streams)(struct connection *conn); /* Returns the number of streams in use on a connection. */
void (*destroy)(void *ctx); /* Let the mux know one of its users left, so it may have to disappear */

View File

@ -322,15 +322,18 @@ int conn_sock_send(struct connection *conn, const void *buf, int len, int flags)
return ret;
}
int conn_unsubscribe(struct connection *conn, void *xprt_ctx, int event_type, void *param)
/* Called from the upper layer, to subscribe <es> to events <event_type>. The
* event subscriber <es> is not allowed to change from a previous call as long
* as at least one event is still subscribed. The <event_type> must only be a
* combination of SUB_RETRY_RECV and SUB_RETRY_SEND. It always returns 0.
*/
int conn_unsubscribe(struct connection *conn, void *xprt_ctx, int event_type, struct wait_event *es)
{
struct wait_event *sw = param;
BUG_ON(event_type & ~(SUB_RETRY_SEND|SUB_RETRY_RECV));
BUG_ON(conn->subs && conn->subs != sw);
BUG_ON(conn->subs && conn->subs != es);
sw->events &= ~event_type;
if (!sw->events)
es->events &= ~event_type;
if (!es->events)
conn->subs = NULL;
if (event_type & SUB_RETRY_RECV)
@ -343,16 +346,18 @@ int conn_unsubscribe(struct connection *conn, void *xprt_ctx, int event_type, vo
return 0;
}
int conn_subscribe(struct connection *conn, void *xprt_ctx, int event_type, void *param)
/* Called from the upper layer, to unsubscribe <es> from events <event_type>
* (undo fcgi_subscribe). The <es> struct is not allowed to differ from the one
* passed to the subscribe() call. It always returns zero.
*/
int conn_subscribe(struct connection *conn, void *xprt_ctx, int event_type, struct wait_event *es)
{
struct wait_event *sw = param;
BUG_ON(event_type & ~(SUB_RETRY_SEND|SUB_RETRY_RECV));
BUG_ON(conn->subs && conn->subs->events & event_type);
BUG_ON(conn->subs && conn->subs != sw);
BUG_ON(conn->subs && conn->subs != es);
conn->subs = sw;
sw->events |= event_type;
conn->subs = es;
es->events |= event_type;
if (event_type & SUB_RETRY_RECV)
__conn_xprt_want_recv(conn);

View File

@ -3695,24 +3695,22 @@ static void fcgi_shutw(struct conn_stream *cs, enum cs_shw_mode mode)
fcgi_do_shutw(fstrm);
}
/* Called from the upper layer, to subscribe to events, such as being able to send.
* The <param> argument here is supposed to be a pointer to a wait_event struct
* which will be passed to fstrm->subs. The event_type must only be a
* combination of SUB_RETRY_RECV and SUB_RETRY_SEND, other values will lead to -1
* being returned. It always returns 0 except for the error above.
/* Called from the upper layer, to subscribe <es> to events <event_type>. The
* event subscriber <es> is not allowed to change from a previous call as long
* as at least one event is still subscribed. The <event_type> must only be a
* combination of SUB_RETRY_RECV and SUB_RETRY_SEND. It always returns 0.
*/
static int fcgi_subscribe(struct conn_stream *cs, int event_type, void *param)
static int fcgi_subscribe(struct conn_stream *cs, int event_type, struct wait_event *es)
{
struct wait_event *sw = param;
struct fcgi_strm *fstrm = cs->ctx;
struct fcgi_conn *fconn = fstrm->fconn;
BUG_ON(event_type & ~(SUB_RETRY_SEND|SUB_RETRY_RECV));
BUG_ON(fstrm->subs && fstrm->subs->events & event_type);
BUG_ON(fstrm->subs && fstrm->subs != sw);
BUG_ON(fstrm->subs && fstrm->subs != es);
sw->events |= event_type;
fstrm->subs = sw;
es->events |= event_type;
fstrm->subs = es;
if (event_type & SUB_RETRY_RECV)
TRACE_DEVEL("unsubscribe(recv)", FCGI_EV_STRM_RECV, fconn->conn, fstrm);
@ -3725,22 +3723,20 @@ static int fcgi_subscribe(struct conn_stream *cs, int event_type, void *param)
return 0;
}
/* Called from the upper layer, to unsubscribe some events (undo fcgi_subscribe).
* The <param> argument here is supposed to be a pointer to the same wait_event
* struct that was passed to fcgi_subscribe() otherwise nothing will be changed.
* It always returns zero.
/* Called from the upper layer, to unsubscribe <es> from events <event_type>
* (undo fcgi_subscribe). The <es> pointer is not allowed to differ from the one
* passed to the subscribe() call. It always returns zero.
*/
static int fcgi_unsubscribe(struct conn_stream *cs, int event_type, void *param)
static int fcgi_unsubscribe(struct conn_stream *cs, int event_type, struct wait_event *es)
{
struct wait_event *sw = param;
struct fcgi_strm *fstrm = cs->ctx;
struct fcgi_conn *fconn = fstrm->fconn;
BUG_ON(event_type & ~(SUB_RETRY_SEND|SUB_RETRY_RECV));
BUG_ON(fstrm->subs && fstrm->subs != sw);
BUG_ON(fstrm->subs && fstrm->subs != es);
sw->events &= ~event_type;
if (!sw->events)
es->events &= ~event_type;
if (!es->events)
fstrm->subs = NULL;
if (event_type & SUB_RETRY_RECV)

View File

@ -2542,20 +2542,22 @@ static void h1_shutw_conn(struct connection *conn, enum cs_shw_mode mode)
TRACE_LEAVE(H1_EV_STRM_SHUT, conn, h1c->h1s);
}
/* Called from the upper layer, to unsubscribe to events */
static int h1_unsubscribe(struct conn_stream *cs, int event_type, void *param)
/* Called from the upper layer, to unsubscribe <es> from events <event_type>
* The <es> pointer is not allowed to differ from the one passed to the
* subscribe() call. It always returns zero.
*/
static int h1_unsubscribe(struct conn_stream *cs, int event_type, struct wait_event *es)
{
struct wait_event *sw = param;
struct h1s *h1s = cs->ctx;
if (!h1s)
return 0;
BUG_ON(event_type & ~(SUB_RETRY_SEND|SUB_RETRY_RECV));
BUG_ON(h1s->subs && h1s->subs != sw);
BUG_ON(h1s->subs && h1s->subs != es);
sw->events &= ~event_type;
if (!sw->events)
es->events &= ~event_type;
if (!es->events)
h1s->subs = NULL;
if (event_type & SUB_RETRY_RECV)
@ -2567,10 +2569,14 @@ static int h1_unsubscribe(struct conn_stream *cs, int event_type, void *param)
return 0;
}
/* Called from the upper layer, to subscribe to events, such as being able to send */
static int h1_subscribe(struct conn_stream *cs, int event_type, void *param)
/* Called from the upper layer, to subscribe <es> to events <event_type>. The
* event subscriber <es> is not allowed to change from a previous call as long
* as at least one event is still subscribed. The <event_type> must only be a
* combination of SUB_RETRY_RECV and SUB_RETRY_SEND. It always returns 0, unless
* the conn_stream <cs> was already detached, in which case it will return -1.
*/
static int h1_subscribe(struct conn_stream *cs, int event_type, struct wait_event *es)
{
struct wait_event *sw = param;
struct h1s *h1s = cs->ctx;
struct h1c *h1c;
@ -2579,10 +2585,10 @@ static int h1_subscribe(struct conn_stream *cs, int event_type, void *param)
BUG_ON(event_type & ~(SUB_RETRY_SEND|SUB_RETRY_RECV));
BUG_ON(h1s->subs && h1s->subs->events & event_type);
BUG_ON(h1s->subs && h1s->subs != sw);
BUG_ON(h1s->subs && h1s->subs != es);
sw->events |= event_type;
h1s->subs = sw;
es->events |= event_type;
h1s->subs = es;
if (event_type & SUB_RETRY_RECV)
TRACE_DEVEL("subscribe(recv)", H1_EV_STRM_RECV, h1s->h1c->conn, h1s);

View File

@ -5589,15 +5589,13 @@ static size_t h2s_make_trailers(struct h2s *h2s, struct htx *htx)
goto end;
}
/* Called from the upper layer, to subscribe to events, such as being able to send.
* The <param> argument here is supposed to be a pointer to a wait_event struct
* which will be passed to h2s->subs. The event_type must only be a
* combination of SUB_RETRY_RECV and SUB_RETRY_SEND, other values will lead to -1
* being returned. It always returns 0 except for the error above.
/* Called from the upper layer, to subscribe <es> to events <event_type>. The
* event subscriber <es> is not allowed to change from a previous call as long
* as at least one event is still subscribed. The <event_type> must only be a
* combination of SUB_RETRY_RECV and SUB_RETRY_SEND. It always returns 0.
*/
static int h2_subscribe(struct conn_stream *cs, int event_type, void *param)
static int h2_subscribe(struct conn_stream *cs, int event_type, struct wait_event *es)
{
struct wait_event *sw = param;
struct h2s *h2s = cs->ctx;
struct h2c *h2c = h2s->h2c;
@ -5605,10 +5603,10 @@ static int h2_subscribe(struct conn_stream *cs, int event_type, void *param)
BUG_ON(event_type & ~(SUB_RETRY_SEND|SUB_RETRY_RECV));
BUG_ON(h2s->subs && h2s->subs->events & event_type);
BUG_ON(h2s->subs && h2s->subs != sw);
BUG_ON(h2s->subs && h2s->subs != es);
sw->events |= event_type;
h2s->subs = sw;
es->events |= event_type;
h2s->subs = es;
if (event_type & SUB_RETRY_RECV)
TRACE_DEVEL("subscribe(recv)", H2_EV_STRM_RECV, h2c->conn, h2s);
@ -5627,23 +5625,21 @@ static int h2_subscribe(struct conn_stream *cs, int event_type, void *param)
return 0;
}
/* Called from the upper layer, to unsubscribe some events (undo h2_subscribe).
* The <param> argument here is supposed to be a pointer to the same wait_event
* struct that was passed to h2_subscribe() otherwise nothing will be changed.
* It always returns zero.
/* Called from the upper layer, to unsubscribe <es> from events <event_type>.
* The <es> pointer is not allowed to differ from the one passed to the
* subscribe() call. It always returns zero.
*/
static int h2_unsubscribe(struct conn_stream *cs, int event_type, void *param)
static int h2_unsubscribe(struct conn_stream *cs, int event_type, struct wait_event *es)
{
struct wait_event *sw = param;
struct h2s *h2s = cs->ctx;
TRACE_ENTER(H2_EV_STRM_SEND|H2_EV_STRM_RECV, h2s->h2c->conn, h2s);
BUG_ON(event_type & ~(SUB_RETRY_SEND|SUB_RETRY_RECV));
BUG_ON(h2s->subs && h2s->subs != sw);
BUG_ON(h2s->subs && h2s->subs != es);
sw->events &= ~event_type;
if (!sw->events)
es->events &= ~event_type;
if (!es->events)
h2s->subs = NULL;
if (event_type & SUB_RETRY_RECV)

View File

@ -304,15 +304,23 @@ static size_t mux_pt_snd_buf(struct conn_stream *cs, struct buffer *buf, size_t
return ret;
}
/* Called from the upper layer, to subscribe to events */
static int mux_pt_subscribe(struct conn_stream *cs, int event_type, void *param)
/* Called from the upper layer, to subscribe <es> to events <event_type>. The
* event subscriber <es> is not allowed to change from a previous call as long
* as at least one event is still subscribed. The <event_type> must only be a
* combination of SUB_RETRY_RECV and SUB_RETRY_SEND. It always returns 0.
*/
static int mux_pt_subscribe(struct conn_stream *cs, int event_type, struct wait_event *es)
{
return (cs->conn->xprt->subscribe(cs->conn, cs->conn->xprt_ctx, event_type, param));
return cs->conn->xprt->subscribe(cs->conn, cs->conn->xprt_ctx, event_type, es);
}
static int mux_pt_unsubscribe(struct conn_stream *cs, int event_type, void *param)
/* Called from the upper layer, to unsubscribe <es> from events <event_type>.
* The <es> pointer is not allowed to differ from the one passed to the
* subscribe() call. It always returns zero.
*/
static int mux_pt_unsubscribe(struct conn_stream *cs, int event_type, struct wait_event *es)
{
return (cs->conn->xprt->unsubscribe(cs->conn, cs->conn->xprt_ctx, event_type, param));
return cs->conn->xprt->unsubscribe(cs->conn, cs->conn->xprt_ctx, event_type, es);
}
#if defined(USE_LINUX_SPLICE)

View File

@ -405,14 +405,23 @@ static size_t raw_sock_from_buf(struct connection *conn, void *xprt_ctx, const s
return done;
}
static int raw_sock_subscribe(struct connection *conn, void *xprt_ctx, int event_type, void *param)
/* Called from the upper layer, to subscribe <es> to events <event_type>. The
* event subscriber <es> is not allowed to change from a previous call as long
* as at least one event is still subscribed. The <event_type> must only be a
* combination of SUB_RETRY_RECV and SUB_RETRY_SEND. It always returns 0.
*/
static int raw_sock_subscribe(struct connection *conn, void *xprt_ctx, int event_type, struct wait_event *es)
{
return conn_subscribe(conn, xprt_ctx, event_type, param);
return conn_subscribe(conn, xprt_ctx, event_type, es);
}
static int raw_sock_unsubscribe(struct connection *conn, void *xprt_ctx, int event_type, void *param)
/* Called from the upper layer, to unsubscribe <es> from events <event_type>.
* The <es> pointer is not allowed to differ from the one passed to the
* subscribe() call. It always returns zero.
*/
static int raw_sock_unsubscribe(struct connection *conn, void *xprt_ctx, int event_type, struct wait_event *es)
{
return conn_unsubscribe(conn, xprt_ctx, event_type, param);
return conn_unsubscribe(conn, xprt_ctx, event_type, es);
}
/* We can't have an underlying XPRT, so just return -1 to signify failure */

View File

@ -6332,9 +6332,14 @@ reneg_ok:
return 0;
}
static int ssl_subscribe(struct connection *conn, void *xprt_ctx, int event_type, void *param)
/* Called from the upper layer, to subscribe <es> to events <event_type>. The
* event subscriber <es> is not allowed to change from a previous call as long
* as at least one event is still subscribed. The <event_type> must only be a
* combination of SUB_RETRY_RECV and SUB_RETRY_SEND. It always returns 0,
* unless the transport layer was already released.
*/
static int ssl_subscribe(struct connection *conn, void *xprt_ctx, int event_type, struct wait_event *es)
{
struct wait_event *sw = param;
struct ssl_sock_ctx *ctx = xprt_ctx;
if (!ctx)
@ -6342,10 +6347,10 @@ static int ssl_subscribe(struct connection *conn, void *xprt_ctx, int event_type
BUG_ON(event_type & ~(SUB_RETRY_SEND|SUB_RETRY_RECV));
BUG_ON(ctx->subs && ctx->subs->events & event_type);
BUG_ON(ctx->subs && ctx->subs != sw);
BUG_ON(ctx->subs && ctx->subs != es);
ctx->subs = sw;
sw->events |= event_type;
ctx->subs = es;
es->events |= event_type;
/* we may have to subscribe to lower layers for new events */
event_type &= ~ctx->wait_event.events;
@ -6354,16 +6359,19 @@ static int ssl_subscribe(struct connection *conn, void *xprt_ctx, int event_type
return 0;
}
static int ssl_unsubscribe(struct connection *conn, void *xprt_ctx, int event_type, void *param)
/* Called from the upper layer, to unsubscribe <es> from events <event_type>.
* The <es> pointer is not allowed to differ from the one passed to the
* subscribe() call. It always returns zero.
*/
static int ssl_unsubscribe(struct connection *conn, void *xprt_ctx, int event_type, struct wait_event *es)
{
struct ssl_sock_ctx *ctx = xprt_ctx;
struct wait_event *sw = param;
BUG_ON(event_type & ~(SUB_RETRY_SEND|SUB_RETRY_RECV));
BUG_ON(ctx->subs && ctx->subs != sw);
BUG_ON(ctx->subs && ctx->subs != es);
sw->events &= ~event_type;
if (!sw->events)
es->events &= ~event_type;
if (!es->events)
ctx->subs = NULL;
/* If we subscribed, and we're not doing the handshake,

View File

@ -196,31 +196,38 @@ static void xprt_handshake_close(struct connection *conn, void *xprt_ctx)
}
}
static int xprt_handshake_subscribe(struct connection *conn, void *xprt_ctx, int event_type, void *param)
/* Called from the upper layer, to subscribe <es> to events <event_type>. The
* event subscriber <es> is not allowed to change from a previous call as long
* as at least one event is still subscribed. The <event_type> must only be a
* combination of SUB_RETRY_RECV and SUB_RETRY_SEND. It always returns 0.
*/
static int xprt_handshake_subscribe(struct connection *conn, void *xprt_ctx, int event_type, struct wait_event *es)
{
struct wait_event *sw = param;
struct xprt_handshake_ctx *ctx = xprt_ctx;
BUG_ON(event_type & ~(SUB_RETRY_SEND|SUB_RETRY_RECV));
BUG_ON(ctx->subs && ctx->subs->events & event_type);
BUG_ON(ctx->subs && ctx->subs != sw);
BUG_ON(ctx->subs && ctx->subs != es);
ctx->subs = sw;
sw->events |= event_type;
ctx->subs = es;
es->events |= event_type;
return 0;
}
static int xprt_handshake_unsubscribe(struct connection *conn, void *xprt_ctx, int event_type, void *param)
/* Called from the upper layer, to unsubscribe <es> from events <event_type>.
* The <es> pointer is not allowed to differ from the one passed to the
* subscribe() call. It always returns zero.
*/
static int xprt_handshake_unsubscribe(struct connection *conn, void *xprt_ctx, int event_type, struct wait_event *es)
{
struct xprt_handshake_ctx *ctx = xprt_ctx;
struct wait_event *sw = param;
BUG_ON(event_type & ~(SUB_RETRY_SEND|SUB_RETRY_RECV));
BUG_ON(ctx->subs && ctx->subs != sw);
BUG_ON(ctx->subs && ctx->subs != es);
sw->events &= ~event_type;
if (!sw->events)
es->events &= ~event_type;
if (!es->events)
ctx->subs = NULL;
return 0;