hc
2024-02-20 102a0743326a03cd1a1202ceda21e175b7d3575c
kernel/fs/nfsd/nfssvc.c
....@@ -426,8 +426,8 @@
426426 {
427427 struct nfsd_net *nn = net_generic(net, nfsd_net_id);
428428
429
- nfsd_file_cache_shutdown_net(net);
430429 nfs4_state_shutdown_net(net);
430
+ nfsd_file_cache_shutdown_net(net);
431431 if (nn->lockd_up) {
432432 lockd_down(net);
433433 nn->lockd_up = false;
....@@ -600,6 +600,37 @@
600600 .svo_module = THIS_MODULE,
601601 };
602602
603
+static void nfsd_complete_shutdown(struct net *net)
604
+{
605
+ struct nfsd_net *nn = net_generic(net, nfsd_net_id);
606
+
607
+ WARN_ON(!mutex_is_locked(&nfsd_mutex));
608
+
609
+ nn->nfsd_serv = NULL;
610
+ complete(&nn->nfsd_shutdown_complete);
611
+}
612
+
613
+void nfsd_shutdown_threads(struct net *net)
614
+{
615
+ struct nfsd_net *nn = net_generic(net, nfsd_net_id);
616
+ struct svc_serv *serv;
617
+
618
+ mutex_lock(&nfsd_mutex);
619
+ serv = nn->nfsd_serv;
620
+ if (serv == NULL) {
621
+ mutex_unlock(&nfsd_mutex);
622
+ return;
623
+ }
624
+
625
+ svc_get(serv);
626
+ /* Kill outstanding nfsd threads */
627
+ serv->sv_ops->svo_setup(serv, NULL, 0);
628
+ nfsd_destroy(net);
629
+ mutex_unlock(&nfsd_mutex);
630
+ /* Wait for shutdown of nfsd_serv to complete */
631
+ wait_for_completion(&nn->nfsd_shutdown_complete);
632
+}
633
+
603634 bool i_am_nfsd(void)
604635 {
605636 return kthread_func(current) == nfsd;
....@@ -622,11 +653,13 @@
622653 &nfsd_thread_sv_ops);
623654 if (nn->nfsd_serv == NULL)
624655 return -ENOMEM;
656
+ init_completion(&nn->nfsd_shutdown_complete);
625657
626658 nn->nfsd_serv->sv_maxconn = nn->max_connections;
627659 error = svc_bind(nn->nfsd_serv, net);
628660 if (error < 0) {
629661 svc_destroy(nn->nfsd_serv);
662
+ nfsd_complete_shutdown(net);
630663 return error;
631664 }
632665
....@@ -675,7 +708,7 @@
675708 svc_shutdown_net(nn->nfsd_serv, net);
676709 svc_destroy(nn->nfsd_serv);
677710 if (destroy)
678
- nn->nfsd_serv = NULL;
711
+ nfsd_complete_shutdown(net);
679712 }
680713
681714 int nfsd_set_nrthreads(int n, int *nthreads, struct net *net)