MINOR: connection: skip FD-based syscalls for FD-less connections
Some syscalls at the TCP level act directly on the FD. Some of them are used by TCP actions like set-tos, set-mark, silent-drop, others try to retrieve TCP info, get the source or destination address. These ones must not be called with an invalid FD coming from an FD-less connection, so let's add the relevant tests for this. It's worth noting that all these ones already have fall back plans (do nothing, error, or switch to alternate implementation).
This commit is contained in:
parent
0e9c264ca0
commit
e22267971b
@ -352,7 +352,8 @@ static inline int conn_get_src(struct connection *conn)
|
||||
if (!sockaddr_alloc(&conn->src, NULL, 0))
|
||||
return 0;
|
||||
|
||||
if (conn->ctrl->fam->get_src(conn->handle.fd, (struct sockaddr *)conn->src,
|
||||
if (conn->ctrl->fam->get_src && !(conn->flags & CO_FL_FDLESS) &&
|
||||
conn->ctrl->fam->get_src(conn->handle.fd, (struct sockaddr *)conn->src,
|
||||
sizeof(*conn->src),
|
||||
obj_type(conn->target) != OBJ_TYPE_LISTENER) == -1)
|
||||
return 0;
|
||||
@ -375,7 +376,8 @@ static inline int conn_get_dst(struct connection *conn)
|
||||
if (!sockaddr_alloc(&conn->dst, NULL, 0))
|
||||
return 0;
|
||||
|
||||
if (conn->ctrl->fam->get_dst(conn->handle.fd, (struct sockaddr *)conn->dst,
|
||||
if (conn->ctrl->fam->get_dst && !(conn->flags & CO_FL_FDLESS) &&
|
||||
conn->ctrl->fam->get_dst(conn->handle.fd, (struct sockaddr *)conn->dst,
|
||||
sizeof(*conn->dst),
|
||||
obj_type(conn->target) != OBJ_TYPE_LISTENER) == -1)
|
||||
return 0;
|
||||
@ -389,7 +391,7 @@ static inline int conn_get_dst(struct connection *conn)
|
||||
*/
|
||||
static inline void conn_set_tos(const struct connection *conn, int tos)
|
||||
{
|
||||
if (!conn || !conn_ctrl_ready(conn))
|
||||
if (!conn || !conn_ctrl_ready(conn) || (conn->flags & CO_FL_FDLESS))
|
||||
return;
|
||||
|
||||
#ifdef IP_TOS
|
||||
@ -412,7 +414,7 @@ static inline void conn_set_tos(const struct connection *conn, int tos)
|
||||
*/
|
||||
static inline void conn_set_mark(const struct connection *conn, int mark)
|
||||
{
|
||||
if (!conn || !conn_ctrl_ready(conn))
|
||||
if (!conn || !conn_ctrl_ready(conn) || (conn->flags & CO_FL_FDLESS))
|
||||
return;
|
||||
|
||||
#if defined(SO_MARK)
|
||||
@ -429,7 +431,7 @@ static inline void conn_set_mark(const struct connection *conn, int mark)
|
||||
*/
|
||||
static inline void conn_set_quickack(const struct connection *conn, int value)
|
||||
{
|
||||
if (!conn || !conn_ctrl_ready(conn))
|
||||
if (!conn || !conn_ctrl_ready(conn) || (conn->flags & CO_FL_FDLESS))
|
||||
return;
|
||||
|
||||
#ifdef TCP_QUICKACK
|
||||
|
@ -290,6 +290,9 @@ static enum act_return tcp_exec_action_silent_drop(struct act_rule *rule, struct
|
||||
if (strm)
|
||||
strm->csf->si->flags |= SI_FL_NOLINGER;
|
||||
|
||||
if (conn->flags & CO_FL_FDLESS)
|
||||
goto out;
|
||||
|
||||
/* We're on the client-facing side, we must force to disable lingering to
|
||||
* ensure we will use an RST exclusively and kill any pending data.
|
||||
*/
|
||||
|
@ -332,7 +332,8 @@ static inline int get_tcp_info(const struct arg *args, struct sample *smp,
|
||||
/* The fd may not be available for the tcp_info struct, and the
|
||||
syscal can fail. */
|
||||
optlen = sizeof(info);
|
||||
if (getsockopt(conn->handle.fd, IPPROTO_TCP, TCP_INFO, &info, &optlen) == -1)
|
||||
if ((conn->flags & CO_FL_FDLESS) ||
|
||||
getsockopt(conn->handle.fd, IPPROTO_TCP, TCP_INFO, &info, &optlen) == -1)
|
||||
return 0;
|
||||
|
||||
/* extract the value. */
|
||||
|
@ -1210,7 +1210,7 @@ enum tcpcheck_eval_ret tcpcheck_eval_connect(struct check *check, struct tcpchec
|
||||
ssl_sock_set_alpn(conn, (unsigned char *)s->check.alpn_str, s->check.alpn_len);
|
||||
#endif
|
||||
|
||||
if (conn_ctrl_ready(conn) && (connect->options & TCPCHK_OPT_LINGER)) {
|
||||
if (conn_ctrl_ready(conn) && (connect->options & TCPCHK_OPT_LINGER) && !(conn->flags & CO_FL_FDLESS)) {
|
||||
/* Some servers don't like reset on close */
|
||||
HA_ATOMIC_AND(&fdtab[conn->handle.fd].state, ~FD_LINGER_RISK);
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user