aboutsummaryrefslogtreecommitdiff
path: root/sys/dev/dpaa/dpaa_common.h
diff options
context:
space:
mode:
Diffstat (limited to 'sys/dev/dpaa/dpaa_common.h')
-rw-r--r--sys/dev/dpaa/dpaa_common.h195
1 files changed, 195 insertions, 0 deletions
diff --git a/sys/dev/dpaa/dpaa_common.h b/sys/dev/dpaa/dpaa_common.h
new file mode 100644
index 000000000000..8fa43a034ef5
--- /dev/null
+++ b/sys/dev/dpaa/dpaa_common.h
@@ -0,0 +1,195 @@
+/*
+ * Copyright (c) 2026 Justin Hibbits
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
+ */
+
+#ifndef DPAA_COMMON_H
+#define DPAA_COMMON_H
+
+#include <machine/atomic.h>
+
+int dpaa_map_private_memory(device_t dev, int idx, const char *compat,
+ vm_paddr_t *addrp, size_t *sizep);
+
+struct dpaa_fd {
+ uint64_t liodn:8;
+ uint64_t bpid:8;
+ uint64_t eliodn:4;
+ uint64_t _rsvd1:4;
+ uint64_t addr:40;
+ uint32_t format:3;
+ uint32_t offset:9;
+ uint32_t length:20;
+ uint32_t cmd_stat;
+} __packed;
+
+#define DPAA_FD_FORMAT_SHORT_MBSF 4
+
+#define DPAA_FD_RX_STATUS_DCL4C 0x10000000
+#define DPAA_FD_RX_STATUS_DME 0x01000000
+#define DPAA_FD_RX_STATUS_IPRE_M 0x00300000
+#define DPAA_FD_RX_STATUS_FPE 0x00080000
+#define DPAA_FD_RX_STATUS_FSE 0x00040000
+#define DPAA_FD_RX_STATUS_DIS 0x00020000
+#define DPAA_FD_RX_STATUS_EOF 0x00008000
+#define DPAA_FD_RX_STATUS_NSS 0x00004000
+#define DPAA_FD_RX_STATUS_KSO 0x00002000
+#define DPAA_FD_RX_STATUS_FCL_M 0x00000c00
+#define DPAA_FD_RX_STATUS_IPP 0x00000200
+#define DPAA_FD_RX_STATUS_FLM 0x00000100
+#define DPAA_FD_RX_STATUS_PTE 0x00000080
+#define DPAA_FD_RX_STATUS_ISP 0x00000040
+#define DPAA_FD_RX_STATUS_PHE 0x00000020
+#define DPAA_FD_RX_STATUS_FRDR 0x00000010
+#define DPAA_FD_RX_STATUS_BLE 0x00000008
+#define DPAA_FD_RX_STATUS_L4CV 0x00000004
+#define DPAA_FD_RX_STATUS_IPR 0x00000001
+
+#define DPAA_FD_TX_CMD_RPD 0x40000000
+#define DPAA_FD_TX_CMD_DTC 0x10000000
+#define DPAA_FD_TX_STATUS_UFD 0x04000000
+#define DPAA_FD_TX_STATUS_LGE 0x02000000
+#define DPAA_FD_TX_STATUS_DME 0x01000000
+
+/* Most of the above are error flags, but some aren't */
+#define DPAA_FD_CMD_STAT_ERR_M 0x010ce3e8
+#define DPAA_FD_TX_STAT_ERR_M 0x03000000
+
+#define DPAA_FD_GET_ADDR(fd) ((void *)PHYS_TO_DMAP(fd->addr))
+
+struct dpaa_sgte {
+ uint64_t addr;
+ uint32_t extension:1;
+ uint32_t final:1;
+ uint32_t length:30;
+ uint16_t bpid;
+ uint16_t offset;
+} __packed;
+struct qman_fqr;
+
+
+#define DPAA_NUM_OF_SG_TABLE_ENTRY 16
+
+/*
+ * Ring API infrastructure
+ *
+ * BMan and QMan both use cache-enabled rings. Abstract this away to a more
+ * generalized interface to reduce code copying.
+ *
+ * Requirements:
+ * - Before calling <ring>_init() the ring base (ring->ring) must be initialized
+ * to the base of the ring.
+ */
+#define DPAA_RING_DECLARE(pfx) \
+ struct pfx##_ring { \
+ struct pfx##_entry *ring; \
+ struct pfx##_entry *cursor; \
+ uint8_t vbit; \
+ uint8_t avail; \
+ uint8_t ci; \
+ uint8_t ithresh; \
+ }
+
+/*
+ * Ring functions:
+ *
+ * ring_cyc_diff() -- get the (circular) difference of `l - f`
+ * ring_ring_init() -- Set up the ring structures. Portal must be
+ * initialized beforehand, and ring->ring must be nonzero.
+ * ring_CARRYCLEAR() -- stealth math to do circular roll-over
+ * ring_INC() -- Increment the cursor within the ring
+ * ring_update() -- Update ring entry availability count
+ * ring_start() -- Reserve the next entry in the ring if available.
+ * ring_commit() -- Commit the reserved ring entry by setting the verb and
+ * AVB bit
+ */
+#define DPAA_RING(pfx,sz,pi_e,ci_e,pi_i,ci_i) \
+static inline int \
+pfx##_cyc_diff(uint8_t size, uint8_t f, uint8_t l) \
+{ \
+ if (f <= l) \
+ return (uint8_t)(l - f); \
+ return (uint8_t)(l + size - f); \
+} \
+static inline void \
+pfx##_ring_init(struct pfx##_ring *ring, struct dpaa_portal_softc *portal)\
+{ \
+ uint32_t pi = *(uint32_t*)(portal->sc_ci_va + pi_i) & (sz - 1); \
+ uint32_t ci = *(uint32_t*)(portal->sc_ci_va + ci_i); \
+ ring->ci = ci & (sz - 1); \
+ ring->vbit = !!(ci & sz) << 7; \
+ ring->cursor = ring->ring + pi; \
+ ring->avail = sz - 1 - pfx##_cyc_diff(sz, ring->ci, pi); \
+} \
+static inline void * \
+pfx##_CARRYCLEAR(struct pfx##_entry *p) \
+{ \
+ return ((void *)((uintptr_t)p & (~(uintptr_t)(sz << 6)))); \
+} \
+static inline void \
+pfx##_INC(struct pfx##_ring *ring) \
+{ \
+ struct pfx##_entry *partial = ring->cursor + 1; \
+ ring->cursor = pfx##_CARRYCLEAR(partial); \
+ if (partial != ring->cursor) \
+ ring->vbit ^= 0x80; \
+} \
+static inline uint8_t \
+pfx##_update(struct pfx##_ring *ring, struct dpaa_portal_softc *portal) \
+{ \
+ uint8_t diff, old_ci = ring->ci; \
+ ring->ci = *(uint32_t*)(portal->sc_ci_va + ci_i) & (sz - 1); \
+ diff = pfx##_cyc_diff(sz, old_ci, ring->ci); \
+ ring->avail += diff; \
+ return (diff); \
+} \
+static inline struct pfx##_entry * __unused \
+pfx##_start(struct pfx##_ring *ring, struct dpaa_portal_softc *portal) \
+{ \
+ if (ring->avail <= 1) { \
+ pfx##_update(ring, portal); \
+ if (ring->avail == 0) \
+ return (NULL); \
+ } \
+ dpaa_zero_line(ring->cursor); \
+ return (ring->cursor); \
+} \
+static inline void __unused \
+pfx##_commit(struct pfx##_ring *ring, uint8_t verb) \
+{ \
+ struct pfx##_entry *entry = ring->cursor; \
+ dpaa_lw_barrier(); \
+ entry->verb = verb | ring->vbit; \
+ dpaa_flush_line(entry); \
+ pfx##_INC(ring); \
+ ring->avail--; \
+} struct hack
+
+#ifdef __powerpc__
+static inline void
+dpaa_flush_line(void *line)
+{
+ __asm __volatile ("dcbf 0, %0" :: "r"(line) : "memory");
+}
+
+static inline void
+dpaa_zero_line(void *line)
+{
+ __asm __volatile ("dcbz 0, %0" :: "r"(line) : "memory");
+}
+
+static inline void
+dpaa_touch_line(void *line)
+{
+ __asm __volatile ("dcbt 0, %0" :: "r"(line) : "memory");
+}
+
+static inline void
+dpaa_lw_barrier(void)
+{
+ powerpc_lwsync();
+}
+#endif
+
+#endif