diff options
Diffstat (limited to 'net/ipv4')
-rw-r--r-- | net/ipv4/devinet.c | 14 | ||||
-rw-r--r-- | net/ipv4/fib_semantics.c | 14 | ||||
-rw-r--r-- | net/ipv4/inet_diag.c | 17 | ||||
-rw-r--r-- | net/ipv4/route.c | 5 |
4 files changed, 31 insertions, 19 deletions
diff --git a/net/ipv4/devinet.c b/net/ipv4/devinet.c index 480ace9819f..c4020364096 100644 --- a/net/ipv4/devinet.c +++ b/net/ipv4/devinet.c @@ -1140,7 +1140,7 @@ static int inet_fill_ifaddr(struct sk_buff *skb, struct in_ifaddr *ifa, nlh = nlmsg_put(skb, pid, seq, event, sizeof(*ifm), flags); if (nlh == NULL) - return -ENOBUFS; + return -EMSGSIZE; ifm = nlmsg_data(nlh); ifm->ifa_family = AF_INET; @@ -1167,7 +1167,8 @@ static int inet_fill_ifaddr(struct sk_buff *skb, struct in_ifaddr *ifa, return nlmsg_end(skb, nlh); nla_put_failure: - return nlmsg_cancel(skb, nlh); + nlmsg_cancel(skb, nlh); + return -EMSGSIZE; } static int inet_dump_ifaddr(struct sk_buff *skb, struct netlink_callback *cb) @@ -1225,9 +1226,12 @@ static void rtmsg_ifa(int event, struct in_ifaddr* ifa, struct nlmsghdr *nlh, goto errout; err = inet_fill_ifaddr(skb, ifa, pid, seq, event, 0); - /* failure implies BUG in inet_nlmsg_size() */ - BUG_ON(err < 0); - + if (err < 0) { + /* -EMSGSIZE implies BUG in inet_nlmsg_size() */ + WARN_ON(err == -EMSGSIZE); + kfree_skb(skb); + goto errout; + } err = rtnl_notify(skb, pid, RTNLGRP_IPV4_IFADDR, nlh, GFP_KERNEL); errout: if (err < 0) diff --git a/net/ipv4/fib_semantics.c b/net/ipv4/fib_semantics.c index e63b8a98fb4..be1028c9933 100644 --- a/net/ipv4/fib_semantics.c +++ b/net/ipv4/fib_semantics.c @@ -314,9 +314,12 @@ void rtmsg_fib(int event, __be32 key, struct fib_alias *fa, err = fib_dump_info(skb, info->pid, seq, event, tb_id, fa->fa_type, fa->fa_scope, key, dst_len, fa->fa_tos, fa->fa_info, 0); - /* failure implies BUG in fib_nlmsg_size() */ - BUG_ON(err < 0); - + if (err < 0) { + /* -EMSGSIZE implies BUG in fib_nlmsg_size() */ + WARN_ON(err == -EMSGSIZE); + kfree_skb(skb); + goto errout; + } err = rtnl_notify(skb, info->pid, RTNLGRP_IPV4_ROUTE, info->nlh, GFP_KERNEL); errout: @@ -960,7 +963,7 @@ int fib_dump_info(struct sk_buff *skb, u32 pid, u32 seq, int event, nlh = nlmsg_put(skb, pid, seq, event, sizeof(*rtm), flags); if (nlh == NULL) - return -ENOBUFS; + return -EMSGSIZE; rtm = nlmsg_data(nlh); rtm->rtm_family = AF_INET; @@ -1031,7 +1034,8 @@ int fib_dump_info(struct sk_buff *skb, u32 pid, u32 seq, int event, return nlmsg_end(skb, nlh); nla_put_failure: - return nlmsg_cancel(skb, nlh); + nlmsg_cancel(skb, nlh); + return -EMSGSIZE; } /* diff --git a/net/ipv4/inet_diag.c b/net/ipv4/inet_diag.c index 77761ac4f7b..9cd53addb78 100644 --- a/net/ipv4/inet_diag.c +++ b/net/ipv4/inet_diag.c @@ -153,7 +153,7 @@ static int inet_csk_diag_fill(struct sock *sk, rtattr_failure: nlmsg_failure: skb_trim(skb, b - skb->data); - return -1; + return -EMSGSIZE; } static int inet_twsk_diag_fill(struct inet_timewait_sock *tw, @@ -209,7 +209,7 @@ static int inet_twsk_diag_fill(struct inet_timewait_sock *tw, return skb->len; nlmsg_failure: skb_trim(skb, previous_tail - skb->data); - return -1; + return -EMSGSIZE; } static int sk_diag_fill(struct sock *sk, struct sk_buff *skb, @@ -274,11 +274,14 @@ static int inet_diag_get_exact(struct sk_buff *in_skb, if (!rep) goto out; - if (sk_diag_fill(sk, rep, req->idiag_ext, - NETLINK_CB(in_skb).pid, - nlh->nlmsg_seq, 0, nlh) <= 0) - BUG(); - + err = sk_diag_fill(sk, rep, req->idiag_ext, + NETLINK_CB(in_skb).pid, + nlh->nlmsg_seq, 0, nlh); + if (err < 0) { + WARN_ON(err == -EMSGSIZE); + kfree_skb(rep); + goto out; + } err = netlink_unicast(idiagnl, rep, NETLINK_CB(in_skb).pid, MSG_DONTWAIT); if (err > 0) diff --git a/net/ipv4/route.c b/net/ipv4/route.c index 2daa0dc19d3..baee304a3cb 100644 --- a/net/ipv4/route.c +++ b/net/ipv4/route.c @@ -2635,7 +2635,7 @@ static int rt_fill_info(struct sk_buff *skb, u32 pid, u32 seq, int event, nlh = nlmsg_put(skb, pid, seq, event, sizeof(*r), flags); if (nlh == NULL) - return -ENOBUFS; + return -EMSGSIZE; r = nlmsg_data(nlh); r->rtm_family = AF_INET; @@ -2718,7 +2718,8 @@ static int rt_fill_info(struct sk_buff *skb, u32 pid, u32 seq, int event, return nlmsg_end(skb, nlh); nla_put_failure: - return nlmsg_cancel(skb, nlh); + nlmsg_cancel(skb, nlh); + return -EMSGSIZE; } int inet_rtm_getroute(struct sk_buff *in_skb, struct nlmsghdr* nlh, void *arg) |