lkml.org 
[lkml]   [2018]   [Dec]   [11]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
    Patch in this message
    /
    From
    Subject[PATCH 4.14 23/67] qed: Fix QM getters to always return a valid pq
    Date
    4.14-stable review patch.  If anyone has any objections, please let me know.

    ------------------

    [ Upstream commit eb62cca9bee842e5b23bd0ddfb1f271ca95e8759 ]

    The getter callers doesn't know the valid Physical Queues (PQ) values.
    This patch makes sure that a valid PQ will always be returned.

    The patch consists of 3 fixes:

    - When qed_init_qm_get_idx_from_flags() receives a disabled flag, it
    returned PQ 0, which can potentially be another function's pq. Verify
    that flag is enabled, otherwise return default start_pq.

    - When qed_init_qm_get_idx_from_flags() receives an unknown flag, it
    returned NULL and could lead to a segmentation fault. Return default
    start_pq instead.

    - A modulo operation was added to MCOS/VFS PQ getters to make sure the
    PQ returned is in range of the required flag.

    Fixes: b5a9ee7cf3be ("qed: Revise QM cofiguration")
    Signed-off-by: Denis Bolotin <denis.bolotin@cavium.com>
    Signed-off-by: Michal Kalderon <michal.kalderon@cavium.com>
    Signed-off-by: David S. Miller <davem@davemloft.net>
    Signed-off-by: Sasha Levin <sashal@kernel.org>
    ---
    drivers/net/ethernet/qlogic/qed/qed_dev.c | 24 +++++++++++++++++++----
    1 file changed, 20 insertions(+), 4 deletions(-)

    diff --git a/drivers/net/ethernet/qlogic/qed/qed_dev.c b/drivers/net/ethernet/qlogic/qed/qed_dev.c
    index a51cd1028ecb..16953c4ebd71 100644
    --- a/drivers/net/ethernet/qlogic/qed/qed_dev.c
    +++ b/drivers/net/ethernet/qlogic/qed/qed_dev.c
    @@ -446,6 +446,11 @@ static u16 *qed_init_qm_get_idx_from_flags(struct qed_hwfn *p_hwfn,
    goto err;
    }

    + if (!(qed_get_pq_flags(p_hwfn) & pq_flags)) {
    + DP_ERR(p_hwfn, "pq flag 0x%x is not set\n", pq_flags);
    + goto err;
    + }
    +
    switch (pq_flags) {
    case PQ_FLAGS_RLS:
    return &qm_info->first_rl_pq;
    @@ -468,8 +473,7 @@ static u16 *qed_init_qm_get_idx_from_flags(struct qed_hwfn *p_hwfn,
    }

    err:
    - DP_ERR(p_hwfn, "BAD pq flags %d\n", pq_flags);
    - return NULL;
    + return &qm_info->start_pq;
    }

    /* save pq index in qm info */
    @@ -493,20 +497,32 @@ u16 qed_get_cm_pq_idx_mcos(struct qed_hwfn *p_hwfn, u8 tc)
    {
    u8 max_tc = qed_init_qm_get_num_tcs(p_hwfn);

    + if (max_tc == 0) {
    + DP_ERR(p_hwfn, "pq with flag 0x%lx do not exist\n",
    + PQ_FLAGS_MCOS);
    + return p_hwfn->qm_info.start_pq;
    + }
    +
    if (tc > max_tc)
    DP_ERR(p_hwfn, "tc %d must be smaller than %d\n", tc, max_tc);

    - return qed_get_cm_pq_idx(p_hwfn, PQ_FLAGS_MCOS) + tc;
    + return qed_get_cm_pq_idx(p_hwfn, PQ_FLAGS_MCOS) + (tc % max_tc);
    }

    u16 qed_get_cm_pq_idx_vf(struct qed_hwfn *p_hwfn, u16 vf)
    {
    u16 max_vf = qed_init_qm_get_num_vfs(p_hwfn);

    + if (max_vf == 0) {
    + DP_ERR(p_hwfn, "pq with flag 0x%lx do not exist\n",
    + PQ_FLAGS_VFS);
    + return p_hwfn->qm_info.start_pq;
    + }
    +
    if (vf > max_vf)
    DP_ERR(p_hwfn, "vf %d must be smaller than %d\n", vf, max_vf);

    - return qed_get_cm_pq_idx(p_hwfn, PQ_FLAGS_VFS) + vf;
    + return qed_get_cm_pq_idx(p_hwfn, PQ_FLAGS_VFS) + (vf % max_vf);
    }

    u16 qed_get_cm_pq_idx_rl(struct qed_hwfn *p_hwfn, u8 rl)
    --
    2.19.1


    \
     
     \ /
      Last update: 2018-12-11 17:11    [W:4.049 / U:0.032 seconds]
    ©2003-2020 Jasper Spaans|hosted at Digital Ocean and TransIP|Read the blog|Advertise on this site