cifs: do not disable interface polling on failure
authorShyam Prasad N <sprasad@microsoft.com>
Mon, 2 Jun 2025 17:07:17 +0000 (22:37 +0530)
committerSteve French <stfrench@microsoft.com>
Tue, 3 Jun 2025 23:42:48 +0000 (18:42 -0500)
When a server has multichannel enabled, we keep polling the server
for interfaces periodically. However, when this query fails, we
disable the polling. This can be problematic as it takes away the
chance for the server to start advertizing again.

This change reschedules the delayed work, even if the current call
failed. That way, multichannel sessions can recover.

Signed-off-by: Shyam Prasad N <sprasad@microsoft.com>
Cc: stable@vger.kernel.org
Signed-off-by: Steve French <stfrench@microsoft.com>
fs/smb/client/connect.c
fs/smb/client/smb2pdu.c

index 024817d40c5f51e20f5f2882ed96587ae1bb2d3b..28bc334966237ae8e1948fd96837dedc14e8a40c 100644 (file)
@@ -116,13 +116,9 @@ static void smb2_query_server_interfaces(struct work_struct *work)
        rc = server->ops->query_server_interfaces(xid, tcon, false);
        free_xid(xid);
 
-       if (rc) {
-               if (rc == -EOPNOTSUPP)
-                       return;
-
+       if (rc)
                cifs_dbg(FYI, "%s: failed to query server interfaces: %d\n",
                                __func__, rc);
-       }
 
        queue_delayed_work(cifsiod_wq, &tcon->query_interfaces,
                           (SMB_INTERFACE_POLL_INTERVAL * HZ));
index 96b32d2760719721da9b5ee611fb42b525fb1458..a717be1626a3cca0c73aef8b0e91dba56540eaa8 100644 (file)
@@ -424,6 +424,10 @@ skip_sess_setup:
                free_xid(xid);
                ses->flags &= ~CIFS_SES_FLAGS_PENDING_QUERY_INTERFACES;
 
+               /* regardless of rc value, setup polling */
+               queue_delayed_work(cifsiod_wq, &tcon->query_interfaces,
+                                  (SMB_INTERFACE_POLL_INTERVAL * HZ));
+
                mutex_unlock(&ses->session_mutex);
 
                if (rc == -EOPNOTSUPP && ses->chan_count > 1) {
@@ -444,11 +448,8 @@ skip_sess_setup:
                if (ses->chan_max > ses->chan_count &&
                    ses->iface_count &&
                    !SERVER_IS_CHAN(server)) {
-                       if (ses->chan_count == 1) {
+                       if (ses->chan_count == 1)
                                cifs_server_dbg(VFS, "supports multichannel now\n");
-                               queue_delayed_work(cifsiod_wq, &tcon->query_interfaces,
-                                                (SMB_INTERFACE_POLL_INTERVAL * HZ));
-                       }
 
                        cifs_try_adding_channels(ses);
                }