static void pndisc_destructor(struct pneigh_entry *n);
static void pndisc_redo(struct sk_buff *skb);
-static struct neigh_ops ndisc_generic_ops = {
+static const struct neigh_ops ndisc_generic_ops = {
.family = AF_INET6,
.solicit = ndisc_solicit,
.error_report = ndisc_error_report,
.queue_xmit = dev_queue_xmit,
};
-static struct neigh_ops ndisc_hh_ops = {
+static const struct neigh_ops ndisc_hh_ops = {
.family = AF_INET6,
.solicit = ndisc_solicit,
.error_report = ndisc_error_report,
};
-static struct neigh_ops ndisc_direct_ops = {
+static const struct neigh_ops ndisc_direct_ops = {
.family = AF_INET6,
.output = dev_queue_xmit,
.connected_output = dev_queue_xmit,
1, &err);
if (!skb) {
ND_PRINTK0(KERN_ERR
- "ICMPv6 ND: %s() failed to allocate an skb.\n",
- __func__);
+ "ICMPv6 ND: %s() failed to allocate an skb, err=%d.\n",
+ __func__, err);
return NULL;
}
return;
}
- skb->dst = dst;
+ skb_dst_set(skb, dst);
idev = in6_dev_get(dst->dev);
- IP6_INC_STATS(net, idev, IPSTATS_MIB_OUTREQUESTS);
+ IP6_UPD_PO_STATS(net, idev, IPSTATS_MIB_OUT, skb->len);
err = NF_HOOK(PF_INET6, NF_INET_LOCAL_OUT, skb, NULL, dst->dev,
dst_output);
icmp6h.icmp6_solicited = solicited;
icmp6h.icmp6_override = override;
+ inc_opt |= ifp->idev->cnf.force_tllao;
__ndisc_send(dev, neigh, daddr, src_addr,
&icmp6h, solicited_addr,
inc_opt ? ND_OPT_TARGET_LL_ADDR : 0);
*/
if (skb->pkt_type != PACKET_LOOPBACK)
ND_PRINTK1(KERN_WARNING
- "ICMPv6 NA: someone advertises our address on %s!\n",
- ifp->idev->dev->name);
+ "ICMPv6 NA: someone advertises our address %pI6 on %s!\n",
+ &ifp->addr, ifp->idev->dev->name);
in6_ifa_put(ifp);
return;
}
&ipv6_hdr(ra)->saddr);
nlmsg_end(skb, nlh);
- err = rtnl_notify(skb, net, 0, RTNLGRP_ND_USEROPT, NULL,
- GFP_ATOMIC);
- if (err < 0)
- goto errout;
-
+ rtnl_notify(skb, net, 0, RTNLGRP_ND_USEROPT, NULL, GFP_ATOMIC);
return;
nla_put_failure:
skb->dev->name);
return;
}
- if (in6_dev->cnf.forwarding || !in6_dev->cnf.accept_ra) {
- in6_dev_put(in6_dev);
- return;
- }
if (!ndisc_parse_options(opt, optlen, &ndopts)) {
in6_dev_put(in6_dev);
return;
}
+ /* skip route and link configuration on routers */
+ if (in6_dev->cnf.forwarding || !in6_dev->cnf.accept_ra)
+ goto skip_linkparms;
+
#ifdef CONFIG_IPV6_NDISC_NODETYPE
/* skip link-specific parameters from interior routers */
if (skb->ndisc_nodetype == NDISC_NODETYPE_NODEFAULT)
}
}
-#ifdef CONFIG_IPV6_NDISC_NODETYPE
skip_linkparms:
-#endif
/*
* Process options.
NEIGH_UPDATE_F_ISROUTER);
}
+ /* skip route and link configuration on routers */
+ if (in6_dev->cnf.forwarding || !in6_dev->cnf.accept_ra)
+ goto out;
+
#ifdef CONFIG_IPV6_ROUTE_INFO
if (in6_dev->cnf.accept_ra_rtr_pref && ndopts.nd_opts_ri) {
struct nd_opt_hdr *p;
if (rt->rt6i_flags & RTF_GATEWAY) {
ND_PRINTK2(KERN_WARNING
"ICMPv6 Redirect: destination is not a neighbour.\n");
- dst_release(dst);
- return;
- }
- if (!xrlim_allow(dst, 1*HZ)) {
- dst_release(dst);
- return;
+ goto release;
}
+ if (!xrlim_allow(dst, 1*HZ))
+ goto release;
if (dev->addr_len) {
read_lock_bh(&neigh->lock);
1, &err);
if (buff == NULL) {
ND_PRINTK0(KERN_ERR
- "ICMPv6 Redirect: %s() failed to allocate an skb.\n",
- __func__);
- dst_release(dst);
- return;
+ "ICMPv6 Redirect: %s() failed to allocate an skb, err=%d.\n",
+ __func__, err);
+ goto release;
}
skb_reserve(buff, LL_RESERVED_SPACE(dev));
len, IPPROTO_ICMPV6,
csum_partial(icmph, len, 0));
- buff->dst = dst;
+ skb_dst_set(buff, dst);
idev = in6_dev_get(dst->dev);
- IP6_INC_STATS(net, idev, IPSTATS_MIB_OUTREQUESTS);
+ IP6_UPD_PO_STATS(net, idev, IPSTATS_MIB_OUT, skb->len);
err = NF_HOOK(PF_INET6, NF_INET_LOCAL_OUT, buff, NULL, dst->dev,
dst_output);
if (!err) {
if (likely(idev != NULL))
in6_dev_put(idev);
+ return;
+
+release:
+ dst_release(dst);
}
static void pndisc_redo(struct sk_buff *skb)
}
}
-int ndisc_ifinfo_sysctl_change(struct ctl_table *ctl, int write, struct file * filp, void __user *buffer, size_t *lenp, loff_t *ppos)
+int ndisc_ifinfo_sysctl_change(struct ctl_table *ctl, int write, void __user *buffer, size_t *lenp, loff_t *ppos)
{
struct net_device *dev = ctl->extra1;
struct inet6_dev *idev;
ndisc_warn_deprecated_sysctl(ctl, "syscall", dev ? dev->name : "default");
if (strcmp(ctl->procname, "retrans_time") == 0)
- ret = proc_dointvec(ctl, write, filp, buffer, lenp, ppos);
+ ret = proc_dointvec(ctl, write, buffer, lenp, ppos);
else if (strcmp(ctl->procname, "base_reachable_time") == 0)
ret = proc_dointvec_jiffies(ctl, write,
- filp, buffer, lenp, ppos);
+ buffer, lenp, ppos);
else if ((strcmp(ctl->procname, "retrans_time_ms") == 0) ||
(strcmp(ctl->procname, "base_reachable_time_ms") == 0))
ret = proc_dointvec_ms_jiffies(ctl, write,
- filp, buffer, lenp, ppos);
+ buffer, lenp, ppos);
else
ret = -1;