diff options
-rw-r--r-- | include/uapi/linux/if_tunnel.h | 1 | ||||
-rw-r--r-- | net/mpls/af_mpls.c | 36 |
2 files changed, 37 insertions, 0 deletions
diff --git a/include/uapi/linux/if_tunnel.h b/include/uapi/linux/if_tunnel.h index 2e520883c054..a2f48c01365e 100644 --- a/include/uapi/linux/if_tunnel.h +++ b/include/uapi/linux/if_tunnel.h | |||
@@ -84,6 +84,7 @@ enum tunnel_encap_types { | |||
84 | TUNNEL_ENCAP_NONE, | 84 | TUNNEL_ENCAP_NONE, |
85 | TUNNEL_ENCAP_FOU, | 85 | TUNNEL_ENCAP_FOU, |
86 | TUNNEL_ENCAP_GUE, | 86 | TUNNEL_ENCAP_GUE, |
87 | TUNNEL_ENCAP_MPLS, | ||
87 | }; | 88 | }; |
88 | 89 | ||
89 | #define TUNNEL_ENCAP_FLAG_CSUM (1<<0) | 90 | #define TUNNEL_ENCAP_FLAG_CSUM (1<<0) |
diff --git a/net/mpls/af_mpls.c b/net/mpls/af_mpls.c index c5b9ce41d66f..9745e8f69810 100644 --- a/net/mpls/af_mpls.c +++ b/net/mpls/af_mpls.c | |||
@@ -16,6 +16,7 @@ | |||
16 | #include <net/arp.h> | 16 | #include <net/arp.h> |
17 | #include <net/ip_fib.h> | 17 | #include <net/ip_fib.h> |
18 | #include <net/netevent.h> | 18 | #include <net/netevent.h> |
19 | #include <net/ip_tunnels.h> | ||
19 | #include <net/netns/generic.h> | 20 | #include <net/netns/generic.h> |
20 | #if IS_ENABLED(CONFIG_IPV6) | 21 | #if IS_ENABLED(CONFIG_IPV6) |
21 | #include <net/ipv6.h> | 22 | #include <net/ipv6.h> |
@@ -39,6 +40,36 @@ static int one = 1; | |||
39 | static int label_limit = (1 << 20) - 1; | 40 | static int label_limit = (1 << 20) - 1; |
40 | static int ttl_max = 255; | 41 | static int ttl_max = 255; |
41 | 42 | ||
43 | #if IS_ENABLED(CONFIG_NET_IP_TUNNEL) | ||
44 | size_t ipgre_mpls_encap_hlen(struct ip_tunnel_encap *e) | ||
45 | { | ||
46 | return sizeof(struct mpls_shim_hdr); | ||
47 | } | ||
48 | |||
49 | static const struct ip_tunnel_encap_ops mpls_iptun_ops = { | ||
50 | .encap_hlen = ipgre_mpls_encap_hlen, | ||
51 | }; | ||
52 | |||
53 | static int ipgre_tunnel_encap_add_mpls_ops(void) | ||
54 | { | ||
55 | return ip_tunnel_encap_add_ops(&mpls_iptun_ops, TUNNEL_ENCAP_MPLS); | ||
56 | } | ||
57 | |||
58 | static void ipgre_tunnel_encap_del_mpls_ops(void) | ||
59 | { | ||
60 | ip_tunnel_encap_del_ops(&mpls_iptun_ops, TUNNEL_ENCAP_MPLS); | ||
61 | } | ||
62 | #else | ||
63 | static int ipgre_tunnel_encap_add_mpls_ops(void) | ||
64 | { | ||
65 | return 0; | ||
66 | } | ||
67 | |||
68 | static void ipgre_tunnel_encap_del_mpls_ops(void) | ||
69 | { | ||
70 | } | ||
71 | #endif | ||
72 | |||
42 | static void rtmsg_lfib(int event, u32 label, struct mpls_route *rt, | 73 | static void rtmsg_lfib(int event, u32 label, struct mpls_route *rt, |
43 | struct nlmsghdr *nlh, struct net *net, u32 portid, | 74 | struct nlmsghdr *nlh, struct net *net, u32 portid, |
44 | unsigned int nlm_flags); | 75 | unsigned int nlm_flags); |
@@ -2485,6 +2516,10 @@ static int __init mpls_init(void) | |||
2485 | 0); | 2516 | 0); |
2486 | rtnl_register(PF_MPLS, RTM_GETNETCONF, mpls_netconf_get_devconf, | 2517 | rtnl_register(PF_MPLS, RTM_GETNETCONF, mpls_netconf_get_devconf, |
2487 | mpls_netconf_dump_devconf, 0); | 2518 | mpls_netconf_dump_devconf, 0); |
2519 | err = ipgre_tunnel_encap_add_mpls_ops(); | ||
2520 | if (err) | ||
2521 | pr_err("Can't add mpls over gre tunnel ops\n"); | ||
2522 | |||
2488 | err = 0; | 2523 | err = 0; |
2489 | out: | 2524 | out: |
2490 | return err; | 2525 | return err; |
@@ -2502,6 +2537,7 @@ static void __exit mpls_exit(void) | |||
2502 | dev_remove_pack(&mpls_packet_type); | 2537 | dev_remove_pack(&mpls_packet_type); |
2503 | unregister_netdevice_notifier(&mpls_dev_notifier); | 2538 | unregister_netdevice_notifier(&mpls_dev_notifier); |
2504 | unregister_pernet_subsys(&mpls_net_ops); | 2539 | unregister_pernet_subsys(&mpls_net_ops); |
2540 | ipgre_tunnel_encap_del_mpls_ops(); | ||
2505 | } | 2541 | } |
2506 | module_exit(mpls_exit); | 2542 | module_exit(mpls_exit); |
2507 | 2543 | ||