@@ -248,7 +248,7 @@ int init_smb2_neg_rsp(struct ksmbd_work *work)
248248
249249 rsp = smb2_get_msg (work -> response_buf );
250250
251- WARN_ON (ksmbd_conn_good (work ));
251+ WARN_ON (ksmbd_conn_good (conn ));
252252
253253 rsp -> StructureSize = cpu_to_le16 (65 );
254254 ksmbd_debug (SMB , "conn->dialect 0x%x\n" , conn -> dialect );
@@ -277,7 +277,7 @@ int init_smb2_neg_rsp(struct ksmbd_work *work)
277277 rsp -> SecurityMode |= SMB2_NEGOTIATE_SIGNING_REQUIRED_LE ;
278278 conn -> use_spnego = true;
279279
280- ksmbd_conn_set_need_negotiate (work );
280+ ksmbd_conn_set_need_negotiate (conn );
281281 return 0 ;
282282}
283283
@@ -561,7 +561,7 @@ int smb2_check_user_session(struct ksmbd_work *work)
561561 cmd == SMB2_SESSION_SETUP_HE )
562562 return 0 ;
563563
564- if (!ksmbd_conn_good (work ))
564+ if (!ksmbd_conn_good (conn ))
565565 return - EINVAL ;
566566
567567 sess_id = le64_to_cpu (req_hdr -> SessionId );
@@ -594,7 +594,7 @@ static void destroy_previous_session(struct ksmbd_conn *conn,
594594
595595 prev_sess -> state = SMB2_SESSION_EXPIRED ;
596596 xa_for_each (& prev_sess -> ksmbd_chann_list , index , chann )
597- chann -> conn -> status = KSMBD_SESS_EXITING ;
597+ ksmbd_conn_set_exiting ( chann -> conn ) ;
598598}
599599
600600/**
@@ -1051,7 +1051,7 @@ int smb2_handle_negotiate(struct ksmbd_work *work)
10511051
10521052 ksmbd_debug (SMB , "Received negotiate request\n" );
10531053 conn -> need_neg = false;
1054- if (ksmbd_conn_good (work )) {
1054+ if (ksmbd_conn_good (conn )) {
10551055 pr_err ("conn->tcp_status is already in CifsGood State\n" );
10561056 work -> send_no_response = 1 ;
10571057 return rc ;
@@ -1205,7 +1205,7 @@ int smb2_handle_negotiate(struct ksmbd_work *work)
12051205 }
12061206
12071207 conn -> srv_sec_mode = le16_to_cpu (rsp -> SecurityMode );
1208- ksmbd_conn_set_need_negotiate (work );
1208+ ksmbd_conn_set_need_negotiate (conn );
12091209
12101210err_out :
12111211 if (rc < 0 )
@@ -1628,6 +1628,7 @@ int smb2_sess_setup(struct ksmbd_work *work)
16281628 rsp -> SecurityBufferLength = 0 ;
16291629 inc_rfc1001_len (work -> response_buf , 9 );
16301630
1631+ ksmbd_conn_lock (conn );
16311632 if (!req -> hdr .SessionId ) {
16321633 sess = ksmbd_smb2_session_create ();
16331634 if (!sess ) {
@@ -1675,6 +1676,12 @@ int smb2_sess_setup(struct ksmbd_work *work)
16751676 goto out_err ;
16761677 }
16771678
1679+ if (ksmbd_conn_need_reconnect (conn )) {
1680+ rc = - EFAULT ;
1681+ sess = NULL ;
1682+ goto out_err ;
1683+ }
1684+
16781685 if (ksmbd_session_lookup (conn , sess_id )) {
16791686 rc = - EACCES ;
16801687 goto out_err ;
@@ -1694,12 +1701,20 @@ int smb2_sess_setup(struct ksmbd_work *work)
16941701 rc = - ENOENT ;
16951702 goto out_err ;
16961703 }
1704+
1705+ if (sess -> state == SMB2_SESSION_EXPIRED ) {
1706+ rc = - EFAULT ;
1707+ goto out_err ;
1708+ }
1709+
1710+ if (ksmbd_conn_need_reconnect (conn )) {
1711+ rc = - EFAULT ;
1712+ sess = NULL ;
1713+ goto out_err ;
1714+ }
16971715 }
16981716 work -> sess = sess ;
16991717
1700- if (sess -> state == SMB2_SESSION_EXPIRED )
1701- sess -> state = SMB2_SESSION_IN_PROGRESS ;
1702-
17031718 negblob_off = le16_to_cpu (req -> SecurityBufferOffset );
17041719 negblob_len = le16_to_cpu (req -> SecurityBufferLength );
17051720 if (negblob_off < offsetof(struct smb2_sess_setup_req , Buffer ) ||
@@ -1729,8 +1744,10 @@ int smb2_sess_setup(struct ksmbd_work *work)
17291744 goto out_err ;
17301745 }
17311746
1732- ksmbd_conn_set_good (work );
1733- sess -> state = SMB2_SESSION_VALID ;
1747+ if (!ksmbd_conn_need_reconnect (conn )) {
1748+ ksmbd_conn_set_good (conn );
1749+ sess -> state = SMB2_SESSION_VALID ;
1750+ }
17341751 kfree (sess -> Preauth_HashValue );
17351752 sess -> Preauth_HashValue = NULL ;
17361753 } else if (conn -> preferred_auth_mech == KSMBD_AUTH_NTLMSSP ) {
@@ -1752,8 +1769,10 @@ int smb2_sess_setup(struct ksmbd_work *work)
17521769 if (rc )
17531770 goto out_err ;
17541771
1755- ksmbd_conn_set_good (work );
1756- sess -> state = SMB2_SESSION_VALID ;
1772+ if (!ksmbd_conn_need_reconnect (conn )) {
1773+ ksmbd_conn_set_good (conn );
1774+ sess -> state = SMB2_SESSION_VALID ;
1775+ }
17571776 if (conn -> binding ) {
17581777 struct preauth_session * preauth_sess ;
17591778
@@ -1819,14 +1838,13 @@ int smb2_sess_setup(struct ksmbd_work *work)
18191838 if (sess -> user && sess -> user -> flags & KSMBD_USER_FLAG_DELAY_SESSION )
18201839 try_delay = true;
18211840
1822- xa_erase (& conn -> sessions , sess -> id );
1823- ksmbd_session_destroy (sess );
1824- work -> sess = NULL ;
1841+ sess -> state = SMB2_SESSION_EXPIRED ;
18251842 if (try_delay )
18261843 ssleep (5 );
18271844 }
18281845 }
18291846
1847+ ksmbd_conn_unlock (conn );
18301848 return rc ;
18311849}
18321850
@@ -2050,21 +2068,24 @@ int smb2_session_logoff(struct ksmbd_work *work)
20502068{
20512069 struct ksmbd_conn * conn = work -> conn ;
20522070 struct smb2_logoff_rsp * rsp = smb2_get_msg (work -> response_buf );
2053- struct ksmbd_session * sess = work -> sess ;
2071+ struct ksmbd_session * sess ;
2072+ struct smb2_logoff_req * req = smb2_get_msg (work -> request_buf );
20542073
20552074 rsp -> StructureSize = cpu_to_le16 (4 );
20562075 inc_rfc1001_len (work -> response_buf , 4 );
20572076
20582077 ksmbd_debug (SMB , "request\n" );
20592078
2060- /* setting CifsExiting here may race with start_tcp_sess */
2061- ksmbd_conn_set_need_reconnect (work );
2079+ ksmbd_conn_set_need_reconnect (conn );
20622080 ksmbd_close_session_fds (work );
20632081 ksmbd_conn_wait_idle (conn );
20642082
2083+ /*
2084+ * Re-lookup session to validate if session is deleted
2085+ * while waiting request complete
2086+ */
2087+ sess = ksmbd_session_lookup (conn , le64_to_cpu (req -> hdr .SessionId ));
20652088 if (ksmbd_tree_conn_session_logoff (sess )) {
2066- struct smb2_logoff_req * req = smb2_get_msg (work -> request_buf );
2067-
20682089 ksmbd_debug (SMB , "Invalid tid %d\n" , req -> hdr .Id .SyncId .TreeId );
20692090 rsp -> hdr .Status = STATUS_NETWORK_NAME_DELETED ;
20702091 smb2_set_err_rsp (work );
@@ -2076,9 +2097,7 @@ int smb2_session_logoff(struct ksmbd_work *work)
20762097
20772098 ksmbd_free_user (sess -> user );
20782099 sess -> user = NULL ;
2079-
2080- /* let start_tcp_sess free connection info now */
2081- ksmbd_conn_set_need_negotiate (work );
2100+ ksmbd_conn_set_need_negotiate (conn );
20822101 return 0 ;
20832102}
20842103
0 commit comments