aboutsummaryrefslogtreecommitdiffstats
path: root/net/ipv4/ip_gre.c
diff options
context:
space:
mode:
authorAndrea Bastoni <bastoni@cs.unc.edu>2010-05-30 19:16:45 -0400
committerAndrea Bastoni <bastoni@cs.unc.edu>2010-05-30 19:16:45 -0400
commitada47b5fe13d89735805b566185f4885f5a3f750 (patch)
tree644b88f8a71896307d71438e9b3af49126ffb22b /net/ipv4/ip_gre.c
parent43e98717ad40a4ae64545b5ba047c7b86aa44f4f (diff)
parent3280f21d43ee541f97f8cda5792150d2dbec20d5 (diff)
Merge branch 'wip-2.6.34' into old-private-masterarchived-private-master
Diffstat (limited to 'net/ipv4/ip_gre.c')
-rw-r--r--net/ipv4/ip_gre.c119
1 files changed, 60 insertions, 59 deletions
diff --git a/net/ipv4/ip_gre.c b/net/ipv4/ip_gre.c
index 143333852624..fe381d12ecdd 100644
--- a/net/ipv4/ip_gre.c
+++ b/net/ipv4/ip_gre.c
@@ -14,6 +14,7 @@
14#include <linux/module.h> 14#include <linux/module.h>
15#include <linux/types.h> 15#include <linux/types.h>
16#include <linux/kernel.h> 16#include <linux/kernel.h>
17#include <linux/slab.h>
17#include <asm/uaccess.h> 18#include <asm/uaccess.h>
18#include <linux/skbuff.h> 19#include <linux/skbuff.h>
19#include <linux/netdevice.h> 20#include <linux/netdevice.h>
@@ -125,7 +126,7 @@ static int ipgre_tunnel_bind_dev(struct net_device *dev);
125 126
126#define HASH_SIZE 16 127#define HASH_SIZE 16
127 128
128static int ipgre_net_id; 129static int ipgre_net_id __read_mostly;
129struct ipgre_net { 130struct ipgre_net {
130 struct ip_tunnel *tunnels[4][HASH_SIZE]; 131 struct ip_tunnel *tunnels[4][HASH_SIZE];
131 132
@@ -156,8 +157,13 @@ struct ipgre_net {
156#define tunnels_r tunnels[2] 157#define tunnels_r tunnels[2]
157#define tunnels_l tunnels[1] 158#define tunnels_l tunnels[1]
158#define tunnels_wc tunnels[0] 159#define tunnels_wc tunnels[0]
160/*
161 * Locking : hash tables are protected by RCU and a spinlock
162 */
163static DEFINE_SPINLOCK(ipgre_lock);
159 164
160static DEFINE_RWLOCK(ipgre_lock); 165#define for_each_ip_tunnel_rcu(start) \
166 for (t = rcu_dereference(start); t; t = rcu_dereference(t->next))
161 167
162/* Given src, dst and key, find appropriate for input tunnel. */ 168/* Given src, dst and key, find appropriate for input tunnel. */
163 169
@@ -175,7 +181,7 @@ static struct ip_tunnel * ipgre_tunnel_lookup(struct net_device *dev,
175 ARPHRD_ETHER : ARPHRD_IPGRE; 181 ARPHRD_ETHER : ARPHRD_IPGRE;
176 int score, cand_score = 4; 182 int score, cand_score = 4;
177 183
178 for (t = ign->tunnels_r_l[h0^h1]; t; t = t->next) { 184 for_each_ip_tunnel_rcu(ign->tunnels_r_l[h0 ^ h1]) {
179 if (local != t->parms.iph.saddr || 185 if (local != t->parms.iph.saddr ||
180 remote != t->parms.iph.daddr || 186 remote != t->parms.iph.daddr ||
181 key != t->parms.i_key || 187 key != t->parms.i_key ||
@@ -200,7 +206,7 @@ static struct ip_tunnel * ipgre_tunnel_lookup(struct net_device *dev,
200 } 206 }
201 } 207 }
202 208
203 for (t = ign->tunnels_r[h0^h1]; t; t = t->next) { 209 for_each_ip_tunnel_rcu(ign->tunnels_r[h0 ^ h1]) {
204 if (remote != t->parms.iph.daddr || 210 if (remote != t->parms.iph.daddr ||
205 key != t->parms.i_key || 211 key != t->parms.i_key ||
206 !(t->dev->flags & IFF_UP)) 212 !(t->dev->flags & IFF_UP))
@@ -224,7 +230,7 @@ static struct ip_tunnel * ipgre_tunnel_lookup(struct net_device *dev,
224 } 230 }
225 } 231 }
226 232
227 for (t = ign->tunnels_l[h1]; t; t = t->next) { 233 for_each_ip_tunnel_rcu(ign->tunnels_l[h1]) {
228 if ((local != t->parms.iph.saddr && 234 if ((local != t->parms.iph.saddr &&
229 (local != t->parms.iph.daddr || 235 (local != t->parms.iph.daddr ||
230 !ipv4_is_multicast(local))) || 236 !ipv4_is_multicast(local))) ||
@@ -250,7 +256,7 @@ static struct ip_tunnel * ipgre_tunnel_lookup(struct net_device *dev,
250 } 256 }
251 } 257 }
252 258
253 for (t = ign->tunnels_wc[h1]; t; t = t->next) { 259 for_each_ip_tunnel_rcu(ign->tunnels_wc[h1]) {
254 if (t->parms.i_key != key || 260 if (t->parms.i_key != key ||
255 !(t->dev->flags & IFF_UP)) 261 !(t->dev->flags & IFF_UP))
256 continue; 262 continue;
@@ -276,8 +282,9 @@ static struct ip_tunnel * ipgre_tunnel_lookup(struct net_device *dev,
276 if (cand != NULL) 282 if (cand != NULL)
277 return cand; 283 return cand;
278 284
279 if (ign->fb_tunnel_dev->flags & IFF_UP) 285 dev = ign->fb_tunnel_dev;
280 return netdev_priv(ign->fb_tunnel_dev); 286 if (dev->flags & IFF_UP)
287 return netdev_priv(dev);
281 288
282 return NULL; 289 return NULL;
283} 290}
@@ -311,10 +318,10 @@ static void ipgre_tunnel_link(struct ipgre_net *ign, struct ip_tunnel *t)
311{ 318{
312 struct ip_tunnel **tp = ipgre_bucket(ign, t); 319 struct ip_tunnel **tp = ipgre_bucket(ign, t);
313 320
321 spin_lock_bh(&ipgre_lock);
314 t->next = *tp; 322 t->next = *tp;
315 write_lock_bh(&ipgre_lock); 323 rcu_assign_pointer(*tp, t);
316 *tp = t; 324 spin_unlock_bh(&ipgre_lock);
317 write_unlock_bh(&ipgre_lock);
318} 325}
319 326
320static void ipgre_tunnel_unlink(struct ipgre_net *ign, struct ip_tunnel *t) 327static void ipgre_tunnel_unlink(struct ipgre_net *ign, struct ip_tunnel *t)
@@ -323,9 +330,9 @@ static void ipgre_tunnel_unlink(struct ipgre_net *ign, struct ip_tunnel *t)
323 330
324 for (tp = ipgre_bucket(ign, t); *tp; tp = &(*tp)->next) { 331 for (tp = ipgre_bucket(ign, t); *tp; tp = &(*tp)->next) {
325 if (t == *tp) { 332 if (t == *tp) {
326 write_lock_bh(&ipgre_lock); 333 spin_lock_bh(&ipgre_lock);
327 *tp = t->next; 334 *tp = t->next;
328 write_unlock_bh(&ipgre_lock); 335 spin_unlock_bh(&ipgre_lock);
329 break; 336 break;
330 } 337 }
331 } 338 }
@@ -476,7 +483,7 @@ static void ipgre_err(struct sk_buff *skb, u32 info)
476 break; 483 break;
477 } 484 }
478 485
479 read_lock(&ipgre_lock); 486 rcu_read_lock();
480 t = ipgre_tunnel_lookup(skb->dev, iph->daddr, iph->saddr, 487 t = ipgre_tunnel_lookup(skb->dev, iph->daddr, iph->saddr,
481 flags & GRE_KEY ? 488 flags & GRE_KEY ?
482 *(((__be32 *)p) + (grehlen / 4) - 1) : 0, 489 *(((__be32 *)p) + (grehlen / 4) - 1) : 0,
@@ -494,7 +501,7 @@ static void ipgre_err(struct sk_buff *skb, u32 info)
494 t->err_count = 1; 501 t->err_count = 1;
495 t->err_time = jiffies; 502 t->err_time = jiffies;
496out: 503out:
497 read_unlock(&ipgre_lock); 504 rcu_read_unlock();
498 return; 505 return;
499} 506}
500 507
@@ -573,7 +580,7 @@ static int ipgre_rcv(struct sk_buff *skb)
573 580
574 gre_proto = *(__be16 *)(h + 2); 581 gre_proto = *(__be16 *)(h + 2);
575 582
576 read_lock(&ipgre_lock); 583 rcu_read_lock();
577 if ((tunnel = ipgre_tunnel_lookup(skb->dev, 584 if ((tunnel = ipgre_tunnel_lookup(skb->dev,
578 iph->saddr, iph->daddr, key, 585 iph->saddr, iph->daddr, key,
579 gre_proto))) { 586 gre_proto))) {
@@ -647,13 +654,13 @@ static int ipgre_rcv(struct sk_buff *skb)
647 ipgre_ecn_decapsulate(iph, skb); 654 ipgre_ecn_decapsulate(iph, skb);
648 655
649 netif_rx(skb); 656 netif_rx(skb);
650 read_unlock(&ipgre_lock); 657 rcu_read_unlock();
651 return(0); 658 return(0);
652 } 659 }
653 icmp_send(skb, ICMP_DEST_UNREACH, ICMP_PORT_UNREACH, 0); 660 icmp_send(skb, ICMP_DEST_UNREACH, ICMP_PORT_UNREACH, 0);
654 661
655drop: 662drop:
656 read_unlock(&ipgre_lock); 663 rcu_read_unlock();
657drop_nolock: 664drop_nolock:
658 kfree_skb(skb); 665 kfree_skb(skb);
659 return(0); 666 return(0);
@@ -662,7 +669,8 @@ drop_nolock:
662static netdev_tx_t ipgre_tunnel_xmit(struct sk_buff *skb, struct net_device *dev) 669static netdev_tx_t ipgre_tunnel_xmit(struct sk_buff *skb, struct net_device *dev)
663{ 670{
664 struct ip_tunnel *tunnel = netdev_priv(dev); 671 struct ip_tunnel *tunnel = netdev_priv(dev);
665 struct net_device_stats *stats = &tunnel->dev->stats; 672 struct net_device_stats *stats = &dev->stats;
673 struct netdev_queue *txq = netdev_get_tx_queue(dev, 0);
666 struct iphdr *old_iph = ip_hdr(skb); 674 struct iphdr *old_iph = ip_hdr(skb);
667 struct iphdr *tiph; 675 struct iphdr *tiph;
668 u8 tos; 676 u8 tos;
@@ -786,7 +794,7 @@ static netdev_tx_t ipgre_tunnel_xmit(struct sk_buff *skb, struct net_device *dev
786 } 794 }
787 795
788 if (mtu >= IPV6_MIN_MTU && mtu < skb->len - tunnel->hlen + gre_hlen) { 796 if (mtu >= IPV6_MIN_MTU && mtu < skb->len - tunnel->hlen + gre_hlen) {
789 icmpv6_send(skb, ICMPV6_PKT_TOOBIG, 0, mtu, dev); 797 icmpv6_send(skb, ICMPV6_PKT_TOOBIG, 0, mtu);
790 ip_rt_put(rt); 798 ip_rt_put(rt);
791 goto tx_error; 799 goto tx_error;
792 } 800 }
@@ -803,14 +811,16 @@ static netdev_tx_t ipgre_tunnel_xmit(struct sk_buff *skb, struct net_device *dev
803 tunnel->err_count = 0; 811 tunnel->err_count = 0;
804 } 812 }
805 813
806 max_headroom = LL_RESERVED_SPACE(tdev) + gre_hlen; 814 max_headroom = LL_RESERVED_SPACE(tdev) + gre_hlen + rt->u.dst.header_len;
807 815
808 if (skb_headroom(skb) < max_headroom || skb_shared(skb)|| 816 if (skb_headroom(skb) < max_headroom || skb_shared(skb)||
809 (skb_cloned(skb) && !skb_clone_writable(skb, 0))) { 817 (skb_cloned(skb) && !skb_clone_writable(skb, 0))) {
810 struct sk_buff *new_skb = skb_realloc_headroom(skb, max_headroom); 818 struct sk_buff *new_skb = skb_realloc_headroom(skb, max_headroom);
819 if (max_headroom > dev->needed_headroom)
820 dev->needed_headroom = max_headroom;
811 if (!new_skb) { 821 if (!new_skb) {
812 ip_rt_put(rt); 822 ip_rt_put(rt);
813 stats->tx_dropped++; 823 txq->tx_dropped++;
814 dev_kfree_skb(skb); 824 dev_kfree_skb(skb);
815 return NETDEV_TX_OK; 825 return NETDEV_TX_OK;
816 } 826 }
@@ -1137,12 +1147,9 @@ static int ipgre_header(struct sk_buff *skb, struct net_device *dev,
1137 1147
1138 if (saddr) 1148 if (saddr)
1139 memcpy(&iph->saddr, saddr, 4); 1149 memcpy(&iph->saddr, saddr, 4);
1140 1150 if (daddr)
1141 if (daddr) {
1142 memcpy(&iph->daddr, daddr, 4); 1151 memcpy(&iph->daddr, daddr, 4);
1143 return t->hlen; 1152 if (iph->daddr)
1144 }
1145 if (iph->daddr && !ipv4_is_multicast(iph->daddr))
1146 return t->hlen; 1153 return t->hlen;
1147 1154
1148 return -t->hlen; 1155 return -t->hlen;
@@ -1283,33 +1290,27 @@ static const struct net_protocol ipgre_protocol = {
1283 .netns_ok = 1, 1290 .netns_ok = 1,
1284}; 1291};
1285 1292
1286static void ipgre_destroy_tunnels(struct ipgre_net *ign) 1293static void ipgre_destroy_tunnels(struct ipgre_net *ign, struct list_head *head)
1287{ 1294{
1288 int prio; 1295 int prio;
1289 1296
1290 for (prio = 0; prio < 4; prio++) { 1297 for (prio = 0; prio < 4; prio++) {
1291 int h; 1298 int h;
1292 for (h = 0; h < HASH_SIZE; h++) { 1299 for (h = 0; h < HASH_SIZE; h++) {
1293 struct ip_tunnel *t; 1300 struct ip_tunnel *t = ign->tunnels[prio][h];
1294 while ((t = ign->tunnels[prio][h]) != NULL) 1301
1295 unregister_netdevice(t->dev); 1302 while (t != NULL) {
1303 unregister_netdevice_queue(t->dev, head);
1304 t = t->next;
1305 }
1296 } 1306 }
1297 } 1307 }
1298} 1308}
1299 1309
1300static int ipgre_init_net(struct net *net) 1310static int __net_init ipgre_init_net(struct net *net)
1301{ 1311{
1312 struct ipgre_net *ign = net_generic(net, ipgre_net_id);
1302 int err; 1313 int err;
1303 struct ipgre_net *ign;
1304
1305 err = -ENOMEM;
1306 ign = kzalloc(sizeof(struct ipgre_net), GFP_KERNEL);
1307 if (ign == NULL)
1308 goto err_alloc;
1309
1310 err = net_assign_generic(net, ipgre_net_id, ign);
1311 if (err < 0)
1312 goto err_assign;
1313 1314
1314 ign->fb_tunnel_dev = alloc_netdev(sizeof(struct ip_tunnel), "gre0", 1315 ign->fb_tunnel_dev = alloc_netdev(sizeof(struct ip_tunnel), "gre0",
1315 ipgre_tunnel_setup); 1316 ipgre_tunnel_setup);
@@ -1330,27 +1331,26 @@ static int ipgre_init_net(struct net *net)
1330err_reg_dev: 1331err_reg_dev:
1331 free_netdev(ign->fb_tunnel_dev); 1332 free_netdev(ign->fb_tunnel_dev);
1332err_alloc_dev: 1333err_alloc_dev:
1333 /* nothing */
1334err_assign:
1335 kfree(ign);
1336err_alloc:
1337 return err; 1334 return err;
1338} 1335}
1339 1336
1340static void ipgre_exit_net(struct net *net) 1337static void __net_exit ipgre_exit_net(struct net *net)
1341{ 1338{
1342 struct ipgre_net *ign; 1339 struct ipgre_net *ign;
1340 LIST_HEAD(list);
1343 1341
1344 ign = net_generic(net, ipgre_net_id); 1342 ign = net_generic(net, ipgre_net_id);
1345 rtnl_lock(); 1343 rtnl_lock();
1346 ipgre_destroy_tunnels(ign); 1344 ipgre_destroy_tunnels(ign, &list);
1345 unregister_netdevice_many(&list);
1347 rtnl_unlock(); 1346 rtnl_unlock();
1348 kfree(ign);
1349} 1347}
1350 1348
1351static struct pernet_operations ipgre_net_ops = { 1349static struct pernet_operations ipgre_net_ops = {
1352 .init = ipgre_init_net, 1350 .init = ipgre_init_net,
1353 .exit = ipgre_exit_net, 1351 .exit = ipgre_exit_net,
1352 .id = &ipgre_net_id,
1353 .size = sizeof(struct ipgre_net),
1354}; 1354};
1355 1355
1356static int ipgre_tunnel_validate(struct nlattr *tb[], struct nlattr *data[]) 1356static int ipgre_tunnel_validate(struct nlattr *tb[], struct nlattr *data[])
@@ -1471,7 +1471,7 @@ static void ipgre_tap_setup(struct net_device *dev)
1471 dev->features |= NETIF_F_NETNS_LOCAL; 1471 dev->features |= NETIF_F_NETNS_LOCAL;
1472} 1472}
1473 1473
1474static int ipgre_newlink(struct net_device *dev, struct nlattr *tb[], 1474static int ipgre_newlink(struct net *src_net, struct net_device *dev, struct nlattr *tb[],
1475 struct nlattr *data[]) 1475 struct nlattr *data[])
1476{ 1476{
1477 struct ip_tunnel *nt; 1477 struct ip_tunnel *nt;
@@ -1665,15 +1665,16 @@ static int __init ipgre_init(void)
1665 1665
1666 printk(KERN_INFO "GRE over IPv4 tunneling driver\n"); 1666 printk(KERN_INFO "GRE over IPv4 tunneling driver\n");
1667 1667
1668 if (inet_add_protocol(&ipgre_protocol, IPPROTO_GRE) < 0) { 1668 err = register_pernet_device(&ipgre_net_ops);
1669 if (err < 0)
1670 return err;
1671
1672 err = inet_add_protocol(&ipgre_protocol, IPPROTO_GRE);
1673 if (err < 0) {
1669 printk(KERN_INFO "ipgre init: can't add protocol\n"); 1674 printk(KERN_INFO "ipgre init: can't add protocol\n");
1670 return -EAGAIN; 1675 goto add_proto_failed;
1671 } 1676 }
1672 1677
1673 err = register_pernet_gen_device(&ipgre_net_id, &ipgre_net_ops);
1674 if (err < 0)
1675 goto gen_device_failed;
1676
1677 err = rtnl_link_register(&ipgre_link_ops); 1678 err = rtnl_link_register(&ipgre_link_ops);
1678 if (err < 0) 1679 if (err < 0)
1679 goto rtnl_link_failed; 1680 goto rtnl_link_failed;
@@ -1688,9 +1689,9 @@ out:
1688tap_ops_failed: 1689tap_ops_failed:
1689 rtnl_link_unregister(&ipgre_link_ops); 1690 rtnl_link_unregister(&ipgre_link_ops);
1690rtnl_link_failed: 1691rtnl_link_failed:
1691 unregister_pernet_gen_device(ipgre_net_id, &ipgre_net_ops);
1692gen_device_failed:
1693 inet_del_protocol(&ipgre_protocol, IPPROTO_GRE); 1692 inet_del_protocol(&ipgre_protocol, IPPROTO_GRE);
1693add_proto_failed:
1694 unregister_pernet_device(&ipgre_net_ops);
1694 goto out; 1695 goto out;
1695} 1696}
1696 1697
@@ -1698,9 +1699,9 @@ static void __exit ipgre_fini(void)
1698{ 1699{
1699 rtnl_link_unregister(&ipgre_tap_ops); 1700 rtnl_link_unregister(&ipgre_tap_ops);
1700 rtnl_link_unregister(&ipgre_link_ops); 1701 rtnl_link_unregister(&ipgre_link_ops);
1701 unregister_pernet_gen_device(ipgre_net_id, &ipgre_net_ops);
1702 if (inet_del_protocol(&ipgre_protocol, IPPROTO_GRE) < 0) 1702 if (inet_del_protocol(&ipgre_protocol, IPPROTO_GRE) < 0)
1703 printk(KERN_INFO "ipgre close: can't remove protocol\n"); 1703 printk(KERN_INFO "ipgre close: can't remove protocol\n");
1704 unregister_pernet_device(&ipgre_net_ops);
1704} 1705}
1705 1706
1706module_init(ipgre_init); 1707module_init(ipgre_init);