Add the flow stats process logic in the ctrl VNIC service. The flower firmware pass the flow stats to nfp driver through control message, we store them in the flow_priv structure.
Signed-off-by: Chaoyong He <chaoyong...@corigine.com> Reviewed-by: Niklas Söderlund <niklas.soderl...@corigine.com> --- drivers/net/nfp/flower/nfp_flower.h | 2 + drivers/net/nfp/flower/nfp_flower_cmsg.h | 25 +++++++++++ drivers/net/nfp/flower/nfp_flower_ctrl.c | 73 ++++++++++++++++++++++++++++++-- drivers/net/nfp/nfp_flow.h | 20 +++++++++ 4 files changed, 116 insertions(+), 4 deletions(-) create mode 100644 drivers/net/nfp/nfp_flow.h diff --git a/drivers/net/nfp/flower/nfp_flower.h b/drivers/net/nfp/flower/nfp_flower.h index 48f597a..b90391c 100644 --- a/drivers/net/nfp/flower/nfp_flower.h +++ b/drivers/net/nfp/flower/nfp_flower.h @@ -51,6 +51,8 @@ struct nfp_app_fw_flower { /* PF representor */ struct nfp_flower_representor *pf_repr; + + struct nfp_flow_priv *flow_priv; }; int nfp_init_app_fw_flower(struct nfp_pf_dev *pf_dev); diff --git a/drivers/net/nfp/flower/nfp_flower_cmsg.h b/drivers/net/nfp/flower/nfp_flower_cmsg.h index 0bf8fc8..5c28363 100644 --- a/drivers/net/nfp/flower/nfp_flower_cmsg.h +++ b/drivers/net/nfp/flower/nfp_flower_cmsg.h @@ -129,6 +129,31 @@ struct nfp_flower_cmsg_port_mod { rte_be16_t mtu; }; +/* + * NFP_FLOWER_CMSG_TYPE_FLOW_STATS + * Bit 3 3 2 2 2 2 2 2 2 2 2 2 1 1 1 1 1 1 1 1 1 1 0 0 0 0 0 0 0 0 0 0 + * -----\ 1 0 9 8 7 6 5 4 3 2 1 0 9 8 7 6 5 4 3 2 1 0 9 8 7 6 5 4 3 2 1 0 + * Word +---------------+-----------------------------------------------+ + * 0 | Reserved | Host Context | + * +---------------+-----------------------------------------------+ + * 1 | Packet Count | + * +---------------------------------------------------------------+ + * 2 | Byte Count | + * +---------------------------------------------------------------+ + * 2 | Byte Count | + * +---------------------------------------------------------------+ + * 3 | Host Cookie | + * +---------------------------------------------------------------+ + * 4 | Host Cookie | + * +---------------------------------------------------------------+ + */ +struct nfp_flower_stats_frame { + rte_be32_t stats_con_id; + rte_be32_t pkt_count; + rte_be64_t byte_count; + rte_be64_t stats_cookie; +}; + enum nfp_flower_cmsg_port_type { NFP_FLOWER_CMSG_PORT_TYPE_UNSPEC, NFP_FLOWER_CMSG_PORT_TYPE_PHYS_PORT, diff --git a/drivers/net/nfp/flower/nfp_flower_ctrl.c b/drivers/net/nfp/flower/nfp_flower_ctrl.c index df908ef..bb9efe1 100644 --- a/drivers/net/nfp/flower/nfp_flower_ctrl.c +++ b/drivers/net/nfp/flower/nfp_flower_ctrl.c @@ -10,8 +10,10 @@ #include "../nfp_logs.h" #include "../nfp_ctrl.h" #include "../nfp_rxtx.h" +#include "nfp_flow.h" #include "nfp_flower.h" #include "nfp_flower_ctrl.h" +#include "nfp_flower_cmsg.h" #define MAX_PKT_BURST 32 @@ -222,10 +224,74 @@ return cnt; } +static void +nfp_flower_cmsg_rx_stats(struct nfp_flow_priv *flow_priv, + struct rte_mbuf *mbuf) +{ + char *msg; + uint16_t i; + uint16_t count; + uint16_t msg_len; + uint32_t ctx_id; + struct nfp_flower_stats_frame *stats; + + msg = rte_pktmbuf_mtod(mbuf, char *) + NFP_FLOWER_CMSG_HLEN; + msg_len = mbuf->data_len - NFP_FLOWER_CMSG_HLEN; + count = msg_len / sizeof(struct nfp_flower_stats_frame); + + rte_spinlock_lock(&flow_priv->stats_lock); + for (i = 0; i < count; i++) { + stats = (struct nfp_flower_stats_frame *)msg + i; + ctx_id = rte_be_to_cpu_32(stats->stats_con_id); + flow_priv->stats[ctx_id].pkts += rte_be_to_cpu_32(stats->pkt_count); + flow_priv->stats[ctx_id].bytes += rte_be_to_cpu_64(stats->byte_count); + } + rte_spinlock_unlock(&flow_priv->stats_lock); +} + +static void +nfp_flower_cmsg_rx(struct nfp_flow_priv *flow_priv, + struct rte_mbuf **pkts_burst, + uint16_t count) +{ + uint16_t i; + char *meta; + uint32_t meta_type; + uint32_t meta_info; + struct nfp_flower_cmsg_hdr *cmsg_hdr; + + for (i = 0; i < count; i++) { + meta = rte_pktmbuf_mtod(pkts_burst[i], char *); + + /* Free the unsupported ctrl packet */ + meta_type = rte_be_to_cpu_32(*(uint32_t *)(meta - 8)); + meta_info = rte_be_to_cpu_32(*(uint32_t *)(meta - 4)); + if (meta_type != NFP_NET_META_PORTID || + meta_info != NFP_META_PORT_ID_CTRL) { + PMD_DRV_LOG(ERR, "Incorrect metadata for ctrl packet!"); + rte_pktmbuf_free(pkts_burst[i]); + continue; + } + + cmsg_hdr = (struct nfp_flower_cmsg_hdr *)meta; + if (unlikely(cmsg_hdr->version != NFP_FLOWER_CMSG_VER1)) { + PMD_DRV_LOG(ERR, "Incorrect repr control version!"); + rte_pktmbuf_free(pkts_burst[i]); + continue; + } + + if (cmsg_hdr->type == NFP_FLOWER_CMSG_TYPE_FLOW_STATS) { + /* We need to deal with stats updates from HW asap */ + nfp_flower_cmsg_rx_stats(flow_priv, pkts_burst[i]); + } + + rte_pktmbuf_free(pkts_burst[i]); + } +} + void nfp_flower_ctrl_vnic_poll(struct nfp_app_fw_flower *app_fw_flower) { - uint16_t i; uint16_t count; struct nfp_net_rxq *rxq; struct nfp_net_hw *ctrl_hw; @@ -242,9 +308,8 @@ count = nfp_flower_ctrl_vnic_recv(rxq, pkts_burst, MAX_PKT_BURST); if (count != 0) { app_fw_flower->ctrl_vnic_rx_count += count; - /* Process cmsgs here, only free for now */ - for (i = 0; i < count; i++) - rte_pktmbuf_free(pkts_burst[i]); + /* Process cmsgs here */ + nfp_flower_cmsg_rx(app_fw_flower->flow_priv, pkts_burst, count); } } } diff --git a/drivers/net/nfp/nfp_flow.h b/drivers/net/nfp/nfp_flow.h new file mode 100644 index 0000000..971ba69 --- /dev/null +++ b/drivers/net/nfp/nfp_flow.h @@ -0,0 +1,20 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright (c) 2022 Corigine, Inc. + * All rights reserved. + */ + +#ifndef _NFP_FLOW_H_ +#define _NFP_FLOW_H_ + +struct nfp_fl_stats { + uint64_t pkts; + uint64_t bytes; +}; + +struct nfp_flow_priv { + /* flow stats */ + struct nfp_fl_stats *stats; /**< Store stats of flow. */ + rte_spinlock_t stats_lock; /** < Lock the update of 'stats' field. */ +}; + +#endif /* _NFP_FLOW_H_ */ -- 1.8.3.1