Skip to content

Commit

Permalink
Merge branch 'hns3-next'
Browse files Browse the repository at this point in the history
Huazhong Tan says:

====================
net: hns3: updates for -next

This patchset adds support for tc mqprio offload, hw tc
offload of tc flower, and adpation for max rss size changes.
====================

Signed-off-by: David S. Miller <[email protected]>
  • Loading branch information
davem330 committed Dec 10, 2020
2 parents c0ead55 + cdab7c9 commit a7105e3
Show file tree
Hide file tree
Showing 12 changed files with 759 additions and 151 deletions.
34 changes: 24 additions & 10 deletions drivers/net/ethernet/hisilicon/hns3/hnae3.h
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,9 @@
#include <linux/module.h>
#include <linux/netdevice.h>
#include <linux/pci.h>
#include <linux/pkt_sched.h>
#include <linux/types.h>
#include <net/pkt_cls.h>

#define HNAE3_MOD_VERSION "1.0"

Expand Down Expand Up @@ -457,6 +459,12 @@ struct hnae3_ae_dev {
* Configure the default MAC for specified VF
* get_module_eeprom
* Get the optical module eeprom info.
* add_cls_flower
* Add clsflower rule
* del_cls_flower
* Delete clsflower rule
* cls_flower_active
* Check if any cls flower rule exist
*/
struct hnae3_ae_ops {
int (*init_ae_dev)(struct hnae3_ae_dev *ae_dev);
Expand Down Expand Up @@ -634,6 +642,11 @@ struct hnae3_ae_ops {
int (*get_module_eeprom)(struct hnae3_handle *handle, u32 offset,
u32 len, u8 *data);
bool (*get_cmdq_stat)(struct hnae3_handle *handle);
int (*add_cls_flower)(struct hnae3_handle *handle,
struct flow_cls_offload *cls_flower, int tc);
int (*del_cls_flower)(struct hnae3_handle *handle,
struct flow_cls_offload *cls_flower);
bool (*cls_flower_active)(struct hnae3_handle *handle);
};

struct hnae3_dcb_ops {
Expand All @@ -647,7 +660,8 @@ struct hnae3_dcb_ops {
u8 (*getdcbx)(struct hnae3_handle *);
u8 (*setdcbx)(struct hnae3_handle *, u8);

int (*setup_tc)(struct hnae3_handle *, u8, u8 *);
int (*setup_tc)(struct hnae3_handle *handle,
struct tc_mqprio_qopt_offload *mqprio_qopt);
};

struct hnae3_ae_algo {
Expand All @@ -659,15 +673,17 @@ struct hnae3_ae_algo {
#define HNAE3_INT_NAME_LEN 32
#define HNAE3_ITR_COUNTDOWN_START 100

#define HNAE3_MAX_TC 8
#define HNAE3_MAX_USER_PRIO 8
struct hnae3_tc_info {
u16 tqp_offset; /* TQP offset from base TQP */
u16 tqp_count; /* Total TQPs */
u8 tc; /* TC index */
bool enable; /* If this TC is enable or not */
u8 prio_tc[HNAE3_MAX_USER_PRIO]; /* TC indexed by prio */
u16 tqp_count[HNAE3_MAX_TC];
u16 tqp_offset[HNAE3_MAX_TC];
unsigned long tc_en; /* bitmap of TC enabled */
u8 num_tc; /* Total number of enabled TCs */
bool mqprio_active;
};

#define HNAE3_MAX_TC 8
#define HNAE3_MAX_USER_PRIO 8
struct hnae3_knic_private_info {
struct net_device *netdev; /* Set by KNIC client when init instance */
u16 rss_size; /* Allocated RSS queues */
Expand All @@ -676,9 +692,7 @@ struct hnae3_knic_private_info {
u16 num_tx_desc;
u16 num_rx_desc;

u8 num_tc; /* Total number of enabled TCs */
u8 prio_tc[HNAE3_MAX_USER_PRIO]; /* TC indexed by prio */
struct hnae3_tc_info tc_info[HNAE3_MAX_TC]; /* Idx of array is HW TC */
struct hnae3_tc_info tc_info;

u16 num_tqps; /* total number of TQPs in this handle */
struct hnae3_queue **tqp; /* array base of all TQPs in this instance */
Expand Down
3 changes: 2 additions & 1 deletion drivers/net/ethernet/hisilicon/hns3/hns3_debugfs.c
Original file line number Diff line number Diff line change
Expand Up @@ -385,7 +385,8 @@ static void hns3_dbg_dev_specs(struct hnae3_handle *h)
dev_info(priv->dev, "RX buffer length: %u\n", kinfo->rx_buf_len);
dev_info(priv->dev, "Desc num per TX queue: %u\n", kinfo->num_tx_desc);
dev_info(priv->dev, "Desc num per RX queue: %u\n", kinfo->num_rx_desc);
dev_info(priv->dev, "Total number of enabled TCs: %u\n", kinfo->num_tc);
dev_info(priv->dev, "Total number of enabled TCs: %u\n",
kinfo->tc_info.num_tc);
dev_info(priv->dev, "MAX INT QL: %u\n", dev_specs->int_ql_max);
dev_info(priv->dev, "MAX INT GL: %u\n", dev_specs->max_int_gl);
}
Expand Down
112 changes: 91 additions & 21 deletions drivers/net/ethernet/hisilicon/hns3/hns3_enet.c
Original file line number Diff line number Diff line change
Expand Up @@ -323,27 +323,26 @@ static int hns3_nic_set_real_num_queue(struct net_device *netdev)
{
struct hnae3_handle *h = hns3_get_handle(netdev);
struct hnae3_knic_private_info *kinfo = &h->kinfo;
unsigned int queue_size = kinfo->rss_size * kinfo->num_tc;
struct hnae3_tc_info *tc_info = &kinfo->tc_info;
unsigned int queue_size = kinfo->num_tqps;
int i, ret;

if (kinfo->num_tc <= 1) {
if (tc_info->num_tc <= 1 && !tc_info->mqprio_active) {
netdev_reset_tc(netdev);
} else {
ret = netdev_set_num_tc(netdev, kinfo->num_tc);
ret = netdev_set_num_tc(netdev, tc_info->num_tc);
if (ret) {
netdev_err(netdev,
"netdev_set_num_tc fail, ret=%d!\n", ret);
return ret;
}

for (i = 0; i < HNAE3_MAX_TC; i++) {
if (!kinfo->tc_info[i].enable)
if (!test_bit(i, &tc_info->tc_en))
continue;

netdev_set_tc_queue(netdev,
kinfo->tc_info[i].tc,
kinfo->tc_info[i].tqp_count,
kinfo->tc_info[i].tqp_offset);
netdev_set_tc_queue(netdev, i, tc_info->tqp_count[i],
tc_info->tqp_offset[i]);
}
}

Expand All @@ -369,7 +368,7 @@ static u16 hns3_get_max_available_channels(struct hnae3_handle *h)
u16 alloc_tqps, max_rss_size, rss_size;

h->ae_algo->ops->get_tqps_and_rss_info(h, &alloc_tqps, &max_rss_size);
rss_size = alloc_tqps / h->kinfo.num_tc;
rss_size = alloc_tqps / h->kinfo.tc_info.num_tc;

return min_t(u16, rss_size, max_rss_size);
}
Expand Down Expand Up @@ -508,7 +507,7 @@ static int hns3_nic_net_open(struct net_device *netdev)

kinfo = &h->kinfo;
for (i = 0; i < HNAE3_MAX_USER_PRIO; i++)
netdev_set_prio_tc_map(netdev, i, kinfo->prio_tc[i]);
netdev_set_prio_tc_map(netdev, i, kinfo->tc_info.prio_tc[i]);

if (h->ae_algo->ops->set_timer_task)
h->ae_algo->ops->set_timer_task(priv->ae_handle, true);
Expand Down Expand Up @@ -1669,6 +1668,13 @@ static int hns3_nic_set_features(struct net_device *netdev,
h->ae_algo->ops->enable_fd(h, enable);
}

if ((netdev->features & NETIF_F_HW_TC) > (features & NETIF_F_HW_TC) &&
h->ae_algo->ops->cls_flower_active(h)) {
netdev_err(netdev,
"there are offloaded TC filters active, cannot disable HW TC offload");
return -EINVAL;
}

netdev->features = features;
return 0;
}
Expand Down Expand Up @@ -1794,7 +1800,6 @@ static void hns3_nic_get_stats64(struct net_device *netdev,
static int hns3_setup_tc(struct net_device *netdev, void *type_data)
{
struct tc_mqprio_qopt_offload *mqprio_qopt = type_data;
u8 *prio_tc = mqprio_qopt->qopt.prio_tc_map;
struct hnae3_knic_private_info *kinfo;
u8 tc = mqprio_qopt->qopt.num_tc;
u16 mode = mqprio_qopt->mode;
Expand All @@ -1817,16 +1822,70 @@ static int hns3_setup_tc(struct net_device *netdev, void *type_data)
netif_dbg(h, drv, netdev, "setup tc: num_tc=%u\n", tc);

return (kinfo->dcb_ops && kinfo->dcb_ops->setup_tc) ?
kinfo->dcb_ops->setup_tc(h, tc ? tc : 1, prio_tc) : -EOPNOTSUPP;
kinfo->dcb_ops->setup_tc(h, mqprio_qopt) : -EOPNOTSUPP;
}

static int hns3_setup_tc_cls_flower(struct hns3_nic_priv *priv,
struct flow_cls_offload *flow)
{
int tc = tc_classid_to_hwtc(priv->netdev, flow->classid);
struct hnae3_handle *h = hns3_get_handle(priv->netdev);

switch (flow->command) {
case FLOW_CLS_REPLACE:
if (h->ae_algo->ops->add_cls_flower)
return h->ae_algo->ops->add_cls_flower(h, flow, tc);
break;
case FLOW_CLS_DESTROY:
if (h->ae_algo->ops->del_cls_flower)
return h->ae_algo->ops->del_cls_flower(h, flow);
break;
default:
break;
}

return -EOPNOTSUPP;
}

static int hns3_setup_tc_block_cb(enum tc_setup_type type, void *type_data,
void *cb_priv)
{
struct hns3_nic_priv *priv = cb_priv;

if (!tc_cls_can_offload_and_chain0(priv->netdev, type_data))
return -EOPNOTSUPP;

switch (type) {
case TC_SETUP_CLSFLOWER:
return hns3_setup_tc_cls_flower(priv, type_data);
default:
return -EOPNOTSUPP;
}
}

static LIST_HEAD(hns3_block_cb_list);

static int hns3_nic_setup_tc(struct net_device *dev, enum tc_setup_type type,
void *type_data)
{
if (type != TC_SETUP_QDISC_MQPRIO)
struct hns3_nic_priv *priv = netdev_priv(dev);
int ret;

switch (type) {
case TC_SETUP_QDISC_MQPRIO:
ret = hns3_setup_tc(dev, type_data);
break;
case TC_SETUP_BLOCK:
ret = flow_block_cb_setup_simple(type_data,
&hns3_block_cb_list,
hns3_setup_tc_block_cb,
priv, priv, true);
break;
default:
return -EOPNOTSUPP;
}

return hns3_setup_tc(dev, type_data);
return ret;
}

static int hns3_vlan_rx_add_vid(struct net_device *netdev,
Expand Down Expand Up @@ -2423,6 +2482,11 @@ static void hns3_set_default_feature(struct net_device *netdev)
netdev->vlan_features |= NETIF_F_GSO_UDP_TUNNEL_CSUM;
netdev->hw_enc_features |= NETIF_F_GSO_UDP_TUNNEL_CSUM;
}

if (test_bit(HNAE3_DEV_SUPPORT_FD_FORWARD_TC_B, ae_dev->caps)) {
netdev->hw_features |= NETIF_F_HW_TC;
netdev->features |= NETIF_F_HW_TC;
}
}

static int hns3_alloc_buffer(struct hns3_enet_ring *ring,
Expand Down Expand Up @@ -3980,21 +4044,20 @@ static void hns3_init_ring_hw(struct hns3_enet_ring *ring)
static void hns3_init_tx_ring_tc(struct hns3_nic_priv *priv)
{
struct hnae3_knic_private_info *kinfo = &priv->ae_handle->kinfo;
struct hnae3_tc_info *tc_info = &kinfo->tc_info;
int i;

for (i = 0; i < HNAE3_MAX_TC; i++) {
struct hnae3_tc_info *tc_info = &kinfo->tc_info[i];
int j;

if (!tc_info->enable)
if (!test_bit(i, &tc_info->tc_en))
continue;

for (j = 0; j < tc_info->tqp_count; j++) {
for (j = 0; j < tc_info->tqp_count[i]; j++) {
struct hnae3_queue *q;

q = priv->ring[tc_info->tqp_offset + j].tqp;
hns3_write_dev(q, HNS3_RING_TX_RING_TC_REG,
tc_info->tc);
q = priv->ring[tc_info->tqp_offset[i] + j].tqp;
hns3_write_dev(q, HNS3_RING_TX_RING_TC_REG, i);
}
}
}
Expand Down Expand Up @@ -4121,7 +4184,8 @@ static void hns3_info_show(struct hns3_nic_priv *priv)
dev_info(priv->dev, "RX buffer length: %u\n", kinfo->rx_buf_len);
dev_info(priv->dev, "Desc num per TX queue: %u\n", kinfo->num_tx_desc);
dev_info(priv->dev, "Desc num per RX queue: %u\n", kinfo->num_rx_desc);
dev_info(priv->dev, "Total number of enabled TCs: %u\n", kinfo->num_tc);
dev_info(priv->dev, "Total number of enabled TCs: %u\n",
kinfo->tc_info.num_tc);
dev_info(priv->dev, "Max mtu size: %u\n", priv->netdev->max_mtu);
}

Expand Down Expand Up @@ -4692,6 +4756,12 @@ int hns3_set_channels(struct net_device *netdev,
if (ch->rx_count || ch->tx_count)
return -EINVAL;

if (kinfo->tc_info.mqprio_active) {
dev_err(&netdev->dev,
"it's not allowed to set channels via ethtool when MQPRIO mode is on\n");
return -EINVAL;
}

if (new_tqp_num > hns3_get_max_available_channels(h) ||
new_tqp_num < 1) {
dev_err(&netdev->dev,
Expand Down
2 changes: 2 additions & 0 deletions drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.c
Original file line number Diff line number Diff line change
Expand Up @@ -359,6 +359,8 @@ static void hclge_parse_capability(struct hclge_dev *hdev,
set_bit(HNAE3_DEV_SUPPORT_HW_TX_CSUM_B, ae_dev->caps);
if (hnae3_get_bit(caps, HCLGE_CAP_UDP_TUNNEL_CSUM_B))
set_bit(HNAE3_DEV_SUPPORT_UDP_TUNNEL_CSUM_B, ae_dev->caps);
if (hnae3_get_bit(caps, HCLGE_CAP_FD_FORWARD_TC_B))
set_bit(HNAE3_DEV_SUPPORT_FD_FORWARD_TC_B, ae_dev->caps);
}

static enum hclge_cmd_status
Expand Down
16 changes: 13 additions & 3 deletions drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h
Original file line number Diff line number Diff line change
Expand Up @@ -518,6 +518,8 @@ struct hclge_pf_res_cmd {
#define HCLGE_CFG_SPEED_ABILITY_EXT_M GENMASK(15, 10)
#define HCLGE_CFG_UMV_TBL_SPACE_S 16
#define HCLGE_CFG_UMV_TBL_SPACE_M GENMASK(31, 16)
#define HCLGE_CFG_PF_RSS_SIZE_S 0
#define HCLGE_CFG_PF_RSS_SIZE_M GENMASK(3, 0)

#define HCLGE_CFG_CMD_CNT 4

Expand Down Expand Up @@ -558,18 +560,23 @@ struct hclge_rss_input_tuple_cmd {
};

#define HCLGE_RSS_CFG_TBL_SIZE 16
#define HCLGE_RSS_CFG_TBL_SIZE_H 4
#define HCLGE_RSS_CFG_TBL_BW_H 2U
#define HCLGE_RSS_CFG_TBL_BW_L 8U

struct hclge_rss_indirection_table_cmd {
__le16 start_table_index;
__le16 rss_set_bitmap;
u8 rsv[4];
u8 rss_result[HCLGE_RSS_CFG_TBL_SIZE];
u8 rss_qid_h[HCLGE_RSS_CFG_TBL_SIZE_H];
u8 rss_qid_l[HCLGE_RSS_CFG_TBL_SIZE];
};

#define HCLGE_RSS_TC_OFFSET_S 0
#define HCLGE_RSS_TC_OFFSET_M GENMASK(9, 0)
#define HCLGE_RSS_TC_OFFSET_M GENMASK(10, 0)
#define HCLGE_RSS_TC_SIZE_MSB_B 11
#define HCLGE_RSS_TC_SIZE_S 12
#define HCLGE_RSS_TC_SIZE_M GENMASK(14, 12)
#define HCLGE_RSS_TC_SIZE_MSB_OFFSET 3
#define HCLGE_RSS_TC_VALID_B 15
struct hclge_rss_tc_mode_cmd {
__le16 rss_tc_mode[HCLGE_MAX_TC_NUM];
Expand Down Expand Up @@ -1051,6 +1058,9 @@ struct hclge_fd_tcam_config_3_cmd {
#define HCLGE_FD_AD_WR_RULE_ID_B 0
#define HCLGE_FD_AD_RULE_ID_S 1
#define HCLGE_FD_AD_RULE_ID_M GENMASK(13, 1)
#define HCLGE_FD_AD_TC_OVRD_B 16
#define HCLGE_FD_AD_TC_SIZE_S 17
#define HCLGE_FD_AD_TC_SIZE_M GENMASK(20, 17)

struct hclge_fd_ad_config_cmd {
u8 stage;
Expand Down
Loading

0 comments on commit a7105e3

Please sign in to comment.