From: Anoob Joseph <anoobj@marvell.com>
To: Akhil Goyal <gakhil@marvell.com>, Thomas Monjalon <thomas@monjalon.net>
Cc: Archana Muniganti <marchana@marvell.com>,
Jerin Jacob <jerinj@marvell.com>,
Ankur Dwivedi <adwivedi@marvell.com>,
Tejasree Kondoj <ktejasree@marvell.com>, <dev@dpdk.org>,
Anoob Joseph <anoobj@marvell.com>,
Vidya Sagar Velumuri <vvelumuri@marvell.com>
Subject: [dpdk-dev] [PATCH v2 06/17] common/cnxk: add CPT LF config
Date: Fri, 25 Jun 2021 11:06:38 +0530 [thread overview]
Message-ID: <1624599410-29689-7-git-send-email-anoobj@marvell.com> (raw)
In-Reply-To: <1624599410-29689-1-git-send-email-anoobj@marvell.com>
From: Archana Muniganti <marchana@marvell.com>
Add routines to init & fini CPT LFs. CPT LFs are
queues to the hardware enabling instruction submissions.
Signed-off-by: Anoob Joseph <anoobj@marvell.com>
Signed-off-by: Archana Muniganti <marchana@marvell.com>
Signed-off-by: Vidya Sagar Velumuri <vvelumuri@marvell.com>
---
drivers/common/cnxk/roc_cpt.c | 357 +++++++++++++++++++++++++++++++++++++
drivers/common/cnxk/roc_cpt.h | 20 +++
drivers/common/cnxk/roc_cpt_priv.h | 2 +
drivers/common/cnxk/version.map | 3 +
4 files changed, 382 insertions(+)
diff --git a/drivers/common/cnxk/roc_cpt.c b/drivers/common/cnxk/roc_cpt.c
index e723ee7..02062c1 100644
--- a/drivers/common/cnxk/roc_cpt.c
+++ b/drivers/common/cnxk/roc_cpt.c
@@ -5,6 +5,189 @@
#include "roc_api.h"
#include "roc_priv.h"
+#define CPT_IQ_FC_LEN 128
+#define CPT_IQ_GRP_LEN 16
+
+#define CPT_IQ_NB_DESC_MULTIPLIER 40
+
+/* The effective queue size to software is (CPT_LF_Q_SIZE[SIZE_DIV40] - 1 - 8).
+ *
+ * CPT requires 320 free entries (+8). And 40 entries are required for
+ * allowing CPT to discard packet when the queues are full (+1).
+ */
+#define CPT_IQ_NB_DESC_SIZE_DIV40(nb_desc) \
+ (PLT_DIV_CEIL(nb_desc, CPT_IQ_NB_DESC_MULTIPLIER) + 1 + 8)
+
+#define CPT_IQ_GRP_SIZE(nb_desc) \
+ (CPT_IQ_NB_DESC_SIZE_DIV40(nb_desc) * CPT_IQ_GRP_LEN)
+
+#define CPT_LF_MAX_NB_DESC 128000
+#define CPT_LF_DEFAULT_NB_DESC 1024
+
+static void
+cpt_lf_misc_intr_enb_dis(struct roc_cpt_lf *lf, bool enb)
+{
+ /* Enable all cpt lf error irqs except RQ_DISABLED and CQ_DISABLED */
+ if (enb)
+ plt_write64((BIT_ULL(6) | BIT_ULL(5) | BIT_ULL(3) | BIT_ULL(2) |
+ BIT_ULL(1)),
+ lf->rbase + CPT_LF_MISC_INT_ENA_W1S);
+ else
+ plt_write64((BIT_ULL(6) | BIT_ULL(5) | BIT_ULL(3) | BIT_ULL(2) |
+ BIT_ULL(1)),
+ lf->rbase + CPT_LF_MISC_INT_ENA_W1C);
+}
+
+static void
+cpt_lf_misc_irq(void *param)
+{
+ struct roc_cpt_lf *lf = (struct roc_cpt_lf *)param;
+ struct dev *dev = lf->dev;
+ uint64_t intr;
+
+ intr = plt_read64(lf->rbase + CPT_LF_MISC_INT);
+ if (intr == 0)
+ return;
+
+ plt_err("Err_irq=0x%" PRIx64 " pf=%d, vf=%d", intr, dev->pf, dev->vf);
+
+ /* Clear interrupt */
+ plt_write64(intr, lf->rbase + CPT_LF_MISC_INT);
+}
+
+static int
+cpt_lf_register_misc_irq(struct roc_cpt_lf *lf)
+{
+ struct plt_pci_device *pci_dev = lf->pci_dev;
+ struct plt_intr_handle *handle;
+ int rc, vec;
+
+ handle = &pci_dev->intr_handle;
+
+ vec = lf->msixoff + CPT_LF_INT_VEC_MISC;
+ /* Clear err interrupt */
+ cpt_lf_misc_intr_enb_dis(lf, false);
+ /* Set used interrupt vectors */
+ rc = dev_irq_register(handle, cpt_lf_misc_irq, lf, vec);
+ /* Enable all dev interrupt except for RQ_DISABLED */
+ cpt_lf_misc_intr_enb_dis(lf, true);
+
+ return rc;
+}
+
+static void
+cpt_lf_unregister_misc_irq(struct roc_cpt_lf *lf)
+{
+ struct plt_pci_device *pci_dev = lf->pci_dev;
+ struct plt_intr_handle *handle;
+ int vec;
+
+ handle = &pci_dev->intr_handle;
+
+ vec = lf->msixoff + CPT_LF_INT_VEC_MISC;
+ /* Clear err interrupt */
+ cpt_lf_misc_intr_enb_dis(lf, false);
+ dev_irq_unregister(handle, cpt_lf_misc_irq, lf, vec);
+}
+
+static void
+cpt_lf_done_intr_enb_dis(struct roc_cpt_lf *lf, bool enb)
+{
+ if (enb)
+ plt_write64(0x1, lf->rbase + CPT_LF_DONE_INT_ENA_W1S);
+ else
+ plt_write64(0x1, lf->rbase + CPT_LF_DONE_INT_ENA_W1C);
+}
+
+static void
+cpt_lf_done_irq(void *param)
+{
+ struct roc_cpt_lf *lf = param;
+ uint64_t done_wait;
+ uint64_t intr;
+
+ /* Read the number of completed requests */
+ intr = plt_read64(lf->rbase + CPT_LF_DONE);
+ if (intr == 0)
+ return;
+
+ done_wait = plt_read64(lf->rbase + CPT_LF_DONE_WAIT);
+
+ /* Acknowledge the number of completed requests */
+ plt_write64(intr, lf->rbase + CPT_LF_DONE_ACK);
+
+ plt_write64(done_wait, lf->rbase + CPT_LF_DONE_WAIT);
+}
+
+static int
+cpt_lf_register_done_irq(struct roc_cpt_lf *lf)
+{
+ struct plt_pci_device *pci_dev = lf->pci_dev;
+ struct plt_intr_handle *handle;
+ int rc, vec;
+
+ handle = &pci_dev->intr_handle;
+
+ vec = lf->msixoff + CPT_LF_INT_VEC_DONE;
+
+ /* Clear done interrupt */
+ cpt_lf_done_intr_enb_dis(lf, false);
+
+ /* Set used interrupt vectors */
+ rc = dev_irq_register(handle, cpt_lf_done_irq, lf, vec);
+
+ /* Enable done interrupt */
+ cpt_lf_done_intr_enb_dis(lf, true);
+
+ return rc;
+}
+
+static void
+cpt_lf_unregister_done_irq(struct roc_cpt_lf *lf)
+{
+ struct plt_pci_device *pci_dev = lf->pci_dev;
+ struct plt_intr_handle *handle;
+ int vec;
+
+ handle = &pci_dev->intr_handle;
+
+ vec = lf->msixoff + CPT_LF_INT_VEC_DONE;
+
+ /* Clear done interrupt */
+ cpt_lf_done_intr_enb_dis(lf, false);
+ dev_irq_unregister(handle, cpt_lf_done_irq, lf, vec);
+}
+
+static int
+cpt_lf_register_irqs(struct roc_cpt_lf *lf)
+{
+ int rc;
+
+ if (lf->msixoff == MSIX_VECTOR_INVALID) {
+ plt_err("Invalid CPTLF MSIX vector offset vector: 0x%x",
+ lf->msixoff);
+ return -EINVAL;
+ }
+
+ /* Register lf err interrupt */
+ rc = cpt_lf_register_misc_irq(lf);
+ if (rc)
+ plt_err("Error registering IRQs");
+
+ rc = cpt_lf_register_done_irq(lf);
+ if (rc)
+ plt_err("Error registering IRQs");
+
+ return rc;
+}
+
+static void
+cpt_lf_unregister_irqs(struct roc_cpt_lf *lf)
+{
+ cpt_lf_unregister_misc_irq(lf);
+ cpt_lf_unregister_done_irq(lf);
+}
+
int
roc_cpt_rxc_time_cfg(struct roc_cpt *roc_cpt, struct roc_cpt_rxc_time_cfg *cfg)
{
@@ -146,6 +329,69 @@ cpt_hardware_caps_get(struct dev *dev, union cpt_eng_caps *hw_caps)
return 0;
}
+static uint32_t
+cpt_lf_iq_mem_calc(uint32_t nb_desc)
+{
+ uint32_t len;
+
+ /* Space for instruction group memory */
+ len = CPT_IQ_GRP_SIZE(nb_desc);
+
+ /* Align to 128B */
+ len = PLT_ALIGN(len, ROC_ALIGN);
+
+ /* Space for FC */
+ len += CPT_IQ_FC_LEN;
+
+ /* For instruction queues */
+ len += CPT_IQ_NB_DESC_SIZE_DIV40(nb_desc) * CPT_IQ_NB_DESC_MULTIPLIER *
+ sizeof(struct cpt_inst_s);
+
+ return len;
+}
+
+static inline void
+cpt_iq_init(struct roc_cpt_lf *lf)
+{
+ union cpt_lf_q_size lf_q_size = {.u = 0x0};
+ union cpt_lf_q_base lf_q_base = {.u = 0x0};
+ union cpt_lf_inprog lf_inprog;
+ union cpt_lf_ctl lf_ctl;
+ uintptr_t addr;
+
+ lf->io_addr = lf->rbase + CPT_LF_NQX(0);
+
+ /* Disable command queue */
+ roc_cpt_iq_disable(lf);
+
+ /* Set command queue base address */
+ addr = (uintptr_t)lf->iq_vaddr +
+ PLT_ALIGN(CPT_IQ_GRP_SIZE(lf->nb_desc), ROC_ALIGN);
+
+ lf_q_base.u = addr;
+
+ plt_write64(lf_q_base.u, lf->rbase + CPT_LF_Q_BASE);
+
+ /* Set command queue size */
+ lf_q_size.s.size_div40 = CPT_IQ_NB_DESC_SIZE_DIV40(lf->nb_desc);
+ plt_write64(lf_q_size.u, lf->rbase + CPT_LF_Q_SIZE);
+
+ /* Enable command queue execution */
+ lf_inprog.u = plt_read64(lf->rbase + CPT_LF_INPROG);
+ lf_inprog.s.eena = 1;
+ plt_write64(lf_inprog.u, lf->rbase + CPT_LF_INPROG);
+
+ /* Enable instruction queue enqueuing */
+ lf_ctl.u = plt_read64(lf->rbase + CPT_LF_CTL);
+ lf_ctl.s.ena = 1;
+ lf_ctl.s.fc_ena = 1;
+ lf_ctl.s.fc_up_crossing = 1;
+ lf_ctl.s.fc_hyst_bits = CPT_FC_NUM_HYST_BITS;
+ plt_write64(lf_ctl.u, lf->rbase + CPT_LF_CTL);
+
+ lf->fc_addr = (uint64_t *)addr;
+}
+
int
roc_cpt_dev_configure(struct roc_cpt *roc_cpt, int nb_lf)
{
@@ -210,6 +456,63 @@ cpt_get_blkaddr(struct dev *dev)
}
int
+cpt_lf_init(struct roc_cpt_lf *lf)
+{
+ struct dev *dev = lf->dev;
+ uint64_t blkaddr;
+ void *iq_mem;
+ int rc;
+
+ if (lf->nb_desc == 0 || lf->nb_desc > CPT_LF_MAX_NB_DESC)
+ lf->nb_desc = CPT_LF_DEFAULT_NB_DESC;
+
+ /* Allocate memory for instruction queue for CPT LF. */
+ iq_mem = plt_zmalloc(cpt_lf_iq_mem_calc(lf->nb_desc), ROC_ALIGN);
+ if (iq_mem == NULL)
+ return -ENOMEM;
+
+ blkaddr = cpt_get_blkaddr(dev);
+ lf->rbase = dev->bar2 + ((blkaddr << 20) | (lf->lf_id << 12));
+ lf->iq_vaddr = iq_mem;
+ lf->lmt_base = dev->lmt_base;
+ lf->pf_func = dev->pf_func;
+
+ /* Initialize instruction queue */
+ cpt_iq_init(lf);
+
+ rc = cpt_lf_register_irqs(lf);
+ if (rc)
+ goto disable_iq;
+
+ return 0;
+
+disable_iq:
+ roc_cpt_iq_disable(lf);
+ plt_free(iq_mem);
+ return rc;
+}
+
+int
+roc_cpt_lf_init(struct roc_cpt *roc_cpt, struct roc_cpt_lf *lf)
+{
+ struct cpt *cpt = roc_cpt_to_cpt_priv(roc_cpt);
+ int rc;
+
+ lf->dev = &cpt->dev;
+ lf->roc_cpt = roc_cpt;
+ lf->msixoff = cpt->lf_msix_off[lf->lf_id];
+ lf->pci_dev = cpt->pci_dev;
+
+ rc = cpt_lf_init(lf);
+ if (rc)
+ return rc;
+
+ /* LF init successful */
+ roc_cpt->lf[lf->lf_id] = lf;
+ return rc;
+}
+
+int
roc_cpt_dev_init(struct roc_cpt *roc_cpt)
{
struct plt_pci_device *pci_dev;
@@ -267,6 +570,29 @@ roc_cpt_dev_init(struct roc_cpt *roc_cpt)
return rc;
}
+void
+cpt_lf_fini(struct roc_cpt_lf *lf)
+{
+ /* Unregister IRQ's */
+ cpt_lf_unregister_irqs(lf);
+
+ /* Disable IQ */
+ roc_cpt_iq_disable(lf);
+
+ /* Free memory */
+ plt_free(lf->iq_vaddr);
+ lf->iq_vaddr = NULL;
+}
+
+void
+roc_cpt_lf_fini(struct roc_cpt_lf *lf)
+{
+ if (lf == NULL)
+ return;
+ lf->roc_cpt->lf[lf->lf_id] = NULL;
+ cpt_lf_fini(lf);
+}
+
int
roc_cpt_dev_fini(struct roc_cpt *roc_cpt)
{
@@ -341,3 +667,34 @@ roc_cpt_eng_grp_add(struct roc_cpt *roc_cpt, enum cpt_eng_type eng_type)
return rsp->eng_grp_num;
}
+
+void
+roc_cpt_iq_disable(struct roc_cpt_lf *lf)
+{
+ union cpt_lf_ctl lf_ctl = {.u = 0x0};
+ union cpt_lf_inprog lf_inprog;
+ int timeout = 20;
+
+ /* Disable instructions enqueuing */
+ plt_write64(lf_ctl.u, lf->rbase + CPT_LF_CTL);
+
+ /* Wait for instruction queue to become empty */
+ do {
+ lf_inprog.u = plt_read64(lf->rbase + CPT_LF_INPROG);
+ if (!lf_inprog.s.inflight)
+ break;
+
+ plt_delay_ms(20);
+ if (timeout-- < 0) {
+ plt_err("CPT LF %d is still busy", lf->lf_id);
+ break;
+ }
+
+ } while (1);
+
+ /* Disable executions in the LF's queue.
+ * The queue should be empty at this point
+ */
+ lf_inprog.s.eena = 0x0;
+ plt_write64(lf_inprog.u, lf->rbase + CPT_LF_INPROG);
+}
diff --git a/drivers/common/cnxk/roc_cpt.h b/drivers/common/cnxk/roc_cpt.h
index bae472f..e258ca5 100644
--- a/drivers/common/cnxk/roc_cpt.h
+++ b/drivers/common/cnxk/roc_cpt.h
@@ -14,6 +14,23 @@
#define ROC_CPT_MAX_LFS 64
+struct roc_cpt_lf {
+ /* Input parameters */
+ uint16_t lf_id;
+ uint32_t nb_desc;
+ /* End of Input parameters */
+ struct plt_pci_device *pci_dev;
+ struct dev *dev;
+ struct roc_cpt *roc_cpt;
+ uintptr_t rbase;
+ uintptr_t lmt_base;
+ uint16_t msixoff;
+ uint16_t pf_func;
+ uint64_t *fc_addr;
+ uint64_t io_addr;
+ uint8_t *iq_vaddr;
+} __plt_cache_aligned;
+
struct roc_cpt {
struct plt_pci_device *pci_dev;
struct roc_cpt_lf *lf[ROC_CPT_MAX_LFS];
@@ -44,4 +61,7 @@ int __roc_api roc_cpt_eng_grp_add(struct roc_cpt *roc_cpt,
enum cpt_eng_type eng_type);
int __roc_api roc_cpt_dev_configure(struct roc_cpt *roc_cpt, int nb_lf);
void __roc_api roc_cpt_dev_clear(struct roc_cpt *roc_cpt);
+int __roc_api roc_cpt_lf_init(struct roc_cpt *roc_cpt, struct roc_cpt_lf *lf);
+void __roc_api roc_cpt_lf_fini(struct roc_cpt_lf *lf);
+void __roc_api roc_cpt_iq_disable(struct roc_cpt_lf *lf);
#endif /* _ROC_CPT_H_ */
diff --git a/drivers/common/cnxk/roc_cpt_priv.h b/drivers/common/cnxk/roc_cpt_priv.h
index 0ef6774..6cfa4df 100644
--- a/drivers/common/cnxk/roc_cpt_priv.h
+++ b/drivers/common/cnxk/roc_cpt_priv.h
@@ -30,6 +30,8 @@ int cpt_lfs_detach(struct dev *dev);
int cpt_lfs_alloc(struct dev *dev, uint8_t eng_grpmsk, uint8_t blk,
bool inl_dev_sso);
int cpt_lfs_free(struct dev *dev);
+int cpt_lf_init(struct roc_cpt_lf *lf);
+void cpt_lf_fini(struct roc_cpt_lf *lf);
int cpt_get_msix_offset(struct dev *dev, struct msix_offset_rsp **msix_rsp);
uint64_t cpt_get_blkaddr(struct dev *dev);
diff --git a/drivers/common/cnxk/version.map b/drivers/common/cnxk/version.map
index 13fd026..128997e 100644
--- a/drivers/common/cnxk/version.map
+++ b/drivers/common/cnxk/version.map
@@ -16,6 +16,9 @@ INTERNAL {
roc_cpt_dev_fini;
roc_cpt_dev_init;
roc_cpt_eng_grp_add;
+ roc_cpt_iq_disable;
+ roc_cpt_lf_init;
+ roc_cpt_lf_fini;
roc_cpt_rxc_time_cfg;
roc_error_msg_get;
roc_idev_cpt_get;
--
2.7.4
next prev parent reply other threads:[~2021-06-25 5:37 UTC|newest]
Thread overview: 20+ messages / expand[flat|nested] mbox.gz Atom feed top
[not found] <patches.dpdk.org/project/dpdk/patch/1622649385-22652-1-git-send-email-anoobj@marvell.com/>
2021-06-25 5:36 ` [dpdk-dev] [PATCH v2 00/17] Add CPT in Marvell CNXK common driver Anoob Joseph
2021-06-25 5:36 ` [dpdk-dev] [PATCH v2 01/17] common/cnxk: add CPT HW defines Anoob Joseph
2021-06-25 5:36 ` [dpdk-dev] [PATCH v2 02/17] common/cnxk: update Rx inline IPsec mbox message format Anoob Joseph
2021-06-25 5:36 ` [dpdk-dev] [PATCH v2 03/17] common/cnxk: add CPT dev config routines Anoob Joseph
2021-06-25 5:36 ` [dpdk-dev] [PATCH v2 04/17] common/cnxk: add idev CPT set - get Anoob Joseph
2021-06-25 5:36 ` [dpdk-dev] [PATCH v2 05/17] common/cnxk: add mbox to configure RXC Anoob Joseph
2021-06-25 5:36 ` Anoob Joseph [this message]
2021-06-25 5:36 ` [dpdk-dev] [PATCH v2 07/17] common/cnxk: add CPT diagnostics Anoob Joseph
2021-06-25 5:36 ` [dpdk-dev] [PATCH v2 08/17] common/cnxk: add CPT LF flush Anoob Joseph
2021-06-25 5:36 ` [dpdk-dev] [PATCH v2 09/17] common/cnxk: add inline IPsec configuration mbox Anoob Joseph
2021-06-25 5:36 ` [dpdk-dev] [PATCH v2 10/17] common/cnxk: add SE microcode defines Anoob Joseph
2021-06-25 5:36 ` [dpdk-dev] [PATCH v2 11/17] common/cnxk: add IE " Anoob Joseph
2021-06-25 5:36 ` [dpdk-dev] [PATCH v2 12/17] common/cnxk: add AE " Anoob Joseph
2021-06-25 5:36 ` [dpdk-dev] [PATCH v2 13/17] common/cnxk: add lmtline init Anoob Joseph
2021-06-25 5:36 ` [dpdk-dev] [PATCH v2 14/17] common/cnxk: add fpm tables Anoob Joseph
2021-06-25 5:36 ` [dpdk-dev] [PATCH v2 15/17] common/cnxk: add EC grp static vectors Anoob Joseph
2021-06-25 5:36 ` [dpdk-dev] [PATCH v2 16/17] common/cnxk: add IPsec common code Anoob Joseph
2021-06-25 5:36 ` [dpdk-dev] [PATCH v2 17/17] common/cnxk: add SE set key functions in roc Anoob Joseph
2021-06-28 8:56 ` [dpdk-dev] [PATCH v2 00/17] Add CPT in Marvell CNXK common driver Akhil Goyal
2021-06-28 9:06 ` Akhil Goyal
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=1624599410-29689-7-git-send-email-anoobj@marvell.com \
--to=anoobj@marvell.com \
--cc=adwivedi@marvell.com \
--cc=dev@dpdk.org \
--cc=gakhil@marvell.com \
--cc=jerinj@marvell.com \
--cc=ktejasree@marvell.com \
--cc=marchana@marvell.com \
--cc=thomas@monjalon.net \
--cc=vvelumuri@marvell.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).