new file mode 100644
@@ -0,0 +1,135 @@
+/* SPDX-License-Identifier: MIT */
+/* Copyright(c) 2019-2021, Celeno Communications Ltd. */
+
+#ifndef CL_IPC_H
+#define CL_IPC_H
+
+#include "ipc_shared.h"
+#include "hw.h"
+
+/* Struct used to store information about host buffers (DMA Address and local pointer) */
+struct cl_ipc_hostbuf {
+ ptrdiff_t hostid; /* Ptr to hostbuf client (ipc_host client) structure */
+ dma_addr_t dma_addr; /* Ptr to real hostbuf dma address */
+};
+
+/*
+ * Index in txdesc - updated by host on every push, used by firmware side
+ * Keep this structure aligned to 4-byte
+ */
+struct cl_ipc_txdesc_write_idx {
+ u32 agg[IPC_MAX_BA_SESSIONS];
+ u32 single[MAX_SINGLE_QUEUES];
+ u32 bcmc;
+};
+
+struct cl_ipc_ring_indices {
+ /* Last copy of ipc txdesc write desc right after DMA push operation */
+ volatile struct cl_ipc_txdesc_write_idx txdesc_write_idx;
+ /*
+ * new start sn - equal to last acknowledged sequence number + 1.
+ * Updated by firmware and used by host.
+ */
+ volatile u16 new_ssn_idx[IPC_MAX_BA_SESSIONS];
+ volatile u8 dtim_count[MAX_BSS_NUM];
+ /* Index in rxdesc array, updated by firmware on every payload push, used by host */
+ volatile u32 rxdesc_write_idx[CL_RX_BUF_MAX];
+ /* Index in rxdesc array, updated by host on rxdesc copy completion, used by firmware */
+ volatile u32 rxdesc_read_idx[CL_RX_BUF_MAX];
+ /* BSR data counters */
+ volatile u32 bsr_data_ctrs[TID_MAX];
+};
+
+/* Structure used to store Shared Txring indices */
+struct cl_ipc_ring_indices_elem {
+ struct cl_ipc_ring_indices *indices;
+ dma_addr_t dma_addr;
+};
+
+struct cl_ipc_host_rxbuf {
+ /* Array of drv desc which holds the skb and additional data */
+ ptrdiff_t **ipc_host_rxdesc_ptr;
+ /* Address of payload for embedded push operation (part of rxdesc data) */
+ u32 *dma_payload_addr;
+ /* Dma pointer to array of DMA payload addresses */
+ __le32 dma_payload_base_addr;
+};
+
+/*
+ * struct tx_queues_dma_addr - ipc layer queues addresses casted to DMA addresses
+ *
+ * The ipc layer points to array of txdesc, there are:
+ * 'IPC_MAX_BA_SESSIONS' arrays for aggregation queues
+ * 'MAX_SINGLE_QUEUES' arrayes for singletons queues
+ * '1' arrays for broadcast/unicast queue
+ *
+ * Each one of this arrays should be copied compeletly to the FW, therefore we should
+ * cast all of the arrays to dma addresses.
+ */
+struct tx_queues_dma_addr {
+ u32 agg[IPC_MAX_BA_SESSIONS];
+ u32 single[MAX_SINGLE_QUEUES];
+ u32 bcmc;
+};
+
+/* struct cl_ipc_tx_queues - ipc layer tx queues */
+struct cl_ipc_tx_queues {
+ struct txdesc *ipc_txdesc_agg[IPC_MAX_BA_SESSIONS];
+ struct txdesc *ipc_txdesc_single[MAX_SINGLE_QUEUES];
+ struct txdesc *ipc_txdesc_bcmc;
+ /* Mapping of the TXQ's addresses to DMA addresses */
+ struct tx_queues_dma_addr *queues_dma_addr;
+ /* DMA address of tx_queues_dma_addr */
+ u32 dma_addr;
+};
+
+struct cl_ipc_host_env {
+ /* Pointer to the shared environment */
+ struct cl_ipc_shared_env *shared;
+ /* TX ring indices (RD, WR idx & new_ssn) */
+ struct cl_ipc_ring_indices_elem *ring_indices_elem;
+ /* RX buffers (rxdesc & dma_addr) */
+ ptrdiff_t *ipc_host_rxdesc_rxm[IPC_RXBUF_CNT_RXM];
+ ptrdiff_t *ipc_host_rxdesc_fw[IPC_RXBUF_CNT_FW];
+ struct cl_ipc_host_rxbuf rx_hostbuf_array[CL_RX_BUF_MAX];
+ /* Host last read idx */
+ u32 host_rxdesc_read_idx[CL_RX_BUF_MAX];
+ /* Fields for Radar events handling */
+ struct cl_ipc_hostbuf radar_hostbuf_array[IPC_RADAR_BUF_CNT];
+ u8 radar_host_idx;
+ /* Fields for Emb->App MSGs handling */
+ struct cl_ipc_hostbuf e2a_msg_hostbuf_array[IPC_E2A_MSG_BUF_CNT];
+ u8 e2a_msg_host_idx;
+ /* Fields for Debug MSGs handling */
+ struct cl_ipc_hostbuf dbg_hostbuf_array[IPC_DBG_BUF_CNT];
+ u8 dbg_host_idx;
+ /* IPC queues */
+ struct cl_ipc_tx_queues tx_queues;
+ struct cl_ipc_enhanced_tim enhanced_tim;
+ /* Fields for single confirmation handling */
+ u8 *cfm_virt_base_addr;
+ dma_addr_t cfm_dma_base_addr;
+ /* Index used that points to the first used CFM */
+ u32 cfm_used_idx;
+ /* Tasklets */
+ struct tasklet_struct rxdesc_tasklet;
+ struct tasklet_struct tx_single_cfm_tasklet;
+ struct tasklet_struct tx_agg_cfm_tasklet;
+ struct tasklet_struct msg_tasklet;
+ struct tasklet_struct dbg_tasklet;
+};
+
+int cl_ipc_init(struct cl_hw *cl_hw);
+void cl_ipc_recovery(struct cl_hw *cl_hw);
+void cl_ipc_reset(struct cl_hw *cl_hw);
+void cl_ipc_deinit(struct cl_hw *cl_hw);
+void cl_ipc_stop(struct cl_hw *cl_hw);
+int cl_ipc_rx_elem_alloc(struct cl_hw *cl_hw, struct cl_rx_elem *rx_elem, u32 size);
+void cl_ipc_msgbuf_push(struct cl_ipc_host_env *ipc_env, ptrdiff_t hostid, dma_addr_t hostbuf);
+void cl_ipc_rxbuf_push(struct cl_ipc_host_env *ipc_env, struct cl_rx_elem *rx_elem,
+ u32 rxdesc_read_idx, u32 host_read_idx, enum rx_buf_type type);
+void cl_ipc_radarbuf_push(struct cl_ipc_host_env *ipc_env, ptrdiff_t hostid, dma_addr_t hostbuf);
+void cl_ipc_dbgbuf_push(struct cl_ipc_host_env *ipc_env, ptrdiff_t hostid, dma_addr_t hostbuf);
+void cl_ipc_dbginfobuf_push(struct cl_ipc_host_env *ipc_env, dma_addr_t infobuf);
+
+#endif /* CL_IPC_H */