Since outbound IPsec is not really dependent on SPI,
allow duplicate SPI in outbound inline IPsec sessions.

Signed-off-by: Nithin Dabilpuram <ndabilpu...@marvell.com>
---

Depends-on: series-34428 ("[v4,1/2] common/cnxk: support NPC flow on cn20k")

 drivers/net/cnxk/cn10k_ethdev_sec.c | 14 +++++++-------
 drivers/net/cnxk/cn9k_ethdev_sec.c  | 14 +++++++-------
 drivers/net/cnxk/cnxk_ethdev.h      |  4 ++--
 drivers/net/cnxk/cnxk_ethdev_sec.c  |  8 ++++++--
 4 files changed, 22 insertions(+), 18 deletions(-)

diff --git a/drivers/net/cnxk/cn10k_ethdev_sec.c 
b/drivers/net/cnxk/cn10k_ethdev_sec.c
index 6acab8afa0..41dfba36d3 100644
--- a/drivers/net/cnxk/cn10k_ethdev_sec.c
+++ b/drivers/net/cnxk/cn10k_ethdev_sec.c
@@ -793,13 +793,6 @@ cn10k_eth_sec_session_create(void *device,
        inbound = !!(ipsec->direction == RTE_SECURITY_IPSEC_SA_DIR_INGRESS);
        inl_dev = !!dev->inb.inl_dev;
 
-       /* Search if a session already exits */
-       if (cnxk_eth_sec_sess_get_by_spi(dev, ipsec->spi, inbound)) {
-               plt_err("%s SA with SPI %u already in use",
-                       inbound ? "Inbound" : "Outbound", ipsec->spi);
-               return -EEXIST;
-       }
-
        memset(eth_sec, 0, sizeof(struct cnxk_eth_sec_sess));
        sess_priv.u64 = 0;
 
@@ -821,6 +814,13 @@ cn10k_eth_sec_session_create(void *device,
 
                spi_mask = roc_nix_inl_inb_spi_range(nix, inl_dev, NULL, NULL);
 
+               /* Search if a session already exits */
+               if (cnxk_eth_sec_sess_get_by_sa_idx(dev, ipsec->spi & spi_mask, 
true)) {
+                       plt_err("Inbound SA with SPI/SA index %u already in 
use", ipsec->spi);
+                       rc = -EEXIST;
+                       goto err;
+               }
+
                /* Get Inbound SA from NIX_RX_IPSEC_SA_BASE */
                sa = roc_nix_inl_inb_sa_get(nix, inl_dev, ipsec->spi);
                if (!sa && dev->inb.inl_dev) {
diff --git a/drivers/net/cnxk/cn9k_ethdev_sec.c 
b/drivers/net/cnxk/cn9k_ethdev_sec.c
index 390853c728..5e13dc862e 100644
--- a/drivers/net/cnxk/cn9k_ethdev_sec.c
+++ b/drivers/net/cnxk/cn9k_ethdev_sec.c
@@ -604,13 +604,6 @@ cn9k_eth_sec_session_create(void *device,
        crypto = conf->crypto_xform;
        inbound = !!(ipsec->direction == RTE_SECURITY_IPSEC_SA_DIR_INGRESS);
 
-       /* Search if a session already exists */
-       if (cnxk_eth_sec_sess_get_by_spi(dev, ipsec->spi, inbound)) {
-               plt_err("%s SA with SPI %u already in use",
-                       inbound ? "Inbound" : "Outbound", ipsec->spi);
-               return -EEXIST;
-       }
-
        lock = inbound ? &dev->inb.lock : &dev->outb.lock;
        rte_spinlock_lock(lock);
 
@@ -633,6 +626,13 @@ cn9k_eth_sec_session_create(void *device,
 
                spi_mask = roc_nix_inl_inb_spi_range(nix, false, NULL, NULL);
 
+               /* Search if a session already exits */
+               if (cnxk_eth_sec_sess_get_by_sa_idx(dev, ipsec->spi & spi_mask, 
true)) {
+                       plt_err("Inbound SA with SPI/SA index %u already in 
use", ipsec->spi);
+                       rc = -EEXIST;
+                       goto err;
+               }
+
                /* Get Inbound SA from NIX_RX_IPSEC_SA_BASE. Assume no inline
                 * device always for CN9K.
                 */
diff --git a/drivers/net/cnxk/cnxk_ethdev.h b/drivers/net/cnxk/cnxk_ethdev.h
index 350adc1161..eae5336a9b 100644
--- a/drivers/net/cnxk/cnxk_ethdev.h
+++ b/drivers/net/cnxk/cnxk_ethdev.h
@@ -729,8 +729,8 @@ typedef void (*cnxk_ethdev_rx_offload_cb_t)(uint16_t 
port_id, uint64_t flags);
 __rte_internal
 void cnxk_ethdev_rx_offload_cb_register(cnxk_ethdev_rx_offload_cb_t cb);
 
-struct cnxk_eth_sec_sess *cnxk_eth_sec_sess_get_by_spi(struct cnxk_eth_dev 
*dev,
-                                                      uint32_t spi, bool inb);
+struct cnxk_eth_sec_sess *cnxk_eth_sec_sess_get_by_sa_idx(struct cnxk_eth_dev 
*dev,
+                                                         uint32_t sa_idx, bool 
inb);
 struct cnxk_eth_sec_sess *
 cnxk_eth_sec_sess_get_by_sess(struct cnxk_eth_dev *dev,
                              struct rte_security_session *sess);
diff --git a/drivers/net/cnxk/cnxk_ethdev_sec.c 
b/drivers/net/cnxk/cnxk_ethdev_sec.c
index ef75e5f0f1..2c649c985a 100644
--- a/drivers/net/cnxk/cnxk_ethdev_sec.c
+++ b/drivers/net/cnxk/cnxk_ethdev_sec.c
@@ -231,6 +231,10 @@ cnxk_eth_outb_sa_idx_get(struct cnxk_eth_dev *dev, 
uint32_t *idx_p,
                if (spi > dev->outb.max_sa)
                        return -ENOTSUP;
                idx = spi;
+               if (!plt_bitmap_get(dev->outb.sa_bmap, idx)) {
+                       plt_err("Outbound SA index %u already in use", idx);
+                       return -EEXIST;
+               }
        } else {
                /* Scan bitmap to get the free sa index */
                rc = plt_bitmap_scan(dev->outb.sa_bmap, &pos, &slab);
@@ -265,14 +269,14 @@ cnxk_eth_outb_sa_idx_put(struct cnxk_eth_dev *dev, 
uint32_t idx)
 }
 
 struct cnxk_eth_sec_sess *
-cnxk_eth_sec_sess_get_by_spi(struct cnxk_eth_dev *dev, uint32_t spi, bool inb)
+cnxk_eth_sec_sess_get_by_sa_idx(struct cnxk_eth_dev *dev, uint32_t sa_idx, 
bool inb)
 {
        struct cnxk_eth_sec_sess_list *list;
        struct cnxk_eth_sec_sess *eth_sec;
 
        list = inb ? &dev->inb.list : &dev->outb.list;
        TAILQ_FOREACH(eth_sec, list, entry) {
-               if (eth_sec->spi == spi)
+               if (eth_sec->sa_idx == sa_idx)
                        return eth_sec;
        }
 
-- 
2.34.1

Reply via email to