49
IOMMUMemoryRegion iova_mr; /* IOVA memory region for attached device */
50
AddressSpace iova_as; /* IOVA address space for attached device */
51
RISCVIOMMUState *iommu; /* Managing IOMMU device state */
52
- uint32_t devid; /* Requester identifier, AKA device_id */
52
+ PCIBus *bus; /* PCI bus of the requester */
53
+ uint8_t devfn; /* Requester identifier, AKA device_id */
54
bool notifier; /* IOMMU unmap notifier enabled */
55
QLIST_ENTRY(RISCVIOMMUSpace) list;
56
};
75
/* IOMMU index for transactions without process_id specified. */
76
#define RISCV_IOMMU_NOPROCID 0
77
78
+static uint32_t riscv_iommu_space_devid(RISCVIOMMUSpace *as)
79
+{
80
+ uint32_t devid = PCI_BUILD_BDF(pci_bus_num(as->bus), as->devfn);
81
+
82
+ /* FIXME: PCIe bus remapping for attached endpoints. */
83
+ devid |= as->iommu->bus << 8;
84
+ return devid;
85
+}
86
+
87
static uint8_t riscv_iommu_get_icvec_vector(uint32_t icvec, uint32_t vec_type)
88
{
89
switch (vec_type) {
1389
}
1390
1391
/* Find or allocate address space for a given device */
1382
-static AddressSpace *riscv_iommu_space(RISCVIOMMUState *s, uint32_t devid)
1392
+static AddressSpace *riscv_iommu_space(RISCVIOMMUState *s, PCIBus *bus,
1393
+ int devfn)
1394
{
1395
RISCVIOMMUSpace *as;
1396
1386
- /* FIXME: PCIe bus remapping for attached endpoints. */
1387
- devid |= s->bus << 8;
1388
-
1397
QLIST_FOREACH(as, &s->spaces, list) {
1390
- if (as->devid == devid) {
1398
+ if (as->bus == bus && as->devfn == devfn) {
1399
break;
1400
}
1401
}
1405
as = g_new0(RISCVIOMMUSpace, 1);
1406
1407
as->iommu = s;
1400
- as->devid = devid;
1408
+ as->bus = bus;
1409
+ as->devfn = devfn;
1410
1411
snprintf(name, sizeof(name), "riscv-iommu-%04x:%02x.%d-iova",
1403
- PCI_BUS_NUM(as->devid), PCI_SLOT(as->devid), PCI_FUNC(as->devid));
1412
+ pci_bus_num(bus), PCI_SLOT(devfn), PCI_FUNC(devfn));
1413
1414
/* IOVA address space, untranslated addresses */
1415
memory_region_init_iommu(&as->iova_mr, sizeof(as->iova_mr),
1419
1420
QLIST_INSERT_HEAD(&s->spaces, as, list);
1421
1413
- trace_riscv_iommu_new(s->parent_obj.id, PCI_BUS_NUM(as->devid),
1414
- PCI_SLOT(as->devid), PCI_FUNC(as->devid));
1422
+ trace_riscv_iommu_new(s->parent_obj.id, pci_bus_num(bus),
1423
+ PCI_SLOT(devfn), PCI_FUNC(devfn));
1424
}
1425
return &as->iova_as;
1426
}
1741
pid = get_field(cmd->dword0, RISCV_IOMMU_CMD_ATS_PID);
1742
1743
QLIST_FOREACH(as, &s->spaces, list) {
1735
- if (as->devid == devid) {
1744
+ if (riscv_iommu_space_devid(as) == devid) {
1745
break;
1746
}
1747
}
2754
.addr_mask = ~0ULL,
2755
.perm = flag,
2756
};
2757
+ uint32_t devid = riscv_iommu_space_devid(as);
2758
2749
- ctx = riscv_iommu_ctx(as->iommu, as->devid, iommu_idx, &ref);
2759
+ ctx = riscv_iommu_ctx(as->iommu, devid, iommu_idx, &ref);
2760
if (ctx == NULL) {
2761
/* Translation disabled or invalid. */
2762
iotlb.addr_mask = 0;
2768
}
2769
2770
/* Trace all dma translations with original access flags. */
2761
- trace_riscv_iommu_dma(as->iommu->parent_obj.id, PCI_BUS_NUM(as->devid),
2762
- PCI_SLOT(as->devid), PCI_FUNC(as->devid), iommu_idx,
2771
+ trace_riscv_iommu_dma(as->iommu->parent_obj.id, PCI_BUS_NUM(devid),
2772
+ PCI_SLOT(devid), PCI_FUNC(devid), iommu_idx,
2773
IOMMU_FLAG_STR[flag & IOMMU_RW], iotlb.iova,
2774
iotlb.translated_addr);
2775
2817
2818
/* Find first matching IOMMU */
2819
while (s != NULL && as == NULL) {
2810
- as = riscv_iommu_space(s, PCI_BUILD_BDF(pci_bus_num(bus), devfn));
2820
+ as = riscv_iommu_space(s, bus, devfn);
2821
s = s->iommus.le_next;
2822
}
2823