@@ -20,7 +20,7 @@ static DEFINE_MUTEX(init_lock);
2020static struct ksmbd_conn_ops default_conn_ops ;
2121
2222LIST_HEAD (conn_list );
23- DEFINE_RWLOCK (conn_list_lock );
23+ DECLARE_RWSEM (conn_list_lock );
2424
2525/**
2626 * ksmbd_conn_free() - free resources of the connection instance
@@ -32,9 +32,9 @@ DEFINE_RWLOCK(conn_list_lock);
3232 */
3333void ksmbd_conn_free (struct ksmbd_conn * conn )
3434{
35- write_lock (& conn_list_lock );
35+ down_write (& conn_list_lock );
3636 list_del (& conn -> conns_list );
37- write_unlock (& conn_list_lock );
37+ up_write (& conn_list_lock );
3838
3939 xa_destroy (& conn -> sessions );
4040 kvfree (conn -> request_buf );
@@ -84,9 +84,9 @@ struct ksmbd_conn *ksmbd_conn_alloc(void)
8484 spin_lock_init (& conn -> llist_lock );
8585 INIT_LIST_HEAD (& conn -> lock_list );
8686
87- write_lock (& conn_list_lock );
87+ down_write (& conn_list_lock );
8888 list_add (& conn -> conns_list , & conn_list );
89- write_unlock (& conn_list_lock );
89+ up_write (& conn_list_lock );
9090 return conn ;
9191}
9292
@@ -95,15 +95,15 @@ bool ksmbd_conn_lookup_dialect(struct ksmbd_conn *c)
9595 struct ksmbd_conn * t ;
9696 bool ret = false;
9797
98- read_lock (& conn_list_lock );
98+ down_read (& conn_list_lock );
9999 list_for_each_entry (t , & conn_list , conns_list ) {
100100 if (memcmp (t -> ClientGUID , c -> ClientGUID , SMB2_CLIENT_GUID_SIZE ))
101101 continue ;
102102
103103 ret = true;
104104 break ;
105105 }
106- read_unlock (& conn_list_lock );
106+ up_read (& conn_list_lock );
107107 return ret ;
108108}
109109
@@ -157,9 +157,37 @@ void ksmbd_conn_unlock(struct ksmbd_conn *conn)
157157 mutex_unlock (& conn -> srv_mutex );
158158}
159159
160- void ksmbd_conn_wait_idle ( struct ksmbd_conn * conn )
160+ void ksmbd_all_conn_set_status ( u64 sess_id , u32 status )
161161{
162+ struct ksmbd_conn * conn ;
163+
164+ down_read (& conn_list_lock );
165+ list_for_each_entry (conn , & conn_list , conns_list ) {
166+ if (conn -> binding || xa_load (& conn -> sessions , sess_id ))
167+ WRITE_ONCE (conn -> status , status );
168+ }
169+ up_read (& conn_list_lock );
170+ }
171+
172+ void ksmbd_conn_wait_idle (struct ksmbd_conn * conn , u64 sess_id )
173+ {
174+ struct ksmbd_conn * bind_conn ;
175+
162176 wait_event (conn -> req_running_q , atomic_read (& conn -> req_running ) < 2 );
177+
178+ down_read (& conn_list_lock );
179+ list_for_each_entry (bind_conn , & conn_list , conns_list ) {
180+ if (bind_conn == conn )
181+ continue ;
182+
183+ if ((bind_conn -> binding || xa_load (& bind_conn -> sessions , sess_id )) &&
184+ !ksmbd_conn_releasing (bind_conn ) &&
185+ atomic_read (& bind_conn -> req_running )) {
186+ wait_event (bind_conn -> req_running_q ,
187+ atomic_read (& bind_conn -> req_running ) == 0 );
188+ }
189+ }
190+ up_read (& conn_list_lock );
163191}
164192
165193int ksmbd_conn_write (struct ksmbd_work * work )
@@ -360,10 +388,10 @@ int ksmbd_conn_handler_loop(void *p)
360388 }
361389
362390out :
391+ ksmbd_conn_set_releasing (conn );
363392 /* Wait till all reference dropped to the Server object*/
364393 wait_event (conn -> r_count_q , atomic_read (& conn -> r_count ) == 0 );
365394
366-
367395 if (IS_ENABLED (CONFIG_UNICODE ))
368396 utf8_unload (conn -> um );
369397 unload_nls (conn -> local_nls );
@@ -407,7 +435,7 @@ static void stop_sessions(void)
407435 struct ksmbd_transport * t ;
408436
409437again :
410- read_lock (& conn_list_lock );
438+ down_read (& conn_list_lock );
411439 list_for_each_entry (conn , & conn_list , conns_list ) {
412440 struct task_struct * task ;
413441
@@ -418,12 +446,12 @@ static void stop_sessions(void)
418446 task -> comm , task_pid_nr (task ));
419447 ksmbd_conn_set_exiting (conn );
420448 if (t -> ops -> shutdown ) {
421- read_unlock (& conn_list_lock );
449+ up_read (& conn_list_lock );
422450 t -> ops -> shutdown (t );
423- read_lock (& conn_list_lock );
451+ down_read (& conn_list_lock );
424452 }
425453 }
426- read_unlock (& conn_list_lock );
454+ up_read (& conn_list_lock );
427455
428456 if (!list_empty (& conn_list )) {
429457 schedule_timeout_interruptible (HZ / 10 ); /* 100ms */
0 commit comments