net/sched: propagate tc_fill_tclass() error

Change tc_fill_tclass() to return -EMSGSIZE when skb is too small.

Change its caller to propagate this error (instead of -EINVAL)

Signed-off-by: Eric Dumazet <edumazet@google.com>
Link: https://patch.msgid.link/20260430023628.3216283-2-edumazet@google.com
Signed-off-by: Jakub Kicinski <kuba@kernel.org>
This commit is contained in:
Eric Dumazet 2026-04-30 02:36:25 +00:00 committed by Jakub Kicinski
parent bc6a9b667f
commit db6ac77b04

View File

@ -1987,15 +1987,16 @@ static int tc_fill_tclass(struct sk_buff *skb, struct Qdisc *q,
out_nlmsg_trim:
nla_put_failure:
nlmsg_trim(skb, b);
return -1;
return -EMSGSIZE;
}
static int tclass_notify(struct net *net, struct sk_buff *oskb,
struct nlmsghdr *n, struct Qdisc *q,
unsigned long cl, int event, struct netlink_ext_ack *extack)
{
struct sk_buff *skb;
u32 portid = oskb ? NETLINK_CB(oskb).portid : 0;
struct sk_buff *skb;
int ret;
if (!rtnl_notify_needed(net, n->nlmsg_flags, RTNLGRP_TC))
return 0;
@ -2004,9 +2005,10 @@ static int tclass_notify(struct net *net, struct sk_buff *oskb,
if (!skb)
return -ENOBUFS;
if (tc_fill_tclass(skb, q, cl, portid, n->nlmsg_seq, 0, event, extack) < 0) {
ret = tc_fill_tclass(skb, q, cl, portid, n->nlmsg_seq, 0, event, extack);
if (ret < 0) {
kfree_skb(skb);
return -EINVAL;
return ret;
}
return rtnetlink_send(skb, net, portid, RTNLGRP_TC,
@ -2017,17 +2019,19 @@ static int tclass_get_notify(struct net *net, struct sk_buff *oskb,
struct nlmsghdr *n, struct Qdisc *q,
unsigned long cl, struct netlink_ext_ack *extack)
{
struct sk_buff *skb;
u32 portid = oskb ? NETLINK_CB(oskb).portid : 0;
struct sk_buff *skb;
int ret;
skb = alloc_skb(NLMSG_GOODSIZE, GFP_KERNEL);
if (!skb)
return -ENOBUFS;
if (tc_fill_tclass(skb, q, cl, portid, n->nlmsg_seq, 0, RTM_NEWTCLASS,
extack) < 0) {
ret = tc_fill_tclass(skb, q, cl, portid, n->nlmsg_seq, 0,
RTM_NEWTCLASS, extack);
if (ret < 0) {
kfree_skb(skb);
return -EINVAL;
return ret;
}
return rtnetlink_send(skb, net, portid, RTNLGRP_TC,
@ -2041,7 +2045,7 @@ static int tclass_del_notify(struct net *net,
struct netlink_ext_ack *extack)
{
u32 portid = oskb ? NETLINK_CB(oskb).portid : 0;
struct sk_buff *skb;
struct sk_buff *skb = NULL;
int err = 0;
if (!cops->delete)
@ -2052,13 +2056,12 @@ static int tclass_del_notify(struct net *net,
if (!skb)
return -ENOBUFS;
if (tc_fill_tclass(skb, q, cl, portid, n->nlmsg_seq, 0,
RTM_DELTCLASS, extack) < 0) {
err = tc_fill_tclass(skb, q, cl, portid, n->nlmsg_seq, 0,
RTM_DELTCLASS, extack);
if (err < 0) {
kfree_skb(skb);
return -EINVAL;
return err;
}
} else {
skb = NULL;
}
err = cops->delete(q, cl, extack);