If the interface is down, the CAN controller might be powered down, the
clock disabled, and/or its external reset asserted.
Don't call do_get_berr_counter() to read the CAN bus error counters if
the interface is down. This fixes a generic logic problem that exists
on all platforms.
Fixes: ec56acfef2af1 ("can: flexcan: flexcan_get_berr_counter(): switch on clocks before accessing ecr register")
Cc: stable@vger.kernel.org
Signed-off-by: ChunYuZhiQiang <redacted>
---
v1 -> v2:
- Reword the commit message to drop the MDIS reasoning.
- Add Fixes: tag.
v2 -> v3:
- Use the title and commit message suggested by Bough Chen.
- Drop the i.MX8QXP-specific crash dump and erratum explanation.
- Drop the m_can reference.
- Drop the Link: tag.
v3 -> v4:
- Move the netif_running() check from the flexcan driver to
can_fill_info() and can_get_size() in the CAN core, as suggested by
Marc Kleine-Budde. This covers all CAN drivers, not just flexcan.
drivers/net/can/dev/netlink.c | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/drivers/net/can/dev/netlink.c b/drivers/net/can/dev/netlink.c
index 6f83b87d54fc..d17f4e9cc144 100644
--- a/drivers/net/can/dev/netlink.c
+++ b/drivers/net/can/dev/netlink.c
@@ -584,7 +584,7 @@ static size_t can_get_size(const struct net_device *dev)
size += nla_total_size(sizeof(u32)); /* IFLA_CAN_STATE */
size += nla_total_size(sizeof(struct can_ctrlmode)); /* IFLA_CAN_CTRLMODE */
size += nla_total_size(sizeof(u32)); /* IFLA_CAN_RESTART_MS */
- if (priv->do_get_berr_counter) /* IFLA_CAN_BERR_COUNTER */
+ if (priv->do_get_berr_counter && netif_running(dev)) /* IFLA_CAN_BERR_COUNTER */
size += nla_total_size(sizeof(struct can_berr_counter));
if (priv->termination_const) {
size += nla_total_size(sizeof(priv->termination)); /* IFLA_CAN_TERMINATION */@@ -735,7 +735,7 @@ static int can_fill_info(struct sk_buff *skb, const struct net_device *dev)
nla_put(skb, IFLA_CAN_CTRLMODE, sizeof(cm), &cm) ||
nla_put_u32(skb, IFLA_CAN_RESTART_MS, priv->restart_ms) ||
- (priv->do_get_berr_counter &&
+ (priv->do_get_berr_counter && netif_running(dev) &&
!priv->do_get_berr_counter(dev, &bec) &&
nla_put(skb, IFLA_CAN_BERR_COUNTER, sizeof(bec), &bec)) ||
--
2.47.3