tcp_input: drop SYN when no free node in the backlog

Wait for the client to retransmit the ack before trying to allocate the
backlog

Signed-off-by: zhanghongyu <zhanghongyu@xiaomi.com>
This commit is contained in:
zhanghongyu 2023-04-17 22:07:31 +08:00 committed by Xiang Xiao
parent 6063c0516e
commit 9162800255
4 changed files with 46 additions and 5 deletions

View file

@ -1430,7 +1430,7 @@ int tcp_backlogadd(FAR struct tcp_conn_s *conn,
#endif
/****************************************************************************
* Name: tcp_backlogavailable
* Name: tcp_backlogpending
*
* Description:
* Called from poll(). Before waiting for a new connection, poll will
@ -1441,10 +1441,28 @@ int tcp_backlogadd(FAR struct tcp_conn_s *conn,
*
****************************************************************************/
#ifdef CONFIG_NET_TCPBACKLOG
bool tcp_backlogpending(FAR struct tcp_conn_s *conn);
#else
# define tcp_backlogpending(c) (false)
#endif
/****************************************************************************
* Name: tcp_backlogavailable
*
* Description:
* Called from tcp_input(). Before alloc a new accept connection, tcp_input
* will call this API to see if there are free node in the backlog.
*
* Assumptions:
* Called from network socket logic with the network locked
*
****************************************************************************/
#ifdef CONFIG_NET_TCPBACKLOG
bool tcp_backlogavailable(FAR struct tcp_conn_s *conn);
#else
# define tcp_backlogavailable(c) (false)
# define tcp_backlogavailable(c) (true)
#endif
/****************************************************************************

View file

@ -252,7 +252,7 @@ int tcp_backlogadd(FAR struct tcp_conn_s *conn,
}
/****************************************************************************
* Name: tcp_backlogremove
* Name: tcp_backlogpending
*
* Description:
* Called from poll(). Before waiting for a new connection, poll will
@ -263,11 +263,28 @@ int tcp_backlogadd(FAR struct tcp_conn_s *conn,
*
****************************************************************************/
bool tcp_backlogavailable(FAR struct tcp_conn_s *conn)
bool tcp_backlogpending(FAR struct tcp_conn_s *conn)
{
return (conn && conn->backlog && !sq_empty(&conn->backlog->bl_pending));
}
/****************************************************************************
* Name: tcp_backlogavailable
*
* Description:
* Called from tcp_input(). Before alloc a new accept connection, tcp_input
* will call this API to see if there are free node in the backlog.
*
* Assumptions:
* Called from network socket logic with the network locked
*
****************************************************************************/
bool tcp_backlogavailable(FAR struct tcp_conn_s *conn)
{
return (conn && conn->backlog && !sq_empty(&conn->backlog->bl_free));
}
/****************************************************************************
* Name: tcp_backlogremove
*

View file

@ -761,6 +761,12 @@ static void tcp_input(FAR struct net_driver_s *dev, uint8_t domain,
if ((conn = tcp_findlistener(&uaddr, tmp16)) != NULL)
#endif
{
if (!tcp_backlogavailable(conn))
{
nerr("ERROR: no free containers for TCP BACKLOG!\n");
goto drop;
}
/* We matched the incoming packet with a connection in LISTEN.
* We now need to create a new connection and send a SYNACK in
* response.

View file

@ -288,7 +288,7 @@ int tcp_pollsetup(FAR struct socket *psock, FAR struct pollfd *fds)
/* Check for read data or backlogged connection availability now */
if (conn->readahead != NULL || tcp_backlogavailable(conn))
if (conn->readahead != NULL || tcp_backlogpending(conn))
{
/* Normal data may be read without blocking. */