Message ID | 5db04a37335895e04e98bdf53aff3c8ecb6774db.1621189738.git.lucien.xin@gmail.com |
---|---|
State | New |
Headers | show |
Series | [net] tipc: wait and exit until all work queues are done | expand |
Hello: This patch was applied to netdev/net.git (refs/heads/master): On Mon, 17 May 2021 02:28:58 +0800 you wrote: > On some host, a crash could be triggered simply by repeating these > commands several times: > > # modprobe tipc > # tipc bearer enable media udp name UDP1 localip 127.0.0.1 > # rmmod tipc > > [...] Here is the summary with links: - [net] tipc: wait and exit until all work queues are done https://git.kernel.org/netdev/net/c/04c26faa51d1 You are awesome, thank you! -- Deet-doot-dot, I am a bot. https://korg.docs.kernel.org/patchwork/pwbot.html
diff --git a/net/tipc/core.c b/net/tipc/core.c index 5cc1f03..72f3ac7 100644 --- a/net/tipc/core.c +++ b/net/tipc/core.c @@ -119,6 +119,8 @@ static void __net_exit tipc_exit_net(struct net *net) #ifdef CONFIG_TIPC_CRYPTO tipc_crypto_stop(&tipc_net(net)->crypto_tx); #endif + while (atomic_read(&tn->wq_count)) + cond_resched(); } static void __net_exit tipc_pernet_pre_exit(struct net *net) diff --git a/net/tipc/core.h b/net/tipc/core.h index 03de7b2..5741ae4 100644 --- a/net/tipc/core.h +++ b/net/tipc/core.h @@ -149,6 +149,8 @@ struct tipc_net { #endif /* Work item for net finalize */ struct tipc_net_work final_work; + /* The numbers of work queues in schedule */ + atomic_t wq_count; }; static inline struct tipc_net *tipc_net(struct net *net) diff --git a/net/tipc/udp_media.c b/net/tipc/udp_media.c index e556d2c..c2bb818 100644 --- a/net/tipc/udp_media.c +++ b/net/tipc/udp_media.c @@ -814,6 +814,7 @@ static void cleanup_bearer(struct work_struct *work) kfree_rcu(rcast, rcu); } + atomic_dec(&tipc_net(sock_net(ub->ubsock->sk))->wq_count); dst_cache_destroy(&ub->rcast.dst_cache); udp_tunnel_sock_release(ub->ubsock); synchronize_net(); @@ -834,6 +835,7 @@ static void tipc_udp_disable(struct tipc_bearer *b) RCU_INIT_POINTER(ub->bearer, NULL); /* sock_release need to be done outside of rtnl lock */ + atomic_inc(&tipc_net(sock_net(ub->ubsock->sk))->wq_count); INIT_WORK(&ub->work, cleanup_bearer); schedule_work(&ub->work); }