@@ -101,6 +101,7 @@ struct l2tp_skb_cb {
101
101
102
102
static atomic_t l2tp_tunnel_count ;
103
103
static atomic_t l2tp_session_count ;
104
+ static struct workqueue_struct * l2tp_wq ;
104
105
105
106
/* per-net private data for this module */
106
107
static unsigned int l2tp_net_id ;
@@ -122,7 +123,6 @@ static inline struct l2tp_net *l2tp_pernet(struct net *net)
122
123
return net_generic (net , l2tp_net_id );
123
124
}
124
125
125
-
126
126
/* Tunnel reference counts. Incremented per session that is added to
127
127
* the tunnel.
128
128
*/
@@ -1277,16 +1277,16 @@ EXPORT_SYMBOL_GPL(l2tp_xmit_skb);
1277
1277
static void l2tp_tunnel_destruct (struct sock * sk )
1278
1278
{
1279
1279
struct l2tp_tunnel * tunnel ;
1280
+ struct l2tp_net * pn ;
1280
1281
1281
1282
tunnel = sk -> sk_user_data ;
1282
1283
if (tunnel == NULL )
1283
1284
goto end ;
1284
1285
1285
1286
l2tp_info (tunnel , L2TP_MSG_CONTROL , "%s: closing...\n" , tunnel -> name );
1286
1287
1287
- /* Close all sessions */
1288
- l2tp_tunnel_closeall (tunnel );
1289
1288
1289
+ /* Disable udp encapsulation */
1290
1290
switch (tunnel -> encap ) {
1291
1291
case L2TP_ENCAPTYPE_UDP :
1292
1292
/* No longer an encapsulation socket. See net/ipv4/udp.c */
@@ -1298,17 +1298,23 @@ static void l2tp_tunnel_destruct(struct sock *sk)
1298
1298
}
1299
1299
1300
1300
/* Remove hooks into tunnel socket */
1301
- tunnel -> sock = NULL ;
1302
1301
sk -> sk_destruct = tunnel -> old_sk_destruct ;
1303
1302
sk -> sk_user_data = NULL ;
1303
+ tunnel -> sock = NULL ;
1304
1304
1305
- /* Call the original destructor */
1306
- if (sk -> sk_destruct )
1307
- (* sk -> sk_destruct )(sk );
1305
+ /* Remove the tunnel struct from the tunnel list */
1306
+ pn = l2tp_pernet (tunnel -> l2tp_net );
1307
+ spin_lock_bh (& pn -> l2tp_tunnel_list_lock );
1308
+ list_del_rcu (& tunnel -> list );
1309
+ spin_unlock_bh (& pn -> l2tp_tunnel_list_lock );
1310
+ atomic_dec (& l2tp_tunnel_count );
1308
1311
1309
- /* We're finished with the socket */
1312
+ l2tp_tunnel_closeall ( tunnel );
1310
1313
l2tp_tunnel_dec_refcount (tunnel );
1311
1314
1315
+ /* Call the original destructor */
1316
+ if (sk -> sk_destruct )
1317
+ (* sk -> sk_destruct )(sk );
1312
1318
end :
1313
1319
return ;
1314
1320
}
@@ -1382,20 +1388,41 @@ static void l2tp_tunnel_closeall(struct l2tp_tunnel *tunnel)
1382
1388
*/
1383
1389
static void l2tp_tunnel_free (struct l2tp_tunnel * tunnel )
1384
1390
{
1385
- struct l2tp_net * pn = l2tp_pernet (tunnel -> l2tp_net );
1386
-
1387
1391
BUG_ON (atomic_read (& tunnel -> ref_count ) != 0 );
1388
1392
BUG_ON (tunnel -> sock != NULL );
1389
-
1390
1393
l2tp_info (tunnel , L2TP_MSG_CONTROL , "%s: free...\n" , tunnel -> name );
1391
-
1392
- /* Remove from tunnel list */
1393
- spin_lock_bh (& pn -> l2tp_tunnel_list_lock );
1394
- list_del_rcu (& tunnel -> list );
1395
1394
kfree_rcu (tunnel , rcu );
1396
- spin_unlock_bh ( & pn -> l2tp_tunnel_list_lock );
1395
+ }
1397
1396
1398
- atomic_dec (& l2tp_tunnel_count );
1397
+ /* Workqueue tunnel deletion function */
1398
+ static void l2tp_tunnel_del_work (struct work_struct * work )
1399
+ {
1400
+ struct l2tp_tunnel * tunnel = NULL ;
1401
+ struct socket * sock = NULL ;
1402
+ struct sock * sk = NULL ;
1403
+
1404
+ tunnel = container_of (work , struct l2tp_tunnel , del_work );
1405
+ sk = l2tp_tunnel_sock_lookup (tunnel );
1406
+ if (!sk )
1407
+ return ;
1408
+
1409
+ sock = sk -> sk_socket ;
1410
+ BUG_ON (!sock );
1411
+
1412
+ /* Force the tunnel socket to close. This will eventually
1413
+ * cause the tunnel to be deleted via the normal socket close
1414
+ * mechanisms when userspace closes the tunnel socket.
1415
+ */
1416
+ inet_shutdown (sock , 2 );
1417
+
1418
+ /* If the tunnel's socket was created by the kernel,
1419
+ * close the socket here since the socket was not
1420
+ * created by userspace.
1421
+ */
1422
+ if (sock -> file == NULL )
1423
+ inet_release (sock );
1424
+
1425
+ l2tp_tunnel_sock_put (sk );
1399
1426
}
1400
1427
1401
1428
/* Create a socket for the tunnel, if one isn't set up by
@@ -1657,6 +1684,9 @@ int l2tp_tunnel_create(struct net *net, int fd, int version, u32 tunnel_id, u32
1657
1684
1658
1685
sk -> sk_allocation = GFP_ATOMIC ;
1659
1686
1687
+ /* Init delete workqueue struct */
1688
+ INIT_WORK (& tunnel -> del_work , l2tp_tunnel_del_work );
1689
+
1660
1690
/* Add tunnel to our list */
1661
1691
INIT_LIST_HEAD (& tunnel -> list );
1662
1692
atomic_inc (& l2tp_tunnel_count );
@@ -1688,33 +1718,7 @@ EXPORT_SYMBOL_GPL(l2tp_tunnel_create);
1688
1718
*/
1689
1719
int l2tp_tunnel_delete (struct l2tp_tunnel * tunnel )
1690
1720
{
1691
- int err = - EBADF ;
1692
- struct socket * sock = NULL ;
1693
- struct sock * sk = NULL ;
1694
-
1695
- sk = l2tp_tunnel_sock_lookup (tunnel );
1696
- if (!sk )
1697
- goto out ;
1698
-
1699
- sock = sk -> sk_socket ;
1700
- BUG_ON (!sock );
1701
-
1702
- /* Force the tunnel socket to close. This will eventually
1703
- * cause the tunnel to be deleted via the normal socket close
1704
- * mechanisms when userspace closes the tunnel socket.
1705
- */
1706
- err = inet_shutdown (sock , 2 );
1707
-
1708
- /* If the tunnel's socket was created by the kernel,
1709
- * close the socket here since the socket was not
1710
- * created by userspace.
1711
- */
1712
- if (sock -> file == NULL )
1713
- err = inet_release (sock );
1714
-
1715
- l2tp_tunnel_sock_put (sk );
1716
- out :
1717
- return err ;
1721
+ return (false == queue_work (l2tp_wq , & tunnel -> del_work ));
1718
1722
}
1719
1723
EXPORT_SYMBOL_GPL (l2tp_tunnel_delete );
1720
1724
@@ -1912,6 +1916,13 @@ static int __init l2tp_init(void)
1912
1916
if (rc )
1913
1917
goto out ;
1914
1918
1919
+ l2tp_wq = alloc_workqueue ("l2tp" , WQ_NON_REENTRANT | WQ_UNBOUND , 0 );
1920
+ if (!l2tp_wq ) {
1921
+ pr_err ("alloc_workqueue failed\n" );
1922
+ rc = - ENOMEM ;
1923
+ goto out ;
1924
+ }
1925
+
1915
1926
pr_info ("L2TP core driver, %s\n" , L2TP_DRV_VERSION );
1916
1927
1917
1928
out :
@@ -1921,6 +1932,10 @@ static int __init l2tp_init(void)
1921
1932
static void __exit l2tp_exit (void )
1922
1933
{
1923
1934
unregister_pernet_device (& l2tp_net_ops );
1935
+ if (l2tp_wq ) {
1936
+ destroy_workqueue (l2tp_wq );
1937
+ l2tp_wq = NULL ;
1938
+ }
1924
1939
}
1925
1940
1926
1941
module_init (l2tp_init );
0 commit comments