18c2ecf20Sopenharmony_ci/* SPDX-License-Identifier: GPL-2.0-only */ 28c2ecf20Sopenharmony_ci/* 38c2ecf20Sopenharmony_ci * IOMMU API for ARM architected SMMUv3 implementations. 48c2ecf20Sopenharmony_ci * 58c2ecf20Sopenharmony_ci * Copyright (C) 2015 ARM Limited 68c2ecf20Sopenharmony_ci */ 78c2ecf20Sopenharmony_ci 88c2ecf20Sopenharmony_ci#ifndef _ARM_SMMU_V3_H 98c2ecf20Sopenharmony_ci#define _ARM_SMMU_V3_H 108c2ecf20Sopenharmony_ci 118c2ecf20Sopenharmony_ci#include <linux/bitfield.h> 128c2ecf20Sopenharmony_ci#include <linux/iommu.h> 138c2ecf20Sopenharmony_ci#include <linux/kernel.h> 148c2ecf20Sopenharmony_ci#include <linux/mmzone.h> 158c2ecf20Sopenharmony_ci#include <linux/sizes.h> 168c2ecf20Sopenharmony_ci 178c2ecf20Sopenharmony_ci/* MMIO registers */ 188c2ecf20Sopenharmony_ci#define ARM_SMMU_IDR0 0x0 198c2ecf20Sopenharmony_ci#define IDR0_ST_LVL GENMASK(28, 27) 208c2ecf20Sopenharmony_ci#define IDR0_ST_LVL_2LVL 1 218c2ecf20Sopenharmony_ci#define IDR0_STALL_MODEL GENMASK(25, 24) 228c2ecf20Sopenharmony_ci#define IDR0_STALL_MODEL_STALL 0 238c2ecf20Sopenharmony_ci#define IDR0_STALL_MODEL_FORCE 2 248c2ecf20Sopenharmony_ci#define IDR0_TTENDIAN GENMASK(22, 21) 258c2ecf20Sopenharmony_ci#define IDR0_TTENDIAN_MIXED 0 268c2ecf20Sopenharmony_ci#define IDR0_TTENDIAN_LE 2 278c2ecf20Sopenharmony_ci#define IDR0_TTENDIAN_BE 3 288c2ecf20Sopenharmony_ci#define IDR0_CD2L (1 << 19) 298c2ecf20Sopenharmony_ci#define IDR0_VMID16 (1 << 18) 308c2ecf20Sopenharmony_ci#define IDR0_PRI (1 << 16) 318c2ecf20Sopenharmony_ci#define IDR0_SEV (1 << 14) 328c2ecf20Sopenharmony_ci#define IDR0_MSI (1 << 13) 338c2ecf20Sopenharmony_ci#define IDR0_ASID16 (1 << 12) 348c2ecf20Sopenharmony_ci#define IDR0_ATS (1 << 10) 358c2ecf20Sopenharmony_ci#define IDR0_HYP (1 << 9) 368c2ecf20Sopenharmony_ci#define IDR0_COHACC (1 << 4) 378c2ecf20Sopenharmony_ci#define IDR0_TTF GENMASK(3, 2) 388c2ecf20Sopenharmony_ci#define IDR0_TTF_AARCH64 2 398c2ecf20Sopenharmony_ci#define IDR0_TTF_AARCH32_64 3 408c2ecf20Sopenharmony_ci#define IDR0_S1P (1 << 1) 418c2ecf20Sopenharmony_ci#define IDR0_S2P (1 << 0) 428c2ecf20Sopenharmony_ci 438c2ecf20Sopenharmony_ci#define ARM_SMMU_IDR1 0x4 448c2ecf20Sopenharmony_ci#define IDR1_TABLES_PRESET (1 << 30) 458c2ecf20Sopenharmony_ci#define IDR1_QUEUES_PRESET (1 << 29) 468c2ecf20Sopenharmony_ci#define IDR1_REL (1 << 28) 478c2ecf20Sopenharmony_ci#define IDR1_CMDQS GENMASK(25, 21) 488c2ecf20Sopenharmony_ci#define IDR1_EVTQS GENMASK(20, 16) 498c2ecf20Sopenharmony_ci#define IDR1_PRIQS GENMASK(15, 11) 508c2ecf20Sopenharmony_ci#define IDR1_SSIDSIZE GENMASK(10, 6) 518c2ecf20Sopenharmony_ci#define IDR1_SIDSIZE GENMASK(5, 0) 528c2ecf20Sopenharmony_ci 538c2ecf20Sopenharmony_ci#define ARM_SMMU_IDR3 0xc 548c2ecf20Sopenharmony_ci#define IDR3_RIL (1 << 10) 558c2ecf20Sopenharmony_ci 568c2ecf20Sopenharmony_ci#define ARM_SMMU_IDR5 0x14 578c2ecf20Sopenharmony_ci#define IDR5_STALL_MAX GENMASK(31, 16) 588c2ecf20Sopenharmony_ci#define IDR5_GRAN64K (1 << 6) 598c2ecf20Sopenharmony_ci#define IDR5_GRAN16K (1 << 5) 608c2ecf20Sopenharmony_ci#define IDR5_GRAN4K (1 << 4) 618c2ecf20Sopenharmony_ci#define IDR5_OAS GENMASK(2, 0) 628c2ecf20Sopenharmony_ci#define IDR5_OAS_32_BIT 0 638c2ecf20Sopenharmony_ci#define IDR5_OAS_36_BIT 1 648c2ecf20Sopenharmony_ci#define IDR5_OAS_40_BIT 2 658c2ecf20Sopenharmony_ci#define IDR5_OAS_42_BIT 3 668c2ecf20Sopenharmony_ci#define IDR5_OAS_44_BIT 4 678c2ecf20Sopenharmony_ci#define IDR5_OAS_48_BIT 5 688c2ecf20Sopenharmony_ci#define IDR5_OAS_52_BIT 6 698c2ecf20Sopenharmony_ci#define IDR5_VAX GENMASK(11, 10) 708c2ecf20Sopenharmony_ci#define IDR5_VAX_52_BIT 1 718c2ecf20Sopenharmony_ci 728c2ecf20Sopenharmony_ci#define ARM_SMMU_CR0 0x20 738c2ecf20Sopenharmony_ci#define CR0_ATSCHK (1 << 4) 748c2ecf20Sopenharmony_ci#define CR0_CMDQEN (1 << 3) 758c2ecf20Sopenharmony_ci#define CR0_EVTQEN (1 << 2) 768c2ecf20Sopenharmony_ci#define CR0_PRIQEN (1 << 1) 778c2ecf20Sopenharmony_ci#define CR0_SMMUEN (1 << 0) 788c2ecf20Sopenharmony_ci 798c2ecf20Sopenharmony_ci#define ARM_SMMU_CR0ACK 0x24 808c2ecf20Sopenharmony_ci 818c2ecf20Sopenharmony_ci#define ARM_SMMU_CR1 0x28 828c2ecf20Sopenharmony_ci#define CR1_TABLE_SH GENMASK(11, 10) 838c2ecf20Sopenharmony_ci#define CR1_TABLE_OC GENMASK(9, 8) 848c2ecf20Sopenharmony_ci#define CR1_TABLE_IC GENMASK(7, 6) 858c2ecf20Sopenharmony_ci#define CR1_QUEUE_SH GENMASK(5, 4) 868c2ecf20Sopenharmony_ci#define CR1_QUEUE_OC GENMASK(3, 2) 878c2ecf20Sopenharmony_ci#define CR1_QUEUE_IC GENMASK(1, 0) 888c2ecf20Sopenharmony_ci/* CR1 cacheability fields don't quite follow the usual TCR-style encoding */ 898c2ecf20Sopenharmony_ci#define CR1_CACHE_NC 0 908c2ecf20Sopenharmony_ci#define CR1_CACHE_WB 1 918c2ecf20Sopenharmony_ci#define CR1_CACHE_WT 2 928c2ecf20Sopenharmony_ci 938c2ecf20Sopenharmony_ci#define ARM_SMMU_CR2 0x2c 948c2ecf20Sopenharmony_ci#define CR2_PTM (1 << 2) 958c2ecf20Sopenharmony_ci#define CR2_RECINVSID (1 << 1) 968c2ecf20Sopenharmony_ci#define CR2_E2H (1 << 0) 978c2ecf20Sopenharmony_ci 988c2ecf20Sopenharmony_ci#define ARM_SMMU_GBPA 0x44 998c2ecf20Sopenharmony_ci#define GBPA_UPDATE (1 << 31) 1008c2ecf20Sopenharmony_ci#define GBPA_ABORT (1 << 20) 1018c2ecf20Sopenharmony_ci 1028c2ecf20Sopenharmony_ci#define ARM_SMMU_IRQ_CTRL 0x50 1038c2ecf20Sopenharmony_ci#define IRQ_CTRL_EVTQ_IRQEN (1 << 2) 1048c2ecf20Sopenharmony_ci#define IRQ_CTRL_PRIQ_IRQEN (1 << 1) 1058c2ecf20Sopenharmony_ci#define IRQ_CTRL_GERROR_IRQEN (1 << 0) 1068c2ecf20Sopenharmony_ci 1078c2ecf20Sopenharmony_ci#define ARM_SMMU_IRQ_CTRLACK 0x54 1088c2ecf20Sopenharmony_ci 1098c2ecf20Sopenharmony_ci#define ARM_SMMU_GERROR 0x60 1108c2ecf20Sopenharmony_ci#define GERROR_SFM_ERR (1 << 8) 1118c2ecf20Sopenharmony_ci#define GERROR_MSI_GERROR_ABT_ERR (1 << 7) 1128c2ecf20Sopenharmony_ci#define GERROR_MSI_PRIQ_ABT_ERR (1 << 6) 1138c2ecf20Sopenharmony_ci#define GERROR_MSI_EVTQ_ABT_ERR (1 << 5) 1148c2ecf20Sopenharmony_ci#define GERROR_MSI_CMDQ_ABT_ERR (1 << 4) 1158c2ecf20Sopenharmony_ci#define GERROR_PRIQ_ABT_ERR (1 << 3) 1168c2ecf20Sopenharmony_ci#define GERROR_EVTQ_ABT_ERR (1 << 2) 1178c2ecf20Sopenharmony_ci#define GERROR_CMDQ_ERR (1 << 0) 1188c2ecf20Sopenharmony_ci#define GERROR_ERR_MASK 0x1fd 1198c2ecf20Sopenharmony_ci 1208c2ecf20Sopenharmony_ci#define ARM_SMMU_GERRORN 0x64 1218c2ecf20Sopenharmony_ci 1228c2ecf20Sopenharmony_ci#define ARM_SMMU_GERROR_IRQ_CFG0 0x68 1238c2ecf20Sopenharmony_ci#define ARM_SMMU_GERROR_IRQ_CFG1 0x70 1248c2ecf20Sopenharmony_ci#define ARM_SMMU_GERROR_IRQ_CFG2 0x74 1258c2ecf20Sopenharmony_ci 1268c2ecf20Sopenharmony_ci#define ARM_SMMU_STRTAB_BASE 0x80 1278c2ecf20Sopenharmony_ci#define STRTAB_BASE_RA (1UL << 62) 1288c2ecf20Sopenharmony_ci#define STRTAB_BASE_ADDR_MASK GENMASK_ULL(51, 6) 1298c2ecf20Sopenharmony_ci 1308c2ecf20Sopenharmony_ci#define ARM_SMMU_STRTAB_BASE_CFG 0x88 1318c2ecf20Sopenharmony_ci#define STRTAB_BASE_CFG_FMT GENMASK(17, 16) 1328c2ecf20Sopenharmony_ci#define STRTAB_BASE_CFG_FMT_LINEAR 0 1338c2ecf20Sopenharmony_ci#define STRTAB_BASE_CFG_FMT_2LVL 1 1348c2ecf20Sopenharmony_ci#define STRTAB_BASE_CFG_SPLIT GENMASK(10, 6) 1358c2ecf20Sopenharmony_ci#define STRTAB_BASE_CFG_LOG2SIZE GENMASK(5, 0) 1368c2ecf20Sopenharmony_ci 1378c2ecf20Sopenharmony_ci#define ARM_SMMU_CMDQ_BASE 0x90 1388c2ecf20Sopenharmony_ci#define ARM_SMMU_CMDQ_PROD 0x98 1398c2ecf20Sopenharmony_ci#define ARM_SMMU_CMDQ_CONS 0x9c 1408c2ecf20Sopenharmony_ci 1418c2ecf20Sopenharmony_ci#define ARM_SMMU_EVTQ_BASE 0xa0 1428c2ecf20Sopenharmony_ci#define ARM_SMMU_EVTQ_PROD 0x100a8 1438c2ecf20Sopenharmony_ci#define ARM_SMMU_EVTQ_CONS 0x100ac 1448c2ecf20Sopenharmony_ci#define ARM_SMMU_EVTQ_IRQ_CFG0 0xb0 1458c2ecf20Sopenharmony_ci#define ARM_SMMU_EVTQ_IRQ_CFG1 0xb8 1468c2ecf20Sopenharmony_ci#define ARM_SMMU_EVTQ_IRQ_CFG2 0xbc 1478c2ecf20Sopenharmony_ci 1488c2ecf20Sopenharmony_ci#define ARM_SMMU_PRIQ_BASE 0xc0 1498c2ecf20Sopenharmony_ci#define ARM_SMMU_PRIQ_PROD 0x100c8 1508c2ecf20Sopenharmony_ci#define ARM_SMMU_PRIQ_CONS 0x100cc 1518c2ecf20Sopenharmony_ci#define ARM_SMMU_PRIQ_IRQ_CFG0 0xd0 1528c2ecf20Sopenharmony_ci#define ARM_SMMU_PRIQ_IRQ_CFG1 0xd8 1538c2ecf20Sopenharmony_ci#define ARM_SMMU_PRIQ_IRQ_CFG2 0xdc 1548c2ecf20Sopenharmony_ci 1558c2ecf20Sopenharmony_ci#define ARM_SMMU_REG_SZ 0xe00 1568c2ecf20Sopenharmony_ci 1578c2ecf20Sopenharmony_ci/* Common MSI config fields */ 1588c2ecf20Sopenharmony_ci#define MSI_CFG0_ADDR_MASK GENMASK_ULL(51, 2) 1598c2ecf20Sopenharmony_ci#define MSI_CFG2_SH GENMASK(5, 4) 1608c2ecf20Sopenharmony_ci#define MSI_CFG2_MEMATTR GENMASK(3, 0) 1618c2ecf20Sopenharmony_ci 1628c2ecf20Sopenharmony_ci/* Common memory attribute values */ 1638c2ecf20Sopenharmony_ci#define ARM_SMMU_SH_NSH 0 1648c2ecf20Sopenharmony_ci#define ARM_SMMU_SH_OSH 2 1658c2ecf20Sopenharmony_ci#define ARM_SMMU_SH_ISH 3 1668c2ecf20Sopenharmony_ci#define ARM_SMMU_MEMATTR_DEVICE_nGnRE 0x1 1678c2ecf20Sopenharmony_ci#define ARM_SMMU_MEMATTR_OIWB 0xf 1688c2ecf20Sopenharmony_ci 1698c2ecf20Sopenharmony_ci#define Q_IDX(llq, p) ((p) & ((1 << (llq)->max_n_shift) - 1)) 1708c2ecf20Sopenharmony_ci#define Q_WRP(llq, p) ((p) & (1 << (llq)->max_n_shift)) 1718c2ecf20Sopenharmony_ci#define Q_OVERFLOW_FLAG (1U << 31) 1728c2ecf20Sopenharmony_ci#define Q_OVF(p) ((p) & Q_OVERFLOW_FLAG) 1738c2ecf20Sopenharmony_ci#define Q_ENT(q, p) ((q)->base + \ 1748c2ecf20Sopenharmony_ci Q_IDX(&((q)->llq), p) * \ 1758c2ecf20Sopenharmony_ci (q)->ent_dwords) 1768c2ecf20Sopenharmony_ci 1778c2ecf20Sopenharmony_ci#define Q_BASE_RWA (1UL << 62) 1788c2ecf20Sopenharmony_ci#define Q_BASE_ADDR_MASK GENMASK_ULL(51, 5) 1798c2ecf20Sopenharmony_ci#define Q_BASE_LOG2SIZE GENMASK(4, 0) 1808c2ecf20Sopenharmony_ci 1818c2ecf20Sopenharmony_ci/* Ensure DMA allocations are naturally aligned */ 1828c2ecf20Sopenharmony_ci#ifdef CONFIG_CMA_ALIGNMENT 1838c2ecf20Sopenharmony_ci#define Q_MAX_SZ_SHIFT (PAGE_SHIFT + CONFIG_CMA_ALIGNMENT) 1848c2ecf20Sopenharmony_ci#else 1858c2ecf20Sopenharmony_ci#define Q_MAX_SZ_SHIFT (PAGE_SHIFT + MAX_ORDER - 1) 1868c2ecf20Sopenharmony_ci#endif 1878c2ecf20Sopenharmony_ci 1888c2ecf20Sopenharmony_ci/* 1898c2ecf20Sopenharmony_ci * Stream table. 1908c2ecf20Sopenharmony_ci * 1918c2ecf20Sopenharmony_ci * Linear: Enough to cover 1 << IDR1.SIDSIZE entries 1928c2ecf20Sopenharmony_ci * 2lvl: 128k L1 entries, 1938c2ecf20Sopenharmony_ci * 256 lazy entries per table (each table covers a PCI bus) 1948c2ecf20Sopenharmony_ci */ 1958c2ecf20Sopenharmony_ci#define STRTAB_L1_SZ_SHIFT 20 1968c2ecf20Sopenharmony_ci#define STRTAB_SPLIT 8 1978c2ecf20Sopenharmony_ci 1988c2ecf20Sopenharmony_ci#define STRTAB_L1_DESC_DWORDS 1 1998c2ecf20Sopenharmony_ci#define STRTAB_L1_DESC_SPAN GENMASK_ULL(4, 0) 2008c2ecf20Sopenharmony_ci#define STRTAB_L1_DESC_L2PTR_MASK GENMASK_ULL(51, 6) 2018c2ecf20Sopenharmony_ci 2028c2ecf20Sopenharmony_ci#define STRTAB_STE_DWORDS 8 2038c2ecf20Sopenharmony_ci#define STRTAB_STE_0_V (1UL << 0) 2048c2ecf20Sopenharmony_ci#define STRTAB_STE_0_CFG GENMASK_ULL(3, 1) 2058c2ecf20Sopenharmony_ci#define STRTAB_STE_0_CFG_ABORT 0 2068c2ecf20Sopenharmony_ci#define STRTAB_STE_0_CFG_BYPASS 4 2078c2ecf20Sopenharmony_ci#define STRTAB_STE_0_CFG_S1_TRANS 5 2088c2ecf20Sopenharmony_ci#define STRTAB_STE_0_CFG_S2_TRANS 6 2098c2ecf20Sopenharmony_ci 2108c2ecf20Sopenharmony_ci#define STRTAB_STE_0_S1FMT GENMASK_ULL(5, 4) 2118c2ecf20Sopenharmony_ci#define STRTAB_STE_0_S1FMT_LINEAR 0 2128c2ecf20Sopenharmony_ci#define STRTAB_STE_0_S1FMT_64K_L2 2 2138c2ecf20Sopenharmony_ci#define STRTAB_STE_0_S1CTXPTR_MASK GENMASK_ULL(51, 6) 2148c2ecf20Sopenharmony_ci#define STRTAB_STE_0_S1CDMAX GENMASK_ULL(63, 59) 2158c2ecf20Sopenharmony_ci 2168c2ecf20Sopenharmony_ci#define STRTAB_STE_1_S1DSS GENMASK_ULL(1, 0) 2178c2ecf20Sopenharmony_ci#define STRTAB_STE_1_S1DSS_TERMINATE 0x0 2188c2ecf20Sopenharmony_ci#define STRTAB_STE_1_S1DSS_BYPASS 0x1 2198c2ecf20Sopenharmony_ci#define STRTAB_STE_1_S1DSS_SSID0 0x2 2208c2ecf20Sopenharmony_ci 2218c2ecf20Sopenharmony_ci#define STRTAB_STE_1_S1C_CACHE_NC 0UL 2228c2ecf20Sopenharmony_ci#define STRTAB_STE_1_S1C_CACHE_WBRA 1UL 2238c2ecf20Sopenharmony_ci#define STRTAB_STE_1_S1C_CACHE_WT 2UL 2248c2ecf20Sopenharmony_ci#define STRTAB_STE_1_S1C_CACHE_WB 3UL 2258c2ecf20Sopenharmony_ci#define STRTAB_STE_1_S1CIR GENMASK_ULL(3, 2) 2268c2ecf20Sopenharmony_ci#define STRTAB_STE_1_S1COR GENMASK_ULL(5, 4) 2278c2ecf20Sopenharmony_ci#define STRTAB_STE_1_S1CSH GENMASK_ULL(7, 6) 2288c2ecf20Sopenharmony_ci 2298c2ecf20Sopenharmony_ci#define STRTAB_STE_1_S1STALLD (1UL << 27) 2308c2ecf20Sopenharmony_ci 2318c2ecf20Sopenharmony_ci#define STRTAB_STE_1_EATS GENMASK_ULL(29, 28) 2328c2ecf20Sopenharmony_ci#define STRTAB_STE_1_EATS_ABT 0UL 2338c2ecf20Sopenharmony_ci#define STRTAB_STE_1_EATS_TRANS 1UL 2348c2ecf20Sopenharmony_ci#define STRTAB_STE_1_EATS_S1CHK 2UL 2358c2ecf20Sopenharmony_ci 2368c2ecf20Sopenharmony_ci#define STRTAB_STE_1_STRW GENMASK_ULL(31, 30) 2378c2ecf20Sopenharmony_ci#define STRTAB_STE_1_STRW_NSEL1 0UL 2388c2ecf20Sopenharmony_ci#define STRTAB_STE_1_STRW_EL2 2UL 2398c2ecf20Sopenharmony_ci 2408c2ecf20Sopenharmony_ci#define STRTAB_STE_1_SHCFG GENMASK_ULL(45, 44) 2418c2ecf20Sopenharmony_ci#define STRTAB_STE_1_SHCFG_INCOMING 1UL 2428c2ecf20Sopenharmony_ci 2438c2ecf20Sopenharmony_ci#define STRTAB_STE_2_S2VMID GENMASK_ULL(15, 0) 2448c2ecf20Sopenharmony_ci#define STRTAB_STE_2_VTCR GENMASK_ULL(50, 32) 2458c2ecf20Sopenharmony_ci#define STRTAB_STE_2_VTCR_S2T0SZ GENMASK_ULL(5, 0) 2468c2ecf20Sopenharmony_ci#define STRTAB_STE_2_VTCR_S2SL0 GENMASK_ULL(7, 6) 2478c2ecf20Sopenharmony_ci#define STRTAB_STE_2_VTCR_S2IR0 GENMASK_ULL(9, 8) 2488c2ecf20Sopenharmony_ci#define STRTAB_STE_2_VTCR_S2OR0 GENMASK_ULL(11, 10) 2498c2ecf20Sopenharmony_ci#define STRTAB_STE_2_VTCR_S2SH0 GENMASK_ULL(13, 12) 2508c2ecf20Sopenharmony_ci#define STRTAB_STE_2_VTCR_S2TG GENMASK_ULL(15, 14) 2518c2ecf20Sopenharmony_ci#define STRTAB_STE_2_VTCR_S2PS GENMASK_ULL(18, 16) 2528c2ecf20Sopenharmony_ci#define STRTAB_STE_2_S2AA64 (1UL << 51) 2538c2ecf20Sopenharmony_ci#define STRTAB_STE_2_S2ENDI (1UL << 52) 2548c2ecf20Sopenharmony_ci#define STRTAB_STE_2_S2PTW (1UL << 54) 2558c2ecf20Sopenharmony_ci#define STRTAB_STE_2_S2R (1UL << 58) 2568c2ecf20Sopenharmony_ci 2578c2ecf20Sopenharmony_ci#define STRTAB_STE_3_S2TTB_MASK GENMASK_ULL(51, 4) 2588c2ecf20Sopenharmony_ci 2598c2ecf20Sopenharmony_ci/* 2608c2ecf20Sopenharmony_ci * Context descriptors. 2618c2ecf20Sopenharmony_ci * 2628c2ecf20Sopenharmony_ci * Linear: when less than 1024 SSIDs are supported 2638c2ecf20Sopenharmony_ci * 2lvl: at most 1024 L1 entries, 2648c2ecf20Sopenharmony_ci * 1024 lazy entries per table. 2658c2ecf20Sopenharmony_ci */ 2668c2ecf20Sopenharmony_ci#define CTXDESC_SPLIT 10 2678c2ecf20Sopenharmony_ci#define CTXDESC_L2_ENTRIES (1 << CTXDESC_SPLIT) 2688c2ecf20Sopenharmony_ci 2698c2ecf20Sopenharmony_ci#define CTXDESC_L1_DESC_DWORDS 1 2708c2ecf20Sopenharmony_ci#define CTXDESC_L1_DESC_V (1UL << 0) 2718c2ecf20Sopenharmony_ci#define CTXDESC_L1_DESC_L2PTR_MASK GENMASK_ULL(51, 12) 2728c2ecf20Sopenharmony_ci 2738c2ecf20Sopenharmony_ci#define CTXDESC_CD_DWORDS 8 2748c2ecf20Sopenharmony_ci#define CTXDESC_CD_0_TCR_T0SZ GENMASK_ULL(5, 0) 2758c2ecf20Sopenharmony_ci#define CTXDESC_CD_0_TCR_TG0 GENMASK_ULL(7, 6) 2768c2ecf20Sopenharmony_ci#define CTXDESC_CD_0_TCR_IRGN0 GENMASK_ULL(9, 8) 2778c2ecf20Sopenharmony_ci#define CTXDESC_CD_0_TCR_ORGN0 GENMASK_ULL(11, 10) 2788c2ecf20Sopenharmony_ci#define CTXDESC_CD_0_TCR_SH0 GENMASK_ULL(13, 12) 2798c2ecf20Sopenharmony_ci#define CTXDESC_CD_0_TCR_EPD0 (1ULL << 14) 2808c2ecf20Sopenharmony_ci#define CTXDESC_CD_0_TCR_EPD1 (1ULL << 30) 2818c2ecf20Sopenharmony_ci 2828c2ecf20Sopenharmony_ci#define CTXDESC_CD_0_ENDI (1UL << 15) 2838c2ecf20Sopenharmony_ci#define CTXDESC_CD_0_V (1UL << 31) 2848c2ecf20Sopenharmony_ci 2858c2ecf20Sopenharmony_ci#define CTXDESC_CD_0_TCR_IPS GENMASK_ULL(34, 32) 2868c2ecf20Sopenharmony_ci#define CTXDESC_CD_0_TCR_TBI0 (1ULL << 38) 2878c2ecf20Sopenharmony_ci 2888c2ecf20Sopenharmony_ci#define CTXDESC_CD_0_AA64 (1UL << 41) 2898c2ecf20Sopenharmony_ci#define CTXDESC_CD_0_S (1UL << 44) 2908c2ecf20Sopenharmony_ci#define CTXDESC_CD_0_R (1UL << 45) 2918c2ecf20Sopenharmony_ci#define CTXDESC_CD_0_A (1UL << 46) 2928c2ecf20Sopenharmony_ci#define CTXDESC_CD_0_ASET (1UL << 47) 2938c2ecf20Sopenharmony_ci#define CTXDESC_CD_0_ASID GENMASK_ULL(63, 48) 2948c2ecf20Sopenharmony_ci 2958c2ecf20Sopenharmony_ci#define CTXDESC_CD_1_TTB0_MASK GENMASK_ULL(51, 4) 2968c2ecf20Sopenharmony_ci 2978c2ecf20Sopenharmony_ci/* 2988c2ecf20Sopenharmony_ci * When the SMMU only supports linear context descriptor tables, pick a 2998c2ecf20Sopenharmony_ci * reasonable size limit (64kB). 3008c2ecf20Sopenharmony_ci */ 3018c2ecf20Sopenharmony_ci#define CTXDESC_LINEAR_CDMAX ilog2(SZ_64K / (CTXDESC_CD_DWORDS << 3)) 3028c2ecf20Sopenharmony_ci 3038c2ecf20Sopenharmony_ci/* Command queue */ 3048c2ecf20Sopenharmony_ci#define CMDQ_ENT_SZ_SHIFT 4 3058c2ecf20Sopenharmony_ci#define CMDQ_ENT_DWORDS ((1 << CMDQ_ENT_SZ_SHIFT) >> 3) 3068c2ecf20Sopenharmony_ci#define CMDQ_MAX_SZ_SHIFT (Q_MAX_SZ_SHIFT - CMDQ_ENT_SZ_SHIFT) 3078c2ecf20Sopenharmony_ci 3088c2ecf20Sopenharmony_ci#define CMDQ_CONS_ERR GENMASK(30, 24) 3098c2ecf20Sopenharmony_ci#define CMDQ_ERR_CERROR_NONE_IDX 0 3108c2ecf20Sopenharmony_ci#define CMDQ_ERR_CERROR_ILL_IDX 1 3118c2ecf20Sopenharmony_ci#define CMDQ_ERR_CERROR_ABT_IDX 2 3128c2ecf20Sopenharmony_ci#define CMDQ_ERR_CERROR_ATC_INV_IDX 3 3138c2ecf20Sopenharmony_ci 3148c2ecf20Sopenharmony_ci#define CMDQ_PROD_OWNED_FLAG Q_OVERFLOW_FLAG 3158c2ecf20Sopenharmony_ci 3168c2ecf20Sopenharmony_ci/* 3178c2ecf20Sopenharmony_ci * This is used to size the command queue and therefore must be at least 3188c2ecf20Sopenharmony_ci * BITS_PER_LONG so that the valid_map works correctly (it relies on the 3198c2ecf20Sopenharmony_ci * total number of queue entries being a multiple of BITS_PER_LONG). 3208c2ecf20Sopenharmony_ci */ 3218c2ecf20Sopenharmony_ci#define CMDQ_BATCH_ENTRIES BITS_PER_LONG 3228c2ecf20Sopenharmony_ci 3238c2ecf20Sopenharmony_ci#define CMDQ_0_OP GENMASK_ULL(7, 0) 3248c2ecf20Sopenharmony_ci#define CMDQ_0_SSV (1UL << 11) 3258c2ecf20Sopenharmony_ci 3268c2ecf20Sopenharmony_ci#define CMDQ_PREFETCH_0_SID GENMASK_ULL(63, 32) 3278c2ecf20Sopenharmony_ci#define CMDQ_PREFETCH_1_SIZE GENMASK_ULL(4, 0) 3288c2ecf20Sopenharmony_ci#define CMDQ_PREFETCH_1_ADDR_MASK GENMASK_ULL(63, 12) 3298c2ecf20Sopenharmony_ci 3308c2ecf20Sopenharmony_ci#define CMDQ_CFGI_0_SSID GENMASK_ULL(31, 12) 3318c2ecf20Sopenharmony_ci#define CMDQ_CFGI_0_SID GENMASK_ULL(63, 32) 3328c2ecf20Sopenharmony_ci#define CMDQ_CFGI_1_LEAF (1UL << 0) 3338c2ecf20Sopenharmony_ci#define CMDQ_CFGI_1_RANGE GENMASK_ULL(4, 0) 3348c2ecf20Sopenharmony_ci 3358c2ecf20Sopenharmony_ci#define CMDQ_TLBI_0_NUM GENMASK_ULL(16, 12) 3368c2ecf20Sopenharmony_ci#define CMDQ_TLBI_RANGE_NUM_MAX 31 3378c2ecf20Sopenharmony_ci#define CMDQ_TLBI_0_SCALE GENMASK_ULL(24, 20) 3388c2ecf20Sopenharmony_ci#define CMDQ_TLBI_0_VMID GENMASK_ULL(47, 32) 3398c2ecf20Sopenharmony_ci#define CMDQ_TLBI_0_ASID GENMASK_ULL(63, 48) 3408c2ecf20Sopenharmony_ci#define CMDQ_TLBI_1_LEAF (1UL << 0) 3418c2ecf20Sopenharmony_ci#define CMDQ_TLBI_1_TTL GENMASK_ULL(9, 8) 3428c2ecf20Sopenharmony_ci#define CMDQ_TLBI_1_TG GENMASK_ULL(11, 10) 3438c2ecf20Sopenharmony_ci#define CMDQ_TLBI_1_VA_MASK GENMASK_ULL(63, 12) 3448c2ecf20Sopenharmony_ci#define CMDQ_TLBI_1_IPA_MASK GENMASK_ULL(51, 12) 3458c2ecf20Sopenharmony_ci 3468c2ecf20Sopenharmony_ci#define CMDQ_ATC_0_SSID GENMASK_ULL(31, 12) 3478c2ecf20Sopenharmony_ci#define CMDQ_ATC_0_SID GENMASK_ULL(63, 32) 3488c2ecf20Sopenharmony_ci#define CMDQ_ATC_0_GLOBAL (1UL << 9) 3498c2ecf20Sopenharmony_ci#define CMDQ_ATC_1_SIZE GENMASK_ULL(5, 0) 3508c2ecf20Sopenharmony_ci#define CMDQ_ATC_1_ADDR_MASK GENMASK_ULL(63, 12) 3518c2ecf20Sopenharmony_ci 3528c2ecf20Sopenharmony_ci#define CMDQ_PRI_0_SSID GENMASK_ULL(31, 12) 3538c2ecf20Sopenharmony_ci#define CMDQ_PRI_0_SID GENMASK_ULL(63, 32) 3548c2ecf20Sopenharmony_ci#define CMDQ_PRI_1_GRPID GENMASK_ULL(8, 0) 3558c2ecf20Sopenharmony_ci#define CMDQ_PRI_1_RESP GENMASK_ULL(13, 12) 3568c2ecf20Sopenharmony_ci 3578c2ecf20Sopenharmony_ci#define CMDQ_SYNC_0_CS GENMASK_ULL(13, 12) 3588c2ecf20Sopenharmony_ci#define CMDQ_SYNC_0_CS_NONE 0 3598c2ecf20Sopenharmony_ci#define CMDQ_SYNC_0_CS_IRQ 1 3608c2ecf20Sopenharmony_ci#define CMDQ_SYNC_0_CS_SEV 2 3618c2ecf20Sopenharmony_ci#define CMDQ_SYNC_0_MSH GENMASK_ULL(23, 22) 3628c2ecf20Sopenharmony_ci#define CMDQ_SYNC_0_MSIATTR GENMASK_ULL(27, 24) 3638c2ecf20Sopenharmony_ci#define CMDQ_SYNC_0_MSIDATA GENMASK_ULL(63, 32) 3648c2ecf20Sopenharmony_ci#define CMDQ_SYNC_1_MSIADDR_MASK GENMASK_ULL(51, 2) 3658c2ecf20Sopenharmony_ci 3668c2ecf20Sopenharmony_ci/* Event queue */ 3678c2ecf20Sopenharmony_ci#define EVTQ_ENT_SZ_SHIFT 5 3688c2ecf20Sopenharmony_ci#define EVTQ_ENT_DWORDS ((1 << EVTQ_ENT_SZ_SHIFT) >> 3) 3698c2ecf20Sopenharmony_ci#define EVTQ_MAX_SZ_SHIFT (Q_MAX_SZ_SHIFT - EVTQ_ENT_SZ_SHIFT) 3708c2ecf20Sopenharmony_ci 3718c2ecf20Sopenharmony_ci#define EVTQ_0_ID GENMASK_ULL(7, 0) 3728c2ecf20Sopenharmony_ci 3738c2ecf20Sopenharmony_ci/* PRI queue */ 3748c2ecf20Sopenharmony_ci#define PRIQ_ENT_SZ_SHIFT 4 3758c2ecf20Sopenharmony_ci#define PRIQ_ENT_DWORDS ((1 << PRIQ_ENT_SZ_SHIFT) >> 3) 3768c2ecf20Sopenharmony_ci#define PRIQ_MAX_SZ_SHIFT (Q_MAX_SZ_SHIFT - PRIQ_ENT_SZ_SHIFT) 3778c2ecf20Sopenharmony_ci 3788c2ecf20Sopenharmony_ci#define PRIQ_0_SID GENMASK_ULL(31, 0) 3798c2ecf20Sopenharmony_ci#define PRIQ_0_SSID GENMASK_ULL(51, 32) 3808c2ecf20Sopenharmony_ci#define PRIQ_0_PERM_PRIV (1UL << 58) 3818c2ecf20Sopenharmony_ci#define PRIQ_0_PERM_EXEC (1UL << 59) 3828c2ecf20Sopenharmony_ci#define PRIQ_0_PERM_READ (1UL << 60) 3838c2ecf20Sopenharmony_ci#define PRIQ_0_PERM_WRITE (1UL << 61) 3848c2ecf20Sopenharmony_ci#define PRIQ_0_PRG_LAST (1UL << 62) 3858c2ecf20Sopenharmony_ci#define PRIQ_0_SSID_V (1UL << 63) 3868c2ecf20Sopenharmony_ci 3878c2ecf20Sopenharmony_ci#define PRIQ_1_PRG_IDX GENMASK_ULL(8, 0) 3888c2ecf20Sopenharmony_ci#define PRIQ_1_ADDR_MASK GENMASK_ULL(63, 12) 3898c2ecf20Sopenharmony_ci 3908c2ecf20Sopenharmony_ci/* High-level queue structures */ 3918c2ecf20Sopenharmony_ci#define ARM_SMMU_POLL_TIMEOUT_US 1000000 /* 1s! */ 3928c2ecf20Sopenharmony_ci#define ARM_SMMU_POLL_SPIN_COUNT 10 3938c2ecf20Sopenharmony_ci 3948c2ecf20Sopenharmony_ci#define MSI_IOVA_BASE 0x8000000 3958c2ecf20Sopenharmony_ci#define MSI_IOVA_LENGTH 0x100000 3968c2ecf20Sopenharmony_ci 3978c2ecf20Sopenharmony_cienum pri_resp { 3988c2ecf20Sopenharmony_ci PRI_RESP_DENY = 0, 3998c2ecf20Sopenharmony_ci PRI_RESP_FAIL = 1, 4008c2ecf20Sopenharmony_ci PRI_RESP_SUCC = 2, 4018c2ecf20Sopenharmony_ci}; 4028c2ecf20Sopenharmony_ci 4038c2ecf20Sopenharmony_cistruct arm_smmu_cmdq_ent { 4048c2ecf20Sopenharmony_ci /* Common fields */ 4058c2ecf20Sopenharmony_ci u8 opcode; 4068c2ecf20Sopenharmony_ci bool substream_valid; 4078c2ecf20Sopenharmony_ci 4088c2ecf20Sopenharmony_ci /* Command-specific fields */ 4098c2ecf20Sopenharmony_ci union { 4108c2ecf20Sopenharmony_ci #define CMDQ_OP_PREFETCH_CFG 0x1 4118c2ecf20Sopenharmony_ci struct { 4128c2ecf20Sopenharmony_ci u32 sid; 4138c2ecf20Sopenharmony_ci u8 size; 4148c2ecf20Sopenharmony_ci u64 addr; 4158c2ecf20Sopenharmony_ci } prefetch; 4168c2ecf20Sopenharmony_ci 4178c2ecf20Sopenharmony_ci #define CMDQ_OP_CFGI_STE 0x3 4188c2ecf20Sopenharmony_ci #define CMDQ_OP_CFGI_ALL 0x4 4198c2ecf20Sopenharmony_ci #define CMDQ_OP_CFGI_CD 0x5 4208c2ecf20Sopenharmony_ci #define CMDQ_OP_CFGI_CD_ALL 0x6 4218c2ecf20Sopenharmony_ci struct { 4228c2ecf20Sopenharmony_ci u32 sid; 4238c2ecf20Sopenharmony_ci u32 ssid; 4248c2ecf20Sopenharmony_ci union { 4258c2ecf20Sopenharmony_ci bool leaf; 4268c2ecf20Sopenharmony_ci u8 span; 4278c2ecf20Sopenharmony_ci }; 4288c2ecf20Sopenharmony_ci } cfgi; 4298c2ecf20Sopenharmony_ci 4308c2ecf20Sopenharmony_ci #define CMDQ_OP_TLBI_NH_ASID 0x11 4318c2ecf20Sopenharmony_ci #define CMDQ_OP_TLBI_NH_VA 0x12 4328c2ecf20Sopenharmony_ci #define CMDQ_OP_TLBI_EL2_ALL 0x20 4338c2ecf20Sopenharmony_ci #define CMDQ_OP_TLBI_S12_VMALL 0x28 4348c2ecf20Sopenharmony_ci #define CMDQ_OP_TLBI_S2_IPA 0x2a 4358c2ecf20Sopenharmony_ci #define CMDQ_OP_TLBI_NSNH_ALL 0x30 4368c2ecf20Sopenharmony_ci struct { 4378c2ecf20Sopenharmony_ci u8 num; 4388c2ecf20Sopenharmony_ci u8 scale; 4398c2ecf20Sopenharmony_ci u16 asid; 4408c2ecf20Sopenharmony_ci u16 vmid; 4418c2ecf20Sopenharmony_ci bool leaf; 4428c2ecf20Sopenharmony_ci u8 ttl; 4438c2ecf20Sopenharmony_ci u8 tg; 4448c2ecf20Sopenharmony_ci u64 addr; 4458c2ecf20Sopenharmony_ci } tlbi; 4468c2ecf20Sopenharmony_ci 4478c2ecf20Sopenharmony_ci #define CMDQ_OP_ATC_INV 0x40 4488c2ecf20Sopenharmony_ci #define ATC_INV_SIZE_ALL 52 4498c2ecf20Sopenharmony_ci struct { 4508c2ecf20Sopenharmony_ci u32 sid; 4518c2ecf20Sopenharmony_ci u32 ssid; 4528c2ecf20Sopenharmony_ci u64 addr; 4538c2ecf20Sopenharmony_ci u8 size; 4548c2ecf20Sopenharmony_ci bool global; 4558c2ecf20Sopenharmony_ci } atc; 4568c2ecf20Sopenharmony_ci 4578c2ecf20Sopenharmony_ci #define CMDQ_OP_PRI_RESP 0x41 4588c2ecf20Sopenharmony_ci struct { 4598c2ecf20Sopenharmony_ci u32 sid; 4608c2ecf20Sopenharmony_ci u32 ssid; 4618c2ecf20Sopenharmony_ci u16 grpid; 4628c2ecf20Sopenharmony_ci enum pri_resp resp; 4638c2ecf20Sopenharmony_ci } pri; 4648c2ecf20Sopenharmony_ci 4658c2ecf20Sopenharmony_ci #define CMDQ_OP_CMD_SYNC 0x46 4668c2ecf20Sopenharmony_ci struct { 4678c2ecf20Sopenharmony_ci u64 msiaddr; 4688c2ecf20Sopenharmony_ci } sync; 4698c2ecf20Sopenharmony_ci }; 4708c2ecf20Sopenharmony_ci}; 4718c2ecf20Sopenharmony_ci 4728c2ecf20Sopenharmony_cistruct arm_smmu_ll_queue { 4738c2ecf20Sopenharmony_ci union { 4748c2ecf20Sopenharmony_ci u64 val; 4758c2ecf20Sopenharmony_ci struct { 4768c2ecf20Sopenharmony_ci u32 prod; 4778c2ecf20Sopenharmony_ci u32 cons; 4788c2ecf20Sopenharmony_ci }; 4798c2ecf20Sopenharmony_ci struct { 4808c2ecf20Sopenharmony_ci atomic_t prod; 4818c2ecf20Sopenharmony_ci atomic_t cons; 4828c2ecf20Sopenharmony_ci } atomic; 4838c2ecf20Sopenharmony_ci u8 __pad[SMP_CACHE_BYTES]; 4848c2ecf20Sopenharmony_ci } ____cacheline_aligned_in_smp; 4858c2ecf20Sopenharmony_ci u32 max_n_shift; 4868c2ecf20Sopenharmony_ci}; 4878c2ecf20Sopenharmony_ci 4888c2ecf20Sopenharmony_cistruct arm_smmu_queue { 4898c2ecf20Sopenharmony_ci struct arm_smmu_ll_queue llq; 4908c2ecf20Sopenharmony_ci int irq; /* Wired interrupt */ 4918c2ecf20Sopenharmony_ci 4928c2ecf20Sopenharmony_ci __le64 *base; 4938c2ecf20Sopenharmony_ci dma_addr_t base_dma; 4948c2ecf20Sopenharmony_ci u64 q_base; 4958c2ecf20Sopenharmony_ci 4968c2ecf20Sopenharmony_ci size_t ent_dwords; 4978c2ecf20Sopenharmony_ci 4988c2ecf20Sopenharmony_ci u32 __iomem *prod_reg; 4998c2ecf20Sopenharmony_ci u32 __iomem *cons_reg; 5008c2ecf20Sopenharmony_ci}; 5018c2ecf20Sopenharmony_ci 5028c2ecf20Sopenharmony_cistruct arm_smmu_queue_poll { 5038c2ecf20Sopenharmony_ci ktime_t timeout; 5048c2ecf20Sopenharmony_ci unsigned int delay; 5058c2ecf20Sopenharmony_ci unsigned int spin_cnt; 5068c2ecf20Sopenharmony_ci bool wfe; 5078c2ecf20Sopenharmony_ci}; 5088c2ecf20Sopenharmony_ci 5098c2ecf20Sopenharmony_cistruct arm_smmu_cmdq { 5108c2ecf20Sopenharmony_ci struct arm_smmu_queue q; 5118c2ecf20Sopenharmony_ci atomic_long_t *valid_map; 5128c2ecf20Sopenharmony_ci atomic_t owner_prod; 5138c2ecf20Sopenharmony_ci atomic_t lock; 5148c2ecf20Sopenharmony_ci}; 5158c2ecf20Sopenharmony_ci 5168c2ecf20Sopenharmony_cistruct arm_smmu_cmdq_batch { 5178c2ecf20Sopenharmony_ci u64 cmds[CMDQ_BATCH_ENTRIES * CMDQ_ENT_DWORDS]; 5188c2ecf20Sopenharmony_ci int num; 5198c2ecf20Sopenharmony_ci}; 5208c2ecf20Sopenharmony_ci 5218c2ecf20Sopenharmony_cistruct arm_smmu_evtq { 5228c2ecf20Sopenharmony_ci struct arm_smmu_queue q; 5238c2ecf20Sopenharmony_ci u32 max_stalls; 5248c2ecf20Sopenharmony_ci}; 5258c2ecf20Sopenharmony_ci 5268c2ecf20Sopenharmony_cistruct arm_smmu_priq { 5278c2ecf20Sopenharmony_ci struct arm_smmu_queue q; 5288c2ecf20Sopenharmony_ci}; 5298c2ecf20Sopenharmony_ci 5308c2ecf20Sopenharmony_ci/* High-level stream table and context descriptor structures */ 5318c2ecf20Sopenharmony_cistruct arm_smmu_strtab_l1_desc { 5328c2ecf20Sopenharmony_ci u8 span; 5338c2ecf20Sopenharmony_ci 5348c2ecf20Sopenharmony_ci __le64 *l2ptr; 5358c2ecf20Sopenharmony_ci dma_addr_t l2ptr_dma; 5368c2ecf20Sopenharmony_ci}; 5378c2ecf20Sopenharmony_ci 5388c2ecf20Sopenharmony_cistruct arm_smmu_ctx_desc { 5398c2ecf20Sopenharmony_ci u16 asid; 5408c2ecf20Sopenharmony_ci u64 ttbr; 5418c2ecf20Sopenharmony_ci u64 tcr; 5428c2ecf20Sopenharmony_ci u64 mair; 5438c2ecf20Sopenharmony_ci 5448c2ecf20Sopenharmony_ci refcount_t refs; 5458c2ecf20Sopenharmony_ci struct mm_struct *mm; 5468c2ecf20Sopenharmony_ci}; 5478c2ecf20Sopenharmony_ci 5488c2ecf20Sopenharmony_cistruct arm_smmu_l1_ctx_desc { 5498c2ecf20Sopenharmony_ci __le64 *l2ptr; 5508c2ecf20Sopenharmony_ci dma_addr_t l2ptr_dma; 5518c2ecf20Sopenharmony_ci}; 5528c2ecf20Sopenharmony_ci 5538c2ecf20Sopenharmony_cistruct arm_smmu_ctx_desc_cfg { 5548c2ecf20Sopenharmony_ci __le64 *cdtab; 5558c2ecf20Sopenharmony_ci dma_addr_t cdtab_dma; 5568c2ecf20Sopenharmony_ci struct arm_smmu_l1_ctx_desc *l1_desc; 5578c2ecf20Sopenharmony_ci unsigned int num_l1_ents; 5588c2ecf20Sopenharmony_ci}; 5598c2ecf20Sopenharmony_ci 5608c2ecf20Sopenharmony_cistruct arm_smmu_s1_cfg { 5618c2ecf20Sopenharmony_ci struct arm_smmu_ctx_desc_cfg cdcfg; 5628c2ecf20Sopenharmony_ci struct arm_smmu_ctx_desc cd; 5638c2ecf20Sopenharmony_ci u8 s1fmt; 5648c2ecf20Sopenharmony_ci u8 s1cdmax; 5658c2ecf20Sopenharmony_ci}; 5668c2ecf20Sopenharmony_ci 5678c2ecf20Sopenharmony_cistruct arm_smmu_s2_cfg { 5688c2ecf20Sopenharmony_ci u16 vmid; 5698c2ecf20Sopenharmony_ci u64 vttbr; 5708c2ecf20Sopenharmony_ci u64 vtcr; 5718c2ecf20Sopenharmony_ci}; 5728c2ecf20Sopenharmony_ci 5738c2ecf20Sopenharmony_cistruct arm_smmu_strtab_cfg { 5748c2ecf20Sopenharmony_ci __le64 *strtab; 5758c2ecf20Sopenharmony_ci dma_addr_t strtab_dma; 5768c2ecf20Sopenharmony_ci struct arm_smmu_strtab_l1_desc *l1_desc; 5778c2ecf20Sopenharmony_ci unsigned int num_l1_ents; 5788c2ecf20Sopenharmony_ci 5798c2ecf20Sopenharmony_ci u64 strtab_base; 5808c2ecf20Sopenharmony_ci u32 strtab_base_cfg; 5818c2ecf20Sopenharmony_ci}; 5828c2ecf20Sopenharmony_ci 5838c2ecf20Sopenharmony_ci/* An SMMUv3 instance */ 5848c2ecf20Sopenharmony_cistruct arm_smmu_device { 5858c2ecf20Sopenharmony_ci struct device *dev; 5868c2ecf20Sopenharmony_ci void __iomem *base; 5878c2ecf20Sopenharmony_ci void __iomem *page1; 5888c2ecf20Sopenharmony_ci 5898c2ecf20Sopenharmony_ci#define ARM_SMMU_FEAT_2_LVL_STRTAB (1 << 0) 5908c2ecf20Sopenharmony_ci#define ARM_SMMU_FEAT_2_LVL_CDTAB (1 << 1) 5918c2ecf20Sopenharmony_ci#define ARM_SMMU_FEAT_TT_LE (1 << 2) 5928c2ecf20Sopenharmony_ci#define ARM_SMMU_FEAT_TT_BE (1 << 3) 5938c2ecf20Sopenharmony_ci#define ARM_SMMU_FEAT_PRI (1 << 4) 5948c2ecf20Sopenharmony_ci#define ARM_SMMU_FEAT_ATS (1 << 5) 5958c2ecf20Sopenharmony_ci#define ARM_SMMU_FEAT_SEV (1 << 6) 5968c2ecf20Sopenharmony_ci#define ARM_SMMU_FEAT_MSI (1 << 7) 5978c2ecf20Sopenharmony_ci#define ARM_SMMU_FEAT_COHERENCY (1 << 8) 5988c2ecf20Sopenharmony_ci#define ARM_SMMU_FEAT_TRANS_S1 (1 << 9) 5998c2ecf20Sopenharmony_ci#define ARM_SMMU_FEAT_TRANS_S2 (1 << 10) 6008c2ecf20Sopenharmony_ci#define ARM_SMMU_FEAT_STALLS (1 << 11) 6018c2ecf20Sopenharmony_ci#define ARM_SMMU_FEAT_HYP (1 << 12) 6028c2ecf20Sopenharmony_ci#define ARM_SMMU_FEAT_STALL_FORCE (1 << 13) 6038c2ecf20Sopenharmony_ci#define ARM_SMMU_FEAT_VAX (1 << 14) 6048c2ecf20Sopenharmony_ci#define ARM_SMMU_FEAT_RANGE_INV (1 << 15) 6058c2ecf20Sopenharmony_ci#define ARM_SMMU_FEAT_BTM (1 << 16) 6068c2ecf20Sopenharmony_ci#define ARM_SMMU_FEAT_SVA (1 << 17) 6078c2ecf20Sopenharmony_ci u32 features; 6088c2ecf20Sopenharmony_ci 6098c2ecf20Sopenharmony_ci#define ARM_SMMU_OPT_SKIP_PREFETCH (1 << 0) 6108c2ecf20Sopenharmony_ci#define ARM_SMMU_OPT_PAGE0_REGS_ONLY (1 << 1) 6118c2ecf20Sopenharmony_ci#define ARM_SMMU_OPT_MSIPOLL (1 << 2) 6128c2ecf20Sopenharmony_ci u32 options; 6138c2ecf20Sopenharmony_ci 6148c2ecf20Sopenharmony_ci struct arm_smmu_cmdq cmdq; 6158c2ecf20Sopenharmony_ci struct arm_smmu_evtq evtq; 6168c2ecf20Sopenharmony_ci struct arm_smmu_priq priq; 6178c2ecf20Sopenharmony_ci 6188c2ecf20Sopenharmony_ci int gerr_irq; 6198c2ecf20Sopenharmony_ci int combined_irq; 6208c2ecf20Sopenharmony_ci 6218c2ecf20Sopenharmony_ci unsigned long ias; /* IPA */ 6228c2ecf20Sopenharmony_ci unsigned long oas; /* PA */ 6238c2ecf20Sopenharmony_ci unsigned long pgsize_bitmap; 6248c2ecf20Sopenharmony_ci 6258c2ecf20Sopenharmony_ci#define ARM_SMMU_MAX_ASIDS (1 << 16) 6268c2ecf20Sopenharmony_ci unsigned int asid_bits; 6278c2ecf20Sopenharmony_ci 6288c2ecf20Sopenharmony_ci#define ARM_SMMU_MAX_VMIDS (1 << 16) 6298c2ecf20Sopenharmony_ci unsigned int vmid_bits; 6308c2ecf20Sopenharmony_ci DECLARE_BITMAP(vmid_map, ARM_SMMU_MAX_VMIDS); 6318c2ecf20Sopenharmony_ci 6328c2ecf20Sopenharmony_ci unsigned int ssid_bits; 6338c2ecf20Sopenharmony_ci unsigned int sid_bits; 6348c2ecf20Sopenharmony_ci 6358c2ecf20Sopenharmony_ci struct arm_smmu_strtab_cfg strtab_cfg; 6368c2ecf20Sopenharmony_ci 6378c2ecf20Sopenharmony_ci /* IOMMU core code handle */ 6388c2ecf20Sopenharmony_ci struct iommu_device iommu; 6398c2ecf20Sopenharmony_ci}; 6408c2ecf20Sopenharmony_ci 6418c2ecf20Sopenharmony_ci/* SMMU private data for each master */ 6428c2ecf20Sopenharmony_cistruct arm_smmu_master { 6438c2ecf20Sopenharmony_ci struct arm_smmu_device *smmu; 6448c2ecf20Sopenharmony_ci struct device *dev; 6458c2ecf20Sopenharmony_ci struct arm_smmu_domain *domain; 6468c2ecf20Sopenharmony_ci struct list_head domain_head; 6478c2ecf20Sopenharmony_ci u32 *sids; 6488c2ecf20Sopenharmony_ci unsigned int num_sids; 6498c2ecf20Sopenharmony_ci bool ats_enabled; 6508c2ecf20Sopenharmony_ci bool sva_enabled; 6518c2ecf20Sopenharmony_ci struct list_head bonds; 6528c2ecf20Sopenharmony_ci unsigned int ssid_bits; 6538c2ecf20Sopenharmony_ci}; 6548c2ecf20Sopenharmony_ci 6558c2ecf20Sopenharmony_ci/* SMMU private data for an IOMMU domain */ 6568c2ecf20Sopenharmony_cienum arm_smmu_domain_stage { 6578c2ecf20Sopenharmony_ci ARM_SMMU_DOMAIN_S1 = 0, 6588c2ecf20Sopenharmony_ci ARM_SMMU_DOMAIN_S2, 6598c2ecf20Sopenharmony_ci ARM_SMMU_DOMAIN_NESTED, 6608c2ecf20Sopenharmony_ci ARM_SMMU_DOMAIN_BYPASS, 6618c2ecf20Sopenharmony_ci}; 6628c2ecf20Sopenharmony_ci 6638c2ecf20Sopenharmony_cistruct arm_smmu_domain { 6648c2ecf20Sopenharmony_ci struct arm_smmu_device *smmu; 6658c2ecf20Sopenharmony_ci struct mutex init_mutex; /* Protects smmu pointer */ 6668c2ecf20Sopenharmony_ci 6678c2ecf20Sopenharmony_ci struct io_pgtable_ops *pgtbl_ops; 6688c2ecf20Sopenharmony_ci bool non_strict; 6698c2ecf20Sopenharmony_ci atomic_t nr_ats_masters; 6708c2ecf20Sopenharmony_ci 6718c2ecf20Sopenharmony_ci enum arm_smmu_domain_stage stage; 6728c2ecf20Sopenharmony_ci union { 6738c2ecf20Sopenharmony_ci struct arm_smmu_s1_cfg s1_cfg; 6748c2ecf20Sopenharmony_ci struct arm_smmu_s2_cfg s2_cfg; 6758c2ecf20Sopenharmony_ci }; 6768c2ecf20Sopenharmony_ci 6778c2ecf20Sopenharmony_ci struct iommu_domain domain; 6788c2ecf20Sopenharmony_ci 6798c2ecf20Sopenharmony_ci struct list_head devices; 6808c2ecf20Sopenharmony_ci spinlock_t devices_lock; 6818c2ecf20Sopenharmony_ci}; 6828c2ecf20Sopenharmony_ci 6838c2ecf20Sopenharmony_ciextern struct xarray arm_smmu_asid_xa; 6848c2ecf20Sopenharmony_ciextern struct mutex arm_smmu_asid_lock; 6858c2ecf20Sopenharmony_ci 6868c2ecf20Sopenharmony_ciint arm_smmu_write_ctx_desc(struct arm_smmu_domain *smmu_domain, int ssid, 6878c2ecf20Sopenharmony_ci struct arm_smmu_ctx_desc *cd); 6888c2ecf20Sopenharmony_civoid arm_smmu_tlb_inv_asid(struct arm_smmu_device *smmu, u16 asid); 6898c2ecf20Sopenharmony_cibool arm_smmu_free_asid(struct arm_smmu_ctx_desc *cd); 6908c2ecf20Sopenharmony_ci 6918c2ecf20Sopenharmony_ci#ifdef CONFIG_ARM_SMMU_V3_SVA 6928c2ecf20Sopenharmony_cibool arm_smmu_sva_supported(struct arm_smmu_device *smmu); 6938c2ecf20Sopenharmony_cibool arm_smmu_master_sva_supported(struct arm_smmu_master *master); 6948c2ecf20Sopenharmony_cibool arm_smmu_master_sva_enabled(struct arm_smmu_master *master); 6958c2ecf20Sopenharmony_ciint arm_smmu_master_enable_sva(struct arm_smmu_master *master); 6968c2ecf20Sopenharmony_ciint arm_smmu_master_disable_sva(struct arm_smmu_master *master); 6978c2ecf20Sopenharmony_ci#else /* CONFIG_ARM_SMMU_V3_SVA */ 6988c2ecf20Sopenharmony_cistatic inline bool arm_smmu_sva_supported(struct arm_smmu_device *smmu) 6998c2ecf20Sopenharmony_ci{ 7008c2ecf20Sopenharmony_ci return false; 7018c2ecf20Sopenharmony_ci} 7028c2ecf20Sopenharmony_ci 7038c2ecf20Sopenharmony_cistatic inline bool arm_smmu_master_sva_supported(struct arm_smmu_master *master) 7048c2ecf20Sopenharmony_ci{ 7058c2ecf20Sopenharmony_ci return false; 7068c2ecf20Sopenharmony_ci} 7078c2ecf20Sopenharmony_ci 7088c2ecf20Sopenharmony_cistatic inline bool arm_smmu_master_sva_enabled(struct arm_smmu_master *master) 7098c2ecf20Sopenharmony_ci{ 7108c2ecf20Sopenharmony_ci return false; 7118c2ecf20Sopenharmony_ci} 7128c2ecf20Sopenharmony_ci 7138c2ecf20Sopenharmony_cistatic inline int arm_smmu_master_enable_sva(struct arm_smmu_master *master) 7148c2ecf20Sopenharmony_ci{ 7158c2ecf20Sopenharmony_ci return -ENODEV; 7168c2ecf20Sopenharmony_ci} 7178c2ecf20Sopenharmony_ci 7188c2ecf20Sopenharmony_cistatic inline int arm_smmu_master_disable_sva(struct arm_smmu_master *master) 7198c2ecf20Sopenharmony_ci{ 7208c2ecf20Sopenharmony_ci return -ENODEV; 7218c2ecf20Sopenharmony_ci} 7228c2ecf20Sopenharmony_ci#endif /* CONFIG_ARM_SMMU_V3_SVA */ 7238c2ecf20Sopenharmony_ci#endif /* _ARM_SMMU_V3_H */ 724