aboutsummaryrefslogtreecommitdiffstats
path: root/net/l2tp
diff options
context:
space:
mode:
authorJames Chapman <jchapman@katalix.com>2012-04-29 17:48:55 -0400
committerDavid S. Miller <davem@davemloft.net>2012-05-01 09:30:55 -0400
commit5dac94e109263e75ab7fe4e66ef88e9b49f500bf (patch)
treed87a313b3078911e612e7b18d99853be282b7700 /net/l2tp
parenta32e0eec7042b21ccb52896cf715e3e2641fed93 (diff)
l2tp: let iproute2 create L2TPv3 IP tunnels using IPv6
The netlink API lets users create unmanaged L2TPv3 tunnels using iproute2. Until now, a request to create an unmanaged L2TPv3 IP encapsulation tunnel over IPv6 would be rejected with EPROTONOSUPPORT. Now that l2tp_ip6 implements sockets for L2TP IP encapsulation over IPv6, we can add support for that tunnel type. Signed-off-by: James Chapman <jchapman@katalix.com> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'net/l2tp')
-rw-r--r--net/l2tp/l2tp_core.c72
1 files changed, 50 insertions, 22 deletions
diff --git a/net/l2tp/l2tp_core.c b/net/l2tp/l2tp_core.c
index 55fc569c8170..456b52d8f6d8 100644
--- a/net/l2tp/l2tp_core.c
+++ b/net/l2tp/l2tp_core.c
@@ -1368,6 +1368,7 @@ static int l2tp_tunnel_sock_create(u32 tunnel_id, u32 peer_tunnel_id, struct l2t
1368 struct sockaddr_in udp_addr; 1368 struct sockaddr_in udp_addr;
1369#if IS_ENABLED(CONFIG_IPV6) 1369#if IS_ENABLED(CONFIG_IPV6)
1370 struct sockaddr_in6 udp6_addr; 1370 struct sockaddr_in6 udp6_addr;
1371 struct sockaddr_l2tpip6 ip6_addr;
1371#endif 1372#endif
1372 struct sockaddr_l2tpip ip_addr; 1373 struct sockaddr_l2tpip ip_addr;
1373 struct socket *sock = NULL; 1374 struct socket *sock = NULL;
@@ -1437,32 +1438,59 @@ static int l2tp_tunnel_sock_create(u32 tunnel_id, u32 peer_tunnel_id, struct l2t
1437 case L2TP_ENCAPTYPE_IP: 1438 case L2TP_ENCAPTYPE_IP:
1438#if IS_ENABLED(CONFIG_IPV6) 1439#if IS_ENABLED(CONFIG_IPV6)
1439 if (cfg->local_ip6 && cfg->peer_ip6) { 1440 if (cfg->local_ip6 && cfg->peer_ip6) {
1440 /* IP encap over IPv6 not yet supported */ 1441 err = sock_create(AF_INET6, SOCK_DGRAM, IPPROTO_L2TP,
1441 err = -EPROTONOSUPPORT; 1442 sockp);
1442 goto out; 1443 if (err < 0)
1443 } 1444 goto out;
1444#endif
1445 err = sock_create(AF_INET, SOCK_DGRAM, IPPROTO_L2TP, sockp);
1446 if (err < 0)
1447 goto out;
1448 1445
1449 sock = *sockp; 1446 sock = *sockp;
1450 1447
1451 memset(&ip_addr, 0, sizeof(ip_addr)); 1448 memset(&ip6_addr, 0, sizeof(ip6_addr));
1452 ip_addr.l2tp_family = AF_INET; 1449 ip6_addr.l2tp_family = AF_INET6;
1453 ip_addr.l2tp_addr = cfg->local_ip; 1450 memcpy(&ip6_addr.l2tp_addr, cfg->local_ip6,
1454 ip_addr.l2tp_conn_id = tunnel_id; 1451 sizeof(ip6_addr.l2tp_addr));
1455 err = kernel_bind(sock, (struct sockaddr *) &ip_addr, sizeof(ip_addr)); 1452 ip6_addr.l2tp_conn_id = tunnel_id;
1456 if (err < 0) 1453 err = kernel_bind(sock, (struct sockaddr *) &ip6_addr,
1457 goto out; 1454 sizeof(ip6_addr));
1455 if (err < 0)
1456 goto out;
1458 1457
1459 ip_addr.l2tp_family = AF_INET; 1458 ip6_addr.l2tp_family = AF_INET6;
1460 ip_addr.l2tp_addr = cfg->peer_ip; 1459 memcpy(&ip6_addr.l2tp_addr, cfg->peer_ip6,
1461 ip_addr.l2tp_conn_id = peer_tunnel_id; 1460 sizeof(ip6_addr.l2tp_addr));
1462 err = kernel_connect(sock, (struct sockaddr *) &ip_addr, sizeof(ip_addr), 0); 1461 ip6_addr.l2tp_conn_id = peer_tunnel_id;
1463 if (err < 0) 1462 err = kernel_connect(sock,
1464 goto out; 1463 (struct sockaddr *) &ip6_addr,
1464 sizeof(ip6_addr), 0);
1465 if (err < 0)
1466 goto out;
1467 } else
1468#endif
1469 {
1470 err = sock_create(AF_INET, SOCK_DGRAM, IPPROTO_L2TP,
1471 sockp);
1472 if (err < 0)
1473 goto out;
1465 1474
1475 sock = *sockp;
1476
1477 memset(&ip_addr, 0, sizeof(ip_addr));
1478 ip_addr.l2tp_family = AF_INET;
1479 ip_addr.l2tp_addr = cfg->local_ip;
1480 ip_addr.l2tp_conn_id = tunnel_id;
1481 err = kernel_bind(sock, (struct sockaddr *) &ip_addr,
1482 sizeof(ip_addr));
1483 if (err < 0)
1484 goto out;
1485
1486 ip_addr.l2tp_family = AF_INET;
1487 ip_addr.l2tp_addr = cfg->peer_ip;
1488 ip_addr.l2tp_conn_id = peer_tunnel_id;
1489 err = kernel_connect(sock, (struct sockaddr *) &ip_addr,
1490 sizeof(ip_addr), 0);
1491 if (err < 0)
1492 goto out;
1493 }
1466 break; 1494 break;
1467 1495
1468 default: 1496 default: