Commit ef848b7e authored by Lu Baolu's avatar Lu Baolu Committed by Joerg Roedel

iommu/vt-d: Setup pasid entry for RID2PASID support

when the scalable mode is enabled, there is no second level
page translation pointer in the context entry any more (for
DMA request without PASID). Instead, a new RID2PASID field
is introduced in the context entry. Software can choose any
PASID value to set RID2PASID and then setup the translation
in the corresponding PASID entry. Upon receiving a DMA request
without PASID, hardware will firstly look at this RID2PASID
field and then treat this request as a request with a pasid
value specified in RID2PASID field.

Though software is allowed to use any PASID for the RID2PASID,
we will always use the PASID 0 as a sort of design decision.

Cc: Ashok Raj <ashok.raj@intel.com>
Cc: Jacob Pan <jacob.jun.pan@linux.intel.com>
Cc: Kevin Tian <kevin.tian@intel.com>
Signed-off-by: default avatarSanjay Kumar <sanjay.k.kumar@intel.com>
Signed-off-by: default avatarLiu Yi L <yi.l.liu@intel.com>
Signed-off-by: default avatarLu Baolu <baolu.lu@linux.intel.com>
Reviewed-by: default avatarAshok Raj <ashok.raj@intel.com>
Signed-off-by: default avatarJoerg Roedel <jroedel@suse.de>
parent 6f7db75e
...@@ -2462,6 +2462,22 @@ static struct dmar_domain *dmar_insert_one_dev_info(struct intel_iommu *iommu, ...@@ -2462,6 +2462,22 @@ static struct dmar_domain *dmar_insert_one_dev_info(struct intel_iommu *iommu,
dmar_remove_one_dev_info(domain, dev); dmar_remove_one_dev_info(domain, dev);
return NULL; return NULL;
} }
/* Setup the PASID entry for requests without PASID: */
spin_lock(&iommu->lock);
if (hw_pass_through && domain_type_is_si(domain))
ret = intel_pasid_setup_pass_through(iommu, domain,
dev, PASID_RID2PASID);
else
ret = intel_pasid_setup_second_level(iommu, domain,
dev, PASID_RID2PASID);
spin_unlock(&iommu->lock);
if (ret) {
pr_err("Setup RID2PASID for %s failed\n",
dev_name(dev));
dmar_remove_one_dev_info(domain, dev);
return NULL;
}
} }
if (dev && domain_context_mapping(domain, dev)) { if (dev && domain_context_mapping(domain, dev)) {
...@@ -4825,6 +4841,10 @@ static void __dmar_remove_one_dev_info(struct device_domain_info *info) ...@@ -4825,6 +4841,10 @@ static void __dmar_remove_one_dev_info(struct device_domain_info *info)
iommu = info->iommu; iommu = info->iommu;
if (info->dev) { if (info->dev) {
if (dev_is_pci(info->dev) && sm_supported(iommu))
intel_pasid_tear_down_entry(iommu, info->dev,
PASID_RID2PASID);
iommu_disable_dev_iotlb(info); iommu_disable_dev_iotlb(info);
domain_context_clear(iommu, info->dev); domain_context_clear(iommu, info->dev);
intel_pasid_free_table(info->dev); intel_pasid_free_table(info->dev);
......
...@@ -10,6 +10,7 @@ ...@@ -10,6 +10,7 @@
#ifndef __INTEL_PASID_H #ifndef __INTEL_PASID_H
#define __INTEL_PASID_H #define __INTEL_PASID_H
#define PASID_RID2PASID 0x0
#define PASID_MIN 0x1 #define PASID_MIN 0x1
#define PASID_MAX 0x100000 #define PASID_MAX 0x100000
#define PASID_PTE_MASK 0x3F #define PASID_PTE_MASK 0x3F
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment