From ff7cb4cb45f0311e2b198d0833e1af520b7e7c4e Mon Sep 17 00:00:00 2001 From: Libor Peltan <libor.peltan@nic.cz> Date: Mon, 15 Nov 2021 15:24:06 +0100 Subject: [PATCH] xdp-tcp: bugfix: crash when two packets for same conn... ...and one of them is closing it --- src/libknot/xdp/tcp.c | 6 ++---- src/libknot/xdp/tcp.h | 2 +- tests/libknot/test_xdp_tcp.c | 1 + 3 files changed, 4 insertions(+), 5 deletions(-) diff --git a/src/libknot/xdp/tcp.c b/src/libknot/xdp/tcp.c index fed16e554f..c6c10ec3c6 100644 --- a/src/libknot/xdp/tcp.c +++ b/src/libknot/xdp/tcp.c @@ -381,8 +381,7 @@ int knot_tcp_recv(knot_tcp_relay_t *relays, knot_xdp_msg_t *msgs, uint32_t count case XDP_TCP_CLOSING2: if (msg->payload.iov_len == 0) { // otherwise ignore close tcp_table_remove(pconn, tcp_table); - del_conn(conn); - relay->conn = NULL; + relay->answer = XDP_TCP_FREE; } break; } @@ -414,8 +413,7 @@ int knot_tcp_recv(knot_tcp_relay_t *relays, knot_xdp_msg_t *msgs, uint32_t count if (conn != NULL && msg->seqno == conn->seqno) { relay->action = XDP_TCP_RESET; tcp_table_remove(pconn, tcp_table); - del_conn(conn); - relay->conn = NULL; + relay->answer = XDP_TCP_FREE; } else if (conn != NULL) { relay->auto_answer = KNOT_XDP_MSG_ACK; } diff --git a/src/libknot/xdp/tcp.h b/src/libknot/xdp/tcp.h index cefd96780e..2cde210bed 100644 --- a/src/libknot/xdp/tcp.h +++ b/src/libknot/xdp/tcp.h @@ -125,7 +125,7 @@ inline static uint32_t knot_tcp_next_seqno(const knot_xdp_msg_t *msg) inline static bool knot_tcp_relay_empty(const knot_tcp_relay_t *r) { - return r->action == XDP_TCP_NOOP && r->auto_answer == 0 && r->inbufs_count == 0; + return r->action == XDP_TCP_NOOP && r->answer == XDP_TCP_NOOP && r->auto_answer == 0 && r->inbufs_count == 0; } /*! diff --git a/tests/libknot/test_xdp_tcp.c b/tests/libknot/test_xdp_tcp.c index d0299af25e..b88bee7785 100644 --- a/tests/libknot/test_xdp_tcp.c +++ b/tests/libknot/test_xdp_tcp.c @@ -380,6 +380,7 @@ void test_close(void) check_sent(0, 0, 0, 0); is_int(conns_pre - 1, test_table->usage, "close: connection removed"); is_int(conns_pre - 1, tcp_table_timeout_length(test_table), "close: timeout list size"); + knot_tcp_cleanup(test_table, &rl, 1); } void test_many(void) -- GitLab