ethtool: tsinfo: fix uninitialized stats on the by-PHC path

tsinfo_prepare_data() has two code paths: a "by-PHC" path for
user-specified hardware timestamping providers, and the old path.
Commit 89e281ebff ("ethtool: init tsinfo stats if requested") added
ethtool_stats_init() to mark stat slots as ETHTOOL_STAT_NOT_SET before
the driver callback populates them, but placed the call inside the
old-path block.

When commit b9e3f7dc9e ("net: ethtool: tsinfo: Enhance tsinfo to
support several hwtstamp by net topology") added the by-PHC early
return, it landed above the stats initialization. On that path
the stats array retains the zero-fill from ethnl_init_reply_data()'s
zalloc. This leads to the reply including a stats nest with four
zero-valued attributes that should have been absent.

Reject GET requests for stats with HWTSTAMP_PROVIDER or dump.

Fixes: b9e3f7dc9e ("net: ethtool: tsinfo: Enhance tsinfo to support several hwtstamp by net topology")
Reviewed-by: Maxime Chevallier <maxime.chevallier@bootlin.com>
Link: https://patch.msgid.link/20260526153533.2779187-7-kuba@kernel.org
Signed-off-by: Jakub Kicinski <kuba@kernel.org>
This commit is contained in:
Jakub Kicinski 2026-05-26 08:35:29 -07:00
parent 6386bd772d
commit 1de405699c

View File

@ -83,6 +83,11 @@ tsinfo_parse_request(struct ethnl_req_info *req_base,
if (!tb[ETHTOOL_A_TSINFO_HWTSTAMP_PROVIDER])
return 0;
if (req_base->flags & ETHTOOL_FLAG_STATS) {
NL_SET_ERR_MSG(extack, "can't query statistics for a provider");
return -EOPNOTSUPP;
}
return ts_parse_hwtst_provider(tb[ETHTOOL_A_TSINFO_HWTSTAMP_PROVIDER],
&req->hwprov_desc, extack, &mod);
}
@ -523,6 +528,12 @@ int ethnl_tsinfo_start(struct netlink_callback *cb)
if (ret < 0)
goto free_reply_data;
if (req_info->base.flags & ETHTOOL_FLAG_STATS) {
NL_SET_ERR_MSG(cb->extack, "stats not supported in dump");
ret = -EOPNOTSUPP;
goto err_dev_put;
}
ctx->req_info = req_info;
ctx->reply_data = reply_data;
ctx->pos_ifindex = 0;
@ -532,6 +543,8 @@ int ethnl_tsinfo_start(struct netlink_callback *cb)
return 0;
err_dev_put:
ethnl_parse_header_dev_put(&req_info->base);
free_reply_data:
kfree(reply_data);
free_req_info: