summaryrefslogtreecommitdiff
path: root/fs
diff options
context:
space:
mode:
authorEnzo Matsumiya <ematsumiya@suse.de>2025-06-16 16:15:16 -0300
committerEnzo Matsumiya <ematsumiya@suse.de>2025-06-16 16:46:25 -0300
commit1944700ae1e2009e398e44e7bf0559001be0a787 (patch)
tree1b60eb6d184a4066a6a41e6cb9388ef89aa53451 /fs
parent962f1f332f07206e2023ee0f7e2dbaf5762bb4cd (diff)
downloadlinux-1944700ae1e2009e398e44e7bf0559001be0a787.tar.gz
linux-1944700ae1e2009e398e44e7bf0559001be0a787.tar.bz2
linux-1944700ae1e2009e398e44e7bf0559001be0a787.zip
smb: client: don't add channel servers to list
Server channels are useless and unused on cifs_tcp_ses_list, so don't even add them to it. Signed-off-by: Enzo Matsumiya <ematsumiya@suse.de>
Diffstat (limited to 'fs')
-rw-r--r--fs/smb/client/cifs_debug.c91
-rw-r--r--fs/smb/client/connect.c21
2 files changed, 64 insertions, 48 deletions
diff --git a/fs/smb/client/cifs_debug.c b/fs/smb/client/cifs_debug.c
index 02cd49c747dd..b3e15e935ab9 100644
--- a/fs/smb/client/cifs_debug.c
+++ b/fs/smb/client/cifs_debug.c
@@ -365,11 +365,6 @@ static int cifs_debug_data_proc_show(struct seq_file *m, void *v)
#ifdef CONFIG_CIFS_SMB_DIRECT
struct smbdirect_socket_parameters *sp;
#endif
-
- /* channel info will be printed as a part of sessions below */
- if (SERVER_IS_CHAN(server))
- continue;
-
c++;
seq_printf(m, "\n%d) ConnectionId: 0x%llx ",
c, server->conn_id);
@@ -651,20 +646,68 @@ skip_rdma:
return 0;
}
+static void cifs_reset_server_stats(struct TCP_Server_Info *server)
+{
+ int i;
+
+ server->max_in_flight = 0;
+#ifdef CONFIG_CIFS_STATS2
+ for (i = 0; i < NUMBER_OF_SMB2_COMMANDS; i++) {
+ atomic_set(&server->num_cmds[i], 0);
+ atomic_set(&server->smb2slowcmd[i], 0);
+ server->time_per_cmd[i] = 0;
+ server->slowest_cmd[i] = 0;
+ server->fastest_cmd[0] = 0;
+ }
+#endif /* CONFIG_CIFS_STATS2 */
+}
+
+static void cifs_reset_stats(struct TCP_Server_Info *server)
+{
+ struct cifs_tcon *tcon;
+ struct cifs_ses *ses;
+ int i;
+
+ list_for_each_entry(ses, &server->smb_ses_list, smb_ses_list) {
+ if (cifs_ses_exiting(ses))
+ continue;
+ for (i = 0; i < ses->chan_max; i++) {
+ struct TCP_Server_Info *chan_server = ses->chans[i].server;
+
+ if (!chan_server)
+ continue;
+
+ spin_lock(&ses->ses_lock);
+ spin_lock(&ses->chan_lock);
+ if (!cifs_chan_needs_reconnect(ses, server))
+ cifs_reset_server_stats(chan_server);
+ spin_unlock(&ses->chan_lock);
+ spin_unlock(&ses->ses_lock);
+ }
+
+ list_for_each_entry(tcon, &ses->tcon_list, tcon_list) {
+ atomic_set(&tcon->num_smbs_sent, 0);
+ spin_lock(&tcon->stat_lock);
+ tcon->bytes_read = 0;
+ tcon->bytes_written = 0;
+ tcon->stats_from_time = ktime_get_real_seconds();
+ spin_unlock(&tcon->stat_lock);
+ if (server->ops->clear_stats)
+ server->ops->clear_stats(tcon);
+ }
+ }
+}
+
static ssize_t cifs_stats_proc_write(struct file *file,
const char __user *buffer, size_t count, loff_t *ppos)
{
+ struct TCP_Server_Info *server;
bool bv;
int rc;
- struct TCP_Server_Info *server;
- struct cifs_ses *ses;
- struct cifs_tcon *tcon;
rc = kstrtobool_from_user(buffer, count, &bv);
if (rc == 0) {
#ifdef CONFIG_CIFS_STATS2
- int i;
-
atomic_set(&total_buf_alloc_count, 0);
atomic_set(&total_small_buf_alloc_count, 0);
#endif /* CONFIG_CIFS_STATS2 */
@@ -676,32 +719,8 @@ static ssize_t cifs_stats_proc_write(struct file *file,
GlobalCurrentXid = 0;
spin_unlock(&GlobalMid_Lock);
spin_lock(&cifs_tcp_ses_lock);
- list_for_each_entry(server, &cifs_tcp_ses_list, tcp_ses_list) {
- server->max_in_flight = 0;
-#ifdef CONFIG_CIFS_STATS2
- for (i = 0; i < NUMBER_OF_SMB2_COMMANDS; i++) {
- atomic_set(&server->num_cmds[i], 0);
- atomic_set(&server->smb2slowcmd[i], 0);
- server->time_per_cmd[i] = 0;
- server->slowest_cmd[i] = 0;
- server->fastest_cmd[0] = 0;
- }
-#endif /* CONFIG_CIFS_STATS2 */
- list_for_each_entry(ses, &server->smb_ses_list, smb_ses_list) {
- if (cifs_ses_exiting(ses))
- continue;
- list_for_each_entry(tcon, &ses->tcon_list, tcon_list) {
- atomic_set(&tcon->num_smbs_sent, 0);
- spin_lock(&tcon->stat_lock);
- tcon->bytes_read = 0;
- tcon->bytes_written = 0;
- tcon->stats_from_time = ktime_get_real_seconds();
- spin_unlock(&tcon->stat_lock);
- if (server->ops->clear_stats)
- server->ops->clear_stats(tcon);
- }
- }
- }
+ list_for_each_entry(server, &cifs_tcp_ses_list, tcp_ses_list)
+ cifs_reset_stats(server);
spin_unlock(&cifs_tcp_ses_lock);
} else {
return rc;
diff --git a/fs/smb/client/connect.c b/fs/smb/client/connect.c
index c66bd630b769..1ac1a483dd73 100644
--- a/fs/smb/client/connect.c
+++ b/fs/smb/client/connect.c
@@ -1642,12 +1642,7 @@ cifs_find_tcp_session(struct smb3_fs_context *ctx)
spin_lock(&cifs_tcp_ses_lock);
list_for_each_entry(server, &cifs_tcp_ses_list, tcp_ses_list) {
spin_lock(&server->srv_lock);
- /*
- * Skip ses channels since they're only handled in lower layers
- * (e.g. cifs_send_recv).
- */
- if (SERVER_IS_CHAN(server) ||
- !match_server(server, ctx, false)) {
+ if (!match_server(server, ctx, false)) {
spin_unlock(&server->srv_lock);
continue;
}
@@ -1824,10 +1819,10 @@ cifs_get_tcp_session(struct smb3_fs_context *ctx,
spin_lock(&cifs_tcp_ses_lock);
++primary_server->srv_count;
spin_unlock(&cifs_tcp_ses_lock);
+ tcp_ses->primary_server = primary_server;
} else {
- primary_server = tcp_ses;
+ tcp_ses->primary_server = tcp_ses;
}
- tcp_ses->primary_server = primary_server;
spin_lock_init(&tcp_ses->iface_lock);
INIT_LIST_HEAD(&tcp_ses->iface_list);
init_waitqueue_head(&tcp_ses->response_q);
@@ -1917,10 +1912,12 @@ smbd_connected:
tcp_ses->nr_targets = 1;
tcp_ses->ignore_signature = ctx->ignore_signature;
- /* thread spawned, put it on the list */
- spin_lock(&cifs_tcp_ses_lock);
- list_add(&tcp_ses->tcp_ses_list, &cifs_tcp_ses_list);
- spin_unlock(&cifs_tcp_ses_lock);
+ /* thread spawned, put it on the list (primary servers only) */
+ if (!primary_server) {
+ spin_lock(&cifs_tcp_ses_lock);
+ list_add(&tcp_ses->tcp_ses_list, &cifs_tcp_ses_list);
+ spin_unlock(&cifs_tcp_ses_lock);
+ }
/* queue echo request delayed work */
queue_delayed_work(cifsiod_wq, &tcp_ses->echo, tcp_ses->echo_interval);