Groups | Search | Server Info | Keyboard shortcuts | Login | Register [http] [https] [nntp] [nntps]


Groups > linux.kernel > #1253285 > unrolled thread

[PATCH 0/8] iommu: Make core iommu-groups code more generic

Started byJoerg Roedel <joro@8bytes.org>
First post2015-10-22 00:00 +0200
Last post2015-10-22 00:00 +0200
Articles 10 — 2 participants

Back to article view | Back to linux.kernel


Contents

  [PATCH 0/8] iommu: Make core iommu-groups code more generic Joerg Roedel <joro@8bytes.org> - 2015-10-22 00:00 +0200
    [PATCH 3/8] iommu: Add generic_device_group() function Joerg Roedel <joro@8bytes.org> - 2015-10-22 00:00 +0200
    [PATCH 5/8] iommu/fsl: Convert to device_group call-back Joerg Roedel <joro@8bytes.org> - 2015-10-22 00:00 +0200
    [PATCH 2/8] iommu: Export and rename iommu_group_get_for_pci_dev() Joerg Roedel <joro@8bytes.org> - 2015-10-22 00:00 +0200
    [PATCH 7/8] iommu: Remove is_pci_dev() fall-back from iommu_group_get_for_dev Joerg Roedel <joro@8bytes.org> - 2015-10-22 00:00 +0200
    [PATCH 8/8] iommu: Move default domain allocation to iommu_group_get_for_dev() Joerg Roedel <joro@8bytes.org> - 2015-10-22 00:00 +0200
      Re: [PATCH 8/8] iommu: Move default domain allocation to  iommu_group_get_for_dev() Will Deacon <will.deacon@arm.com> - 2015-10-29 19:30 +0100
        Re: [PATCH 8/8] iommu: Move default domain allocation to  iommu_group_get_for_dev() Joerg Roedel <joro@8bytes.org> - 2015-10-30 15:20 +0100
    [PATCH 6/8] iommu/arm-smmu: Switch to device_group call-back Joerg Roedel <joro@8bytes.org> - 2015-10-22 00:00 +0200
    [PATCH 1/8] iommu: Revive device_group iommu-ops call-back Joerg Roedel <joro@8bytes.org> - 2015-10-22 00:00 +0200

#1253285 — [PATCH 0/8] iommu: Make core iommu-groups code more generic

FromJoerg Roedel <joro@8bytes.org>
Date2015-10-22 00:00 +0200
Subject[PATCH 0/8] iommu: Make core iommu-groups code more generic
Message-ID<qm9Am-7mh-3@gated-at.bofh.it>
Hi,

this patch-set makes the core code for managing iommu-groups
more generic by lifting its dependencies on PCI. The core
function iommu_group_get_for_dev() had a hard dev_is_pci()
check in it, followed by PCI specific handling.

This check is removed in favour of the the revived
device_group() iommu-ops call-back. With this call-back an
IOMMU driver can define how the devices it manages are
grouped together. Two functions, one generic and one for PCI
devices, are provided that can be uses as a device_group()
call-back or might be used in such a call-back.

The existing drivers making use of the iommu_group_get_for_dev()
function are converted to this call-back.

	
	Joerg

Joerg Roedel (8):
  iommu: Revive device_group iommu-ops call-back
  iommu: Export and rename iommu_group_get_for_pci_dev()
  iommu: Add generic_device_group() function
  iommu: Add device_group call-back to x86 iommu drivers
  iommu/fsl: Convert to device_group call-back
  iommu/arm-smmu: Switch to device_group call-back
  iommu: Remove is_pci_dev() fall-back from iommu_group_get_for_dev
  iommu: Move default domain allocation to iommu_group_get_for_dev()

 drivers/iommu/amd_iommu.c       |  1 +
 drivers/iommu/arm-smmu-v3.c     |  1 +
 drivers/iommu/arm-smmu.c        | 77 ++++++++++++++++++++++++-----------------
 drivers/iommu/fsl_pamu_domain.c | 41 +++++++++-------------
 drivers/iommu/intel-iommu.c     |  1 +
 drivers/iommu/iommu.c           | 46 +++++++++++++++++-------
 include/linux/iommu.h           |  7 +++-
 7 files changed, 105 insertions(+), 69 deletions(-)

-- 
1.9.1

--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Please read the FAQ at  http://www.tux.org/lkml/

[toc] | [next] | [standalone]


#1253287 — [PATCH 3/8] iommu: Add generic_device_group() function

FromJoerg Roedel <joro@8bytes.org>
Date2015-10-22 00:00 +0200
Subject[PATCH 3/8] iommu: Add generic_device_group() function
Message-ID<qm9An-7mh-15@gated-at.bofh.it>
In reply to#1253285
From: Joerg Roedel <jroedel@suse.de>

This function can be used as a device_group call-back and
just allocates one iommu-group per device.

Signed-off-by: Joerg Roedel <jroedel@suse.de>
---
 drivers/iommu/iommu.c | 15 +++++++++++++++
 include/linux/iommu.h |  2 ++
 2 files changed, 17 insertions(+)

diff --git a/drivers/iommu/iommu.c b/drivers/iommu/iommu.c
index fdea700..a80c9c5 100644
--- a/drivers/iommu/iommu.c
+++ b/drivers/iommu/iommu.c
@@ -728,6 +728,21 @@ static int get_pci_alias_or_group(struct pci_dev *pdev, u16 alias, void *opaque)
 }
 
 /*
+ * Generic device_group call-back function. It just allocates one
+ * iommu-group per device.
+ */
+struct iommu_group *generic_device_group(struct device *dev)
+{
+	struct iommu_group *group;
+
+	group = iommu_group_alloc();
+	if (IS_ERR(group))
+		return NULL;
+
+	return group;
+}
+
+/*
  * Use standard PCI bus topology, isolation features, and DMA alias quirks
  * to find or create an IOMMU group for a device.
  */
diff --git a/include/linux/iommu.h b/include/linux/iommu.h
index 8026e6a..c73824f 100644
--- a/include/linux/iommu.h
+++ b/include/linux/iommu.h
@@ -318,6 +318,8 @@ static inline size_t iommu_map_sg(struct iommu_domain *domain,
 
 /* PCI device grouping function */
 extern struct iommu_group *pci_device_group(struct device *dev);
+/* Generic device grouping function */
+extern struct iommu_group *generic_device_group(struct device *dev);
 
 #else /* CONFIG_IOMMU_API */
 
-- 
1.9.1

--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Please read the FAQ at  http://www.tux.org/lkml/

[toc] | [prev] | [next] | [standalone]


#1253290 — [PATCH 5/8] iommu/fsl: Convert to device_group call-back

FromJoerg Roedel <joro@8bytes.org>
Date2015-10-22 00:00 +0200
Subject[PATCH 5/8] iommu/fsl: Convert to device_group call-back
Message-ID<qm9An-7mh-21@gated-at.bofh.it>
In reply to#1253285
From: Joerg Roedel <jroedel@suse.de>

Convert the fsl pamu driver to make use of the new
device_group call-back.

Cc: Varun Sethi <Varun.Sethi@freescale.com>
Signed-off-by: Joerg Roedel <jroedel@suse.de>
---
 drivers/iommu/fsl_pamu_domain.c | 41 ++++++++++++++++-------------------------
 1 file changed, 16 insertions(+), 25 deletions(-)

diff --git a/drivers/iommu/fsl_pamu_domain.c b/drivers/iommu/fsl_pamu_domain.c
index 1d45293..da0e1e3 100644
--- a/drivers/iommu/fsl_pamu_domain.c
+++ b/drivers/iommu/fsl_pamu_domain.c
@@ -923,7 +923,7 @@ static struct iommu_group *get_pci_device_group(struct pci_dev *pdev)
 	pci_endpt_partioning = check_pci_ctl_endpt_part(pci_ctl);
 	/* We can partition PCIe devices so assign device group to the device */
 	if (pci_endpt_partioning) {
-		group = iommu_group_get_for_dev(&pdev->dev);
+		group = pci_device_group(&pdev->dev);
 
 		/*
 		 * PCIe controller is not a paritionable entity
@@ -956,44 +956,34 @@ static struct iommu_group *get_pci_device_group(struct pci_dev *pdev)
 	return group;
 }
 
-static int fsl_pamu_add_device(struct device *dev)
+static struct iommu_group *fsl_pamu_device_group(struct device *dev)
 {
 	struct iommu_group *group = ERR_PTR(-ENODEV);
-	struct pci_dev *pdev;
-	const u32 *prop;
-	int ret = 0, len;
+	int len;
 
 	/*
 	 * For platform devices we allocate a separate group for
 	 * each of the devices.
 	 */
-	if (dev_is_pci(dev)) {
-		pdev = to_pci_dev(dev);
-		/* Don't create device groups for virtual PCI bridges */
-		if (pdev->subordinate)
-			return 0;
+	if (dev_is_pci(dev))
+		group = get_pci_device_group(to_pci_dev(dev));
+	else if (of_get_property(dev->of_node, "fsl,liodn", &len))
+		group = get_device_iommu_group(dev);
 
-		group = get_pci_device_group(pdev);
+	return group;
+}
 
-	} else {
-		prop = of_get_property(dev->of_node, "fsl,liodn", &len);
-		if (prop)
-			group = get_device_iommu_group(dev);
-	}
+static int fsl_pamu_add_device(struct device *dev)
+{
+	struct iommu_group *group;
 
+	group = iommu_group_get_for_dev(dev);
 	if (IS_ERR(group))
 		return PTR_ERR(group);
 
-	/*
-	 * Check if device has already been added to an iommu group.
-	 * Group could have already been created for a PCI device in
-	 * the iommu_group_get_for_dev path.
-	 */
-	if (!dev->iommu_group)
-		ret = iommu_group_add_device(group, dev);
-
 	iommu_group_put(group);
-	return ret;
+
+	return 0;
 }
 
 static void fsl_pamu_remove_device(struct device *dev)
@@ -1072,6 +1062,7 @@ static const struct iommu_ops fsl_pamu_ops = {
 	.domain_get_attr = fsl_pamu_get_domain_attr,
 	.add_device	= fsl_pamu_add_device,
 	.remove_device	= fsl_pamu_remove_device,
+	.device_group   = fsl_pamu_device_group,
 };
 
 int __init pamu_domain_init(void)
-- 
1.9.1

--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Please read the FAQ at  http://www.tux.org/lkml/

[toc] | [prev] | [next] | [standalone]


#1253294 — [PATCH 2/8] iommu: Export and rename iommu_group_get_for_pci_dev()

FromJoerg Roedel <joro@8bytes.org>
Date2015-10-22 00:00 +0200
Subject[PATCH 2/8] iommu: Export and rename iommu_group_get_for_pci_dev()
Message-ID<qm9An-7mh-29@gated-at.bofh.it>
In reply to#1253285
From: Joerg Roedel <jroedel@suse.de>

Rename that function to pci_device_group() and export it, so
that IOMMU drivers can use it as their device_group
call-back.

Signed-off-by: Joerg Roedel <jroedel@suse.de>
---
 drivers/iommu/iommu.c | 8 ++++++--
 include/linux/iommu.h | 3 +++
 2 files changed, 9 insertions(+), 2 deletions(-)

diff --git a/drivers/iommu/iommu.c b/drivers/iommu/iommu.c
index 5637463..fdea700 100644
--- a/drivers/iommu/iommu.c
+++ b/drivers/iommu/iommu.c
@@ -731,13 +731,17 @@ static int get_pci_alias_or_group(struct pci_dev *pdev, u16 alias, void *opaque)
  * Use standard PCI bus topology, isolation features, and DMA alias quirks
  * to find or create an IOMMU group for a device.
  */
-static struct iommu_group *iommu_group_get_for_pci_dev(struct pci_dev *pdev)
+struct iommu_group *pci_device_group(struct device *dev)
 {
+	struct pci_dev *pdev = to_pci_dev(dev);
 	struct group_for_pci_data data;
 	struct pci_bus *bus;
 	struct iommu_group *group = NULL;
 	u64 devfns[4] = { 0 };
 
+	if (WARN_ON(!dev_is_pci(dev)))
+		return ERR_PTR(-EINVAL);
+
 	/*
 	 * Find the upstream DMA alias for the device.  A device must not
 	 * be aliased due to topology in order to have its own IOMMU group.
@@ -827,7 +831,7 @@ struct iommu_group *iommu_group_get_for_dev(struct device *dev)
 	if (ops && ops->device_group)
 		group = ops->device_group(dev);
 	else if (dev_is_pci(dev))
-		group = iommu_group_get_for_pci_dev(to_pci_dev(dev));
+		group = pci_device_group(dev);
 
 	if (IS_ERR(group))
 		return group;
diff --git a/include/linux/iommu.h b/include/linux/iommu.h
index 5a19952..8026e6a 100644
--- a/include/linux/iommu.h
+++ b/include/linux/iommu.h
@@ -316,6 +316,9 @@ static inline size_t iommu_map_sg(struct iommu_domain *domain,
 	return domain->ops->map_sg(domain, iova, sg, nents, prot);
 }
 
+/* PCI device grouping function */
+extern struct iommu_group *pci_device_group(struct device *dev);
+
 #else /* CONFIG_IOMMU_API */
 
 struct iommu_ops {};
-- 
1.9.1

--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Please read the FAQ at  http://www.tux.org/lkml/

[toc] | [prev] | [next] | [standalone]


#1253295 — [PATCH 7/8] iommu: Remove is_pci_dev() fall-back from iommu_group_get_for_dev

FromJoerg Roedel <joro@8bytes.org>
Date2015-10-22 00:00 +0200
Subject[PATCH 7/8] iommu: Remove is_pci_dev() fall-back from iommu_group_get_for_dev
Message-ID<qm9Ao-7mh-35@gated-at.bofh.it>
In reply to#1253285
From: Joerg Roedel <jroedel@suse.de>

All callers of iommu_group_get_for_dev() provide a
device_group call-back now, so this fall-back is no longer
needed.

Signed-off-by: Joerg Roedel <jroedel@suse.de>
---
 drivers/iommu/iommu.c | 2 --
 1 file changed, 2 deletions(-)

diff --git a/drivers/iommu/iommu.c b/drivers/iommu/iommu.c
index a80c9c5..e2b5526 100644
--- a/drivers/iommu/iommu.c
+++ b/drivers/iommu/iommu.c
@@ -845,8 +845,6 @@ struct iommu_group *iommu_group_get_for_dev(struct device *dev)
 
 	if (ops && ops->device_group)
 		group = ops->device_group(dev);
-	else if (dev_is_pci(dev))
-		group = pci_device_group(dev);
 
 	if (IS_ERR(group))
 		return group;
-- 
1.9.1

--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Please read the FAQ at  http://www.tux.org/lkml/

[toc] | [prev] | [next] | [standalone]


#1253297 — [PATCH 8/8] iommu: Move default domain allocation to iommu_group_get_for_dev()

FromJoerg Roedel <joro@8bytes.org>
Date2015-10-22 00:00 +0200
Subject[PATCH 8/8] iommu: Move default domain allocation to iommu_group_get_for_dev()
Message-ID<qm9Ao-7mh-37@gated-at.bofh.it>
In reply to#1253285
From: Joerg Roedel <jroedel@suse.de>

Now that the iommu core support for iommu groups is not
pci-centric anymore, we can move default domain allocation
to the bus independent iommu_group_get_for_dev() function.

Signed-off-by: Joerg Roedel <jroedel@suse.de>
---
 drivers/iommu/iommu.c | 18 ++++++++++--------
 1 file changed, 10 insertions(+), 8 deletions(-)

diff --git a/drivers/iommu/iommu.c b/drivers/iommu/iommu.c
index e2b5526..abae363 100644
--- a/drivers/iommu/iommu.c
+++ b/drivers/iommu/iommu.c
@@ -810,14 +810,6 @@ struct iommu_group *pci_device_group(struct device *dev)
 	if (IS_ERR(group))
 		return NULL;
 
-	/*
-	 * Try to allocate a default domain - needs support from the
-	 * IOMMU driver.
-	 */
-	group->default_domain = __iommu_domain_alloc(pdev->dev.bus,
-						     IOMMU_DOMAIN_DMA);
-	group->domain = group->default_domain;
-
 	return group;
 }
 
@@ -849,6 +841,16 @@ struct iommu_group *iommu_group_get_for_dev(struct device *dev)
 	if (IS_ERR(group))
 		return group;
 
+	/*
+	 * Try to allocate a default domain - needs support from the
+	 * IOMMU driver.
+	 */
+	if (!group->default_domain) {
+		group->default_domain = __iommu_domain_alloc(dev->bus,
+							     IOMMU_DOMAIN_DMA);
+		group->domain = group->default_domain;
+	}
+
 	ret = iommu_group_add_device(group, dev);
 	if (ret) {
 		iommu_group_put(group);
-- 
1.9.1

--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Please read the FAQ at  http://www.tux.org/lkml/

[toc] | [prev] | [next] | [standalone]


#1258943 — Re: [PATCH 8/8] iommu: Move default domain allocation to iommu_group_get_for_dev()

FromWill Deacon <will.deacon@arm.com>
Date2015-10-29 19:30 +0100
SubjectRe: [PATCH 8/8] iommu: Move default domain allocation to iommu_group_get_for_dev()
Message-ID<qp07v-3Hz-1@gated-at.bofh.it>
In reply to#1253297
Hi Joerg,

Looking at this from an SMMU perspective, I think there's an issue
with attaching to the default domain like this.

On Wed, Oct 21, 2015 at 11:51:43PM +0200, Joerg Roedel wrote:
> From: Joerg Roedel <jroedel@suse.de>
> 
> Now that the iommu core support for iommu groups is not
> pci-centric anymore, we can move default domain allocation
> to the bus independent iommu_group_get_for_dev() function.
> 
> Signed-off-by: Joerg Roedel <jroedel@suse.de>
> ---
>  drivers/iommu/iommu.c | 18 ++++++++++--------
>  1 file changed, 10 insertions(+), 8 deletions(-)
> 
> diff --git a/drivers/iommu/iommu.c b/drivers/iommu/iommu.c
> index e2b5526..abae363 100644
> --- a/drivers/iommu/iommu.c
> +++ b/drivers/iommu/iommu.c
> @@ -810,14 +810,6 @@ struct iommu_group *pci_device_group(struct device *dev)
>  	if (IS_ERR(group))
>  		return NULL;
>  
> -	/*
> -	 * Try to allocate a default domain - needs support from the
> -	 * IOMMU driver.
> -	 */
> -	group->default_domain = __iommu_domain_alloc(pdev->dev.bus,
> -						     IOMMU_DOMAIN_DMA);
> -	group->domain = group->default_domain;
> -
>  	return group;
>  }
>  
> @@ -849,6 +841,16 @@ struct iommu_group *iommu_group_get_for_dev(struct device *dev)
>  	if (IS_ERR(group))
>  		return group;
>  
> +	/*
> +	 * Try to allocate a default domain - needs support from the
> +	 * IOMMU driver.
> +	 */
> +	if (!group->default_domain) {
> +		group->default_domain = __iommu_domain_alloc(dev->bus,
> +							     IOMMU_DOMAIN_DMA);
> +		group->domain = group->default_domain;
> +	}
> +
>  	ret = iommu_group_add_device(group, dev);
>  	if (ret) {
>  		iommu_group_put(group);

The call to iommu_group_get_for_dev in arm_smmu_add_device will end up
calling __iommu_attach_device, since group->domain will now be initialised
by the code above. This means the SMMU driver will see an ->attach_dev
call for a device that is part-way through an ->add_device callback and
will be missing the initialisation necessary for us to idenfity the SMMU
instance to which is corresponds. In fact, the iommudata for the group
won't be initialised at all, so the whole thing will fail afaict.

Note that I haven't actually taken this for a spin, so I could be missing
something.

Will
--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Please read the FAQ at  http://www.tux.org/lkml/

[toc] | [prev] | [next] | [standalone]


#1259522 — Re: [PATCH 8/8] iommu: Move default domain allocation to iommu_group_get_for_dev()

FromJoerg Roedel <joro@8bytes.org>
Date2015-10-30 15:20 +0100
SubjectRe: [PATCH 8/8] iommu: Move default domain allocation to iommu_group_get_for_dev()
Message-ID<qpiHa-6Pg-33@gated-at.bofh.it>
In reply to#1258943
Hi Will,

On Thu, Oct 29, 2015 at 06:22:49PM +0000, Will Deacon wrote:
> The call to iommu_group_get_for_dev in arm_smmu_add_device will end up
> calling __iommu_attach_device, since group->domain will now be initialised
> by the code above. This means the SMMU driver will see an ->attach_dev
> call for a device that is part-way through an ->add_device callback and
> will be missing the initialisation necessary for us to idenfity the SMMU
> instance to which is corresponds. In fact, the iommudata for the group
> won't be initialised at all, so the whole thing will fail afaict.
> 
> Note that I haven't actually taken this for a spin, so I could be missing
> something.

Yeah, I havn't looked at how to convert the ARM-SMMU drivers to default
domains yet, so the issue you describe above is totally possible.

But there is no way to trigger it yet, because your domain_alloc
function can not yet allocate IOMMU_DOMAIN_DMA domains. While converting
the issue must be fixed, of course.

I tested this patch-set on an AMD Seattle system and it worked fine
there.


	Joerg

--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Please read the FAQ at  http://www.tux.org/lkml/

[toc] | [prev] | [next] | [standalone]


#1253299 — [PATCH 6/8] iommu/arm-smmu: Switch to device_group call-back

FromJoerg Roedel <joro@8bytes.org>
Date2015-10-22 00:00 +0200
Subject[PATCH 6/8] iommu/arm-smmu: Switch to device_group call-back
Message-ID<qm9Ao-7mh-45@gated-at.bofh.it>
In reply to#1253285
From: Joerg Roedel <jroedel@suse.de>

This converts the ARM SMMU and the SMMUv3 driver to use the
new device_group call-back.

Cc: Will Deacon <will.deacon@arm.com>
Signed-off-by: Joerg Roedel <jroedel@suse.de>
---
 drivers/iommu/arm-smmu-v3.c |  1 +
 drivers/iommu/arm-smmu.c    | 77 +++++++++++++++++++++++++++------------------
 2 files changed, 47 insertions(+), 31 deletions(-)

diff --git a/drivers/iommu/arm-smmu-v3.c b/drivers/iommu/arm-smmu-v3.c
index 286e890..e9e591c 100644
--- a/drivers/iommu/arm-smmu-v3.c
+++ b/drivers/iommu/arm-smmu-v3.c
@@ -1902,6 +1902,7 @@ static struct iommu_ops arm_smmu_ops = {
 	.iova_to_phys		= arm_smmu_iova_to_phys,
 	.add_device		= arm_smmu_add_device,
 	.remove_device		= arm_smmu_remove_device,
+	.device_group		= pci_device_group,
 	.domain_get_attr	= arm_smmu_domain_get_attr,
 	.domain_set_attr	= arm_smmu_domain_set_attr,
 	.pgsize_bitmap		= -1UL, /* Restricted during device attach */
diff --git a/drivers/iommu/arm-smmu.c b/drivers/iommu/arm-smmu.c
index 48a39df..b4c0629 100644
--- a/drivers/iommu/arm-smmu.c
+++ b/drivers/iommu/arm-smmu.c
@@ -1292,33 +1292,25 @@ static void __arm_smmu_release_pci_iommudata(void *data)
 	kfree(data);
 }
 
-static int arm_smmu_add_pci_device(struct pci_dev *pdev)
+static int arm_smmu_init_pci_device(struct pci_dev *pdev,
+				    struct iommu_group *group)
 {
-	int i, ret;
-	u16 sid;
-	struct iommu_group *group;
 	struct arm_smmu_master_cfg *cfg;
-
-	group = iommu_group_get_for_dev(&pdev->dev);
-	if (IS_ERR(group))
-		return PTR_ERR(group);
+	u16 sid;
+	int i;
 
 	cfg = iommu_group_get_iommudata(group);
 	if (!cfg) {
 		cfg = kzalloc(sizeof(*cfg), GFP_KERNEL);
-		if (!cfg) {
-			ret = -ENOMEM;
-			goto out_put_group;
-		}
+		if (!cfg)
+			return -ENOMEM;
 
 		iommu_group_set_iommudata(group, cfg,
 					  __arm_smmu_release_pci_iommudata);
 	}
 
-	if (cfg->num_streamids >= MAX_MASTER_STREAMIDS) {
-		ret = -ENOSPC;
-		goto out_put_group;
-	}
+	if (cfg->num_streamids >= MAX_MASTER_STREAMIDS)
+		return -ENOSPC;
 
 	/*
 	 * Assume Stream ID == Requester ID for now.
@@ -1334,16 +1326,13 @@ static int arm_smmu_add_pci_device(struct pci_dev *pdev)
 		cfg->streamids[cfg->num_streamids++] = sid;
 
 	return 0;
-out_put_group:
-	iommu_group_put(group);
-	return ret;
 }
 
-static int arm_smmu_add_platform_device(struct device *dev)
+static int arm_smmu_init_platform_device(struct device *dev,
+					 struct iommu_group *group)
 {
-	struct iommu_group *group;
-	struct arm_smmu_master *master;
 	struct arm_smmu_device *smmu = find_smmu_for_device(dev);
+	struct arm_smmu_master *master;
 
 	if (!smmu)
 		return -ENODEV;
@@ -1352,21 +1341,20 @@ static int arm_smmu_add_platform_device(struct device *dev)
 	if (!master)
 		return -ENODEV;
 
-	/* No automatic group creation for platform devices */
-	group = iommu_group_alloc();
-	if (IS_ERR(group))
-		return PTR_ERR(group);
-
 	iommu_group_set_iommudata(group, &master->cfg, NULL);
-	return iommu_group_add_device(group, dev);
+
+	return 0;
 }
 
 static int arm_smmu_add_device(struct device *dev)
 {
-	if (dev_is_pci(dev))
-		return arm_smmu_add_pci_device(to_pci_dev(dev));
+	struct iommu_group *group;
 
-	return arm_smmu_add_platform_device(dev);
+	group = iommu_group_get_for_dev(dev);
+	if (IS_ERR(group))
+		return PTR_ERR(group);
+
+	return 0;
 }
 
 static void arm_smmu_remove_device(struct device *dev)
@@ -1374,6 +1362,32 @@ static void arm_smmu_remove_device(struct device *dev)
 	iommu_group_remove_device(dev);
 }
 
+static struct iommu_group *arm_smmu_device_group(struct device *dev)
+{
+	struct iommu_group *group;
+	int ret;
+
+	if (dev_is_pci(dev))
+		group = pci_device_group(dev);
+	else
+		group = generic_device_group(dev);
+
+	if (IS_ERR(group))
+		return group;
+
+	if (dev_is_pci(dev))
+		ret = arm_smmu_init_pci_device(to_pci_dev(dev), group);
+	else
+		ret = arm_smmu_init_platform_device(dev, group);
+
+	if (ret) {
+		iommu_group_put(group);
+		group = ERR_PTR(ret);
+	}
+
+	return group;
+}
+
 static int arm_smmu_domain_get_attr(struct iommu_domain *domain,
 				    enum iommu_attr attr, void *data)
 {
@@ -1430,6 +1444,7 @@ static struct iommu_ops arm_smmu_ops = {
 	.iova_to_phys		= arm_smmu_iova_to_phys,
 	.add_device		= arm_smmu_add_device,
 	.remove_device		= arm_smmu_remove_device,
+	.device_group		= arm_smmu_device_group,
 	.domain_get_attr	= arm_smmu_domain_get_attr,
 	.domain_set_attr	= arm_smmu_domain_set_attr,
 	.pgsize_bitmap		= -1UL, /* Restricted during device attach */
-- 
1.9.1

--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Please read the FAQ at  http://www.tux.org/lkml/

[toc] | [prev] | [next] | [standalone]


#1253302 — [PATCH 1/8] iommu: Revive device_group iommu-ops call-back

FromJoerg Roedel <joro@8bytes.org>
Date2015-10-22 00:00 +0200
Subject[PATCH 1/8] iommu: Revive device_group iommu-ops call-back
Message-ID<qm9Ao-7mh-49@gated-at.bofh.it>
In reply to#1253285
From: Joerg Roedel <jroedel@suse.de>

That call-back is currently unused, change it into a
call-back function for finding the right IOMMU group for a
device.
This is a first step to remove the hard-coded PCI dependency
in the iommu-group code.

Signed-off-by: Joerg Roedel <jroedel@suse.de>
---
 drivers/iommu/iommu.c | 9 ++++++---
 include/linux/iommu.h | 2 +-
 2 files changed, 7 insertions(+), 4 deletions(-)

diff --git a/drivers/iommu/iommu.c b/drivers/iommu/iommu.c
index 049df49..5637463 100644
--- a/drivers/iommu/iommu.c
+++ b/drivers/iommu/iommu.c
@@ -814,6 +814,7 @@ static struct iommu_group *iommu_group_get_for_pci_dev(struct pci_dev *pdev)
  */
 struct iommu_group *iommu_group_get_for_dev(struct device *dev)
 {
+	const struct iommu_ops *ops = dev->bus->iommu_ops;
 	struct iommu_group *group;
 	int ret;
 
@@ -821,10 +822,12 @@ struct iommu_group *iommu_group_get_for_dev(struct device *dev)
 	if (group)
 		return group;
 
-	if (!dev_is_pci(dev))
-		return ERR_PTR(-EINVAL);
+	group = ERR_PTR(-EINVAL);
 
-	group = iommu_group_get_for_pci_dev(to_pci_dev(dev));
+	if (ops && ops->device_group)
+		group = ops->device_group(dev);
+	else if (dev_is_pci(dev))
+		group = iommu_group_get_for_pci_dev(to_pci_dev(dev));
 
 	if (IS_ERR(group))
 		return group;
diff --git a/include/linux/iommu.h b/include/linux/iommu.h
index f9c1b6d..5a19952 100644
--- a/include/linux/iommu.h
+++ b/include/linux/iommu.h
@@ -167,7 +167,7 @@ struct iommu_ops {
 	phys_addr_t (*iova_to_phys)(struct iommu_domain *domain, dma_addr_t iova);
 	int (*add_device)(struct device *dev);
 	void (*remove_device)(struct device *dev);
-	int (*device_group)(struct device *dev, unsigned int *groupid);
+	struct iommu_group *(*device_group)(struct device *dev);
 	int (*domain_get_attr)(struct iommu_domain *domain,
 			       enum iommu_attr attr, void *data);
 	int (*domain_set_attr)(struct iommu_domain *domain,
-- 
1.9.1

--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Please read the FAQ at  http://www.tux.org/lkml/

[toc] | [prev] | [standalone]


Back to top | Article view | linux.kernel


csiph-web