net/bnxt: support alloc and program key and act tables
authorMike Baucom <michael.baucom@broadcom.com>
Wed, 15 Apr 2020 08:18:59 +0000 (13:48 +0530)
committerFerruh Yigit <ferruh.yigit@intel.com>
Tue, 21 Apr 2020 11:57:08 +0000 (13:57 +0200)
This patch does the following
1. Gets the action tables information from the action template id
2. Gets the class tables information from the class template id
3. Initializes the registry file
4. Allocates a flow id from the flow table
5. Process the class & action tables

Signed-off-by: Mike Baucom <michael.baucom@broadcom.com>
Signed-off-by: Venkat Duvvuru <venkatkumar.duvvuru@broadcom.com>
Reviewed-by: Lance Richardson <lance.richardson@broadcom.com>
Reviewed-by: Ajit Khaparde <ajit.khaparde@broadcom.com>
drivers/net/bnxt/tf_ulp/ulp_flow_db.c
drivers/net/bnxt/tf_ulp/ulp_flow_db.h
drivers/net/bnxt/tf_ulp/ulp_mapper.c
drivers/net/bnxt/tf_ulp/ulp_mapper.h
drivers/net/bnxt/tf_ulp/ulp_template_db.c
drivers/net/bnxt/tf_ulp/ulp_template_db.h
drivers/net/bnxt/tf_ulp/ulp_template_struct.h

index eecee6b..ee703a1 100644 (file)
@@ -302,6 +302,43 @@ int32_t    ulp_flow_db_deinit(struct bnxt_ulp_context *ulp_ctxt)
        return 0;
 }
 
+/*
+ * Allocate the flow database entry
+ *
+ * ulp_ctxt [in] Ptr to ulp_context
+ * tbl_idx [in] Specify it is regular or default flow
+ * fid [out] The index to the flow entry
+ *
+ * returns 0 on success and negative on failure.
+ */
+int32_t ulp_flow_db_fid_alloc(struct bnxt_ulp_context          *ulp_ctxt,
+                             enum bnxt_ulp_flow_db_tables      tbl_idx,
+                             uint32_t                          *fid)
+{
+       struct bnxt_ulp_flow_db         *flow_db;
+       struct bnxt_ulp_flow_tbl        *flow_tbl;
+
+       *fid = 0; /* Initialize fid to invalid value */
+       flow_db = bnxt_ulp_cntxt_ptr2_flow_db_get(ulp_ctxt);
+       if (!flow_db) {
+               BNXT_TF_DBG(ERR, "Invalid Arguments\n");
+               return -EINVAL;
+       }
+
+       flow_tbl = &flow_db->flow_tbl[tbl_idx];
+       /* check for max flows */
+       if (flow_tbl->num_flows <= flow_tbl->head_index) {
+               BNXT_TF_DBG(ERR, "Flow database has reached max flows\n");
+               return -ENOMEM;
+       }
+       *fid = flow_tbl->flow_tbl_stack[flow_tbl->head_index];
+       flow_tbl->head_index++;
+       ulp_flow_db_active_flow_set(flow_tbl, *fid, 1);
+
+       /* all good, return success */
+       return 0;
+}
+
 /*
  * Allocate the flow database entry.
  * The params->critical_resource has to be set to 0 to allocate a new resource.
index 20109b9..eb5effa 100644 (file)
@@ -83,6 +83,19 @@ int32_t      ulp_flow_db_init(struct bnxt_ulp_context *ulp_ctxt);
  */
 int32_t        ulp_flow_db_deinit(struct bnxt_ulp_context *ulp_ctxt);
 
+/*
+ * Allocate the flow database entry
+ *
+ * ulp_ctxt [in] Ptr to ulp_context
+ * tbl_idx [in] Specify it is regular or default flow
+ * fid [out] The index to the flow entry
+ *
+ * returns 0 on success and negative on failure.
+ */
+int32_t ulp_flow_db_fid_alloc(struct bnxt_ulp_context          *ulp_ctxt,
+                             enum bnxt_ulp_flow_db_tables      tbl_idx,
+                             uint32_t                          *fid);
+
 /*
  * Allocate the flow database entry.
  * The params->critical_resource has to be set to 0 to allocate a new resource.
index 1c550b9..ca4dd45 100644 (file)
 #include "ulp_flow_db.h"
 #include "ulp_mapper.h"
 
-int32_t
-ulp_mapper_action_tbls_process(struct bnxt_ulp_mapper_parms *parms);
-
-int32_t
-ulp_mapper_class_tbls_process(struct bnxt_ulp_mapper_parms *parms);
-
 /*
  * Get the size of the action property for a given index.
  *
@@ -38,7 +32,76 @@ ulp_mapper_act_prop_size_get(uint32_t idx)
 }
 
 /*
- * Get the list of result fields that implement the flow action
+ * Get the list of result fields that implement the flow action.
+ * Gets a device dependent list of tables that implement the action template id.
+ *
+ * dev_id [in] The device id of the forwarding element
+ *
+ * tid [in] The action template id that matches the flow
+ *
+ * num_tbls [out] The number of action tables in the returned array
+ *
+ * Returns An array of action tables to implement the flow, or NULL on error.
+ */
+static struct bnxt_ulp_mapper_act_tbl_info *
+ulp_mapper_action_tbl_list_get(uint32_t dev_id,
+                              uint32_t tid,
+                              uint32_t *num_tbls)
+{
+       uint32_t        idx;
+       uint32_t        tidx;
+
+       if (!num_tbls) {
+               BNXT_TF_DBG(ERR, "Invalid arguments\n");
+               return NULL;
+       }
+
+       /* template shift and device mask */
+       tidx = ULP_DEVICE_PARAMS_INDEX(tid, dev_id);
+
+       /* NOTE: Need to have something from template compiler to help validate
+        * range of dev_id and act_tid
+        */
+       idx             = ulp_act_tmpl_list[tidx].start_tbl_idx;
+       *num_tbls       = ulp_act_tmpl_list[tidx].num_tbls;
+
+       return &ulp_act_tbl_list[idx];
+}
+
+/** Get a list of classifier tables that implement the flow
+ * Gets a device dependent list of tables that implement the class template id
+ *
+ * dev_id [in] The device id of the forwarding element
+ *
+ * tid [in] The template id that matches the flow
+ *
+ * num_tbls [out] The number of classifier tables in the returned array
+ *
+ * returns An array of classifier tables to implement the flow, or NULL on
+ * error
+ */
+static struct bnxt_ulp_mapper_class_tbl_info *
+ulp_mapper_class_tbl_list_get(uint32_t dev_id,
+                             uint32_t tid,
+                             uint32_t *num_tbls)
+{
+       uint32_t idx;
+       uint32_t tidx = ULP_DEVICE_PARAMS_INDEX(tid, dev_id);
+
+       if (!num_tbls)
+               return NULL;
+
+       /* NOTE: Need to have something from template compiler to help validate
+        * range of dev_id and tid
+        */
+       idx             = ulp_class_tmpl_list[tidx].start_tbl_idx;
+       *num_tbls       = ulp_class_tmpl_list[tidx].num_tbls;
+
+       return &ulp_class_tbl_list[idx];
+}
+
+/*
+ * Get the list of key fields that implement the flow.
  *
  * ctxt [in] The ulp context
  *
@@ -46,7 +109,7 @@ ulp_mapper_act_prop_size_get(uint32_t idx)
  *
  * num_flds [out] The number of key fields in the returned array
  *
- * returns array of Key fields, or NULL on error
+ * Returns array of Key fields, or NULL on error.
  */
 static struct bnxt_ulp_mapper_class_key_field_info *
 ulp_mapper_key_fields_get(struct bnxt_ulp_mapper_class_tbl_info *tbl,
@@ -1158,7 +1221,7 @@ error:
  * Function to process the action template. Iterate through the list
  * action info templates and process it.
  */
-int32_t
+static int32_t
 ulp_mapper_action_tbls_process(struct bnxt_ulp_mapper_parms *parms)
 {
        uint32_t        i;
@@ -1180,7 +1243,7 @@ ulp_mapper_action_tbls_process(struct bnxt_ulp_mapper_parms *parms)
 }
 
 /* Create the classifier table entries for a flow. */
-int32_t
+static int32_t
 ulp_mapper_class_tbls_process(struct bnxt_ulp_mapper_parms *parms)
 {
        uint32_t        i;
@@ -1335,3 +1398,116 @@ ulp_mapper_flow_destroy(struct bnxt_ulp_context *ulp_ctx, uint32_t fid)
                                         fid,
                                         BNXT_ULP_REGULAR_FLOW_TABLE);
 }
+
+/* Function to handle the mapping of the Flow to be compatible
+ * with the underlying hardware.
+ */
+int32_t
+ulp_mapper_flow_create(struct bnxt_ulp_context *ulp_ctx,
+                      uint32_t app_priority __rte_unused,
+                      struct ulp_rte_hdr_bitmap *hdr_bitmap __rte_unused,
+                      struct ulp_rte_hdr_field *hdr_field,
+                      struct ulp_rte_act_bitmap *act_bitmap,
+                      struct ulp_rte_act_prop *act_prop,
+                      uint32_t class_tid,
+                      uint32_t act_tid,
+                      uint32_t *flow_id)
+{
+       struct ulp_regfile              regfile;
+       struct bnxt_ulp_mapper_parms    parms;
+       struct bnxt_ulp_device_params   *device_params;
+       int32_t                         rc, trc;
+
+       /* Initialize the parms structure */
+       memset(&parms, 0, sizeof(parms));
+       parms.act_prop = act_prop;
+       parms.act_bitmap = act_bitmap;
+       parms.regfile = &regfile;
+       parms.hdr_field = hdr_field;
+       parms.tfp = bnxt_ulp_cntxt_tfp_get(ulp_ctx);
+       parms.ulp_ctx = ulp_ctx;
+
+       /* Get the device id from the ulp context */
+       if (bnxt_ulp_cntxt_dev_id_get(ulp_ctx, &parms.dev_id)) {
+               BNXT_TF_DBG(ERR, "Invalid ulp context\n");
+               return -EINVAL;
+       }
+
+       /* Get the action table entry from device id and act context id */
+       parms.act_tid = act_tid;
+       parms.atbls = ulp_mapper_action_tbl_list_get(parms.dev_id,
+                                                    parms.act_tid,
+                                                    &parms.num_atbls);
+       if (!parms.atbls || !parms.num_atbls) {
+               BNXT_TF_DBG(ERR, "No action tables for %d:%d\n",
+                           parms.dev_id, parms.act_tid);
+               return -EINVAL;
+       }
+
+       /* Get the class table entry from device id and act context id */
+       parms.class_tid = class_tid;
+       parms.ctbls = ulp_mapper_class_tbl_list_get(parms.dev_id,
+                                                   parms.class_tid,
+                                                   &parms.num_ctbls);
+       if (!parms.ctbls || !parms.num_ctbls) {
+               BNXT_TF_DBG(ERR, "No class tables for %d:%d\n",
+                           parms.dev_id, parms.class_tid);
+               return -EINVAL;
+       }
+
+       /* Get the byte order for the further processing from device params */
+       device_params = bnxt_ulp_device_params_get(parms.dev_id);
+       if (!device_params) {
+               BNXT_TF_DBG(ERR, "No class tables for %d:%d\n",
+                           parms.dev_id, parms.class_tid);
+               return -EINVAL;
+       }
+       parms.order = device_params->byte_order;
+       parms.encap_byte_swap = device_params->encap_byte_swap;
+
+       /* initialize the registry file for further processing */
+       if (!ulp_regfile_init(parms.regfile)) {
+               BNXT_TF_DBG(ERR, "regfile initialization failed.\n");
+               return -EINVAL;
+       }
+
+       /* Allocate a Flow ID for attaching all resources for the flow to.
+        * Once allocated, all errors have to walk the list of resources and
+        * free each of them.
+        */
+       rc = ulp_flow_db_fid_alloc(ulp_ctx,
+                                  BNXT_ULP_REGULAR_FLOW_TABLE,
+                                  &parms.fid);
+       if (rc) {
+               BNXT_TF_DBG(ERR, "Unable to allocate flow table entry\n");
+               return rc;
+       }
+
+       /* Process the action template list from the selected action table*/
+       rc = ulp_mapper_action_tbls_process(&parms);
+       if (rc) {
+               BNXT_TF_DBG(ERR, "action tables failed creation for %d:%d\n",
+                           parms.dev_id, parms.act_tid);
+               goto flow_error;
+       }
+
+       /* All good. Now process the class template */
+       rc = ulp_mapper_class_tbls_process(&parms);
+       if (rc) {
+               BNXT_TF_DBG(ERR, "class tables failed creation for %d:%d\n",
+                           parms.dev_id, parms.class_tid);
+               goto flow_error;
+       }
+
+       *flow_id = parms.fid;
+
+       return rc;
+
+flow_error:
+       /* Free all resources that were allocated during flow creation */
+       trc = ulp_mapper_flow_destroy(ulp_ctx, parms.fid);
+       if (trc)
+               BNXT_TF_DBG(ERR, "Failed to free all resources rc=%d\n", trc);
+
+       return rc;
+}
index 8655728..5f3d46e 100644 (file)
@@ -38,6 +38,21 @@ struct bnxt_ulp_mapper_parms {
        enum bnxt_ulp_flow_db_tables            tbl_idx;
 };
 
+/*
+ * Function to handle the mapping of the Flow to be compatible
+ * with the underlying hardware.
+ */
+int32_t
+ulp_mapper_flow_create(struct bnxt_ulp_context *ulp_ctx,
+                      uint32_t         app_priority,
+                      struct ulp_rte_hdr_bitmap  *hdr_bitmap,
+                      struct ulp_rte_hdr_field *hdr_field,
+                      struct ulp_rte_act_bitmap *act,
+                      struct ulp_rte_act_prop *act_prop,
+                      uint32_t         class_tid,
+                      uint32_t         act_tid,
+                      uint32_t         *flow_id);
+
 /* Function that frees all resources associated with the flow. */
 int32_t
 ulp_mapper_flow_destroy(struct bnxt_ulp_context        *ulp_ctx, uint32_t fid);
index aefece8..9d52937 100644 (file)
@@ -110,6 +110,74 @@ struct bnxt_ulp_device_params ulp_device_params[] = {
        }
 };
 
+struct bnxt_ulp_mapper_tbl_list_info ulp_class_tmpl_list[] = {
+       [((0 << BNXT_ULP_LOG2_MAX_NUM_DEV) | BNXT_ULP_DEVICE_ID_WH_PLUS)] = {
+       .device_name = BNXT_ULP_DEVICE_ID_WH_PLUS,
+       .num_tbls = 3,
+       .start_tbl_idx = 0
+       }
+};
+
+struct bnxt_ulp_mapper_class_tbl_info ulp_class_tbl_list[] = {
+       {
+       .resource_func = BNXT_ULP_RESOURCE_FUNC_TCAM_TABLE,
+       .table_type = TF_TCAM_TBL_TYPE_L2_CTXT_TCAM,
+       .direction = TF_DIR_RX,
+       .priority = BNXT_ULP_PRIORITY_LEVEL_0,
+       .srch_b4_alloc = BNXT_ULP_SEARCH_BEFORE_ALLOC_NO,
+       .key_start_idx = 0,
+       .blob_key_bit_size = 167,
+       .key_bit_size = 167,
+       .key_num_fields = 13,
+       .result_start_idx = 0,
+       .result_bit_size = 64,
+       .result_num_fields = 13,
+       .ident_start_idx = 0,
+       .ident_nums = 1,
+       .mark_enable = BNXT_ULP_MARK_ENABLE_NO,
+       .critical_resource = 0,
+       .regfile_wr_idx = BNXT_ULP_REGFILE_INDEX_NOT_USED
+       },
+       {
+       .resource_func = BNXT_ULP_RESOURCE_FUNC_TCAM_TABLE,
+       .table_type = TF_TCAM_TBL_TYPE_PROF_TCAM,
+       .direction = TF_DIR_RX,
+       .priority = BNXT_ULP_PRIORITY_LEVEL_0,
+       .srch_b4_alloc = BNXT_ULP_SEARCH_BEFORE_ALLOC_NO,
+       .key_start_idx = 13,
+       .blob_key_bit_size = 81,
+       .key_bit_size = 81,
+       .key_num_fields = 42,
+       .result_start_idx = 13,
+       .result_bit_size = 38,
+       .result_num_fields = 8,
+       .ident_start_idx = 1,
+       .ident_nums = 1,
+       .mark_enable = BNXT_ULP_MARK_ENABLE_NO,
+       .critical_resource = 0,
+       .regfile_wr_idx = BNXT_ULP_REGFILE_INDEX_NOT_USED
+       },
+       {
+       .resource_func = BNXT_ULP_RESOURCE_FUNC_EM_TABLE,
+       .table_type = TF_MEM_EXTERNAL,
+       .direction = TF_DIR_RX,
+       .priority = BNXT_ULP_PRIORITY_NOT_USED,
+       .srch_b4_alloc = BNXT_ULP_SEARCH_BEFORE_ALLOC_NO,
+       .key_start_idx = 55,
+       .blob_key_bit_size = 448,
+       .key_bit_size = 197,
+       .key_num_fields = 11,
+       .result_start_idx = 21,
+       .result_bit_size = 64,
+       .result_num_fields = 9,
+       .ident_start_idx = 2,
+       .ident_nums = 0,
+       .mark_enable = BNXT_ULP_MARK_ENABLE_YES,
+       .critical_resource = 1,
+       .regfile_wr_idx = BNXT_ULP_REGFILE_INDEX_NOT_USED
+       }
+};
+
 struct bnxt_ulp_mapper_class_key_field_info ulp_class_key_field_list[] = {
        {
        .field_bit_size = 12,
@@ -938,6 +1006,28 @@ struct bnxt_ulp_mapper_ident_info ulp_ident_list[] = {
        }
 };
 
+struct bnxt_ulp_mapper_tbl_list_info ulp_act_tmpl_list[] = {
+       [((0 << BNXT_ULP_LOG2_MAX_NUM_DEV) | BNXT_ULP_DEVICE_ID_WH_PLUS)] = {
+       .device_name = BNXT_ULP_DEVICE_ID_WH_PLUS,
+       .num_tbls = 1,
+       .start_tbl_idx = 0
+       }
+};
+
+struct bnxt_ulp_mapper_act_tbl_info ulp_act_tbl_list[] = {
+       {
+       .resource_func = BNXT_ULP_RESOURCE_FUNC_INDEX_TABLE,
+       .table_type = TF_TBL_TYPE_EXT,
+       .direction = TF_DIR_RX,
+       .srch_b4_alloc = BNXT_ULP_SEARCH_BEFORE_ALLOC_NO,
+       .result_start_idx = 0,
+       .result_bit_size = 128,
+       .result_num_fields = 26,
+       .encap_num_fields = 0,
+       .regfile_wr_idx = BNXT_ULP_REGFILE_INDEX_ACTION_PTR_MAIN
+       }
+};
+
 struct bnxt_ulp_mapper_result_field_info ulp_act_result_field_list[] = {
        {
        .field_bit_size = 14,
index 733836a..957b21a 100644 (file)
@@ -12,6 +12,7 @@
 #define ULP_TEMPLATE_DB_H_
 
 #define BNXT_ULP_MAX_NUM_DEVICES 4
+#define BNXT_ULP_LOG2_MAX_NUM_DEV 2
 
 enum bnxt_ulp_action_bit {
        BNXT_ULP_ACTION_BIT_MARK             = 0x0000000000000001,
@@ -127,6 +128,12 @@ enum bnxt_ulp_result_opc {
        BNXT_ULP_RESULT_OPC_LAST = 4
 };
 
+enum bnxt_ulp_search_before_alloc {
+       BNXT_ULP_SEARCH_BEFORE_ALLOC_NO = 0,
+       BNXT_ULP_SEARCH_BEFORE_ALLOC_YES = 1,
+       BNXT_ULP_SEARCH_BEFORE_ALLOC_LAST = 2
+};
+
 enum bnxt_ulp_spec_opc {
        BNXT_ULP_SPEC_OPC_SET_TO_CONSTANT = 0,
        BNXT_ULP_SPEC_OPC_SET_TO_HDR_FIELD = 1,
index e28d049..b7094c5 100644 (file)
 #include "rte_flow.h"
 #include "tf_core.h"
 
+struct ulp_rte_hdr_bitmap {
+       uint64_t        bits;
+};
+
 /* Structure to store the protocol fields */
 #define RTE_PARSER_FLOW_HDR_FIELD_SIZE         16
 struct ulp_rte_hdr_field {
@@ -51,6 +55,13 @@ struct bnxt_ulp_device_params {
        uint32_t                        num_resources_per_flow;
 };
 
+/* Flow Mapper */
+struct bnxt_ulp_mapper_tbl_list_info {
+       uint32_t        device_name;
+       uint32_t        start_tbl_idx;
+       uint32_t        num_tbls;
+};
+
 struct bnxt_ulp_mapper_class_tbl_info {
        enum bnxt_ulp_resource_func     resource_func;
        uint32_t        table_type;
@@ -132,7 +143,25 @@ struct bnxt_ulp_mapper_ident_info {
 extern struct bnxt_ulp_device_params ulp_device_params[];
 
 /*
- * The ulp_data_field_list provides the instructions for creating an action
+ * The ulp_class_tmpl_list and ulp_act_tmpl_list are indexed by the dev_id
+ * and template id (either class or action) returned by the matcher.
+ * The result provides the start index and number of entries in the connected
+ * ulp_class_tbl_list/ulp_act_tbl_list.
+ */
+extern struct bnxt_ulp_mapper_tbl_list_info    ulp_class_tmpl_list[];
+extern struct bnxt_ulp_mapper_tbl_list_info    ulp_act_tmpl_list[];
+
+/*
+ * The ulp_class_tbl_list and ulp_act_tbl_list are indexed based on the results
+ * of the template lists.  Each entry describes the high level details of the
+ * table entry to include the start index and number of instructions in the
+ * field lists.
+ */
+extern struct bnxt_ulp_mapper_class_tbl_info   ulp_class_tbl_list[];
+extern struct bnxt_ulp_mapper_act_tbl_info     ulp_act_tbl_list[];
+
+/*
+ * The ulp_class_result_field_list provides the instructions for creating result
  * records such as tcam/em results.
  */
 extern struct bnxt_ulp_mapper_result_field_info        ulp_class_result_field_list[];