summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorManjunathappa Prakash <prakashpm@codeaurora.org>2017-10-05 18:26:38 -0700
committerGerrit - the friendly Code Review server <code-review@localhost>2017-10-17 21:07:14 -0700
commit5acd0f17abc7a6606131e94fc13257c8ff2a6869 (patch)
tree09be451844930b29c2226cd7fb6857d3863acb19
parent541bae0e32b3605585395264fb8f50815ba65afb (diff)
qcacmn: Add GRO support to NAPI+Rx_thread processing model
GRO aggregations are hanging out of NAPI instance and We cannot use the hif NAPI instance in Rx thread as gro_list inside NAPI is flushed out at the start and end of NAPI poll, this will corrupt the gro_list on which rx_thread is working. Address this concern by creating dummy NAPI instances mapping to each hif NAPI and not scheduling them. Change-Id: I517c4c6158ed3ac073f5f617afde46c7ed07ff3e CRs-Fixed: 2128457
-rw-r--r--dp/inc/cdp_txrx_cmn.h2
-rw-r--r--dp/inc/cdp_txrx_lro.h6
-rw-r--r--hif/inc/hif.h15
-rw-r--r--hif/inc/hif_napi.h4
-rw-r--r--hif/src/ce/ce_api.h2
-rw-r--r--hif/src/ce/ce_main.c2
-rw-r--r--hif/src/hif_main.c37
-rw-r--r--hif/src/hif_napi.c51
8 files changed, 62 insertions, 57 deletions
diff --git a/dp/inc/cdp_txrx_cmn.h b/dp/inc/cdp_txrx_cmn.h
index f84578e447bc..8593921b45f9 100644
--- a/dp/inc/cdp_txrx_cmn.h
+++ b/dp/inc/cdp_txrx_cmn.h
@@ -344,6 +344,8 @@ void
ol_txrx_vdev_register(ol_txrx_vdev_handle vdev,
void *osif_vdev, struct ol_txrx_ops *txrx_ops);
+void ol_register_offld_flush_cb(void (gro_flush_cb)(void *),
+ void *(gro_init_cb)(void));
int
ol_txrx_mgmt_send(
ol_txrx_vdev_handle vdev,
diff --git a/dp/inc/cdp_txrx_lro.h b/dp/inc/cdp_txrx_lro.h
index 8a35d147682e..19e8b111dd29 100644
--- a/dp/inc/cdp_txrx_lro.h
+++ b/dp/inc/cdp_txrx_lro.h
@@ -32,8 +32,8 @@
#ifndef _CDP_TXRX_LRO_H_
#define _CDP_TXRX_LRO_H_
-void ol_register_lro_flush_cb(void (*lro_flush_cb)(void *data),
- void *(lro_init_cb)(void));
-void ol_deregister_lro_flush_cb(void (*lro_deinit_cb)(void *data));
+void ol_register_offld_flush_cb(void (*offld_flush_cb)(void *data),
+ void *(offld_init_cb)(void));
+void ol_deregister_offld_flush_cb(void (*offld_deinit_cb)(void *data));
#endif /* _CDP_TXRX_LRO_H_ */
diff --git a/hif/inc/hif.h b/hif/inc/hif.h
index 86c16bd3ffc1..b0c2fd385da3 100644
--- a/hif/inc/hif.h
+++ b/hif/inc/hif.h
@@ -147,8 +147,8 @@ struct qca_napi_info {
int irq;
struct qca_napi_stat stats[NR_CPUS];
/* will only be present for data rx CE's */
- void (*lro_flush_cb)(void *arg);
- void *lro_ctx;
+ void (*offld_flush_cb)(void *arg);
+ void *offld_ctx;
};
/**
@@ -709,11 +709,12 @@ int ol_copy_ramdump(struct hif_opaque_softc *hif_ctx);
void hif_crash_shutdown(struct hif_opaque_softc *hif_ctx);
void hif_get_hw_info(struct hif_opaque_softc *hif_ctx, u32 *version,
u32 *revision, const char **target_name);
-void hif_lro_flush_cb_register(struct hif_opaque_softc *hif_ctx,
- void (lro_flush_handler)(void *arg),
- void *(lro_init_handler)(void));
-void hif_lro_flush_cb_deregister(struct hif_opaque_softc *hif_ctx,
- void (lro_deinit_cb)(void *arg));
+
+void hif_offld_flush_cb_register(struct hif_opaque_softc *scn,
+ void (offld_flush_handler)(void *),
+ void *(offld_init_handler)(void));
+void hif_offld_flush_cb_deregister(struct hif_opaque_softc *hif_ctx,
+ void (offld_deinit_cb)(void *arg));
bool hif_needs_bmi(struct hif_opaque_softc *hif_ctx);
enum qdf_bus_type hif_get_bus_type(struct hif_opaque_softc *hif_hdl);
struct hif_target_info *hif_get_target_info_handle(struct hif_opaque_softc *
diff --git a/hif/inc/hif_napi.h b/hif/inc/hif_napi.h
index 865f156d27dd..dab7876932b2 100644
--- a/hif/inc/hif_napi.h
+++ b/hif/inc/hif_napi.h
@@ -96,7 +96,7 @@ enum qca_napi_event {
#define NAPI_ID2PIPE(i) ((i)-1)
#define NAPI_PIPE2ID(p) ((p)+1)
-int hif_napi_lro_flush_cb_register(struct hif_opaque_softc *hif_hdl,
+int hif_napi_offld_flush_cb_register(struct hif_opaque_softc *hif_hdl,
void (lro_flush_handler)(void *arg),
void *(lro_init_handler)(void));
@@ -123,7 +123,7 @@ int hif_napi_destroy(struct hif_opaque_softc *hif,
int force);
struct qca_napi_data *hif_napi_get_all(struct hif_opaque_softc *hif);
-struct napi_struct *hif_get_napi(int napi_id, void *napi_d);
+struct qca_napi_info *hif_get_napi(int napi_id, void *napi_d);
int hif_napi_event(struct hif_opaque_softc *hif,
enum qca_napi_event event,
diff --git a/hif/src/ce/ce_api.h b/hif/src/ce/ce_api.h
index 836853d12d58..68ef7963c638 100644
--- a/hif/src/ce/ce_api.h
+++ b/hif/src/ce/ce_api.h
@@ -485,13 +485,11 @@ static inline void ce_pkt_error_count_incr(
bool ce_check_rx_pending(struct CE_state *CE_state);
void *hif_ce_get_lro_ctx(struct hif_opaque_softc *hif_hdl, int ctx_id);
-#if defined(FEATURE_LRO)
int ce_lro_flush_cb_register(struct hif_opaque_softc *scn,
void (handler)(void *arg),
void *(lro_init_handler)(void));
int ce_lro_flush_cb_deregister(struct hif_opaque_softc *hif_hdl,
void (lro_deinit_cb)(void *arg));
-#endif
int hif_ce_bus_early_suspend(struct hif_softc *scn);
int hif_ce_bus_late_resume(struct hif_softc *scn);
diff --git a/hif/src/ce/ce_main.c b/hif/src/ce/ce_main.c
index 783b515c1148..e72a4547b614 100644
--- a/hif/src/ce/ce_main.c
+++ b/hif/src/ce/ce_main.c
@@ -2696,6 +2696,7 @@ void *hif_ce_get_lro_ctx(struct hif_opaque_softc *hif_hdl, int ctx_id)
return ce_state->lro_data;
}
+#endif
/**
* ce_lro_flush_cb_register() - register the LRO flush
@@ -2774,7 +2775,6 @@ int ce_lro_flush_cb_deregister(struct hif_opaque_softc *hif_hdl,
}
return rc;
}
-#endif
/**
* hif_map_service_to_pipe() - returns the ce ids pertaining to
diff --git a/hif/src/hif_main.c b/hif/src/hif_main.c
index 6cd21f42f771..ba553465c840 100644
--- a/hif/src/hif_main.c
+++ b/hif/src/hif_main.c
@@ -802,27 +802,27 @@ int hif_get_rx_ctx_id(int ctx_id, struct hif_opaque_softc *hif_hdl)
return ctx_id;
}
-#if defined(FEATURE_LRO)
/**
- * hif_lro_flush_cb_register - API to register for LRO Flush Callback
+ * hif_offld_flush_cb_register - API to register for LRO Flush Callback
* @scn: HIF Context
- * @handler: Function pointer to be called by HIF
- * @data: Private data to be used by the module registering to HIF
+ * @offld_flush_handler: Flush handler
+ * @offld_init_handler: Init handler of Rx offload
*
* Return: void
*/
-void hif_lro_flush_cb_register(struct hif_opaque_softc *scn,
- void (lro_flush_handler)(void *),
- void *(lro_init_handler)(void))
+void hif_offld_flush_cb_register(struct hif_opaque_softc *scn,
+ void (offld_flush_handler)(void *),
+ void *(offld_init_handler)(void))
{
if (hif_napi_enabled(scn, -1))
- hif_napi_lro_flush_cb_register(scn, lro_flush_handler,
- lro_init_handler);
+ hif_napi_offld_flush_cb_register(scn, offld_flush_handler,
+ offld_init_handler);
else
- ce_lro_flush_cb_register(scn, lro_flush_handler,
- lro_init_handler);
+ ce_lro_flush_cb_register(scn, offld_flush_handler,
+ offld_init_handler);
}
+#if defined(FEATURE_LRO)
/**
* hif_get_lro_info - Returns LRO instance for instance ID
* @ctx_id: LRO instance ID
@@ -842,20 +842,21 @@ void *hif_get_lro_info(int ctx_id, struct hif_opaque_softc *hif_hdl)
return data;
}
+
+#endif
/**
- * hif_lro_flush_cb_deregister - API to deregister for LRO Flush Callbacks
+ * hif_offld_flush_cb_deregister - API to deregister offload Flush Callbacks
* @hif_hdl: HIF Context
- * @lro_deinit_cb: LRO deinit callback
+ * @offld_deinit_cb: Rx offload deinit callback
*
* Return: void
*/
-void hif_lro_flush_cb_deregister(struct hif_opaque_softc *hif_hdl,
- void (lro_deinit_cb)(void *))
+void hif_offld_flush_cb_deregister(struct hif_opaque_softc *hif_hdl,
+ void (offld_deinit_cb)(void *))
{
- hif_napi_lro_flush_cb_deregister(hif_hdl, lro_deinit_cb);
- ce_lro_flush_cb_deregister(hif_hdl, lro_deinit_cb);
+ hif_napi_lro_flush_cb_deregister(hif_hdl, offld_deinit_cb);
+ ce_lro_flush_cb_deregister(hif_hdl, offld_deinit_cb);
}
-#endif
/**
* hif_get_target_status - API to get target status
diff --git a/hif/src/hif_napi.c b/hif/src/hif_napi.c
index 8d98eb842c1c..a587049f84fc 100644
--- a/hif/src/hif_napi.c
+++ b/hif/src/hif_napi.c
@@ -184,6 +184,7 @@ int hif_napi_create(struct hif_opaque_softc *hif_ctx,
NAPI_DEBUG("adding napi=%pK to netdev=%pK (poll=%pK, bdgt=%d)",
&(napii->napi), &(napii->netdev), poll, budget);
netif_napi_add(&(napii->netdev), &(napii->napi), poll, budget);
+ napii->offld_ctx = &(napii->napi);
NAPI_DEBUG("after napi_add");
NAPI_DEBUG("napi=0x%pK, netdev=0x%pK",
@@ -323,16 +324,18 @@ int hif_napi_destroy(struct hif_opaque_softc *hif_ctx,
}
/**
- * hif_napi_lro_flush_cb_register() - init and register flush callback for LRO
+ * hif_napi_offld_flush_cb_register() - init and register flush callback
* @hif_hdl: pointer to hif context
- * @lro_flush_handler: register LRO flush callback
- * @lro_init_handler: Callback for initializing LRO
+ * @offld_flush_handler: register Rx offload flush callback
+ * @offld_init_handler: Callback for initializing Rx offfload
+ *
+ * Init and register flush callback for LRO or GRO Rx offload features
*
* Return: positive value on success and 0 on failure
*/
-int hif_napi_lro_flush_cb_register(struct hif_opaque_softc *hif_hdl,
- void (lro_flush_handler)(void *),
- void *(lro_init_handler)(void))
+int hif_napi_offld_flush_cb_register(struct hif_opaque_softc *hif_hdl,
+ void (offld_flush_handler)(void *),
+ void *(offld_init_handler)(void))
{
int rc = 0;
int i;
@@ -348,17 +351,17 @@ int hif_napi_lro_flush_cb_register(struct hif_opaque_softc *hif_hdl,
for (i = 0; i < scn->ce_count; i++) {
napii = napid->napis[i];
if (napii) {
- data = lro_init_handler();
+ data = offld_init_handler();
if (data == NULL) {
- HIF_ERROR("%s: Failed to init LRO for CE %d",
+ HIF_ERROR("%s: Failed to init offld for CE %d",
__func__, i);
continue;
}
- napii->lro_flush_cb = lro_flush_handler;
- napii->lro_ctx = data;
- HIF_DBG("Registering LRO for ce_id %d NAPI callback for %d flush_cb %pK, lro_data %pK\n",
- i, napii->id, napii->lro_flush_cb,
- napii->lro_ctx);
+ napii->offld_flush_cb = offld_flush_handler;
+ napii->offld_ctx = data;
+ HIF_DBG("Registering offld for ce_id %d NAPI callback for %d flush_cb %pK, offld_data %pK\n",
+ i, napii->id, napii->offld_flush_cb,
+ napii->offld_ctx);
rc++;
}
}
@@ -368,12 +371,12 @@ int hif_napi_lro_flush_cb_register(struct hif_opaque_softc *hif_hdl,
return rc;
}
-struct napi_struct *hif_get_napi(int napi_id, void *napi_d)
+struct qca_napi_info *hif_get_napi(int napi_id, void *napi_d)
{
struct qca_napi_data *napid = napi_d;
int id = NAPI_ID2PIPE(napi_id);
- return &(napid->napis[id]->napi);
+ return napid->napis[id];
}
/**
@@ -399,11 +402,11 @@ void hif_napi_lro_flush_cb_deregister(struct hif_opaque_softc *hif_hdl,
napii = napid->napis[i];
if (napii) {
HIF_DBG("deRegistering LRO for ce_id %d NAPI callback for %d flush_cb %pK, lro_data %pK\n",
- i, napii->id, napii->lro_flush_cb,
- napii->lro_ctx);
- napii->lro_flush_cb = NULL;
- lro_deinit_cb(napii->lro_ctx);
- napii->lro_ctx = NULL;
+ i, napii->id, napii->offld_flush_cb,
+ napii->offld_ctx);
+ napii->offld_flush_cb = NULL;
+ lro_deinit_cb(napii->offld_ctx);
+ napii->offld_ctx = NULL;
}
}
} else {
@@ -432,7 +435,7 @@ void *hif_napi_get_lro_info(struct hif_opaque_softc *hif_hdl, int napi_id)
napii = napid->napis[NAPI_ID2PIPE(napi_id)];
if (napii)
- return napii->lro_ctx;
+ return napii->offld_ctx;
return 0;
}
@@ -867,8 +870,8 @@ int hif_napi_poll(struct hif_opaque_softc *hif_ctx,
NAPI_DEBUG("%s: ce_per_engine_service processed %d msgs",
__func__, rc);
- if (napi_info->lro_flush_cb)
- napi_info->lro_flush_cb(napi_info->lro_ctx);
+ if (napi_info->offld_flush_cb)
+ napi_info->offld_flush_cb(napi_info->offld_ctx);
/* do not return 0, if there was some work done,
* even if it is below the scale
@@ -910,8 +913,8 @@ int hif_napi_poll(struct hif_opaque_softc *hif_ctx,
if (normalized >= budget)
normalized = budget - 1;
- /* enable interrupts */
napi_complete(napi);
+ /* enable interrupts */
hif_napi_enable_irq(hif_ctx, napi_info->id);
/* support suspend/resume */
qdf_atomic_dec(&(hif->active_tasklet_cnt));