Skip to content

Commit 745ef10

Browse files
jannaujoergroedel
authored andcommitted
iommu/io-pgtable: Move Apple DART support to its own file
The pte format used by the DARTs found in the Apple M1 (t8103) is not fully compatible with io-pgtable-arm. The 24 MSB are used for subpage protection (mapping only parts of page) and conflict with the address mask. In addition bit 1 is not available for tagging entries but disables subpage protection. Subpage protection could be useful to support a CPU granule of 4k with the fixed IOMMU page size of 16k. The DARTs found on Apple M1 Pro/Max/Ultra use another different pte format which is even less compatible. To support an output address size of 42 bit the address is shifted down by 4. Subpage protection is mandatory and bit 1 signifies uncached mappings used by the display controller. It would be advantageous to share code for all known Apple DART variants to support common features. The page table allocator for DARTs is less complex since it uses a two levels of translation table without support for huge pages. Signed-off-by: Janne Grunau <[email protected]> Acked-by: Robin Murphy <[email protected]> Acked-by: Sven Peter <[email protected]> Acked-by: Hector Martin <[email protected]> Link: https://lore.kernel.org/r/[email protected] [ joro: Fix compile warning in __dart_alloc_pages()] Signed-off-by: Joerg Roedel <[email protected]>
1 parent 7e18e42 commit 745ef10

File tree

6 files changed

+442
-64
lines changed

6 files changed

+442
-64
lines changed

MAINTAINERS

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1887,6 +1887,7 @@ F: drivers/dma/apple-admac.c
18871887
F: drivers/i2c/busses/i2c-pasemi-core.c
18881888
F: drivers/i2c/busses/i2c-pasemi-platform.c
18891889
F: drivers/iommu/apple-dart.c
1890+
F: drivers/iommu/io-pgtable-dart.c
18901891
F: drivers/irqchip/irq-apple-aic.c
18911892
F: drivers/mailbox/apple-mailbox.c
18921893
F: drivers/nvme/host/apple.c

drivers/iommu/Kconfig

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -67,6 +67,17 @@ config IOMMU_IO_PGTABLE_ARMV7S_SELFTEST
6767

6868
If unsure, say N here.
6969

70+
config IOMMU_IO_PGTABLE_DART
71+
bool "Apple DART Formats"
72+
select IOMMU_IO_PGTABLE
73+
depends on ARM64 || (COMPILE_TEST && !GENERIC_ATOMIC64)
74+
help
75+
Enable support for the Apple DART pagetable formats. These include
76+
the t8020 and t6000/t8110 DART formats used in Apple M1/M2 family
77+
SoCs.
78+
79+
If unsure, say N here.
80+
7081
endmenu
7182

7283
config IOMMU_DEBUGFS
@@ -294,7 +305,7 @@ config APPLE_DART
294305
tristate "Apple DART IOMMU Support"
295306
depends on ARCH_APPLE || (COMPILE_TEST && !GENERIC_ATOMIC64)
296307
select IOMMU_API
297-
select IOMMU_IO_PGTABLE_LPAE
308+
select IOMMU_IO_PGTABLE_DART
298309
default ARCH_APPLE
299310
help
300311
Support for Apple DART (Device Address Resolution Table) IOMMUs

drivers/iommu/Makefile

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ obj-$(CONFIG_IOMMU_DMA) += dma-iommu.o
88
obj-$(CONFIG_IOMMU_IO_PGTABLE) += io-pgtable.o
99
obj-$(CONFIG_IOMMU_IO_PGTABLE_ARMV7S) += io-pgtable-arm-v7s.o
1010
obj-$(CONFIG_IOMMU_IO_PGTABLE_LPAE) += io-pgtable-arm.o
11+
obj-$(CONFIG_IOMMU_IO_PGTABLE_DART) += io-pgtable-dart.o
1112
obj-$(CONFIG_IOASID) += ioasid.o
1213
obj-$(CONFIG_IOMMU_IOVA) += iova.o
1314
obj-$(CONFIG_OF_IOMMU) += of_iommu.o

drivers/iommu/io-pgtable-arm.c

Lines changed: 0 additions & 63 deletions
Original file line numberDiff line numberDiff line change
@@ -130,9 +130,6 @@
130130
#define ARM_MALI_LPAE_MEMATTR_IMP_DEF 0x88ULL
131131
#define ARM_MALI_LPAE_MEMATTR_WRITE_ALLOC 0x8DULL
132132

133-
#define APPLE_DART_PTE_PROT_NO_WRITE (1<<7)
134-
#define APPLE_DART_PTE_PROT_NO_READ (1<<8)
135-
136133
/* IOPTE accessors */
137134
#define iopte_deref(pte,d) __va(iopte_to_paddr(pte, d))
138135

@@ -406,15 +403,6 @@ static arm_lpae_iopte arm_lpae_prot_to_pte(struct arm_lpae_io_pgtable *data,
406403
{
407404
arm_lpae_iopte pte;
408405

409-
if (data->iop.fmt == APPLE_DART) {
410-
pte = 0;
411-
if (!(prot & IOMMU_WRITE))
412-
pte |= APPLE_DART_PTE_PROT_NO_WRITE;
413-
if (!(prot & IOMMU_READ))
414-
pte |= APPLE_DART_PTE_PROT_NO_READ;
415-
return pte;
416-
}
417-
418406
if (data->iop.fmt == ARM_64_LPAE_S1 ||
419407
data->iop.fmt == ARM_32_LPAE_S1) {
420408
pte = ARM_LPAE_PTE_nG;
@@ -1107,52 +1095,6 @@ arm_mali_lpae_alloc_pgtable(struct io_pgtable_cfg *cfg, void *cookie)
11071095
return NULL;
11081096
}
11091097

1110-
static struct io_pgtable *
1111-
apple_dart_alloc_pgtable(struct io_pgtable_cfg *cfg, void *cookie)
1112-
{
1113-
struct arm_lpae_io_pgtable *data;
1114-
int i;
1115-
1116-
if (cfg->oas > 36)
1117-
return NULL;
1118-
1119-
data = arm_lpae_alloc_pgtable(cfg);
1120-
if (!data)
1121-
return NULL;
1122-
1123-
/*
1124-
* The table format itself always uses two levels, but the total VA
1125-
* space is mapped by four separate tables, making the MMIO registers
1126-
* an effective "level 1". For simplicity, though, we treat this
1127-
* equivalently to LPAE stage 2 concatenation at level 2, with the
1128-
* additional TTBRs each just pointing at consecutive pages.
1129-
*/
1130-
if (data->start_level < 1)
1131-
goto out_free_data;
1132-
if (data->start_level == 1 && data->pgd_bits > 2)
1133-
goto out_free_data;
1134-
if (data->start_level > 1)
1135-
data->pgd_bits = 0;
1136-
data->start_level = 2;
1137-
cfg->apple_dart_cfg.n_ttbrs = 1 << data->pgd_bits;
1138-
data->pgd_bits += data->bits_per_level;
1139-
1140-
data->pgd = __arm_lpae_alloc_pages(ARM_LPAE_PGD_SIZE(data), GFP_KERNEL,
1141-
cfg);
1142-
if (!data->pgd)
1143-
goto out_free_data;
1144-
1145-
for (i = 0; i < cfg->apple_dart_cfg.n_ttbrs; ++i)
1146-
cfg->apple_dart_cfg.ttbr[i] =
1147-
virt_to_phys(data->pgd + i * ARM_LPAE_GRANULE(data));
1148-
1149-
return &data->iop;
1150-
1151-
out_free_data:
1152-
kfree(data);
1153-
return NULL;
1154-
}
1155-
11561098
struct io_pgtable_init_fns io_pgtable_arm_64_lpae_s1_init_fns = {
11571099
.alloc = arm_64_lpae_alloc_pgtable_s1,
11581100
.free = arm_lpae_free_pgtable,
@@ -1178,11 +1120,6 @@ struct io_pgtable_init_fns io_pgtable_arm_mali_lpae_init_fns = {
11781120
.free = arm_lpae_free_pgtable,
11791121
};
11801122

1181-
struct io_pgtable_init_fns io_pgtable_apple_dart_init_fns = {
1182-
.alloc = apple_dart_alloc_pgtable,
1183-
.free = arm_lpae_free_pgtable,
1184-
};
1185-
11861123
#ifdef CONFIG_IOMMU_IO_PGTABLE_LPAE_SELFTEST
11871124

11881125
static struct io_pgtable_cfg *cfg_cookie __initdata;

0 commit comments

Comments
 (0)