lkml.org 
[lkml]   [2021]   [May]   [24]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
    Patch in this message
    /
    From
    Subject[PATCH AUTOSEL 5.10 40/62] net: liquidio: Add missing null pointer checks
    Date
    From: Tom Seewald <tseewald@gmail.com>

    [ Upstream commit dbc97bfd3918ed9268bfc174cae8a7d6b3d51aad ]

    The functions send_rx_ctrl_cmd() in both liquidio/lio_main.c and
    liquidio/lio_vf_main.c do not check if the call to
    octeon_alloc_soft_command() fails and returns a null pointer. Both
    functions also return void so errors are not propagated back to the
    caller.

    Fix these issues by updating both instances of send_rx_ctrl_cmd() to
    return an integer rather than void, and have them return -ENOMEM if an
    allocation failure occurs. Also update all callers of send_rx_ctrl_cmd()
    so that they now check the return value.

    Cc: David S. Miller <davem@davemloft.net>
    Signed-off-by: Tom Seewald <tseewald@gmail.com>
    Link: https://lore.kernel.org/r/20210503115736.2104747-66-gregkh@linuxfoundation.org
    Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
    Signed-off-by: Sasha Levin <sashal@kernel.org>
    ---
    .../net/ethernet/cavium/liquidio/lio_main.c | 28 +++++++++++++------
    .../ethernet/cavium/liquidio/lio_vf_main.c | 27 +++++++++++++-----
    2 files changed, 40 insertions(+), 15 deletions(-)

    diff --git a/drivers/net/ethernet/cavium/liquidio/lio_main.c b/drivers/net/ethernet/cavium/liquidio/lio_main.c
    index e4c220f30040..e0d18e917108 100644
    --- a/drivers/net/ethernet/cavium/liquidio/lio_main.c
    +++ b/drivers/net/ethernet/cavium/liquidio/lio_main.c
    @@ -1153,7 +1153,7 @@ static void octeon_destroy_resources(struct octeon_device *oct)
    * @lio: per-network private data
    * @start_stop: whether to start or stop
    */
    -static void send_rx_ctrl_cmd(struct lio *lio, int start_stop)
    +static int send_rx_ctrl_cmd(struct lio *lio, int start_stop)
    {
    struct octeon_soft_command *sc;
    union octnet_cmd *ncmd;
    @@ -1161,11 +1161,16 @@ static void send_rx_ctrl_cmd(struct lio *lio, int start_stop)
    int retval;

    if (oct->props[lio->ifidx].rx_on == start_stop)
    - return;
    + return 0;

    sc = (struct octeon_soft_command *)
    octeon_alloc_soft_command(oct, OCTNET_CMD_SIZE,
    16, 0);
    + if (!sc) {
    + netif_info(lio, rx_err, lio->netdev,
    + "Failed to allocate octeon_soft_command struct\n");
    + return -ENOMEM;
    + }

    ncmd = (union octnet_cmd *)sc->virtdptr;

    @@ -1187,18 +1192,19 @@ static void send_rx_ctrl_cmd(struct lio *lio, int start_stop)
    if (retval == IQ_SEND_FAILED) {
    netif_info(lio, rx_err, lio->netdev, "Failed to send RX Control message\n");
    octeon_free_soft_command(oct, sc);
    - return;
    } else {
    /* Sleep on a wait queue till the cond flag indicates that the
    * response arrived or timed-out.
    */
    retval = wait_for_sc_completion_timeout(oct, sc, 0);
    if (retval)
    - return;
    + return retval;

    oct->props[lio->ifidx].rx_on = start_stop;
    WRITE_ONCE(sc->caller_is_done, true);
    }
    +
    + return retval;
    }

    /**
    @@ -1773,6 +1779,7 @@ static int liquidio_open(struct net_device *netdev)
    struct octeon_device_priv *oct_priv =
    (struct octeon_device_priv *)oct->priv;
    struct napi_struct *napi, *n;
    + int ret = 0;

    if (oct->props[lio->ifidx].napi_enabled == 0) {
    tasklet_disable(&oct_priv->droq_tasklet);
    @@ -1808,7 +1815,9 @@ static int liquidio_open(struct net_device *netdev)
    netif_info(lio, ifup, lio->netdev, "Interface Open, ready for traffic\n");

    /* tell Octeon to start forwarding packets to host */
    - send_rx_ctrl_cmd(lio, 1);
    + ret = send_rx_ctrl_cmd(lio, 1);
    + if (ret)
    + return ret;

    /* start periodical statistics fetch */
    INIT_DELAYED_WORK(&lio->stats_wk.work, lio_fetch_stats);
    @@ -1819,7 +1828,7 @@ static int liquidio_open(struct net_device *netdev)
    dev_info(&oct->pci_dev->dev, "%s interface is opened\n",
    netdev->name);

    - return 0;
    + return ret;
    }

    /**
    @@ -1833,6 +1842,7 @@ static int liquidio_stop(struct net_device *netdev)
    struct octeon_device_priv *oct_priv =
    (struct octeon_device_priv *)oct->priv;
    struct napi_struct *napi, *n;
    + int ret = 0;

    ifstate_reset(lio, LIO_IFSTATE_RUNNING);

    @@ -1849,7 +1859,9 @@ static int liquidio_stop(struct net_device *netdev)
    lio->link_changes++;

    /* Tell Octeon that nic interface is down. */
    - send_rx_ctrl_cmd(lio, 0);
    + ret = send_rx_ctrl_cmd(lio, 0);
    + if (ret)
    + return ret;

    if (OCTEON_CN23XX_PF(oct)) {
    if (!oct->msix_on)
    @@ -1884,7 +1896,7 @@ static int liquidio_stop(struct net_device *netdev)

    dev_info(&oct->pci_dev->dev, "%s interface is stopped\n", netdev->name);

    - return 0;
    + return ret;
    }

    /**
    diff --git a/drivers/net/ethernet/cavium/liquidio/lio_vf_main.c b/drivers/net/ethernet/cavium/liquidio/lio_vf_main.c
    index 103440f97bc8..226a7842d2fd 100644
    --- a/drivers/net/ethernet/cavium/liquidio/lio_vf_main.c
    +++ b/drivers/net/ethernet/cavium/liquidio/lio_vf_main.c
    @@ -595,7 +595,7 @@ static void octeon_destroy_resources(struct octeon_device *oct)
    * @lio: per-network private data
    * @start_stop: whether to start or stop
    */
    -static void send_rx_ctrl_cmd(struct lio *lio, int start_stop)
    +static int send_rx_ctrl_cmd(struct lio *lio, int start_stop)
    {
    struct octeon_device *oct = (struct octeon_device *)lio->oct_dev;
    struct octeon_soft_command *sc;
    @@ -603,11 +603,16 @@ static void send_rx_ctrl_cmd(struct lio *lio, int start_stop)
    int retval;

    if (oct->props[lio->ifidx].rx_on == start_stop)
    - return;
    + return 0;

    sc = (struct octeon_soft_command *)
    octeon_alloc_soft_command(oct, OCTNET_CMD_SIZE,
    16, 0);
    + if (!sc) {
    + netif_info(lio, rx_err, lio->netdev,
    + "Failed to allocate octeon_soft_command struct\n");
    + return -ENOMEM;
    + }

    ncmd = (union octnet_cmd *)sc->virtdptr;

    @@ -635,11 +640,13 @@ static void send_rx_ctrl_cmd(struct lio *lio, int start_stop)
    */
    retval = wait_for_sc_completion_timeout(oct, sc, 0);
    if (retval)
    - return;
    + return retval;

    oct->props[lio->ifidx].rx_on = start_stop;
    WRITE_ONCE(sc->caller_is_done, true);
    }
    +
    + return retval;
    }

    /**
    @@ -906,6 +913,7 @@ static int liquidio_open(struct net_device *netdev)
    struct octeon_device_priv *oct_priv =
    (struct octeon_device_priv *)oct->priv;
    struct napi_struct *napi, *n;
    + int ret = 0;

    if (!oct->props[lio->ifidx].napi_enabled) {
    tasklet_disable(&oct_priv->droq_tasklet);
    @@ -932,11 +940,13 @@ static int liquidio_open(struct net_device *netdev)
    (LIQUIDIO_NDEV_STATS_POLL_TIME_MS));

    /* tell Octeon to start forwarding packets to host */
    - send_rx_ctrl_cmd(lio, 1);
    + ret = send_rx_ctrl_cmd(lio, 1);
    + if (ret)
    + return ret;

    dev_info(&oct->pci_dev->dev, "%s interface is opened\n", netdev->name);

    - return 0;
    + return ret;
    }

    /**
    @@ -950,9 +960,12 @@ static int liquidio_stop(struct net_device *netdev)
    struct octeon_device_priv *oct_priv =
    (struct octeon_device_priv *)oct->priv;
    struct napi_struct *napi, *n;
    + int ret = 0;

    /* tell Octeon to stop forwarding packets to host */
    - send_rx_ctrl_cmd(lio, 0);
    + ret = send_rx_ctrl_cmd(lio, 0);
    + if (ret)
    + return ret;

    netif_info(lio, ifdown, lio->netdev, "Stopping interface!\n");
    /* Inform that netif carrier is down */
    @@ -986,7 +999,7 @@ static int liquidio_stop(struct net_device *netdev)

    dev_info(&oct->pci_dev->dev, "%s interface is stopped\n", netdev->name);

    - return 0;
    + return ret;
    }

    /**
    --
    2.30.2
    \
     
     \ /
      Last update: 2021-05-24 17:00    [W:3.744 / U:0.056 seconds]
    ©2003-2020 Jasper Spaans|hosted at Digital Ocean and TransIP|Read the blog|Advertise on this site