iommu/vt-d: Add set domain DOMAIN_ATTR_NESTING attr
This adds the Intel VT-d specific callback of setting DOMAIN_ATTR_NESTING domain attribution. It is necessary to let the VT-d driver know that the domain represents a virtual machine which requires the IOMMU hardware to support nested translation mode. Return success if the IOMMU hardware suports nested mode, otherwise failure. Signed-off-by: Yi Sun <yi.y.sun@linux.intel.com> Signed-off-by: Lu Baolu <baolu.lu@linux.intel.com> Signed-off-by: Joerg Roedel <jroedel@suse.de>
This commit is contained in:
parent
a1948f2e0a
commit
2cd1311a26
@ -315,6 +315,12 @@ static int hw_pass_through = 1;
|
|||||||
*/
|
*/
|
||||||
#define DOMAIN_FLAG_USE_FIRST_LEVEL BIT(2)
|
#define DOMAIN_FLAG_USE_FIRST_LEVEL BIT(2)
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Domain represents a virtual machine which demands iommu nested
|
||||||
|
* translation mode support.
|
||||||
|
*/
|
||||||
|
#define DOMAIN_FLAG_NESTING_MODE BIT(3)
|
||||||
|
|
||||||
#define for_each_domain_iommu(idx, domain) \
|
#define for_each_domain_iommu(idx, domain) \
|
||||||
for (idx = 0; idx < g_num_of_iommus; idx++) \
|
for (idx = 0; idx < g_num_of_iommus; idx++) \
|
||||||
if (domain->iommu_refcnt[idx])
|
if (domain->iommu_refcnt[idx])
|
||||||
@ -5640,6 +5646,24 @@ static inline bool iommu_pasid_support(void)
|
|||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static inline bool nested_mode_support(void)
|
||||||
|
{
|
||||||
|
struct dmar_drhd_unit *drhd;
|
||||||
|
struct intel_iommu *iommu;
|
||||||
|
bool ret = true;
|
||||||
|
|
||||||
|
rcu_read_lock();
|
||||||
|
for_each_active_iommu(iommu, drhd) {
|
||||||
|
if (!sm_supported(iommu) || !ecap_nest(iommu->ecap)) {
|
||||||
|
ret = false;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
rcu_read_unlock();
|
||||||
|
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
static bool intel_iommu_capable(enum iommu_cap cap)
|
static bool intel_iommu_capable(enum iommu_cap cap)
|
||||||
{
|
{
|
||||||
if (cap == IOMMU_CAP_CACHE_COHERENCY)
|
if (cap == IOMMU_CAP_CACHE_COHERENCY)
|
||||||
@ -6018,10 +6042,42 @@ static bool intel_iommu_is_attach_deferred(struct iommu_domain *domain,
|
|||||||
return dev->archdata.iommu == DEFER_DEVICE_DOMAIN_INFO;
|
return dev->archdata.iommu == DEFER_DEVICE_DOMAIN_INFO;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int
|
||||||
|
intel_iommu_domain_set_attr(struct iommu_domain *domain,
|
||||||
|
enum iommu_attr attr, void *data)
|
||||||
|
{
|
||||||
|
struct dmar_domain *dmar_domain = to_dmar_domain(domain);
|
||||||
|
unsigned long flags;
|
||||||
|
int ret = 0;
|
||||||
|
|
||||||
|
if (domain->type != IOMMU_DOMAIN_UNMANAGED)
|
||||||
|
return -EINVAL;
|
||||||
|
|
||||||
|
switch (attr) {
|
||||||
|
case DOMAIN_ATTR_NESTING:
|
||||||
|
spin_lock_irqsave(&device_domain_lock, flags);
|
||||||
|
if (nested_mode_support() &&
|
||||||
|
list_empty(&dmar_domain->devices)) {
|
||||||
|
dmar_domain->flags |= DOMAIN_FLAG_NESTING_MODE;
|
||||||
|
dmar_domain->flags &= ~DOMAIN_FLAG_USE_FIRST_LEVEL;
|
||||||
|
} else {
|
||||||
|
ret = -ENODEV;
|
||||||
|
}
|
||||||
|
spin_unlock_irqrestore(&device_domain_lock, flags);
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
ret = -EINVAL;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
const struct iommu_ops intel_iommu_ops = {
|
const struct iommu_ops intel_iommu_ops = {
|
||||||
.capable = intel_iommu_capable,
|
.capable = intel_iommu_capable,
|
||||||
.domain_alloc = intel_iommu_domain_alloc,
|
.domain_alloc = intel_iommu_domain_alloc,
|
||||||
.domain_free = intel_iommu_domain_free,
|
.domain_free = intel_iommu_domain_free,
|
||||||
|
.domain_set_attr = intel_iommu_domain_set_attr,
|
||||||
.attach_dev = intel_iommu_attach_device,
|
.attach_dev = intel_iommu_attach_device,
|
||||||
.detach_dev = intel_iommu_detach_device,
|
.detach_dev = intel_iommu_detach_device,
|
||||||
.aux_attach_dev = intel_iommu_aux_attach_device,
|
.aux_attach_dev = intel_iommu_aux_attach_device,
|
||||||
|
Loading…
Reference in New Issue
Block a user