net: hns3: fix for RSS configuration loss problem during reset
authorYunsheng Lin <linyunsheng@huawei.com>
Fri, 9 Mar 2018 02:36:58 +0000 (10:36 +0800)
committerDavid S. Miller <davem@davemloft.net>
Fri, 9 Mar 2018 16:33:13 +0000 (11:33 -0500)
RSS configuration will be set to default value by hclge_rss_init_hw
during reset, which causes the RSS configuration loss problem.

This patch fixes it by setting the default value in
hclge_rss_init_cfg function, which will not be called in the reset
process.

Signed-off-by: Yunsheng Lin <linyunsheng@huawei.com>
Signed-off-by: Peng Li <lipeng321@huawei.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_dcb.c
drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.h

index 5018d66331337647515dd15cc35d422d1f242780..407cfabe6d2122c6b509e67b8c828be336b94e96 100644 (file)
@@ -144,6 +144,8 @@ static int hclge_map_update(struct hnae3_handle *h)
        if (ret)
                return ret;
 
+       hclge_rss_indir_init_cfg(hdev);
+
        return hclge_rss_init_hw(hdev);
 }
 
index 747cc8f00116019ab9f900f824c789afd457ecc2..34a09057e7c818bf576741e4ed2bd2a59fb305df 100644 (file)
@@ -3329,67 +3329,28 @@ static int hclge_get_tc_size(struct hnae3_handle *handle)
 
 int hclge_rss_init_hw(struct hclge_dev *hdev)
 {
-       const  u8 hfunc = HCLGE_RSS_HASH_ALGO_TOEPLITZ;
        struct hclge_vport *vport = hdev->vport;
+       u8 *rss_indir = vport[0].rss_indirection_tbl;
+       u16 rss_size = vport[0].alloc_rss_size;
+       u8 *key = vport[0].rss_hash_key;
+       u8 hfunc = vport[0].rss_algo;
        u16 tc_offset[HCLGE_MAX_TC_NUM];
-       u8 rss_key[HCLGE_RSS_KEY_SIZE];
        u16 tc_valid[HCLGE_MAX_TC_NUM];
        u16 tc_size[HCLGE_MAX_TC_NUM];
-       u32 *rss_indir = NULL;
-       u16 rss_size = 0, roundup_size;
-       const u8 *key;
-       int i, ret, j;
-
-       rss_indir = kcalloc(HCLGE_RSS_IND_TBL_SIZE, sizeof(u32), GFP_KERNEL);
-       if (!rss_indir)
-               return -ENOMEM;
-
-       /* Get default RSS key */
-       netdev_rss_key_fill(rss_key, HCLGE_RSS_KEY_SIZE);
-
-       /* Initialize RSS indirect table for each vport */
-       for (j = 0; j < hdev->num_vmdq_vport + 1; j++) {
-               vport[j].rss_tuple_sets.ipv4_tcp_en =
-                       HCLGE_RSS_INPUT_TUPLE_OTHER;
-               vport[j].rss_tuple_sets.ipv4_udp_en =
-                       HCLGE_RSS_INPUT_TUPLE_OTHER;
-               vport[j].rss_tuple_sets.ipv4_sctp_en =
-                       HCLGE_RSS_INPUT_TUPLE_SCTP;
-               vport[j].rss_tuple_sets.ipv4_fragment_en =
-                       HCLGE_RSS_INPUT_TUPLE_OTHER;
-               vport[j].rss_tuple_sets.ipv6_tcp_en =
-                       HCLGE_RSS_INPUT_TUPLE_OTHER;
-               vport[j].rss_tuple_sets.ipv6_udp_en =
-                       HCLGE_RSS_INPUT_TUPLE_OTHER;
-               vport[j].rss_tuple_sets.ipv6_sctp_en =
-                       HCLGE_RSS_INPUT_TUPLE_SCTP;
-               vport[j].rss_tuple_sets.ipv6_fragment_en =
-                       HCLGE_RSS_INPUT_TUPLE_OTHER;
-
-               for (i = 0; i < HCLGE_RSS_IND_TBL_SIZE; i++) {
-                       vport[j].rss_indirection_tbl[i] =
-                               i % vport[j].alloc_rss_size;
-
-                       /* vport 0 is for PF */
-                       if (j != 0)
-                               continue;
+       u16 roundup_size;
+       int i, ret;
 
-                       rss_size = vport[j].alloc_rss_size;
-                       rss_indir[i] = vport[j].rss_indirection_tbl[i];
-               }
-       }
        ret = hclge_set_rss_indir_table(hdev, rss_indir);
        if (ret)
-               goto err;
+               return ret;
 
-       key = rss_key;
        ret = hclge_set_rss_algo_key(hdev, hfunc, key);
        if (ret)
-               goto err;
+               return ret;
 
        ret = hclge_set_rss_input_tuple(hdev);
        if (ret)
-               goto err;
+               return ret;
 
        /* Each TC have the same queue size, and tc_size set to hardware is
         * the log2 of roundup power of two of rss_size, the acutal queue
@@ -3399,8 +3360,7 @@ int hclge_rss_init_hw(struct hclge_dev *hdev)
                dev_err(&hdev->pdev->dev,
                        "Configure rss tc size failed, invalid TC_SIZE = %d\n",
                        rss_size);
-               ret = -EINVAL;
-               goto err;
+               return -EINVAL;
        }
 
        roundup_size = roundup_pow_of_two(rss_size);
@@ -3417,12 +3377,50 @@ int hclge_rss_init_hw(struct hclge_dev *hdev)
                tc_offset[i] = rss_size * i;
        }
 
-       ret = hclge_set_rss_tc_mode(hdev, tc_valid, tc_size, tc_offset);
+       return hclge_set_rss_tc_mode(hdev, tc_valid, tc_size, tc_offset);
+}
 
-err:
-       kfree(rss_indir);
+void hclge_rss_indir_init_cfg(struct hclge_dev *hdev)
+{
+       struct hclge_vport *vport = hdev->vport;
+       int i, j;
 
-       return ret;
+       for (j = 0; j < hdev->num_vmdq_vport + 1; j++) {
+               for (i = 0; i < HCLGE_RSS_IND_TBL_SIZE; i++)
+                       vport[j].rss_indirection_tbl[i] =
+                               i % vport[j].alloc_rss_size;
+       }
+}
+
+static void hclge_rss_init_cfg(struct hclge_dev *hdev)
+{
+       struct hclge_vport *vport = hdev->vport;
+       int i;
+
+       netdev_rss_key_fill(vport->rss_hash_key, HCLGE_RSS_KEY_SIZE);
+
+       for (i = 0; i < hdev->num_vmdq_vport + 1; i++) {
+               vport[i].rss_tuple_sets.ipv4_tcp_en =
+                       HCLGE_RSS_INPUT_TUPLE_OTHER;
+               vport[i].rss_tuple_sets.ipv4_udp_en =
+                       HCLGE_RSS_INPUT_TUPLE_OTHER;
+               vport[i].rss_tuple_sets.ipv4_sctp_en =
+                       HCLGE_RSS_INPUT_TUPLE_SCTP;
+               vport[i].rss_tuple_sets.ipv4_fragment_en =
+                       HCLGE_RSS_INPUT_TUPLE_OTHER;
+               vport[i].rss_tuple_sets.ipv6_tcp_en =
+                       HCLGE_RSS_INPUT_TUPLE_OTHER;
+               vport[i].rss_tuple_sets.ipv6_udp_en =
+                       HCLGE_RSS_INPUT_TUPLE_OTHER;
+               vport[i].rss_tuple_sets.ipv6_sctp_en =
+                       HCLGE_RSS_INPUT_TUPLE_SCTP;
+               vport[i].rss_tuple_sets.ipv6_fragment_en =
+                       HCLGE_RSS_INPUT_TUPLE_OTHER;
+
+               vport[i].rss_algo = HCLGE_RSS_HASH_ALGO_TOEPLITZ;
+       }
+
+       hclge_rss_indir_init_cfg(hdev);
 }
 
 int hclge_bind_ring_with_vector(struct hclge_vport *vport,
@@ -5390,6 +5388,7 @@ static int hclge_init_ae_dev(struct hnae3_ae_dev *ae_dev)
                return ret;
        }
 
+       hclge_rss_init_cfg(hdev);
        ret = hclge_rss_init_hw(hdev);
        if (ret) {
                dev_err(&pdev->dev, "Rss init fail, ret =%d\n", ret);
index 13d399931d932b12790fec2b2c69752eee71144c..7bff6efe3e6d8372b023de75fb68572cc24fd3e9 100644 (file)
@@ -642,6 +642,7 @@ int hclge_set_vf_vlan_common(struct hclge_dev *vport, int vfid,
 
 int hclge_buffer_alloc(struct hclge_dev *hdev);
 int hclge_rss_init_hw(struct hclge_dev *hdev);
+void hclge_rss_indir_init_cfg(struct hclge_dev *hdev);
 
 void hclge_mbx_handler(struct hclge_dev *hdev);
 void hclge_reset_tqp(struct hnae3_handle *handle, u16 queue_id);