Merge tag '6.3-rc4-smb3-client-fixes' of git://git.samba.org/sfrench/cifs-2.6

Pull cifs client fixes from Steve French:
"Four cifs/smb3 client (reconnect and DFS related) fixes, including two
for stable:

- DFS oops fix

- DFS reconnect recursion fix

- An SMB1 parallel reconnect fix

- Trivial dead code removal in smb2_reconnect"

* tag '6.3-rc4-smb3-client-fixes' of git://git.samba.org/sfrench/cifs-2.6:
cifs: get rid of dead check in smb2_reconnect()
cifs: prevent infinite recursion in CIFSGetDFSRefer()
cifs: avoid races in parallel reconnects in smb1
cifs: fix DFS traversal oops without CONFIG_CIFS_DFS_UPCALL

+26 -10
+4 -1
fs/cifs/cifsfs.h
··· 124 #ifdef CONFIG_CIFS_DFS_UPCALL 125 extern struct vfsmount *cifs_dfs_d_automount(struct path *path); 126 #else 127 - #define cifs_dfs_d_automount NULL 128 #endif 129 130 /* Functions related to symlinks */
··· 124 #ifdef CONFIG_CIFS_DFS_UPCALL 125 extern struct vfsmount *cifs_dfs_d_automount(struct path *path); 126 #else 127 + static inline struct vfsmount *cifs_dfs_d_automount(struct path *path) 128 + { 129 + return ERR_PTR(-EREMOTE); 130 + } 131 #endif 132 133 /* Functions related to symlinks */
+22 -8
fs/cifs/cifssmb.c
··· 71 int rc; 72 struct cifs_ses *ses; 73 struct TCP_Server_Info *server; 74 - struct nls_table *nls_codepage; 75 76 /* 77 * SMBs NegProt, SessSetup, uLogoff do not have tcon yet so check for ··· 99 } 100 spin_unlock(&tcon->tc_lock); 101 102 rc = cifs_wait_for_server_reconnect(server, tcon->retry); 103 if (rc) 104 return rc; ··· 111 } 112 spin_unlock(&ses->chan_lock); 113 114 - nls_codepage = load_nls_default(); 115 - 116 /* 117 * Recheck after acquire mutex. If another thread is negotiating 118 * and the server never sends an answer the socket will be closed ··· 120 spin_lock(&server->srv_lock); 121 if (server->tcpStatus == CifsNeedReconnect) { 122 spin_unlock(&server->srv_lock); 123 rc = -EHOSTDOWN; 124 goto out; 125 } 126 spin_unlock(&server->srv_lock); 127 128 /* 129 * need to prevent multiple threads trying to simultaneously 130 * reconnect the same SMB session 131 */ 132 spin_lock(&ses->chan_lock); 133 - if (!cifs_chan_needs_reconnect(ses, server)) { 134 spin_unlock(&ses->chan_lock); 135 136 /* this means that we only need to tree connect */ 137 if (tcon->need_reconnect) 138 goto skip_sess_setup; 139 140 - rc = -EHOSTDOWN; 141 goto out; 142 } 143 spin_unlock(&ses->chan_lock); 144 145 - mutex_lock(&ses->session_mutex); 146 rc = cifs_negotiate_protocol(0, ses, server); 147 if (!rc) 148 rc = cifs_setup_session(0, ses, server, nls_codepage); ··· 4382 return -ENODEV; 4383 4384 getDFSRetry: 4385 - rc = smb_init(SMB_COM_TRANSACTION2, 15, ses->tcon_ipc, (void **) &pSMB, 4386 - (void **) &pSMBr); 4387 if (rc) 4388 return rc; 4389
··· 71 int rc; 72 struct cifs_ses *ses; 73 struct TCP_Server_Info *server; 74 + struct nls_table *nls_codepage = NULL; 75 76 /* 77 * SMBs NegProt, SessSetup, uLogoff do not have tcon yet so check for ··· 99 } 100 spin_unlock(&tcon->tc_lock); 101 102 + again: 103 rc = cifs_wait_for_server_reconnect(server, tcon->retry); 104 if (rc) 105 return rc; ··· 110 } 111 spin_unlock(&ses->chan_lock); 112 113 + mutex_lock(&ses->session_mutex); 114 /* 115 * Recheck after acquire mutex. If another thread is negotiating 116 * and the server never sends an answer the socket will be closed ··· 120 spin_lock(&server->srv_lock); 121 if (server->tcpStatus == CifsNeedReconnect) { 122 spin_unlock(&server->srv_lock); 123 + mutex_lock(&ses->session_mutex); 124 + 125 + if (tcon->retry) 126 + goto again; 127 rc = -EHOSTDOWN; 128 goto out; 129 } 130 spin_unlock(&server->srv_lock); 131 132 + nls_codepage = load_nls_default(); 133 + 134 /* 135 * need to prevent multiple threads trying to simultaneously 136 * reconnect the same SMB session 137 */ 138 + spin_lock(&ses->ses_lock); 139 spin_lock(&ses->chan_lock); 140 + if (!cifs_chan_needs_reconnect(ses, server) && 141 + ses->ses_status == SES_GOOD) { 142 spin_unlock(&ses->chan_lock); 143 + spin_unlock(&ses->ses_lock); 144 145 /* this means that we only need to tree connect */ 146 if (tcon->need_reconnect) 147 goto skip_sess_setup; 148 149 + mutex_unlock(&ses->session_mutex); 150 goto out; 151 } 152 spin_unlock(&ses->chan_lock); 153 + spin_unlock(&ses->ses_lock); 154 155 rc = cifs_negotiate_protocol(0, ses, server); 156 if (!rc) 157 rc = cifs_setup_session(0, ses, server, nls_codepage); ··· 4373 return -ENODEV; 4374 4375 getDFSRetry: 4376 + /* 4377 + * Use smb_init_no_reconnect() instead of smb_init() as 4378 + * CIFSGetDFSRefer() may be called from cifs_reconnect_tcon() and thus 4379 + * causing an infinite recursion. 4380 + */ 4381 + rc = smb_init_no_reconnect(SMB_COM_TRANSACTION2, 15, ses->tcon_ipc, 4382 + (void **)&pSMB, (void **)&pSMBr); 4383 if (rc) 4384 return rc; 4385
-1
fs/cifs/smb2pdu.c
··· 310 case SMB2_READ: 311 case SMB2_WRITE: 312 case SMB2_LOCK: 313 - case SMB2_IOCTL: 314 case SMB2_QUERY_DIRECTORY: 315 case SMB2_CHANGE_NOTIFY: 316 case SMB2_QUERY_INFO:
··· 310 case SMB2_READ: 311 case SMB2_WRITE: 312 case SMB2_LOCK: 313 case SMB2_QUERY_DIRECTORY: 314 case SMB2_CHANGE_NOTIFY: 315 case SMB2_QUERY_INFO: