summaryrefslogtreecommitdiffstats
path: root/lib/route
diff options
context:
space:
mode:
authorThomas Haller <thaller@redhat.com>2020-04-17 14:14:55 (GMT)
committerThomas Haller <thaller@redhat.com>2020-04-17 15:03:40 (GMT)
commit4be60621c615b6afc9312560517a4b345ac9bbcd (patch)
tree41d53c9ed04ca5a0a114754d028ab59204e18b79 /lib/route
parentba3c51c44c3c85d9cbd0c26b21eec9a6f0572949 (diff)
downloadlibnl-4be60621c615b6afc9312560517a4b345ac9bbcd.zip
libnl-4be60621c615b6afc9312560517a4b345ac9bbcd.tar.gz
libnl-4be60621c615b6afc9312560517a4b345ac9bbcd.tar.bz2
route/link: avoid cloning link policy in link_msg_parser()
Most families don't have a "link->l_af_ops", and those that do, mostly don't define ao_protinfo_policy. Only clone the policy if necessary.
Diffstat (limited to 'lib/route')
-rw-r--r--lib/route/link.c10
1 files changed, 6 insertions, 4 deletions
diff --git a/lib/route/link.c b/lib/route/link.c
index 76c090f..9733f51 100644
--- a/lib/route/link.c
+++ b/lib/route/link.c
@@ -571,13 +571,12 @@ static int link_msg_parser(struct nl_cache_ops *ops, struct sockaddr_nl *who,
struct nlmsghdr *n, struct nl_parser_param *pp)
{
_nl_auto_rtnl_link struct rtnl_link *link = NULL;
+ struct nla_policy real_link_policy[ARRAY_SIZE(rtln_link_policy)];
+ struct nla_policy *link_policy = rtln_link_policy;
struct rtnl_link_af_ops *af_ops_family;
struct ifinfomsg *ifi;
struct nlattr *tb[IFLA_MAX+1];
int err, family;
- struct nla_policy real_link_policy[IFLA_MAX+1];
-
- memcpy(&real_link_policy, rtln_link_policy, sizeof(rtln_link_policy));
link = rtnl_link_alloc();
if (link == NULL)
@@ -600,15 +599,18 @@ static int link_msg_parser(struct nl_cache_ops *ops, struct sockaddr_nl *who,
if ((link->l_af_ops = af_lookup_and_alloc(link, family))) {
if (link->l_af_ops->ao_protinfo_policy) {
+ _NL_STATIC_ASSERT (sizeof(rtln_link_policy) == sizeof(real_link_policy));
+ memcpy(&real_link_policy, rtln_link_policy, sizeof(rtln_link_policy));
memcpy(&real_link_policy[IFLA_PROTINFO],
link->l_af_ops->ao_protinfo_policy,
sizeof(struct nla_policy));
+ link_policy = real_link_policy;
}
}
af_ops_family = link->l_af_ops;
- err = nlmsg_parse(n, sizeof(*ifi), tb, IFLA_MAX, real_link_policy);
+ err = nlmsg_parse(n, sizeof(*ifi), tb, IFLA_MAX, link_policy);
if (err < 0)
return err;