@@ -55,6 +55,7 @@ struct flow_nic_dev {
uint16_t ports; /* number of in-ports addressable on this NIC */
/* flow profile this NIC is initially prepared for */
enum flow_eth_dev_profile flow_profile;
+ int flow_mgnt_prepared;
struct hw_mod_resource_s res[RES_COUNT];/* raw NIC resource allocation table */
void *km_res_handle;
@@ -46,6 +46,11 @@ enum res_type_e {
*/
#define MAX_OUTPUT_DEST (128)
+struct flow_handle {
+ struct flow_eth_dev *dev;
+ struct flow_handle *next;
+};
+
void km_free_ndev_resource_management(void **handle);
void kcc_free_ndev_resource_management(void **handle);
@@ -210,10 +210,29 @@ static int nic_remove_eth_port_dev(struct flow_nic_dev *ndev, struct flow_eth_de
static void flow_ndev_reset(struct flow_nic_dev *ndev)
{
+ const struct profile_inline_ops *profile_inline_ops = get_profile_inline_ops();
+
+ if (profile_inline_ops == NULL) {
+ NT_LOG(ERR, FILTER, "%s: profile_inline module uninitialized", __func__);
+ return;
+ }
+
/* Delete all eth-port devices created on this NIC device */
while (ndev->eth_base)
flow_delete_eth_dev(ndev->eth_base);
+ /* Error check */
+ while (ndev->flow_base) {
+ NT_LOG(ERR, FILTER,
+ "ERROR : Flows still defined but all eth-ports deleted. Flow %p",
+ ndev->flow_base);
+
+ profile_inline_ops->flow_destroy_profile_inline(ndev->flow_base->dev,
+ ndev->flow_base, NULL);
+ }
+
+ profile_inline_ops->done_flow_management_of_ndev_profile_inline(ndev);
+
km_free_ndev_resource_management(&ndev->km_res_handle);
kcc_free_ndev_resource_management(&ndev->kcc_res_handle);
@@ -255,6 +274,13 @@ static void flow_ndev_reset(struct flow_nic_dev *ndev)
int flow_delete_eth_dev(struct flow_eth_dev *eth_dev)
{
+ const struct profile_inline_ops *profile_inline_ops = get_profile_inline_ops();
+
+ if (profile_inline_ops == NULL) {
+ NT_LOG(ERR, FILTER, "%s: profile_inline module uninitialized", __func__);
+ return -1;
+ }
+
struct flow_nic_dev *ndev = eth_dev->ndev;
if (!ndev) {
@@ -271,6 +297,20 @@ int flow_delete_eth_dev(struct flow_eth_dev *eth_dev)
/* delete all created flows from this device */
pthread_mutex_lock(&ndev->mtx);
+ struct flow_handle *flow = ndev->flow_base;
+
+ while (flow) {
+ if (flow->dev == eth_dev) {
+ struct flow_handle *flow_next = flow->next;
+ profile_inline_ops->flow_destroy_locked_profile_inline(eth_dev, flow,
+ NULL);
+ flow = flow_next;
+
+ } else {
+ flow = flow->next;
+ }
+ }
+
/*
* remove unmatched queue if setup in QSL
* remove exception queue setting in QSL UNM
@@ -435,6 +475,24 @@ static struct flow_eth_dev *flow_get_eth_dev(uint8_t adapter_no, uint8_t port_no
eth_dev->port = port_no;
eth_dev->port_id = port_id;
+ /* First time then NIC is initialized */
+ if (!ndev->flow_mgnt_prepared) {
+ ndev->flow_profile = flow_profile;
+
+ /* Initialize modules if needed - recipe 0 is used as no-match and must be setup */
+ if (profile_inline_ops != NULL &&
+ profile_inline_ops->initialize_flow_management_of_ndev_profile_inline(ndev))
+ goto err_exit0;
+
+ } else {
+ /* check if same flow type is requested, otherwise fail */
+ if (ndev->flow_profile != flow_profile) {
+ NT_LOG(ERR, FILTER,
+ "ERROR: Different flow types requested on same NIC device. Not supported.");
+ goto err_exit0;
+ }
+ }
+
/* Allocate the requested queues in HW for this dev */
for (i = 0; i < alloc_rx_queues; i++) {
@@ -8,6 +8,20 @@
#include "flow_api_profile_inline.h"
#include "ntnic_mod_reg.h"
+/*
+ * Public functions
+ */
+
+int initialize_flow_management_of_ndev_profile_inline(struct flow_nic_dev *ndev __rte_unused)
+{
+ return -1;
+}
+
+int done_flow_management_of_ndev_profile_inline(struct flow_nic_dev *ndev __rte_unused)
+{
+ return 0;
+}
+
struct flow_handle *flow_create_profile_inline(struct flow_eth_dev *dev __rte_unused,
const struct rte_flow_attr *attr __rte_unused,
uint16_t forced_vlan_vid __rte_unused,
@@ -51,6 +65,12 @@ int flow_destroy_profile_inline(struct flow_eth_dev *dev, struct flow_handle *fl
}
static const struct profile_inline_ops ops = {
+ /*
+ * Management
+ */
+ .done_flow_management_of_ndev_profile_inline = done_flow_management_of_ndev_profile_inline,
+ .initialize_flow_management_of_ndev_profile_inline =
+ initialize_flow_management_of_ndev_profile_inline,
/*
* Flow functionality
*/
@@ -11,6 +11,14 @@
#include "flow_api.h"
#include "stream_binary_flow_api.h"
+/*
+ * Management
+ */
+
+int done_flow_management_of_ndev_profile_inline(struct flow_nic_dev *ndev);
+
+int initialize_flow_management_of_ndev_profile_inline(struct flow_nic_dev *ndev);
+
/*
* Flow functionality
*/
@@ -226,6 +226,14 @@ const struct flow_backend_ops *get_flow_backend_ops(void);
void flow_backend_init(void);
struct profile_inline_ops {
+ /*
+ * Management
+ */
+
+ int (*done_flow_management_of_ndev_profile_inline)(struct flow_nic_dev *ndev);
+
+ int (*initialize_flow_management_of_ndev_profile_inline)(struct flow_nic_dev *ndev);
+
/*
* Flow functionality
*/