Skip to contentSkip to conversation

iommu/arm-smmu: Fix stream-match conflict with IOMMU_DOMAIN_DMA

PATCH New Will Deacon 4 participants 12 messages Apr 1, 2016 – Apr 15, 2016 IOMMU

lore
Share & tools
lore
#0 lore raw

PATCH 1/1 iommu/arm-smmu: Fix stream-match conflict with IOMMU_DOMAIN_DMA

Commit cbf8277ef456 ("iommu/arm-smmu: Treat IOMMU_DOMAIN_DMA as bypass for now") ignores requests to attach a device to the default domain since, without IOMMU-basked DMA ops available everywhere, the default domain will just lead to unexpected transaction faults being reported.

Unfortunately, the way this was implemented on SMMUv2 causes a regression with VFIO PCI device passthrough under KVM on AMD Seattle. On this system, the host controller device is associated with both a pci_dev *and* a platform_device, and can therefore end up with duplicate SMR entries, resulting in a stream-match conflict at runtime.

This patch amends the original fix so that attaching to IOMMU_DOMAIN_DMA is rejected even before configuring the SMRs. This restores the old behaviour for now, but we'll need to look at handing host controllers specially when we come to supporting the default domain fully.

---
 drivers/iommu/arm-smmu.c | 14 ++++++++------
 1 file changed, 8 insertions(+), 6 deletions(-)
drivers/iommu/arm-smmu.c +8 -6
index e933679a3266..2f186d22477f 100644
@@ -1098,18 +1098,20 @@ static int arm_smmu_domain_add_master(struct arm_smmu_domain *smmu_domain,
 	struct arm_smmu_device *smmu = smmu_domain->smmu;
 	void __iomem *gr0_base = ARM_SMMU_GR0(smmu);
 
-	/* Devices in an IOMMU group may already be configured */
-	ret = arm_smmu_master_configure_smrs(smmu, cfg);
-	if (ret)
-		return ret == -EEXIST ? 0 : ret;
-
 	/*
 	 * FIXME: This won't be needed once we have IOMMU-backed DMA ops
-	 * for all devices behind the SMMU.
+	 * for all devices behind the SMMU. Note that we need to take
+	 * care configuring SMRs for devices both a platform_device and
+	 * and a PCI device (i.e. a PCI host controller)
 	 */
 	if (smmu_domain->domain.type == IOMMU_DOMAIN_DMA)
 		return 0;
 
+	/* Devices in an IOMMU group may already be configured */
+	ret = arm_smmu_master_configure_smrs(smmu, cfg);
+	if (ret)
+		return ret == -EEXIST ? 0 : ret;
+
 	for (i = 0; i < cfg->num_streamids; ++i) {
 		u32 idx, s2cr;
 
Signature · 1 line
2.1.4
#1 lore raw

PATCH 1/1 iommu/arm-smmu: Fix stream-match conflict with IOMMU_DOMAIN_DMA

Hi Will,

Quoted 11 lines · Will Deacon

Commit cbf8277ef456 ("iommu/arm-smmu: Treat IOMMU_DOMAIN_DMA as bypass for now") ignores requests to attach a device to the default domain since, without IOMMU-basked DMA ops available everywhere, the default domain will just lead to unexpected transaction faults being reported.

Unfortunately, the way this was implemented on SMMUv2 causes a regression with VFIO PCI device passthrough under KVM on AMD Seattle. On this system, the host controller device is associated with both a pci_dev *and* a platform_device, and can therefore end up with duplicate SMR entries, resulting in a stream-match conflict at runtime.

Quoted 4 lines

This patch amends the original fix so that attaching to IOMMU_DOMAIN_DMA is rejected even before configuring the SMRs. This restores the old behaviour for now, but we'll need to look at handing host controllers specially when we come to supporting the default domain fully.

This works fine for me, before and after PCIe assignment. However before giving my T-b I would like to investigate another regression I observe wrt SRIOV assignment. Assigning the 1st VF works fine. However assigning a second VF does not work anymore (it used to in the past). I get -ENOSPC from arm_smmu_master_configure_smrs

Best Regards

Eric

Quoted 39 lines
---
 drivers/iommu/arm-smmu.c | 14 ++++++++------
 1 file changed, 8 insertions(+), 6 deletions(-)
drivers/iommu/arm-smmu.c +8 -6
index e933679a3266..2f186d22477f 100644
@@ -1098,18 +1098,20 @@ static int arm_smmu_domain_add_master(struct arm_smmu_domain *smmu_domain,
 	struct arm_smmu_device *smmu = smmu_domain->smmu;
 	void __iomem *gr0_base = ARM_SMMU_GR0(smmu);
 
-	/* Devices in an IOMMU group may already be configured */
-	ret = arm_smmu_master_configure_smrs(smmu, cfg);
-	if (ret)
-		return ret == -EEXIST ? 0 : ret;
-
 	/*
 	 * FIXME: This won't be needed once we have IOMMU-backed DMA ops
-	 * for all devices behind the SMMU.
+	 * for all devices behind the SMMU. Note that we need to take
+	 * care configuring SMRs for devices both a platform_device and
+	 * and a PCI device (i.e. a PCI host controller)
 	 */
 	if (smmu_domain->domain.type == IOMMU_DOMAIN_DMA)
 		return 0;
 
+	/* Devices in an IOMMU group may already be configured */
+	ret = arm_smmu_master_configure_smrs(smmu, cfg);
+	if (ret)
+		return ret == -EEXIST ? 0 : ret;
+
 	for (i = 0; i < cfg->num_streamids; ++i) {
 		u32 idx, s2cr;
 
#2 lore raw

PATCH 1/1 iommu/arm-smmu: Fix stream-match conflict with IOMMU_DOMAIN_DMA

Hi Eric,

Quoted 17 lines · Eric Auger
Quoted 11 lines · Will Deacon

Commit cbf8277ef456 ("iommu/arm-smmu: Treat IOMMU_DOMAIN_DMA as bypass for now") ignores requests to attach a device to the default domain since, without IOMMU-basked DMA ops available everywhere, the default domain will just lead to unexpected transaction faults being reported.

Unfortunately, the way this was implemented on SMMUv2 causes a regression with VFIO PCI device passthrough under KVM on AMD Seattle. On this system, the host controller device is associated with both a pci_dev *and* a platform_device, and can therefore end up with duplicate SMR entries, resulting in a stream-match conflict at runtime.

Quoted 4 lines

This patch amends the original fix so that attaching to IOMMU_DOMAIN_DMA is rejected even before configuring the SMRs. This restores the old behaviour for now, but we'll need to look at handing host controllers specially when we come to supporting the default domain fully.

Quoted 5 lines

This works fine for me, before and after PCIe assignment. However before giving my T-b I would like to investigate another regression I observe wrt SRIOV assignment. Assigning the 1st VF works fine. However assigning a second VF does not work anymore (it used to in the past). I get -ENOSPC from arm_smmu_master_configure_smrs

Did you get anywhere debugging this?

Will

#3 lore raw

PATCH 1/1 iommu/arm-smmu: Fix stream-match conflict with IOMMU_DOMAIN_DMA

Hi Will,

Quoted 20 lines · Will Deacon

Hi Eric,

Quoted 17 lines · Eric Auger
Quoted 15 lines · Will Deacon

Commit cbf8277ef456 ("iommu/arm-smmu: Treat IOMMU_DOMAIN_DMA as bypass for now") ignores requests to attach a device to the default domain since, without IOMMU-basked DMA ops available everywhere, the default domain will just lead to unexpected transaction faults being reported.

Unfortunately, the way this was implemented on SMMUv2 causes a regression with VFIO PCI device passthrough under KVM on AMD Seattle. On this system, the host controller device is associated with both a pci_dev *and* a platform_device, and can therefore end up with duplicate SMR entries, resulting in a stream-match conflict at runtime.

This patch amends the original fix so that attaching to IOMMU_DOMAIN_DMA is rejected even before configuring the SMRs. This restores the old behaviour for now, but we'll need to look at handing host controllers specially when we come to supporting the default domain fully.

Quoted 7 lines
Quoted 5 lines

This works fine for me, before and after PCIe assignment. However before giving my T-b I would like to investigate another regression I observe wrt SRIOV assignment. Assigning the 1st VF works fine. However assigning a second VF does not work anymore (it used to in the past). I get -ENOSPC from arm_smmu_master_configure_smrs

Did you get anywhere debugging this?

Yes: http://www.spinics.net/lists/arm-kernel/msg495024.html

Eric

Quoted 3 lines

Will

reviewer
#4 lore raw

PATCH 1/1 iommu/arm-smmu: Fix stream-match conflict with IOMMU_DOMAIN_DMA

In reply to Will Deacon
Quoted 11 lines · Will Deacon

Commit cbf8277ef456 ("iommu/arm-smmu: Treat IOMMU_DOMAIN_DMA as bypass for now") ignores requests to attach a device to the default domain since, without IOMMU-basked DMA ops available everywhere, the default domain will just lead to unexpected transaction faults being reported.

Unfortunately, the way this was implemented on SMMUv2 causes a regression with VFIO PCI device passthrough under KVM on AMD Seattle. On this system, the host controller device is associated with both a pci_dev *and* a platform_device, and can therefore end up with duplicate SMR entries, resulting in a stream-match conflict at runtime.

Quoted 4 lines

This patch amends the original fix so that attaching to IOMMU_DOMAIN_DMA is rejected even before configuring the SMRs. This restores the old behaviour for now, but we'll need to look at handing host controllers specially when we come to supporting the default domain fully.

FWIW this is already solved with the generic bindings, as in most cases the host controller won't need an "iommus" property - for those that do actually have their own IDs for the platform device side, any aliasing with the PCI-derived IDs from "iommu-map" is magically taken care of in the group allocation code. That cross-bus-grouping should also apply to legacy masters too, since they look the same by the time we get to that point, so there should be no more stream match conflicts either way. I'll be working on a v2 of that series this week, so I'll rebase on top of this fix.

Robin.

Quoted 38 lines
---
  drivers/iommu/arm-smmu.c | 14 ++++++++------
  1 file changed, 8 insertions(+), 6 deletions(-)
drivers/iommu/arm-smmu.c +8 -6
index e933679a3266..2f186d22477f 100644
@@ -1098,18 +1098,20 @@ static int arm_smmu_domain_add_master(struct arm_smmu_domain *smmu_domain,
  	struct arm_smmu_device *smmu = smmu_domain->smmu;
  	void __iomem *gr0_base = ARM_SMMU_GR0(smmu);
 
-	/* Devices in an IOMMU group may already be configured */
-	ret = arm_smmu_master_configure_smrs(smmu, cfg);
-	if (ret)
-		return ret == -EEXIST ? 0 : ret;
-
  	/*
  	 * FIXME: This won't be needed once we have IOMMU-backed DMA ops
-	 * for all devices behind the SMMU.
+	 * for all devices behind the SMMU. Note that we need to take
+	 * care configuring SMRs for devices both a platform_device and
+	 * and a PCI device (i.e. a PCI host controller)
  	 */
  	if (smmu_domain->domain.type == IOMMU_DOMAIN_DMA)
  		return 0;
 
+	/* Devices in an IOMMU group may already be configured */
+	ret = arm_smmu_master_configure_smrs(smmu, cfg);
+	if (ret)
+		return ret == -EEXIST ? 0 : ret;
+
  	for (i = 0; i < cfg->num_streamids; ++i) {
  		u32 idx, s2cr;
 
#5 lore raw

PATCH 1/1 iommu/arm-smmu: Fix stream-match conflict with IOMMU_DOMAIN_DMA

Hi Robin,

Quoted 17 lines · Robin Murphy
Quoted 11 lines · Will Deacon

Commit cbf8277ef456 ("iommu/arm-smmu: Treat IOMMU_DOMAIN_DMA as bypass for now") ignores requests to attach a device to the default domain since, without IOMMU-basked DMA ops available everywhere, the default domain will just lead to unexpected transaction faults being reported.

Unfortunately, the way this was implemented on SMMUv2 causes a regression with VFIO PCI device passthrough under KVM on AMD Seattle. On this system, the host controller device is associated with both a pci_dev *and* a platform_device, and can therefore end up with duplicate SMR entries, resulting in a stream-match conflict at runtime.

Quoted 4 lines

This patch amends the original fix so that attaching to IOMMU_DOMAIN_DMA is rejected even before configuring the SMRs. This restores the old behaviour for now, but we'll need to look at handing host controllers specially when we come to supporting the default domain fully.

Quoted 9 lines

FWIW this is already solved with the generic bindings, as in most cases the host controller won't need an "iommus" property - for those that do actually have their own IDs for the platform device side, any aliasing with the PCI-derived IDs from "iommu-map" is magically taken care of in the group allocation code. That cross-bus-grouping should also apply to legacy masters too, since they look the same by the time we get to that point, so there should be no more stream match conflicts either way. I'll be working on a v2 of that series this week, so I'll rebase on top of this fix.

Thanks for the notice.

Besides the fault I was experiencing before that fix I also face a regression with respect to SRIOV 2d VF assignment. It appears it is due to a shortage of context banks and not a shortage of SMRs as I thought at the beginning. The -ENOSPC is returned by arm_smmu_init_domain_context (__arm_smmu_alloc_bitmap). arm_smmu_init_domain_context is called even if handle a default iommu domain and if my understanding is correct we shouldn't consume any context bank in that case.

Best Regards

Eric

Quoted 43 lines

Robin.

Quoted 39 lines
---
  drivers/iommu/arm-smmu.c | 14 ++++++++------
  1 file changed, 8 insertions(+), 6 deletions(-)
drivers/iommu/arm-smmu.c +8 -6
index e933679a3266..2f186d22477f 100644
@@ -1098,18 +1098,20 @@ static int arm_smmu_domain_add_master(struct
 arm_smmu_domain *smmu_domain,
      struct arm_smmu_device *smmu = smmu_domain->smmu;
      void __iomem *gr0_base = ARM_SMMU_GR0(smmu);
 
-    /* Devices in an IOMMU group may already be configured */
-    ret = arm_smmu_master_configure_smrs(smmu, cfg);
-    if (ret)
-        return ret == -EEXIST ? 0 : ret;
-
      /*
       * FIXME: This won't be needed once we have IOMMU-backed DMA ops
-     * for all devices behind the SMMU.
+     * for all devices behind the SMMU. Note that we need to take
+     * care configuring SMRs for devices both a platform_device and
+     * and a PCI device (i.e. a PCI host controller)
       */
      if (smmu_domain->domain.type == IOMMU_DOMAIN_DMA)
          return 0;
 
+    /* Devices in an IOMMU group may already be configured */
+    ret = arm_smmu_master_configure_smrs(smmu, cfg);
+    if (ret)
+        return ret == -EEXIST ? 0 : ret;
+
      for (i = 0; i < cfg->num_streamids; ++i) {
          u32 idx, s2cr;
reviewer
#6 lore raw

PATCH 1/1 iommu/arm-smmu: Don't allocate resources for bypass domains

Until we get fully plumbed into of_iommu_configure, our default IOMMU_DOMAIN_DMA domains just bypass translation. Since we achieve that by leaving the stream table entries set to bypass instead of pointing at a translation context, the context bank we allocate for the domain is completely wasted. Context banks are typically a rather limited resource, so don't hog ones we don't need.

---
 drivers/iommu/arm-smmu.c | 8 +++++++-
 1 file changed, 7 insertions(+), 1 deletion(-)
drivers/iommu/arm-smmu.c +7 -1
index 5158feb..7c39ac4 100644
@@ -826,6 +826,12 @@ static int arm_smmu_init_domain_context(struct iommu_domain *domain,
 	if (smmu_domain->smmu)
 		goto out_unlock;
 
+	/* We're bypassing these SIDs, so don't allocate an actual context */
+	if (domain->type == IOMMU_DOMAIN_DMA) {
+		smmu_domain->smmu = smmu;
+		goto out_unlock;
+	}
+
 	/*
 	 * Mapping the requested stage onto what we support is surprisingly
 	 * complicated, mainly because the spec allows S1+S2 SMMUs without
@@ -948,7 +954,7 @@ static void arm_smmu_destroy_domain_context(struct iommu_domain *domain)
 	void __iomem *cb_base;
 	int irq;
 
-	if (!smmu)
+	if (!smmu || domain->type == IOMMU_DOMAIN_DMA)
 		return;
 
 	/*
Signature · 1 line
2.7.3.dirty
#7 lore raw

PATCH 1/1 iommu/arm-smmu: Don't allocate resources for bypass domains

Quoted 6 lines · Robin Murphy

Until we get fully plumbed into of_iommu_configure, our default IOMMU_DOMAIN_DMA domains just bypass translation. Since we achieve that by leaving the stream table entries set to bypass instead of pointing at a translation context, the context bank we allocate for the domain is completely wasted. Context banks are typically a rather limited resource, so don't hog ones we don't need.

Eric, does this resolve your remaining passthrough regressions when applied on top of my patch?

Will

Quoted 35 lines
---
 drivers/iommu/arm-smmu.c | 8 +++++++-
 1 file changed, 7 insertions(+), 1 deletion(-)
drivers/iommu/arm-smmu.c +7 -1
index 5158feb..7c39ac4 100644
@@ -826,6 +826,12 @@ static int arm_smmu_init_domain_context(struct iommu_domain *domain,
 	if (smmu_domain->smmu)
 		goto out_unlock;
 
+	/* We're bypassing these SIDs, so don't allocate an actual context */
+	if (domain->type == IOMMU_DOMAIN_DMA) {
+		smmu_domain->smmu = smmu;
+		goto out_unlock;
+	}
+
 	/*
 	 * Mapping the requested stage onto what we support is surprisingly
 	 * complicated, mainly because the spec allows S1+S2 SMMUs without
@@ -948,7 +954,7 @@ static void arm_smmu_destroy_domain_context(struct iommu_domain *domain)
 	void __iomem *cb_base;
 	int irq;
 
-	if (!smmu)
+	if (!smmu || domain->type == IOMMU_DOMAIN_DMA)
 		return;
 
 	/*
Signature · 1 line
2.7.3.dirty
#8 lore raw

PATCH 1/1 iommu/arm-smmu: Don't allocate resources for bypass domains

Hi Will,

Quoted 10 lines · Will Deacon
Quoted 6 lines · Robin Murphy

Until we get fully plumbed into of_iommu_configure, our default IOMMU_DOMAIN_DMA domains just bypass translation. Since we achieve that by leaving the stream table entries set to bypass instead of pointing at a translation context, the context bank we allocate for the domain is completely wasted. Context banks are typically a rather limited resource, so don't hog ones we don't need.

Eric, does this resolve your remaining passthrough regressions when applied on top of my patch?

Yes it does. Thank you for the fixes.

Best Regards

Eric

Quoted 38 lines

Will

Quoted 35 lines
---
 drivers/iommu/arm-smmu.c | 8 +++++++-
 1 file changed, 7 insertions(+), 1 deletion(-)
drivers/iommu/arm-smmu.c +7 -1
index 5158feb..7c39ac4 100644
@@ -826,6 +826,12 @@ static int arm_smmu_init_domain_context(struct iommu_domain *domain,
 	if (smmu_domain->smmu)
 		goto out_unlock;
 
+	/* We're bypassing these SIDs, so don't allocate an actual context */
+	if (domain->type == IOMMU_DOMAIN_DMA) {
+		smmu_domain->smmu = smmu;
+		goto out_unlock;
+	}
+
 	/*
 	 * Mapping the requested stage onto what we support is surprisingly
 	 * complicated, mainly because the spec allows S1+S2 SMMUs without
@@ -948,7 +954,7 @@ static void arm_smmu_destroy_domain_context(struct iommu_domain *domain)
 	void __iomem *cb_base;
 	int irq;
 
-	if (!smmu)
+	if (!smmu || domain->type == IOMMU_DOMAIN_DMA)
 		return;
 
 	/*
Signature · 1 line
2.7.3.dirty
#9 lore raw

PATCH 1/1 iommu/arm-smmu: Don't allocate resources for bypass domains

In reply to Robin Murphy

Hi Robin,

Quoted 7 lines · Robin Murphy

Until we get fully plumbed into of_iommu_configure, our default IOMMU_DOMAIN_DMA domains just bypass translation. Since we achieve that by leaving the stream table entries set to bypass instead of pointing at a translation context, the context bank we allocate for the domain is completely wasted. Context banks are typically a rather limited resource, so don't hog ones we don't need.

Thanks for this fix. I recovered the ability to assign more than VFs on Overdrive HW.

Best Regards

Eric

Quoted 33 lines
---
 drivers/iommu/arm-smmu.c | 8 +++++++-
 1 file changed, 7 insertions(+), 1 deletion(-)
drivers/iommu/arm-smmu.c +7 -1
index 5158feb..7c39ac4 100644
@@ -826,6 +826,12 @@ static int arm_smmu_init_domain_context(struct iommu_domain *domain,
 	if (smmu_domain->smmu)
 		goto out_unlock;
 
+	/* We're bypassing these SIDs, so don't allocate an actual context */
+	if (domain->type == IOMMU_DOMAIN_DMA) {
+		smmu_domain->smmu = smmu;
+		goto out_unlock;
+	}
+
 	/*
 	 * Mapping the requested stage onto what we support is surprisingly
 	 * complicated, mainly because the spec allows S1+S2 SMMUs without
@@ -948,7 +954,7 @@ static void arm_smmu_destroy_domain_context(struct iommu_domain *domain)
 	void __iomem *cb_base;
 	int irq;
 
-	if (!smmu)
+	if (!smmu || domain->type == IOMMU_DOMAIN_DMA)
 		return;
 
 	/*
#10 lore raw

PATCH 1/1 iommu/arm-smmu: Fix stream-match conflict with IOMMU_DOMAIN_DMA

In reply to Will Deacon

Hi Will,

Quoted 11 lines · Will Deacon

Commit cbf8277ef456 ("iommu/arm-smmu: Treat IOMMU_DOMAIN_DMA as bypass for now") ignores requests to attach a device to the default domain since, without IOMMU-basked DMA ops available everywhere, the default domain will just lead to unexpected transaction faults being reported.

Unfortunately, the way this was implemented on SMMUv2 causes a regression with VFIO PCI device passthrough under KVM on AMD Seattle. On this system, the host controller device is associated with both a pci_dev *and* a platform_device, and can therefore end up with duplicate SMR entries, resulting in a stream-match conflict at runtime.

Quoted 5 lines

This patch amends the original fix so that attaching to IOMMU_DOMAIN_DMA is rejected even before configuring the SMRs. This restores the old behaviour for now, but we'll need to look at handing host controllers specially when we come to supporting the default domain fully.

Best Regards

Eric

Quoted 38 lines
---
 drivers/iommu/arm-smmu.c | 14 ++++++++------
 1 file changed, 8 insertions(+), 6 deletions(-)
drivers/iommu/arm-smmu.c +8 -6
index e933679a3266..2f186d22477f 100644
@@ -1098,18 +1098,20 @@ static int arm_smmu_domain_add_master(struct arm_smmu_domain *smmu_domain,
 	struct arm_smmu_device *smmu = smmu_domain->smmu;
 	void __iomem *gr0_base = ARM_SMMU_GR0(smmu);
 
-	/* Devices in an IOMMU group may already be configured */
-	ret = arm_smmu_master_configure_smrs(smmu, cfg);
-	if (ret)
-		return ret == -EEXIST ? 0 : ret;
-
 	/*
 	 * FIXME: This won't be needed once we have IOMMU-backed DMA ops
-	 * for all devices behind the SMMU.
+	 * for all devices behind the SMMU. Note that we need to take
+	 * care configuring SMRs for devices both a platform_device and
+	 * and a PCI device (i.e. a PCI host controller)
 	 */
 	if (smmu_domain->domain.type == IOMMU_DOMAIN_DMA)
 		return 0;
 
+	/* Devices in an IOMMU group may already be configured */
+	ret = arm_smmu_master_configure_smrs(smmu, cfg);
+	if (ret)
+		return ret == -EEXIST ? 0 : ret;
+
 	for (i = 0; i < cfg->num_streamids; ++i) {
 		u32 idx, s2cr;
 
#11 lore raw

PATCH 1/1 iommu/arm-smmu: Fix stream-match conflict with IOMMU_DOMAIN_DMA

Quoted 13 lines · Eric Auger

Hi Will,

Quoted 11 lines · Will Deacon

Commit cbf8277ef456 ("iommu/arm-smmu: Treat IOMMU_DOMAIN_DMA as bypass for now") ignores requests to attach a device to the default domain since, without IOMMU-basked DMA ops available everywhere, the default domain will just lead to unexpected transaction faults being reported.

Unfortunately, the way this was implemented on SMMUv2 causes a regression with VFIO PCI device passthrough under KVM on AMD Seattle. On this system, the host controller device is associated with both a pci_dev *and* a platform_device, and can therefore end up with duplicate SMR entries, resulting in a stream-match conflict at runtime.

Quoted 6 lines
Quoted 5 lines

This patch amends the original fix so that attaching to IOMMU_DOMAIN_DMA is rejected even before configuring the SMRs. This restores the old behaviour for now, but we'll need to look at handing host controllers specially when we come to supporting the default domain fully.

Tested on my LS2085A board too.

Regards,
Yang

Quoted 49 lines

Best Regards

Eric

Quoted 28 lines
---
  drivers/iommu/arm-smmu.c | 14 ++++++++------
  1 file changed, 8 insertions(+), 6 deletions(-)
drivers/iommu/arm-smmu.c +3 -6
index e933679a3266..2f186d22477f 100644
@@ -1098,18 +1098,20 @@ static int arm_smmu_domain_add_master(struct arm_smmu_domain *smmu_domain,
  	struct arm_smmu_device *smmu = smmu_domain->smmu;
  	void __iomem *gr0_base = ARM_SMMU_GR0(smmu);
 
-	/* Devices in an IOMMU group may already be configured */
-	ret = arm_smmu_master_configure_smrs(smmu, cfg);
-	if (ret)
-		return ret == -EEXIST ? 0 : ret;
-
  	/*
  	 * FIXME: This won't be needed once we have IOMMU-backed DMA ops
-	 * for all devices behind the SMMU.
+	 * for all devices behind the SMMU. Note that we need to take
+	 * care configuring SMRs for devices both a platform_device and
+	 * and a PCI device (i.e. a PCI host controller)
  	 */
  	if (smmu_domain->domain.type == IOMMU_DOMAIN_DMA)

drivers/iommu/arm-smmu.c static int arm_smmu_domain_add_master(struct arm_smmu_domain *smmu_domain, · line 1117

Quoted 10 lines
drivers/iommu/arm-smmu.c +5 -0
  		return 0;
 
+	/* Devices in an IOMMU group may already be configured */
+	ret = arm_smmu_master_configure_smrs(smmu, cfg);
+	if (ret)
+		return ret == -EEXIST ? 0 : ret;
+
  	for (i = 0; i < cfg->num_streamids; ++i) {
  		u32 idx, s2cr;
 

_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel at lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel