]> git.ipfire.org Git - thirdparty/kernel/stable.git/commitdiff
can: do not increase rx statistics when generating a CAN rx error message frame
authorVincent Mailhol <mailhol.vincent@wanadoo.fr>
Tue, 7 Dec 2021 12:15:27 +0000 (21:15 +0900)
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Sat, 14 Dec 2024 18:51:25 +0000 (19:51 +0100)
[ Upstream commit 676068db69b847f06fe054fca15bf6b107bd24da ]

The CAN error message frames (i.e. error skb) are an interface
specific to socket CAN. The payload of the CAN error message frames
does not correspond to any actual data sent on the wire. Only an error
flag and a delimiter are transmitted when an error occurs (c.f. ISO
11898-1 section 10.4.4.2 "Error flag").

For this reason, it makes no sense to increment the rx_packets and
rx_bytes fields of struct net_device_stats because no actual payload
were transmitted on the wire.

This patch fixes all the CAN drivers.

Link: https://lore.kernel.org/all/20211207121531.42941-2-mailhol.vincent@wanadoo.fr
CC: Marc Kleine-Budde <mkl@pengutronix.de>
CC: Nicolas Ferre <nicolas.ferre@microchip.com>
CC: Alexandre Belloni <alexandre.belloni@bootlin.com>
CC: Ludovic Desroches <ludovic.desroches@microchip.com>
CC: Chandrasekar Ramakrishnan <rcsekar@samsung.com>
CC: Maxime Ripard <mripard@kernel.org>
CC: Chen-Yu Tsai <wens@csie.org>
CC: Jernej Skrabec <jernej.skrabec@gmail.com>
CC: Appana Durga Kedareswara rao <appana.durga.rao@xilinx.com>
CC: Naga Sureshkumar Relli <naga.sureshkumar.relli@xilinx.com>
CC: Michal Simek <michal.simek@xilinx.com>
CC: Stephane Grosjean <s.grosjean@peak-system.com>
Tested-by: Jimmy Assarsson <extja@kvaser.com> # kvaser
Signed-off-by: Vincent Mailhol <mailhol.vincent@wanadoo.fr>
Acked-by: Stefan Mätje <stefan.maetje@esd.eu> # esd_usb2
Tested-by: Stefan Mätje <stefan.maetje@esd.eu> # esd_usb2
Signed-off-by: Marc Kleine-Budde <mkl@pengutronix.de>
Stable-dep-of: 9e66242504f4 ("can: c_can: c_can_handle_bus_err(): update statistics if skb allocation fails")
Signed-off-by: Sasha Levin <sashal@kernel.org>
27 files changed:
drivers/net/can/at91_can.c
drivers/net/can/c_can/c_can_main.c
drivers/net/can/cc770/cc770.c
drivers/net/can/dev/dev.c
drivers/net/can/dev/rx-offload.c
drivers/net/can/ifi_canfd/ifi_canfd.c
drivers/net/can/kvaser_pciefd.c
drivers/net/can/m_can/m_can.c
drivers/net/can/mscan/mscan.c
drivers/net/can/pch_can.c
drivers/net/can/peak_canfd/peak_canfd.c
drivers/net/can/rcar/rcar_can.c
drivers/net/can/rcar/rcar_canfd.c
drivers/net/can/sja1000/sja1000.c
drivers/net/can/sun4i_can.c
drivers/net/can/usb/ems_usb.c
drivers/net/can/usb/esd_usb2.c
drivers/net/can/usb/etas_es58x/es58x_core.c
drivers/net/can/usb/kvaser_usb/kvaser_usb_core.c
drivers/net/can/usb/kvaser_usb/kvaser_usb_hydra.c
drivers/net/can/usb/kvaser_usb/kvaser_usb_leaf.c
drivers/net/can/usb/peak_usb/pcan_usb.c
drivers/net/can/usb/peak_usb/pcan_usb_fd.c
drivers/net/can/usb/peak_usb/pcan_usb_pro.c
drivers/net/can/usb/ucan.c
drivers/net/can/usb/usb_8dev.c
drivers/net/can/xilinx_can.c

index b06af90a996408118e660e7c9e391f191dfb582c..26cb3d886978954584659ebc9304e8027cfb7d1e 100644 (file)
@@ -553,8 +553,6 @@ static void at91_rx_overflow_err(struct net_device *dev)
        cf->can_id |= CAN_ERR_CRTL;
        cf->data[1] = CAN_ERR_CRTL_RX_OVERFLOW;
 
-       stats->rx_packets++;
-       stats->rx_bytes += cf->len;
        netif_receive_skb(skb);
 }
 
@@ -779,8 +777,6 @@ static int at91_poll_err(struct net_device *dev, int quota, u32 reg_sr)
 
        at91_poll_err_frame(dev, cf, reg_sr);
 
-       dev->stats.rx_packets++;
-       dev->stats.rx_bytes += cf->len;
        netif_receive_skb(skb);
 
        return 1;
@@ -1037,8 +1033,6 @@ static void at91_irq_err(struct net_device *dev)
 
        at91_irq_err_state(dev, cf, new_state);
 
-       dev->stats.rx_packets++;
-       dev->stats.rx_bytes += cf->len;
        netif_rx(skb);
 
        priv->can.state = new_state;
index 8ab43f1272bd9a023208dd920807b1af30c59d20..d9595eb3e125f00317cd14c38e896414c9a5fb18 100644 (file)
@@ -919,7 +919,6 @@ static int c_can_handle_state_change(struct net_device *dev,
        unsigned int reg_err_counter;
        unsigned int rx_err_passive;
        struct c_can_priv *priv = netdev_priv(dev);
-       struct net_device_stats *stats = &dev->stats;
        struct can_frame *cf;
        struct sk_buff *skb;
        struct can_berr_counter bec;
@@ -995,8 +994,6 @@ static int c_can_handle_state_change(struct net_device *dev,
                break;
        }
 
-       stats->rx_packets++;
-       stats->rx_bytes += cf->len;
        netif_receive_skb(skb);
 
        return 1;
@@ -1068,8 +1065,6 @@ static int c_can_handle_bus_err(struct net_device *dev,
                break;
        }
 
-       stats->rx_packets++;
-       stats->rx_bytes += cf->len;
        netif_receive_skb(skb);
        return 1;
 }
index f8a130f594e2ebbc155bb6b867aa3102845d329a..a5fd8ccedec2197aac8e1114ceb72b67d2e5e3a1 100644 (file)
@@ -499,7 +499,6 @@ static void cc770_rx(struct net_device *dev, unsigned int mo, u8 ctrl1)
 static int cc770_err(struct net_device *dev, u8 status)
 {
        struct cc770_priv *priv = netdev_priv(dev);
-       struct net_device_stats *stats = &dev->stats;
        struct can_frame *cf;
        struct sk_buff *skb;
        u8 lec;
@@ -571,8 +570,6 @@ static int cc770_err(struct net_device *dev, u8 status)
        }
 
 
-       stats->rx_packets++;
-       stats->rx_bytes += cf->len;
        netif_rx(skb);
 
        return 0;
index 94916f2d24d410766747f46b90666c917b6473ed..62d3e4d1fe99e4c6a8518b51135d1fcd5bef4616 100644 (file)
@@ -136,7 +136,6 @@ EXPORT_SYMBOL_GPL(can_change_state);
 static void can_restart(struct net_device *dev)
 {
        struct can_priv *priv = netdev_priv(dev);
-       struct net_device_stats *stats = &dev->stats;
        struct sk_buff *skb;
        struct can_frame *cf;
        int err;
@@ -156,9 +155,6 @@ static void can_restart(struct net_device *dev)
 
        cf->can_id |= CAN_ERR_RESTARTED;
 
-       stats->rx_packets++;
-       stats->rx_bytes += cf->len;
-
        netif_rx_ni(skb);
 
 restart:
index 37b0cc65237b7ea5d5ca62152a29dd19ce2d5c6f..7dbf46b9ca5dd9869ffd62882286766eaf08160f 100644 (file)
@@ -54,8 +54,10 @@ static int can_rx_offload_napi_poll(struct napi_struct *napi, int quota)
                struct can_frame *cf = (struct can_frame *)skb->data;
 
                work_done++;
-               stats->rx_packets++;
-               stats->rx_bytes += cf->len;
+               if (!(cf->can_id & CAN_ERR_FLAG)) {
+                       stats->rx_packets++;
+                       stats->rx_bytes += cf->len;
+               }
                netif_receive_skb(skb);
        }
 
index 5bb957a26bc6975d04adf26762a117c6217ef0d2..e8318e984bf2f194f8f22d4f8e3eb1a195ad5020 100644 (file)
@@ -430,8 +430,6 @@ static int ifi_canfd_handle_lec_err(struct net_device *ndev)
               priv->base + IFI_CANFD_INTERRUPT);
        writel(IFI_CANFD_ERROR_CTR_ER_ENABLE, priv->base + IFI_CANFD_ERROR_CTR);
 
-       stats->rx_packets++;
-       stats->rx_bytes += cf->len;
        netif_receive_skb(skb);
 
        return 1;
@@ -456,7 +454,6 @@ static int ifi_canfd_handle_state_change(struct net_device *ndev,
                                         enum can_state new_state)
 {
        struct ifi_canfd_priv *priv = netdev_priv(ndev);
-       struct net_device_stats *stats = &ndev->stats;
        struct can_frame *cf;
        struct sk_buff *skb;
        struct can_berr_counter bec;
@@ -522,8 +519,6 @@ static int ifi_canfd_handle_state_change(struct net_device *ndev,
                break;
        }
 
-       stats->rx_packets++;
-       stats->rx_bytes += cf->len;
        netif_receive_skb(skb);
 
        return 1;
index 477bc56b1206050843563b906f13c3bc4bbbc83b..26bc8c7ad75b9ad52c6feb4667a4c94aef492e3c 100644 (file)
@@ -1327,9 +1327,6 @@ static int kvaser_pciefd_rx_error_frame(struct kvaser_pciefd_can *can,
        cf->data[6] = bec.txerr;
        cf->data[7] = bec.rxerr;
 
-       stats->rx_packets++;
-       stats->rx_bytes += cf->len;
-
        netif_rx(skb);
        return 0;
 }
@@ -1524,8 +1521,6 @@ static void kvaser_pciefd_handle_nack_packet(struct kvaser_pciefd_can *can,
 
        if (skb) {
                cf->can_id |= CAN_ERR_BUSERROR;
-               stats->rx_bytes += cf->len;
-               stats->rx_packets++;
                netif_rx(skb);
        } else {
                stats->rx_dropped++;
index a87f6ce86cea38f2058937ec7af407f5694fafb4..abc3907feb739d7d667c9c21441b2ea48810aaa8 100644 (file)
@@ -653,9 +653,6 @@ static int m_can_handle_lec_err(struct net_device *dev,
                break;
        }
 
-       stats->rx_packets++;
-       stats->rx_bytes += cf->len;
-
        if (cdev->is_peripheral)
                timestamp = m_can_get_timestamp(cdev);
 
@@ -712,7 +709,6 @@ static int m_can_handle_state_change(struct net_device *dev,
                                     enum can_state new_state)
 {
        struct m_can_classdev *cdev = netdev_priv(dev);
-       struct net_device_stats *stats = &dev->stats;
        struct can_frame *cf;
        struct sk_buff *skb;
        struct can_berr_counter bec;
@@ -777,9 +773,6 @@ static int m_can_handle_state_change(struct net_device *dev,
                break;
        }
 
-       stats->rx_packets++;
-       stats->rx_bytes += cf->len;
-
        if (cdev->is_peripheral)
                timestamp = m_can_get_timestamp(cdev);
 
index fa32e418eb296db955c34c1df62a7e9aa9f70c32..9e1cce0260da6aa4e558d61767f36704abc9b575 100644 (file)
@@ -401,13 +401,14 @@ static int mscan_rx_poll(struct napi_struct *napi, int quota)
                        continue;
                }
 
-               if (canrflg & MSCAN_RXF)
+               if (canrflg & MSCAN_RXF) {
                        mscan_get_rx_frame(dev, frame);
-               else if (canrflg & MSCAN_ERR_IF)
+                       stats->rx_packets++;
+                       stats->rx_bytes += frame->len;
+               } else if (canrflg & MSCAN_ERR_IF) {
                        mscan_get_err_frame(dev, frame, canrflg);
+               }
 
-               stats->rx_packets++;
-               stats->rx_bytes += frame->len;
                work_done++;
                netif_receive_skb(skb);
        }
index cd8d536c6fb20b6891a2f00905c96c03be873192..da01ce36ed59296fd222ee7dfcf9ed096a5eb2a2 100644 (file)
@@ -561,9 +561,6 @@ static void pch_can_error(struct net_device *ndev, u32 status)
 
        priv->can.state = state;
        netif_receive_skb(skb);
-
-       stats->rx_packets++;
-       stats->rx_bytes += cf->len;
 }
 
 static irqreturn_t pch_can_interrupt(int irq, void *dev_id)
index d08718e98e110206f0ef11085102d0e4a38fa2e8..d5b8bc6d29804910e43b97923204104c75cfe94a 100644 (file)
@@ -409,8 +409,6 @@ static int pucan_handle_status(struct peak_canfd_priv *priv,
                return -ENOMEM;
        }
 
-       stats->rx_packets++;
-       stats->rx_bytes += cf->len;
        pucan_netif_rx(skb, msg->ts_low, msg->ts_high);
 
        return 0;
@@ -438,8 +436,6 @@ static int pucan_handle_cache_critical(struct peak_canfd_priv *priv)
        cf->data[6] = priv->bec.txerr;
        cf->data[7] = priv->bec.rxerr;
 
-       stats->rx_bytes += cf->len;
-       stats->rx_packets++;
        netif_rx(skb);
 
        return 0;
index 945b319de841cf097a49ae1743d7cb08d3ff6edc..68ad7da5c07e04e2bcbea31919ae294b73c1845b 100644 (file)
@@ -223,7 +223,6 @@ static void tx_failure_cleanup(struct net_device *ndev)
 static void rcar_can_error(struct net_device *ndev)
 {
        struct rcar_can_priv *priv = netdev_priv(ndev);
-       struct net_device_stats *stats = &ndev->stats;
        struct can_frame *cf;
        struct sk_buff *skb;
        u8 eifr, txerr = 0, rxerr = 0;
@@ -362,11 +361,8 @@ static void rcar_can_error(struct net_device *ndev)
                }
        }
 
-       if (skb) {
-               stats->rx_packets++;
-               stats->rx_bytes += cf->len;
+       if (skb)
                netif_rx(skb);
-       }
 }
 
 static void rcar_can_tx_done(struct net_device *ndev)
index 4e230e1456647fb5f1d51f65f2c07ea332f271d0..9d5b8cda8fc54eba6620e57146c95dce207c6baa 100644 (file)
@@ -1033,8 +1033,6 @@ static void rcar_canfd_error(struct net_device *ndev, u32 cerfl,
        /* Clear channel error interrupts that are handled */
        rcar_canfd_write(priv->base, RCANFD_CERFL(ch),
                         RCANFD_CERFL_ERR(~cerfl));
-       stats->rx_packets++;
-       stats->rx_bytes += cf->len;
        netif_rx(skb);
 }
 
@@ -1176,8 +1174,6 @@ static void rcar_canfd_state_change(struct net_device *ndev,
                rx_state = txerr <= rxerr ? state : 0;
 
                can_change_state(ndev, cf, tx_state, rx_state);
-               stats->rx_packets++;
-               stats->rx_bytes += cf->len;
                netif_rx(skb);
        }
 }
index aae2677e24f996690008e6387a9c8e1d0420aa77..1e4c797679674da02c6b1b2f38f4798447696cc5 100644 (file)
@@ -488,8 +488,6 @@ static int sja1000_err(struct net_device *dev, uint8_t isrc, uint8_t status)
                        can_bus_off(dev);
        }
 
-       stats->rx_packets++;
-       stats->rx_bytes += cf->len;
        netif_rx(skb);
 
        return 0;
index ad8f50807aca575e3da25ec891888cb2412907db..ab9adfe92a94bb60a51d132d7009bd29ea0359e8 100644 (file)
@@ -621,13 +621,10 @@ static int sun4i_can_err(struct net_device *dev, u8 isrc, u8 status)
                        can_bus_off(dev);
        }
 
-       if (likely(skb)) {
-               stats->rx_packets++;
-               stats->rx_bytes += cf->len;
+       if (likely(skb))
                netif_rx(skb);
-       } else {
+       else
                return -ENOMEM;
-       }
 
        return 0;
 }
index a1b7c1a451c0c027d15829347ef1e2fe3339b365..0581e70ab903e7921bd707109aac35c61431fc29 100644 (file)
@@ -397,8 +397,6 @@ static void ems_usb_rx_err(struct ems_usb *dev, struct ems_cpc_msg *msg)
                stats->rx_errors++;
        }
 
-       stats->rx_packets++;
-       stats->rx_bytes += cf->len;
        netif_rx(skb);
 }
 
index 1abdf88597de0574a4a4db5bcf315ea2c1d460a3..14104cb02fb1ad0562653c860365b30749b91bc3 100644 (file)
@@ -301,8 +301,6 @@ static void esd_usb2_rx_event(struct esd_usb2_net_priv *priv,
                priv->bec.txerr = txerr;
                priv->bec.rxerr = rxerr;
 
-               stats->rx_packets++;
-               stats->rx_bytes += cf->len;
                netif_rx(skb);
        }
 }
index 0e6faf962ebbcd19d19ab2417f5dcdef2b396d71..34d374d301e50ef7ba031a1b148dd9d8061a006d 100644 (file)
@@ -849,13 +849,6 @@ int es58x_rx_err_msg(struct net_device *netdev, enum es58x_err error,
                break;
        }
 
-       /* driver/net/can/dev.c:can_restart() takes in account error
-        * messages in the RX stats. Doing the same here for
-        * consistency.
-        */
-       netdev->stats.rx_packets++;
-       netdev->stats.rx_bytes += CAN_ERR_DLC;
-
        if (cf) {
                if (cf->data[1])
                        cf->can_id |= CAN_ERR_CRTL;
index 95ed2005539295d237735b70a6918f7df5e58949..f6cb5ba61ac9309517649df14b726ee73ed7cc32 100644 (file)
@@ -315,8 +315,6 @@ int kvaser_usb_can_rx_over_error(struct net_device *netdev)
        cf->can_id |= CAN_ERR_CRTL;
        cf->data[1] = CAN_ERR_CRTL_RX_OVERFLOW;
 
-       stats->rx_packets++;
-       stats->rx_bytes += cf->len;
        netif_rx(skb);
 
        return 0;
index 562105b8a632760ab72140c20f3a3afee9de7b53..684c9685ba613e51637ff17b38b38971513f5183 100644 (file)
@@ -922,7 +922,6 @@ static void kvaser_usb_hydra_update_state(struct kvaser_usb_net_priv *priv,
        struct net_device *netdev = priv->netdev;
        struct can_frame *cf;
        struct sk_buff *skb;
-       struct net_device_stats *stats;
        enum can_state new_state, old_state;
 
        old_state = priv->can.state;
@@ -974,9 +973,6 @@ static void kvaser_usb_hydra_update_state(struct kvaser_usb_net_priv *priv,
                cf->data[7] = bec->rxerr;
        }
 
-       stats = &netdev->stats;
-       stats->rx_packets++;
-       stats->rx_bytes += cf->len;
        netif_rx(skb);
 }
 
@@ -1131,8 +1127,6 @@ kvaser_usb_hydra_error_frame(struct kvaser_usb_net_priv *priv,
                cf->data[7] = bec.rxerr;
        }
 
-       stats->rx_packets++;
-       stats->rx_bytes += cf->len;
        netif_rx(skb);
 
        priv->bec.txerr = bec.txerr;
@@ -1166,8 +1160,6 @@ static void kvaser_usb_hydra_one_shot_fail(struct kvaser_usb_net_priv *priv,
        }
 
        stats->tx_errors++;
-       stats->rx_packets++;
-       stats->rx_bytes += cf->len;
        netif_rx(skb);
 }
 
index ad3103391c7934db4274518c98592cf19b58a090..43ec0566466615cc4eac66c25d1d5718089cbd45 100644 (file)
@@ -907,8 +907,6 @@ static void kvaser_usb_leaf_tx_acknowledge(const struct kvaser_usb *dev,
                if (skb) {
                        cf->can_id |= CAN_ERR_RESTARTED;
 
-                       stats->rx_packets++;
-                       stats->rx_bytes += cf->len;
                        netif_rx(skb);
                } else {
                        netdev_err(priv->netdev,
@@ -1131,8 +1129,6 @@ static void kvaser_usb_leaf_rx_error(const struct kvaser_usb *dev,
                cf->data[7] = es->rxerr;
        }
 
-       stats->rx_packets++;
-       stats->rx_bytes += cf->len;
        netif_rx(skb);
 }
 
index af8d3dadbbb8bb9ef1ff0fbf79f61adf07b9da1b..d7adc313a6eda05e78f84d907f74964ddfb98bed 100644 (file)
@@ -520,8 +520,6 @@ static int pcan_usb_decode_error(struct pcan_usb_msg_context *mc, u8 n,
                                     &hwts->hwtstamp);
        }
 
-       mc->netdev->stats.rx_packets++;
-       mc->netdev->stats.rx_bytes += cf->len;
        netif_rx(skb);
 
        return 0;
index 6bd12549f101422f02b044c90d352a203feeb7b3..185f5a98d21770b00ac22831c5dd50e095c2c25e 100644 (file)
@@ -577,9 +577,6 @@ static int pcan_usb_fd_decode_status(struct pcan_usb_fd_if *usb_if,
        if (!skb)
                return -ENOMEM;
 
-       netdev->stats.rx_packets++;
-       netdev->stats.rx_bytes += cf->len;
-
        peak_usb_netif_rx_64(skb, le32_to_cpu(sm->ts_low),
                             le32_to_cpu(sm->ts_high));
 
index 858ab22708fcd2d4c7b417ce9501bdef7638672d..f6d19879bf404a4fc17bb1312a0c07199667c0c8 100644 (file)
@@ -660,8 +660,6 @@ static int pcan_usb_pro_handle_error(struct pcan_usb_pro_interface *usb_if,
 
        hwts = skb_hwtstamps(skb);
        peak_usb_get_ts_time(&usb_if->time_ref, le32_to_cpu(er->ts32), &hwts->hwtstamp);
-       netdev->stats.rx_packets++;
-       netdev->stats.rx_bytes += can_frame->len;
        netif_rx(skb);
 
        return 0;
index 1679cbe45ded2c913fe3debb41e3974dd90a8a6c..d582c39fc8d0e643711169ea69f27f410943ac88 100644 (file)
@@ -621,8 +621,10 @@ static void ucan_rx_can_msg(struct ucan_priv *up, struct ucan_message_in *m)
                memcpy(cf->data, m->msg.can_msg.data, cf->len);
 
        /* don't count error frames as real packets */
-       stats->rx_packets++;
-       stats->rx_bytes += cf->len;
+       if (!(cf->can_id & CAN_ERR_FLAG)) {
+               stats->rx_packets++;
+               stats->rx_bytes += cf->len;
+       }
 
        /* pass it to Linux */
        netif_rx(skb);
index a5dee2ee24656264e696c0e076a65feeeb44eb34..3dbb689535d1ed8a521e9c3896642166eb116706 100644 (file)
@@ -450,8 +450,6 @@ static void usb_8dev_rx_err_msg(struct usb_8dev_priv *priv,
        priv->bec.txerr = txerr;
        priv->bec.rxerr = rxerr;
 
-       stats->rx_packets++;
-       stats->rx_bytes += cf->len;
        netif_rx(skb);
 }
 
index a2e751f0ae0b150883a273eee98fc8c493432e8d..cb48598e32ad89f9be29f3a8e1633f06d1b3042a 100644 (file)
@@ -966,13 +966,8 @@ static void xcan_update_error_state_after_rxtx(struct net_device *ndev)
 
                xcan_set_error_state(ndev, new_state, skb ? cf : NULL);
 
-               if (skb) {
-                       struct net_device_stats *stats = &ndev->stats;
-
-                       stats->rx_packets++;
-                       stats->rx_bytes += cf->len;
+               if (skb)
                        netif_rx(skb);
-               }
        }
 }
 
@@ -1096,8 +1091,6 @@ static void xcan_err_interrupt(struct net_device *ndev, u32 isr)
                if (skb) {
                        skb_cf->can_id |= cf.can_id;
                        memcpy(skb_cf->data, cf.data, CAN_ERR_DLC);
-                       stats->rx_packets++;
-                       stats->rx_bytes += CAN_ERR_DLC;
                        netif_rx(skb);
                }
        }