Add msg channel and hwlock init implementation<br /> <br />Signed-off-by: Junlong Wang <wang.junlong1@zte.com.cn> <br />---<br /> drivers/net/zxdh/meson.build   |   1 +<br /> drivers/net/zxdh/zxdh_ethdev.c |  15 +++<br /> drivers/net/zxdh/zxdh_ethdev.h |   1 +<br /> drivers/net/zxdh/zxdh_msg.c    | 170 +++++++++++++++++++++++++++++++++<br /> drivers/net/zxdh/zxdh_msg.h    |  67 +++++++++++++<br /> 5 files changed, 254 insertions(+)<br /> create mode 100644 drivers/net/zxdh/zxdh_msg.c<br /> create mode 100644 drivers/net/zxdh/zxdh_msg.h<br /> <br />diff --git a/drivers/net/zxdh/meson.build b/drivers/net/zxdh/meson.build<br />index 7db4e7bc71..2e0c8fddae 100644<br />--- a/drivers/net/zxdh/meson.build<br />+++ b/drivers/net/zxdh/meson.build<br />@@ -16,4 +16,5 @@ endif<br /> sources = files(<br />         'zxdh_ethdev.c',<br />         'zxdh_pci.c',<br />+        'zxdh_msg.c',<br /> )<br />diff --git a/drivers/net/zxdh/zxdh_ethdev.c b/drivers/net/zxdh/zxdh_ethdev.c<br />index ae20e00317..bb7c1253c9 100644<br />--- a/drivers/net/zxdh/zxdh_ethdev.c<br />+++ b/drivers/net/zxdh/zxdh_ethdev.c<br />@@ -9,6 +9,7 @@<br /> #include "zxdh_ethdev.h" <br /> #include "zxdh_logs.h" <br /> #include "zxdh_pci.h" <br />+#include "zxdh_msg.h" <br />  <br /> struct zxdh_hw_internal zxdh_hw_internal[RTE_MAX_ETHPORTS];<br />  <br />@@ -85,9 +86,23 @@ zxdh_eth_dev_init(struct rte_eth_dev *eth_dev)<br />     if (ret < 0)<br />         goto err_zxdh_init;<br />  <br />+    ret = zxdh_msg_chan_init();<br />+    if (ret != 0) {<br />+        PMD_DRV_LOG(ERR, "Failed to init bar msg chan");<br />+        goto err_zxdh_init;<br />+    }<br />+    hw->msg_chan_init = 1;<br />+<br />+    ret = zxdh_msg_chan_hwlock_init(eth_dev);<br />+    if (ret != 0) {<br />+        PMD_DRV_LOG(ERR, "zxdh_msg_chan_hwlock_init failed ret %d", ret);<br />+        goto err_zxdh_init;<br />+    }<br />+<br />     return ret;<br />  <br /> err_zxdh_init:<br />+    zxdh_bar_msg_chan_exit();<br />     rte_free(eth_dev->data->mac_addrs);<br />     eth_dev->data->mac_addrs = NULL;<br />     return ret;<br />diff --git a/drivers/net/zxdh/zxdh_ethdev.h b/drivers/net/zxdh/zxdh_ethdev.h<br />index a22ac15065..20ead56e44 100644<br />--- a/drivers/net/zxdh/zxdh_ethdev.h<br />+++ b/drivers/net/zxdh/zxdh_ethdev.h<br />@@ -51,6 +51,7 @@ struct zxdh_hw {<br />  <br />     uint8_t duplex;<br />     uint8_t is_pf;<br />+    uint8_t msg_chan_init;<br /> };<br />  <br /> #ifdef __cplusplus<br />diff --git a/drivers/net/zxdh/zxdh_msg.c b/drivers/net/zxdh/zxdh_msg.c<br />new file mode 100644<br />index 0000000000..319a9cab57<br />--- /dev/null<br />+++ b/drivers/net/zxdh/zxdh_msg.c<br />@@ -0,0 +1,170 @@<br />+/* SPDX-License-Identifier: BSD-3-Clause<br />+ * Copyright(c) 2024 ZTE Corporation<br />+ */<br />+<br />+#include <stdbool.h> <br />+<br />+#include <rte_common.h> <br />+#include <rte_memcpy.h> <br />+#include <rte_spinlock.h> <br />+#include <rte_cycles.h> <br />+#include <inttypes.h> <br />+#include <rte_malloc.h> <br />+<br />+#include "zxdh_ethdev.h" <br />+#include "zxdh_logs.h" <br />+#include "zxdh_msg.h" <br />+<br />+#define ZXDH_REPS_INFO_FLAG_USABLE  0x00<br />+#define ZXDH_BAR_SEQID_NUM_MAX      256<br />+<br />+#define ZXDH_PCIEID_IS_PF_MASK      (0x0800)<br />+#define ZXDH_PCIEID_PF_IDX_MASK     (0x0700)<br />+#define ZXDH_PCIEID_VF_IDX_MASK     (0x00ff)<br />+#define ZXDH_PCIEID_EP_IDX_MASK     (0x7000)<br />+/* PCIEID bit field offset */<br />+#define ZXDH_PCIEID_PF_IDX_OFFSET   (8)<br />+#define ZXDH_PCIEID_EP_IDX_OFFSET   (12)<br />+<br />+#define ZXDH_MULTIPLY_BY_8(x)       ((x) << 3)<br />+#define ZXDH_MULTIPLY_BY_32(x)      ((x) << 5)<br />+#define ZXDH_MULTIPLY_BY_256(x)     ((x) << 8)<br />+<br />+#define ZXDH_MAX_EP_NUM              (4)<br />+#define ZXDH_MAX_HARD_SPINLOCK_NUM   (511)<br />+<br />+#define ZXDH_BAR0_SPINLOCK_OFFSET       (0x4000)<br />+#define ZXDH_FW_SHRD_OFFSET             (0x5000)<br />+#define ZXDH_FW_SHRD_INNER_HW_LABEL_PAT (0x800)<br />+#define ZXDH_HW_LABEL_OFFSET   \<br />+    (ZXDH_FW_SHRD_OFFSET + ZXDH_FW_SHRD_INNER_HW_LABEL_PAT)<br />+<br />+struct zxdh_dev_stat {<br />+    bool is_mpf_scanned;<br />+    bool is_res_init;<br />+    int16_t dev_cnt; /* probe cnt */<br />+};<br />+<br />+struct zxdh_seqid_item {<br />+    void *reps_addr;<br />+    uint16_t id;<br />+    uint16_t buffer_len;<br />+    uint16_t flag;<br />+};<br />+<br />+struct zxdh_seqid_ring {<br />+    uint16_t cur_id;<br />+    rte_spinlock_t lock;<br />+    struct zxdh_seqid_item reps_info_tbl[ZXDH_BAR_SEQID_NUM_MAX];<br />+};<br />+<br />+static struct zxdh_dev_stat g_dev_stat;<br />+static struct zxdh_seqid_ring g_seqid_ring;<br />+static rte_spinlock_t chan_lock;<br />+<br />+static uint16_t<br />+zxdh_pcie_id_to_hard_lock(uint16_t src_pcieid, uint8_t dst)<br />+{<br />+    uint16_t lock_id = 0;<br />+    uint16_t pf_idx = (src_pcieid & ZXDH_PCIEID_PF_IDX_MASK) >> ZXDH_PCIEID_PF_IDX_OFFSET;<br />+    uint16_t ep_idx = (src_pcieid & ZXDH_PCIEID_EP_IDX_MASK) >> ZXDH_PCIEID_EP_IDX_OFFSET;<br />+<br />+    switch (dst) {<br />+    /* msg to risc */<br />+    case ZXDH_MSG_CHAN_END_RISC:<br />+        lock_id = ZXDH_MULTIPLY_BY_8(ep_idx) + pf_idx;<br />+        break;<br />+    /* msg to pf/vf */<br />+    case ZXDH_MSG_CHAN_END_VF:<br />+    case ZXDH_MSG_CHAN_END_PF:<br />+        lock_id = ZXDH_MULTIPLY_BY_8(ep_idx) + pf_idx +<br />+                ZXDH_MULTIPLY_BY_8(1 + ZXDH_MAX_EP_NUM);<br />+        break;<br />+    default:<br />+        lock_id = 0;<br />+        break;<br />+    }<br />+    if (lock_id >= ZXDH_MAX_HARD_SPINLOCK_NUM)<br />+        lock_id = 0;<br />+<br />+    return lock_id;<br />+}<br />+<br />+static void<br />+label_write(uint64_t label_lock_addr, uint32_t lock_id, uint16_t value)<br />+{<br />+    *(volatile uint16_t *)(label_lock_addr + lock_id * 2) = value;<br />+}<br />+<br />+static void<br />+spinlock_write(uint64_t virt_lock_addr, uint32_t lock_id, uint8_t data)<br />+{<br />+    *(volatile uint8_t *)((uint64_t)virt_lock_addr + (uint64_t)lock_id) = data;<br />+}<br />+<br />+static int32_t<br />+zxdh_spinlock_unlock(uint32_t virt_lock_id, uint64_t virt_addr, uint64_t label_addr)<br />+{<br />+    label_write((uint64_t)label_addr, virt_lock_id, 0);<br />+    spinlock_write(virt_addr, virt_lock_id, 0);<br />+    return 0;<br />+}<br />+<br />+/**<br />+ * Fun: PF init hard_spinlock addr<br />+ */<br />+static int<br />+bar_chan_pf_init_spinlock(uint16_t pcie_id, uint64_t bar_base_addr)<br />+{<br />+    int lock_id = zxdh_pcie_id_to_hard_lock(pcie_id, ZXDH_MSG_CHAN_END_RISC);<br />+<br />+    zxdh_spinlock_unlock(lock_id, bar_base_addr + ZXDH_BAR0_SPINLOCK_OFFSET,<br />+            bar_base_addr + ZXDH_HW_LABEL_OFFSET);<br />+    lock_id = zxdh_pcie_id_to_hard_lock(pcie_id, ZXDH_MSG_CHAN_END_VF);<br />+    zxdh_spinlock_unlock(lock_id, bar_base_addr + ZXDH_BAR0_SPINLOCK_OFFSET,<br />+            bar_base_addr + ZXDH_HW_LABEL_OFFSET);<br />+    return 0;<br />+}<br />+<br />+int<br />+zxdh_msg_chan_hwlock_init(struct rte_eth_dev *dev)<br />+{<br />+    struct zxdh_hw *hw = dev->data->dev_private;<br />+<br />+    if (!hw->is_pf)<br />+        return 0;<br />+    return bar_chan_pf_init_spinlock(hw->pcie_id, (uint64_t)(hw->bar_addr[ZXDH_BAR0_INDEX]));<br />+}<br />+<br />+int<br />+zxdh_msg_chan_init(void)<br />+{<br />+    uint16_t seq_id = 0;<br />+<br />+    g_dev_stat.dev_cnt++;<br />+    if (g_dev_stat.is_res_init)<br />+        return ZXDH_BAR_MSG_OK;<br />+<br />+    rte_spinlock_init(&chan_lock);<br />+    g_seqid_ring.cur_id = 0;<br />+    rte_spinlock_init(&g_seqid_ring.lock);<br />+<br />+    for (seq_id = 0; seq_id < ZXDH_BAR_SEQID_NUM_MAX; seq_id++) {<br />+        struct zxdh_seqid_item *reps_info = &g_seqid_ring.reps_info_tbl[seq_id];<br />+<br />+        reps_info->id = seq_id;<br />+        reps_info->flag = ZXDH_REPS_INFO_FLAG_USABLE;<br />+    }<br />+    g_dev_stat.is_res_init = true;<br />+    return ZXDH_BAR_MSG_OK;<br />+}<br />+<br />+int<br />+zxdh_bar_msg_chan_exit(void)<br />+{<br />+    if (!g_dev_stat.is_res_init || (--g_dev_stat.dev_cnt > 0))<br />+        return ZXDH_BAR_MSG_OK;<br />+<br />+    g_dev_stat.is_res_init = false;<br />+    return ZXDH_BAR_MSG_OK;<br />+}<br />diff --git a/drivers/net/zxdh/zxdh_msg.h b/drivers/net/zxdh/zxdh_msg.h<br />new file mode 100644<br />index 0000000000..64e1ad0e7f<br />--- /dev/null<br />+++ b/drivers/net/zxdh/zxdh_msg.h<br />@@ -0,0 +1,67 @@<br />+/* SPDX-License-Identifier: BSD-3-Clause<br />+ * Copyright(c) 2024 ZTE Corporation<br />+ */<br />+<br />+#ifndef ZXDH_MSG_H<br />+#define ZXDH_MSG_H<br />+<br />+#include <stdint.h> <br />+<br />+#include <ethdev_driver.h> <br />+<br />+#ifdef __cplusplus<br />+extern "C" {<br />+#endif<br />+<br />+#define ZXDH_BAR0_INDEX     0<br />+<br />+enum ZXDH_DRIVER_TYPE {<br />+    ZXDH_MSG_CHAN_END_MPF = 0,<br />+    ZXDH_MSG_CHAN_END_PF,<br />+    ZXDH_MSG_CHAN_END_VF,<br />+    ZXDH_MSG_CHAN_END_RISC,<br />+};<br />+<br />+enum ZXDH_BAR_MSG_RTN {<br />+    ZXDH_BAR_MSG_OK = 0,<br />+    ZXDH_BAR_MSG_ERR_MSGID,<br />+    ZXDH_BAR_MSG_ERR_NULL,<br />+    ZXDH_BAR_MSG_ERR_TYPE, /* Message type exception */<br />+    ZXDH_BAR_MSG_ERR_MODULE, /* Module ID exception */<br />+    ZXDH_BAR_MSG_ERR_BODY_NULL, /* Message body exception */<br />+    ZXDH_BAR_MSG_ERR_LEN, /* Message length exception */<br />+    ZXDH_BAR_MSG_ERR_TIME_OUT, /* Message sending length too long */<br />+    ZXDH_BAR_MSG_ERR_NOT_READY, /* Abnormal message sending conditions*/<br />+    ZXDH_BAR_MEG_ERR_NULL_FUNC, /* Empty receive processing function pointer*/<br />+    ZXDH_BAR_MSG_ERR_REPEAT_REGISTER, /* Module duplicate registration*/<br />+    ZXDH_BAR_MSG_ERR_UNGISTER, /* Repeated deregistration*/<br />+    /*<br />+     * The sending interface parameter boundary structure pointer is empty<br />+     */<br />+    ZXDH_BAR_MSG_ERR_NULL_PARA,<br />+    ZXDH_BAR_MSG_ERR_REPSBUFF_LEN, /* The length of reps_buff is too short*/<br />+    /*<br />+     * Unable to find the corresponding message processing function for this module<br />+     */<br />+    ZXDH_BAR_MSG_ERR_MODULE_NOEXIST,<br />+    /*<br />+     * The virtual address in the parameters passed in by the sending interface is empty<br />+     */<br />+    ZXDH_BAR_MSG_ERR_VIRTADDR_NULL,<br />+    ZXDH_BAR_MSG_ERR_REPLY, /* sync msg resp_error */<br />+    ZXDH_BAR_MSG_ERR_MPF_NOT_SCANNED,<br />+    ZXDH_BAR_MSG_ERR_KERNEL_READY,<br />+    ZXDH_BAR_MSG_ERR_USR_RET_ERR,<br />+    ZXDH_BAR_MSG_ERR_ERR_PCIEID,<br />+    ZXDH_BAR_MSG_ERR_SOCKET, /* netlink sockte err */<br />+};<br />+<br />+int zxdh_msg_chan_init(void);<br />+int zxdh_bar_msg_chan_exit(void);<br />+int zxdh_msg_chan_hwlock_init(struct rte_eth_dev *dev);<br />+<br />+#ifdef __cplusplus<br />+}<br />+#endif<br />+<br />+#endif /* ZXDH_MSG_H */<br />--  <br />2.27.0<br />