1 /* SPDX-License-Identifier: GPL-2.0-only */ 2 /* 3 * Copyright © 2022-2024 Rivos Inc. 4 * Copyright © 2023 FORTH-ICS/CARV 5 * 6 * Authors 7 * Tomasz Jeznach <tjeznach@rivosinc.com> 8 * Nick Kossifidis <mick@ics.forth.gr> 9 */ 10 11 #ifndef _RISCV_IOMMU_H_ 12 #define _RISCV_IOMMU_H_ 13 14 #include <linux/iommu.h> 15 #include <linux/types.h> 16 #include <linux/iopoll.h> 17 18 #include "iommu-bits.h" 19 20 struct riscv_iommu_device; 21 22 struct riscv_iommu_queue { 23 atomic_t prod; /* unbounded producer allocation index */ 24 atomic_t head; /* unbounded shadow ring buffer consumer index */ 25 atomic_t tail; /* unbounded shadow ring buffer producer index */ 26 unsigned int mask; /* index mask, queue length - 1 */ 27 unsigned int irq; /* allocated interrupt number */ 28 struct riscv_iommu_device *iommu; /* iommu device handling the queue when active */ 29 void *base; /* ring buffer kernel pointer */ 30 dma_addr_t phys; /* ring buffer physical address */ 31 u16 qbr; /* base register offset, head and tail reference */ 32 u16 qcr; /* control and status register offset */ 33 u8 qid; /* queue identifier, same as RISCV_IOMMU_INTR_XX */ 34 }; 35 36 struct riscv_iommu_device { 37 /* iommu core interface */ 38 struct iommu_device iommu; 39 40 /* iommu hardware */ 41 struct device *dev; 42 43 /* hardware control register space */ 44 void __iomem *reg; 45 46 /* supported and enabled hardware capabilities */ 47 u64 caps; 48 u32 fctl; 49 50 /* available interrupt numbers, MSI or WSI */ 51 unsigned int irqs[RISCV_IOMMU_INTR_COUNT]; 52 unsigned int irqs_count; 53 unsigned int icvec; 54 55 /* hardware queues */ 56 struct riscv_iommu_queue cmdq; 57 struct riscv_iommu_queue fltq; 58 59 /* device directory */ 60 unsigned int ddt_mode; 61 dma_addr_t ddt_phys; 62 u64 *ddt_root; 63 }; 64 65 int riscv_iommu_init(struct riscv_iommu_device *iommu); 66 void riscv_iommu_remove(struct riscv_iommu_device *iommu); 67 68 #define riscv_iommu_readl(iommu, addr) \ 69 readl_relaxed((iommu)->reg + (addr)) 70 71 #define riscv_iommu_readq(iommu, addr) \ 72 readq_relaxed((iommu)->reg + (addr)) 73 74 #define riscv_iommu_writel(iommu, addr, val) \ 75 writel_relaxed((val), (iommu)->reg + (addr)) 76 77 #define riscv_iommu_writeq(iommu, addr, val) \ 78 writeq_relaxed((val), (iommu)->reg + (addr)) 79 80 #define riscv_iommu_readq_timeout(iommu, addr, val, cond, delay_us, timeout_us) \ 81 readx_poll_timeout(readq_relaxed, (iommu)->reg + (addr), val, cond, \ 82 delay_us, timeout_us) 83 84 #define riscv_iommu_readl_timeout(iommu, addr, val, cond, delay_us, timeout_us) \ 85 readx_poll_timeout(readl_relaxed, (iommu)->reg + (addr), val, cond, \ 86 delay_us, timeout_us) 87 88 #endif 89