]> git.ipfire.org Git - thirdparty/kernel/linux.git/commitdiff
ksmbd: limit repeated connections from clients with the same IP
authorNamjae Jeon <linkinjeon@kernel.org>
Tue, 5 Aug 2025 09:13:13 +0000 (18:13 +0900)
committerSteve French <stfrench@microsoft.com>
Thu, 7 Aug 2025 23:22:58 +0000 (18:22 -0500)
Repeated connections from clients with the same IP address may exhaust
the max connections and prevent other normal client connections.
This patch limit repeated connections from clients with the same IP.

Reported-by: tianshuo han <hantianshuo233@gmail.com>
Cc: stable@vger.kernel.org
Signed-off-by: Namjae Jeon <linkinjeon@kernel.org>
Signed-off-by: Steve French <stfrench@microsoft.com>
fs/smb/server/connection.h
fs/smb/server/transport_tcp.c

index dd3e0e3f7bf046bad0573fe900ef829fe82d030e..31dd1caac1e8a80ff9bf5b93fb1ca7f6998b3037 100644 (file)
@@ -46,6 +46,7 @@ struct ksmbd_conn {
        struct mutex                    srv_mutex;
        int                             status;
        unsigned int                    cli_cap;
+       __be32                          inet_addr;
        char                            *request_buf;
        struct ksmbd_transport          *transport;
        struct nls_table                *local_nls;
index 4e9f98db9ff4098425ba315717f5fd1c6aae7579..d72588f33b9cd19e1c1c686cfe6cf87a3d825f72 100644 (file)
@@ -87,6 +87,7 @@ static struct tcp_transport *alloc_transport(struct socket *client_sk)
                return NULL;
        }
 
+       conn->inet_addr = inet_sk(client_sk->sk)->inet_daddr;
        conn->transport = KSMBD_TRANS(t);
        KSMBD_TRANS(t)->conn = conn;
        KSMBD_TRANS(t)->ops = &ksmbd_tcp_transport_ops;
@@ -230,6 +231,8 @@ static int ksmbd_kthread_fn(void *p)
 {
        struct socket *client_sk = NULL;
        struct interface *iface = (struct interface *)p;
+       struct inet_sock *csk_inet;
+       struct ksmbd_conn *conn;
        int ret;
 
        while (!kthread_should_stop()) {
@@ -248,6 +251,20 @@ static int ksmbd_kthread_fn(void *p)
                        continue;
                }
 
+               /*
+                * Limits repeated connections from clients with the same IP.
+                */
+               csk_inet = inet_sk(client_sk->sk);
+               down_read(&conn_list_lock);
+               list_for_each_entry(conn, &conn_list, conns_list)
+                       if (csk_inet->inet_daddr == conn->inet_addr) {
+                               ret = -EAGAIN;
+                               break;
+                       }
+               up_read(&conn_list_lock);
+               if (ret == -EAGAIN)
+                       continue;
+
                if (server_conf.max_connections &&
                    atomic_inc_return(&active_num_conn) >= server_conf.max_connections) {
                        pr_info_ratelimited("Limit the maximum number of connections(%u)\n",