mirror of
https://git.haproxy.org/git/haproxy.git/
synced 2025-08-06 15:17:01 +02:00
MEDIUM: stconn: Use one function to shut connection and applet endpoints
se_shutdown() function is now used to perform a shutdown on a connection endpoint and an applet endpoint. The same function is used for both. sc_conn_shut() function was removed and appctx_shut() function was updated to only deal with the applet stuff.
This commit is contained in:
parent
4b80442832
commit
1e38ac72ce
@ -42,7 +42,7 @@ struct task *task_process_applet(struct task *t, void *context, unsigned int sta
|
|||||||
int appctx_buf_available(void *arg);
|
int appctx_buf_available(void *arg);
|
||||||
void *applet_reserve_svcctx(struct appctx *appctx, size_t size);
|
void *applet_reserve_svcctx(struct appctx *appctx, size_t size);
|
||||||
void applet_reset_svcctx(struct appctx *appctx);
|
void applet_reset_svcctx(struct appctx *appctx);
|
||||||
void appctx_shut(struct appctx *appctx, enum se_shut_mode mode);
|
void appctx_shut(struct appctx *appctx);
|
||||||
|
|
||||||
struct appctx *appctx_new_on(struct applet *applet, struct sedesc *sedesc, int thr);
|
struct appctx *appctx_new_on(struct applet *applet, struct sedesc *sedesc, int thr);
|
||||||
int appctx_finalize_startup(struct appctx *appctx, struct proxy *px, struct buffer *input);
|
int appctx_finalize_startup(struct appctx *appctx, struct proxy *px, struct buffer *input);
|
||||||
|
@ -39,6 +39,8 @@ struct check;
|
|||||||
struct sedesc *sedesc_new();
|
struct sedesc *sedesc_new();
|
||||||
void sedesc_free(struct sedesc *sedesc);
|
void sedesc_free(struct sedesc *sedesc);
|
||||||
|
|
||||||
|
void se_shutdown(struct sedesc *sedesc, enum se_shut_mode mode);
|
||||||
|
|
||||||
struct stconn *sc_new_from_endp(struct sedesc *sedesc, struct session *sess, struct buffer *input);
|
struct stconn *sc_new_from_endp(struct sedesc *sedesc, struct session *sess, struct buffer *input);
|
||||||
struct stconn *sc_new_from_strm(struct stream *strm, unsigned int flags);
|
struct stconn *sc_new_from_strm(struct stream *strm, unsigned int flags);
|
||||||
struct stconn *sc_new_from_check(struct check *check, unsigned int flags);
|
struct stconn *sc_new_from_check(struct check *check, unsigned int flags);
|
||||||
@ -318,27 +320,6 @@ static inline const char *sc_get_data_name(const struct stconn *sc)
|
|||||||
return sc->app_ops->name;
|
return sc->app_ops->name;
|
||||||
}
|
}
|
||||||
|
|
||||||
static inline void sc_conn_shut(struct stconn *sc, enum se_shut_mode mode)
|
|
||||||
{
|
|
||||||
const struct mux_ops *mux;
|
|
||||||
|
|
||||||
BUG_ON(!sc_conn(sc));
|
|
||||||
|
|
||||||
mux = sc_mux_ops(sc);
|
|
||||||
|
|
||||||
if ((mode & (SE_SHW_SILENT|SE_SHW_NORMAL)) && !sc_ep_test(sc, SE_FL_SHW)) {
|
|
||||||
if (mux && mux->shutw)
|
|
||||||
mux->shutw(sc, mode);
|
|
||||||
sc_ep_set(sc, (mode & SE_SHW_NORMAL) ? SE_FL_SHWN : SE_FL_SHWS);
|
|
||||||
}
|
|
||||||
|
|
||||||
if ((mode & (SE_SHR_RESET|SE_SHR_DRAIN)) && !sc_ep_test(sc, SE_FL_SHR)) {
|
|
||||||
if (mux && mux->shutr)
|
|
||||||
mux->shutr(sc, mode);
|
|
||||||
sc_ep_set(sc, (mode & SE_SHR_DRAIN) ? SE_FL_SHRD : SE_FL_SHRR);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Returns non-zero if the stream connector's Rx path is blocked because of
|
/* Returns non-zero if the stream connector's Rx path is blocked because of
|
||||||
* lack of room in the input buffer. This usually happens after applets failed
|
* lack of room in the input buffer. This usually happens after applets failed
|
||||||
* to deliver data into the channel's buffer and reported it via sc_need_room().
|
* to deliver data into the channel's buffer and reported it via sc_need_room().
|
||||||
|
19
src/applet.c
19
src/applet.c
@ -394,26 +394,19 @@ void applet_reset_svcctx(struct appctx *appctx)
|
|||||||
/* call the applet's release() function if any, and marks the sedesc as shut
|
/* call the applet's release() function if any, and marks the sedesc as shut
|
||||||
* once both read and write side are shut. Needs to be called upon close().
|
* once both read and write side are shut. Needs to be called upon close().
|
||||||
*/
|
*/
|
||||||
void appctx_shut(struct appctx *appctx, enum se_shut_mode mode)
|
void appctx_shut(struct appctx *appctx)
|
||||||
{
|
{
|
||||||
if (applet_fl_test(appctx, APPCTX_FL_SHUTDOWN))
|
if (applet_fl_test(appctx, APPCTX_FL_SHUTDOWN))
|
||||||
return;
|
return;
|
||||||
|
|
||||||
TRACE_ENTER(APPLET_EV_RELEASE, appctx);
|
TRACE_ENTER(APPLET_EV_RELEASE, appctx);
|
||||||
if ((mode & (SE_SHW_SILENT|SE_SHW_NORMAL)) && !se_fl_test(appctx->sedesc, SE_FL_SHW))
|
|
||||||
se_fl_set(appctx->sedesc, SE_FL_SHWN);
|
|
||||||
|
|
||||||
if ((mode & (SE_SHR_RESET|SE_SHR_DRAIN)) && !se_fl_test(appctx->sedesc, SE_FL_SHR))
|
if (appctx->applet->release)
|
||||||
se_fl_set(appctx->sedesc, SE_FL_SHRR);
|
appctx->applet->release(appctx);
|
||||||
|
applet_fl_set(appctx, APPCTX_FL_SHUTDOWN);
|
||||||
|
|
||||||
if (se_fl_test(appctx->sedesc, SE_FL_SHR) && se_fl_test(appctx->sedesc, SE_FL_SHW)) {
|
if (LIST_INLIST(&appctx->buffer_wait.list))
|
||||||
if (appctx->applet->release)
|
LIST_DEL_INIT(&appctx->buffer_wait.list);
|
||||||
appctx->applet->release(appctx);
|
|
||||||
applet_fl_set(appctx, APPCTX_FL_SHUTDOWN);
|
|
||||||
|
|
||||||
if (LIST_INLIST(&appctx->buffer_wait.list))
|
|
||||||
LIST_DEL_INIT(&appctx->buffer_wait.list);
|
|
||||||
}
|
|
||||||
|
|
||||||
TRACE_LEAVE(APPLET_EV_RELEASE, appctx);
|
TRACE_LEAVE(APPLET_EV_RELEASE, appctx);
|
||||||
}
|
}
|
||||||
|
@ -1382,7 +1382,7 @@ struct task *process_chk_conn(struct task *t, void *context, unsigned int state)
|
|||||||
* as a failed response coupled with "observe layer7" caused the
|
* as a failed response coupled with "observe layer7" caused the
|
||||||
* server state to be suddenly changed.
|
* server state to be suddenly changed.
|
||||||
*/
|
*/
|
||||||
sc_conn_shut(sc, SE_SHR_DRAIN|SE_SHW_SILENT);
|
se_shutdown(sc->sedesc, SE_SHR_DRAIN|SE_SHW_SILENT);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (sc) {
|
if (sc) {
|
||||||
|
56
src/stconn.c
56
src/stconn.c
@ -131,6 +131,40 @@ void sedesc_free(struct sedesc *sedesc)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Performs a shutdown on the endpoint. This function deals with connection and
|
||||||
|
* applet endpoints. It is responsible to set SE flags corresponding to the
|
||||||
|
* given shut modes and to call right shutdown functions of the endpoint. It is
|
||||||
|
* called from the .abort and .shut app_ops callback functions at the SC level.
|
||||||
|
*/
|
||||||
|
void se_shutdown(struct sedesc *sedesc, enum se_shut_mode mode)
|
||||||
|
{
|
||||||
|
if (se_fl_test(sedesc, SE_FL_T_MUX)) {
|
||||||
|
const struct mux_ops *mux = (sedesc->conn ? sedesc->conn->mux : NULL);
|
||||||
|
|
||||||
|
if ((mode & (SE_SHW_SILENT|SE_SHW_NORMAL)) && !se_fl_test(sedesc, SE_FL_SHW)) {
|
||||||
|
if (mux && mux->shutw)
|
||||||
|
mux->shutw(sedesc->sc, mode);
|
||||||
|
se_fl_set(sedesc, (mode & SE_SHW_NORMAL) ? SE_FL_SHWN : SE_FL_SHWS);
|
||||||
|
}
|
||||||
|
|
||||||
|
if ((mode & (SE_SHR_RESET|SE_SHR_DRAIN)) && !se_fl_test(sedesc, SE_FL_SHR)) {
|
||||||
|
if (mux && mux->shutr)
|
||||||
|
mux->shutr(sedesc->sc, mode);
|
||||||
|
se_fl_set(sedesc, (mode & SE_SHR_DRAIN) ? SE_FL_SHRD : SE_FL_SHRR);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else if (se_fl_test(sedesc, SE_FL_T_APPLET)) {
|
||||||
|
if ((mode & (SE_SHW_SILENT|SE_SHW_NORMAL)) && !se_fl_test(sedesc, SE_FL_SHW))
|
||||||
|
se_fl_set(sedesc, SE_FL_SHWN);
|
||||||
|
|
||||||
|
if ((mode & (SE_SHR_RESET|SE_SHR_DRAIN)) && !se_fl_test(sedesc, SE_FL_SHR))
|
||||||
|
se_fl_set(sedesc, SE_FL_SHRR);
|
||||||
|
|
||||||
|
if (se_fl_test(sedesc, SE_FL_SHR) && se_fl_test(sedesc, SE_FL_SHW))
|
||||||
|
appctx_shut(sedesc->se);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/* Tries to allocate a new stconn and initialize its main fields. On
|
/* Tries to allocate a new stconn and initialize its main fields. On
|
||||||
* failure, nothing is allocated and NULL is returned. It is an internal
|
* failure, nothing is allocated and NULL is returned. It is an internal
|
||||||
* function. The caller must, at least, set the SE_FL_ORPHAN or SE_FL_DETACHED
|
* function. The caller must, at least, set the SE_FL_ORPHAN or SE_FL_DETACHED
|
||||||
@ -405,7 +439,7 @@ static void sc_detach_endp(struct stconn **scp)
|
|||||||
sc_ep_set(sc, SE_FL_ORPHAN);
|
sc_ep_set(sc, SE_FL_ORPHAN);
|
||||||
sc->sedesc->sc = NULL;
|
sc->sedesc->sc = NULL;
|
||||||
sc->sedesc = NULL;
|
sc->sedesc = NULL;
|
||||||
appctx_shut(appctx, SE_SHR_RESET|SE_SHW_NORMAL);
|
se_shutdown(appctx->sedesc, SE_SHR_RESET|SE_SHW_NORMAL);
|
||||||
appctx_free(appctx);
|
appctx_free(appctx);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -700,7 +734,7 @@ static void sc_app_abort_conn(struct stconn *sc)
|
|||||||
return;
|
return;
|
||||||
|
|
||||||
if (sc->flags & SC_FL_SHUT_DONE) {
|
if (sc->flags & SC_FL_SHUT_DONE) {
|
||||||
sc_conn_shut(sc, SE_SHR_RESET|SE_SHW_SILENT);
|
se_shutdown(sc->sedesc, SE_SHR_RESET|SE_SHW_SILENT);
|
||||||
sc->state = SC_ST_DIS;
|
sc->state = SC_ST_DIS;
|
||||||
if (sc->flags & SC_FL_ISBACK)
|
if (sc->flags & SC_FL_ISBACK)
|
||||||
__sc_strm(sc)->conn_exp = TICK_ETERNITY;
|
__sc_strm(sc)->conn_exp = TICK_ETERNITY;
|
||||||
@ -742,11 +776,11 @@ static void sc_app_shut_conn(struct stconn *sc)
|
|||||||
* no risk so we close both sides immediately.
|
* no risk so we close both sides immediately.
|
||||||
*/
|
*/
|
||||||
if (!(sc->flags & (SC_FL_NOLINGER|SC_FL_EOS|SC_FL_ABRT_DONE)) && !(ic->flags & CF_DONT_READ)) {
|
if (!(sc->flags & (SC_FL_NOLINGER|SC_FL_EOS|SC_FL_ABRT_DONE)) && !(ic->flags & CF_DONT_READ)) {
|
||||||
sc_conn_shut(sc, SE_SHW_NORMAL);
|
se_shutdown(sc->sedesc, SE_SHW_NORMAL);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
sc_conn_shut(sc, SE_SHR_RESET|((sc->flags & SC_FL_NOLINGER) ? SE_SHW_SILENT : SE_SHW_NORMAL));
|
se_shutdown(sc->sedesc, SE_SHR_RESET|((sc->flags & SC_FL_NOLINGER) ? SE_SHW_SILENT : SE_SHW_NORMAL));
|
||||||
sc->state = SC_ST_DIS;
|
sc->state = SC_ST_DIS;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@ -754,7 +788,7 @@ static void sc_app_shut_conn(struct stconn *sc)
|
|||||||
/* we may have to close a pending connection, and mark the
|
/* we may have to close a pending connection, and mark the
|
||||||
* response buffer as abort
|
* response buffer as abort
|
||||||
*/
|
*/
|
||||||
sc_conn_shut(sc, SE_SHR_RESET|SE_SHW_SILENT);
|
se_shutdown(sc->sedesc, SE_SHR_RESET|SE_SHW_SILENT);
|
||||||
sc->state = SC_ST_DIS;
|
sc->state = SC_ST_DIS;
|
||||||
break;
|
break;
|
||||||
case SC_ST_CER:
|
case SC_ST_CER:
|
||||||
@ -884,7 +918,7 @@ static void sc_app_abort_applet(struct stconn *sc)
|
|||||||
return;
|
return;
|
||||||
|
|
||||||
if (sc->flags & SC_FL_SHUT_DONE) {
|
if (sc->flags & SC_FL_SHUT_DONE) {
|
||||||
appctx_shut(__sc_appctx(sc), SE_SHR_RESET|SE_SHW_NORMAL);
|
se_shutdown(sc->sedesc, SE_SHR_RESET|SE_SHW_NORMAL);
|
||||||
sc->state = SC_ST_DIS;
|
sc->state = SC_ST_DIS;
|
||||||
if (sc->flags & SC_FL_ISBACK)
|
if (sc->flags & SC_FL_ISBACK)
|
||||||
__sc_strm(sc)->conn_exp = TICK_ETERNITY;
|
__sc_strm(sc)->conn_exp = TICK_ETERNITY;
|
||||||
@ -929,11 +963,11 @@ static void sc_app_shut_applet(struct stconn *sc)
|
|||||||
*/
|
*/
|
||||||
if (!(sc->flags & (SC_FL_ERROR|SC_FL_NOLINGER|SC_FL_EOS|SC_FL_ABRT_DONE)) &&
|
if (!(sc->flags & (SC_FL_ERROR|SC_FL_NOLINGER|SC_FL_EOS|SC_FL_ABRT_DONE)) &&
|
||||||
!(ic->flags & CF_DONT_READ)) {
|
!(ic->flags & CF_DONT_READ)) {
|
||||||
appctx_shut(__sc_appctx(sc), SE_SHW_NORMAL);
|
se_shutdown(sc->sedesc, SE_SHW_NORMAL);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
appctx_shut(__sc_appctx(sc), SE_SHR_RESET|SE_SHW_NORMAL);
|
se_shutdown(sc->sedesc, SE_SHR_RESET|SE_SHW_NORMAL);
|
||||||
sc->state = SC_ST_DIS;
|
sc->state = SC_ST_DIS;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@ -942,7 +976,7 @@ static void sc_app_shut_applet(struct stconn *sc)
|
|||||||
case SC_ST_QUE:
|
case SC_ST_QUE:
|
||||||
case SC_ST_TAR:
|
case SC_ST_TAR:
|
||||||
/* Note that none of these states may happen with applets */
|
/* Note that none of these states may happen with applets */
|
||||||
appctx_shut(__sc_appctx(sc), SE_SHR_RESET|SE_SHW_NORMAL);
|
se_shutdown(sc->sedesc, SE_SHR_RESET|SE_SHW_NORMAL);
|
||||||
sc->state = SC_ST_DIS;
|
sc->state = SC_ST_DIS;
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
@ -1202,7 +1236,7 @@ static void sc_conn_eos(struct stconn *sc)
|
|||||||
|
|
||||||
do_close:
|
do_close:
|
||||||
/* OK we completely close the socket here just as if we went through sc_shut[rw]() */
|
/* OK we completely close the socket here just as if we went through sc_shut[rw]() */
|
||||||
sc_conn_shut(sc, SE_SHR_RESET|SE_SHW_SILENT);
|
se_shutdown(sc->sedesc, SE_SHR_RESET|SE_SHW_SILENT);
|
||||||
|
|
||||||
sc->flags &= ~SC_FL_SHUT_WANTED;
|
sc->flags &= ~SC_FL_SHUT_WANTED;
|
||||||
sc->flags |= SC_FL_SHUT_DONE;
|
sc->flags |= SC_FL_SHUT_DONE;
|
||||||
@ -1866,7 +1900,7 @@ static void sc_applet_eos(struct stconn *sc)
|
|||||||
return;
|
return;
|
||||||
|
|
||||||
if (sc->flags & SC_FL_SHUT_DONE) {
|
if (sc->flags & SC_FL_SHUT_DONE) {
|
||||||
appctx_shut(__sc_appctx(sc), SE_SHR_RESET|SE_SHW_NORMAL);
|
se_shutdown(sc->sedesc, SE_SHR_RESET|SE_SHW_NORMAL);
|
||||||
sc->state = SC_ST_DIS;
|
sc->state = SC_ST_DIS;
|
||||||
if (sc->flags & SC_FL_ISBACK)
|
if (sc->flags & SC_FL_ISBACK)
|
||||||
__sc_strm(sc)->conn_exp = TICK_ETERNITY;
|
__sc_strm(sc)->conn_exp = TICK_ETERNITY;
|
||||||
|
Loading…
Reference in New Issue
Block a user