mirror of
https://git.rwth-aachen.de/acs/public/villas/node/
synced 2025-03-09 00:00:00 +01:00
vfio: track if IOMMU is enabled to prepare for non-IOMMU mode
This commit is contained in:
parent
1f42f5bb63
commit
94ba899b21
2 changed files with 38 additions and 3 deletions
|
@ -135,6 +135,9 @@ public:
|
|||
/** munmap() a region which has been mapped by vfio_map_region() */
|
||||
bool memoryUnmap(uintptr_t phys, size_t length);
|
||||
|
||||
bool isIommuEnabled() const
|
||||
{ return this->hasIommu; }
|
||||
|
||||
private:
|
||||
VfioGroup& getOrAttachGroup(int index);
|
||||
|
||||
|
@ -143,6 +146,7 @@ private:
|
|||
int version;
|
||||
int extensions;
|
||||
uint64_t iova_next; /**< Next free IOVA address */
|
||||
bool hasIommu;
|
||||
|
||||
/// All groups bound to this container
|
||||
std::list<std::unique_ptr<VfioGroup>> groups;
|
||||
|
|
|
@ -108,12 +108,25 @@ VfioContainer::VfioContainer()
|
|||
logger->error("Failed to get VFIO extensions");
|
||||
throw std::exception();
|
||||
}
|
||||
else if (ret > 0)
|
||||
else if (ret > 0) {
|
||||
extensions |= (1 << i);
|
||||
}
|
||||
}
|
||||
|
||||
logger->debug("Version: {:#x}", version);
|
||||
hasIommu = false;
|
||||
|
||||
if(not (extensions & (1 << VFIO_NOIOMMU_IOMMU))) {
|
||||
if(not (extensions & (1 << VFIO_TYPE1_IOMMU))) {
|
||||
logger->error("No supported IOMMU extension found");
|
||||
throw std::exception();
|
||||
} else {
|
||||
hasIommu = true;
|
||||
}
|
||||
}
|
||||
|
||||
logger->debug("Version: {:#x}", version);
|
||||
logger->debug("Extensions: {:#x}", extensions);
|
||||
logger->debug("IOMMU: {}", hasIommu ? "yes" : "no");
|
||||
}
|
||||
|
||||
|
||||
|
@ -319,6 +332,11 @@ VfioContainer::memoryMap(uintptr_t virt, uintptr_t phys, size_t length)
|
|||
{
|
||||
int ret;
|
||||
|
||||
if(not hasIommu) {
|
||||
logger->error("DMA mapping not supported without IOMMU");
|
||||
return UINTPTR_MAX;
|
||||
}
|
||||
|
||||
if (length & 0xFFF) {
|
||||
length += 0x1000;
|
||||
length &= ~0xFFF;
|
||||
|
@ -363,6 +381,10 @@ VfioContainer::memoryUnmap(uintptr_t phys, size_t length)
|
|||
{
|
||||
int ret;
|
||||
|
||||
if(not hasIommu) {
|
||||
return true;
|
||||
}
|
||||
|
||||
struct vfio_iommu_type1_dma_unmap dmaUnmap;
|
||||
dmaUnmap.argsz = sizeof(struct vfio_iommu_type1_dma_unmap);
|
||||
dmaUnmap.flags = 0;
|
||||
|
@ -554,6 +576,11 @@ VfioDevice::pciHotReset()
|
|||
free(reset);
|
||||
free(reset_info);
|
||||
|
||||
if(not success and not group.container->isIommuEnabled()) {
|
||||
logger->info("PCI hot reset failed, but this is expected without IOMMU");
|
||||
return true;
|
||||
}
|
||||
|
||||
return success;
|
||||
}
|
||||
|
||||
|
@ -740,7 +767,11 @@ VfioGroup::attach(int containerFd, int groupIndex)
|
|||
}
|
||||
|
||||
/* Set IOMMU type */
|
||||
ret = ioctl(containerFd, VFIO_SET_IOMMU, VFIO_TYPE1_IOMMU);
|
||||
int iommu_type = container.isIommuEnabled() ?
|
||||
VFIO_TYPE1_IOMMU :
|
||||
VFIO_NOIOMMU_IOMMU;
|
||||
|
||||
ret = ioctl(containerFd, VFIO_SET_IOMMU, iommu_type);
|
||||
if (ret < 0) {
|
||||
logger->error("Failed to set IOMMU type of container: {}", ret);
|
||||
return nullptr;
|
||||
|
|
Loading…
Add table
Reference in a new issue