[RFC PATCH v2 44/58] iommu/arm-smmu-v3-kvm: Validate device features
Mostafa Saleh
smostafa at google.com
Thu Dec 12 10:04:08 PST 2024
From: Jean-Philippe Brucker <jean-philippe at linaro.org>
The KVM hypervisor driver supports a small subset of features. Ensure
the implementation is compatible, and disable some unused features.
Signed-off-by: Jean-Philippe Brucker <jean-philippe at linaro.org>
Signed-off-by: Mostafa Saleh <smostafa at google.com>
---
.../iommu/arm/arm-smmu-v3/arm-smmu-v3-kvm.c | 43 +++++++++++++++++++
1 file changed, 43 insertions(+)
diff --git a/drivers/iommu/arm/arm-smmu-v3/arm-smmu-v3-kvm.c b/drivers/iommu/arm/arm-smmu-v3/arm-smmu-v3-kvm.c
index e2d9bd97ddc5..4b0c9ff6e7f1 100644
--- a/drivers/iommu/arm/arm-smmu-v3/arm-smmu-v3-kvm.c
+++ b/drivers/iommu/arm/arm-smmu-v3/arm-smmu-v3-kvm.c
@@ -27,6 +27,45 @@ static size_t kvm_arm_smmu_cur;
static size_t kvm_arm_smmu_count;
static struct hyp_arm_smmu_v3_device *kvm_arm_smmu_array;
+static bool kvm_arm_smmu_validate_features(struct arm_smmu_device *smmu)
+{
+ unsigned int required_features =
+ ARM_SMMU_FEAT_TT_LE;
+ unsigned int forbidden_features =
+ ARM_SMMU_FEAT_STALL_FORCE;
+ unsigned int keep_features =
+ ARM_SMMU_FEAT_2_LVL_STRTAB |
+ ARM_SMMU_FEAT_2_LVL_CDTAB |
+ ARM_SMMU_FEAT_TT_LE |
+ ARM_SMMU_FEAT_SEV |
+ ARM_SMMU_FEAT_COHERENCY |
+ ARM_SMMU_FEAT_TRANS_S1 |
+ ARM_SMMU_FEAT_TRANS_S2 |
+ ARM_SMMU_FEAT_VAX |
+ ARM_SMMU_FEAT_RANGE_INV;
+
+ if (smmu->options & ARM_SMMU_OPT_PAGE0_REGS_ONLY) {
+ dev_err(smmu->dev, "unsupported layout\n");
+ return false;
+ }
+
+ if ((smmu->features & required_features) != required_features) {
+ dev_err(smmu->dev, "missing features 0x%x\n",
+ required_features & ~smmu->features);
+ return false;
+ }
+
+ if (smmu->features & forbidden_features) {
+ dev_err(smmu->dev, "features 0x%x forbidden\n",
+ smmu->features & forbidden_features);
+ return false;
+ }
+
+ smmu->features &= keep_features;
+
+ return true;
+}
+
static int kvm_arm_smmu_probe(struct platform_device *pdev)
{
int ret;
@@ -71,6 +110,9 @@ static int kvm_arm_smmu_probe(struct platform_device *pdev)
if (ret)
return ret;
+ if (!kvm_arm_smmu_validate_features(smmu))
+ return -ENODEV;
+
platform_set_drvdata(pdev, smmu);
/* Hypervisor parameters */
@@ -79,6 +121,7 @@ static int kvm_arm_smmu_probe(struct platform_device *pdev)
hyp_smmu->ias = smmu->ias;
hyp_smmu->mmio_addr = ioaddr;
hyp_smmu->mmio_size = size;
+ hyp_smmu->features = smmu->features;
kvm_arm_smmu_cur++;
return arm_smmu_register_iommu(smmu, &kvm_arm_smmu_ops, ioaddr);
--
2.47.0.338.g60cca15819-goog
More information about the linux-arm-kernel
mailing list