aboutsummaryrefslogtreecommitdiffstats
path: root/net/ipv4/ip_output.c
diff options
context:
space:
mode:
authorDavid S. Miller <davem@davemloft.net>2012-07-02 05:02:15 -0400
committerDavid S. Miller <davem@davemloft.net>2012-07-05 04:02:12 -0400
commita263b3093641fb1ec377582c90986a7fd0625184 (patch)
tree691fdb4703bb88611272bf958d9de1a461f1492a /net/ipv4/ip_output.c
parent11604721a3c4bea60e2ddd9e4e30d741ecdba7b0 (diff)
ipv4: Make neigh lookups directly in output packet path.
Do not use the dst cached neigh, we'll be getting rid of that. Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'net/ipv4/ip_output.c')
-rw-r--r--net/ipv4/ip_output.c12
1 files changed, 8 insertions, 4 deletions
diff --git a/net/ipv4/ip_output.c b/net/ipv4/ip_output.c
index 2630900e480a..6e9a266a0535 100644
--- a/net/ipv4/ip_output.c
+++ b/net/ipv4/ip_output.c
@@ -170,6 +170,7 @@ static inline int ip_finish_output2(struct sk_buff *skb)
170 struct net_device *dev = dst->dev; 170 struct net_device *dev = dst->dev;
171 unsigned int hh_len = LL_RESERVED_SPACE(dev); 171 unsigned int hh_len = LL_RESERVED_SPACE(dev);
172 struct neighbour *neigh; 172 struct neighbour *neigh;
173 u32 nexthop;
173 174
174 if (rt->rt_type == RTN_MULTICAST) { 175 if (rt->rt_type == RTN_MULTICAST) {
175 IP_UPD_PO_STATS(dev_net(dev), IPSTATS_MIB_OUTMCAST, skb->len); 176 IP_UPD_PO_STATS(dev_net(dev), IPSTATS_MIB_OUTMCAST, skb->len);
@@ -191,15 +192,18 @@ static inline int ip_finish_output2(struct sk_buff *skb)
191 skb = skb2; 192 skb = skb2;
192 } 193 }
193 194
194 rcu_read_lock(); 195 rcu_read_lock_bh();
195 neigh = dst_get_neighbour_noref(dst); 196 nexthop = rt->rt_gateway ? rt->rt_gateway : ip_hdr(skb)->daddr;
197 neigh = __ipv4_neigh_lookup_noref(dev, nexthop);
198 if (unlikely(!neigh))
199 neigh = __neigh_create(&arp_tbl, &nexthop, dev, false);
196 if (neigh) { 200 if (neigh) {
197 int res = neigh_output(neigh, skb); 201 int res = neigh_output(neigh, skb);
198 202
199 rcu_read_unlock(); 203 rcu_read_unlock_bh();
200 return res; 204 return res;
201 } 205 }
202 rcu_read_unlock(); 206 rcu_read_unlock_bh();
203 207
204 net_dbg_ratelimited("%s: No header cache and no neighbour!\n", 208 net_dbg_ratelimited("%s: No header cache and no neighbour!\n",
205 __func__); 209 __func__);