All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH 00/15] iommu: Move domain allocation into drivers
@ 2015-01-26 23:51 ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA
  Cc: Will Deacon, Kukjin Kim, David Woodhouse, Heiko Stuebner,
	Hiroshi Doyu, Stephen Warren, Thierry Reding, Alexandre Courbot,
	Alex Williamson, Arnd Bergmann,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r,
	linux-samsung-soc-u79uwXL29TY76Z2rM5mHXA,
	linux-rockchip-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r,
	linux-tegra-u79uwXL29TY76Z2rM5mHXA, Joerg Roedel,
	jroedel-l3A5Bk7waGM

From: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>

Hi,

here is patch-set to replace the existing domain_init and
domain_destroy iommu-ops with the new domain_alloc and
domain_free callbacks

The new callbacks move the allocation of iommu domains into
the iommu driver, allowing them to put a generic
iommu_domain struct into their own domain struct. This makes
domain handling in the drivers more cache efficient and
prepares the introduction of default domains in another
patch-set.

While at it, this patch-set also introduces domain types.
These are internal to the iommu core code for now, there are
three of them:

	* DMA-API domains
	* Identity mapped domains
	* Domains unmanaged by the iommu-core, used for
	  iommu-api so that the users can create their own
	  mappings

The patches have been compile tested for x86, ARM and PPC
and runtime tested on x86 (Intel VT-d and AMD IOMMU).

Please review.

Thanks,

	Joerg

Joerg Roedel (15):
  iommu: Introduce domain_alloc and domain_free iommu_ops
  iommu: Introduce iommu domain types
  iommu/amd: Make use of domain_alloc and domain_free
  iommu/vt-d: Make use of domain_alloc and domain_free
  iommu/omap: Make use of domain_alloc and domain_free
  iommu/arm-smmu: Make use of domain_alloc and domain_free
  iommu/exynos: Make use of domain_alloc and domain_free
  iommu/tegra-smmu: Make use of domain_alloc and domain_free
  iommu/tegra-gart: Make use of domain_alloc and domain_free
  iommu/msm: Make use of domain_alloc and domain_free
  iommu/shmobile: Make use of domain_alloc and domain_free
  iommu/ipmmu-vmsa: Make use of domain_alloc and domain_free
  iommu/rockchip: Make use of domain_alloc and domain_free
  iommu/fsl: Make use of domain_alloc and domain_free
  iommu: Remove domain_init and domain_free iommu_ops

 drivers/iommu/amd_iommu.c       | 84 +++++++++++++++++++++------------------
 drivers/iommu/amd_iommu_types.h |  7 ++--
 drivers/iommu/arm-smmu.c        | 46 +++++++++++++---------
 drivers/iommu/exynos-iommu.c    | 87 ++++++++++++++++++++++-------------------
 drivers/iommu/fsl_pamu_domain.c | 60 +++++++++++++++-------------
 drivers/iommu/fsl_pamu_domain.h |  2 +-
 drivers/iommu/intel-iommu.c     | 48 +++++++++++++----------
 drivers/iommu/iommu.c           | 20 ++--------
 drivers/iommu/ipmmu-vmsa.c      | 43 +++++++++++---------
 drivers/iommu/msm_iommu.c       | 73 +++++++++++++++++-----------------
 drivers/iommu/omap-iommu.c      | 49 +++++++++++++----------
 drivers/iommu/rockchip-iommu.c  | 40 +++++++++++--------
 drivers/iommu/shmobile-iommu.c  | 40 +++++++++++--------
 drivers/iommu/tegra-gart.c      | 67 +++++++++++++++++++++----------
 drivers/iommu/tegra-smmu.c      | 41 ++++++++++---------
 include/linux/iommu.h           | 17 ++++++--
 16 files changed, 407 insertions(+), 317 deletions(-)

-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 00/15] iommu: Move domain allocation into drivers
@ 2015-01-26 23:51 ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu
  Cc: Will Deacon, Kukjin Kim, David Woodhouse, Heiko Stuebner,
	Hiroshi Doyu, Stephen Warren, Thierry Reding, Alexandre Courbot,
	Alex Williamson, Arnd Bergmann, linux-kernel, linux-arm-kernel,
	linux-samsung-soc, linux-rockchip, linux-tegra, Joerg Roedel,
	jroedel

From: Joerg Roedel <jroedel@suse.de>

Hi,

here is patch-set to replace the existing domain_init and
domain_destroy iommu-ops with the new domain_alloc and
domain_free callbacks

The new callbacks move the allocation of iommu domains into
the iommu driver, allowing them to put a generic
iommu_domain struct into their own domain struct. This makes
domain handling in the drivers more cache efficient and
prepares the introduction of default domains in another
patch-set.

While at it, this patch-set also introduces domain types.
These are internal to the iommu core code for now, there are
three of them:

	* DMA-API domains
	* Identity mapped domains
	* Domains unmanaged by the iommu-core, used for
	  iommu-api so that the users can create their own
	  mappings

The patches have been compile tested for x86, ARM and PPC
and runtime tested on x86 (Intel VT-d and AMD IOMMU).

Please review.

Thanks,

	Joerg

Joerg Roedel (15):
  iommu: Introduce domain_alloc and domain_free iommu_ops
  iommu: Introduce iommu domain types
  iommu/amd: Make use of domain_alloc and domain_free
  iommu/vt-d: Make use of domain_alloc and domain_free
  iommu/omap: Make use of domain_alloc and domain_free
  iommu/arm-smmu: Make use of domain_alloc and domain_free
  iommu/exynos: Make use of domain_alloc and domain_free
  iommu/tegra-smmu: Make use of domain_alloc and domain_free
  iommu/tegra-gart: Make use of domain_alloc and domain_free
  iommu/msm: Make use of domain_alloc and domain_free
  iommu/shmobile: Make use of domain_alloc and domain_free
  iommu/ipmmu-vmsa: Make use of domain_alloc and domain_free
  iommu/rockchip: Make use of domain_alloc and domain_free
  iommu/fsl: Make use of domain_alloc and domain_free
  iommu: Remove domain_init and domain_free iommu_ops

 drivers/iommu/amd_iommu.c       | 84 +++++++++++++++++++++------------------
 drivers/iommu/amd_iommu_types.h |  7 ++--
 drivers/iommu/arm-smmu.c        | 46 +++++++++++++---------
 drivers/iommu/exynos-iommu.c    | 87 ++++++++++++++++++++++-------------------
 drivers/iommu/fsl_pamu_domain.c | 60 +++++++++++++++-------------
 drivers/iommu/fsl_pamu_domain.h |  2 +-
 drivers/iommu/intel-iommu.c     | 48 +++++++++++++----------
 drivers/iommu/iommu.c           | 20 ++--------
 drivers/iommu/ipmmu-vmsa.c      | 43 +++++++++++---------
 drivers/iommu/msm_iommu.c       | 73 +++++++++++++++++-----------------
 drivers/iommu/omap-iommu.c      | 49 +++++++++++++----------
 drivers/iommu/rockchip-iommu.c  | 40 +++++++++++--------
 drivers/iommu/shmobile-iommu.c  | 40 +++++++++++--------
 drivers/iommu/tegra-gart.c      | 67 +++++++++++++++++++++----------
 drivers/iommu/tegra-smmu.c      | 41 ++++++++++---------
 include/linux/iommu.h           | 17 ++++++--
 16 files changed, 407 insertions(+), 317 deletions(-)

-- 
1.8.4.5


^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 00/15] iommu: Move domain allocation into drivers
@ 2015-01-26 23:51 ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: linux-arm-kernel

From: Joerg Roedel <jroedel@suse.de>

Hi,

here is patch-set to replace the existing domain_init and
domain_destroy iommu-ops with the new domain_alloc and
domain_free callbacks

The new callbacks move the allocation of iommu domains into
the iommu driver, allowing them to put a generic
iommu_domain struct into their own domain struct. This makes
domain handling in the drivers more cache efficient and
prepares the introduction of default domains in another
patch-set.

While at it, this patch-set also introduces domain types.
These are internal to the iommu core code for now, there are
three of them:

	* DMA-API domains
	* Identity mapped domains
	* Domains unmanaged by the iommu-core, used for
	  iommu-api so that the users can create their own
	  mappings

The patches have been compile tested for x86, ARM and PPC
and runtime tested on x86 (Intel VT-d and AMD IOMMU).

Please review.

Thanks,

	Joerg

Joerg Roedel (15):
  iommu: Introduce domain_alloc and domain_free iommu_ops
  iommu: Introduce iommu domain types
  iommu/amd: Make use of domain_alloc and domain_free
  iommu/vt-d: Make use of domain_alloc and domain_free
  iommu/omap: Make use of domain_alloc and domain_free
  iommu/arm-smmu: Make use of domain_alloc and domain_free
  iommu/exynos: Make use of domain_alloc and domain_free
  iommu/tegra-smmu: Make use of domain_alloc and domain_free
  iommu/tegra-gart: Make use of domain_alloc and domain_free
  iommu/msm: Make use of domain_alloc and domain_free
  iommu/shmobile: Make use of domain_alloc and domain_free
  iommu/ipmmu-vmsa: Make use of domain_alloc and domain_free
  iommu/rockchip: Make use of domain_alloc and domain_free
  iommu/fsl: Make use of domain_alloc and domain_free
  iommu: Remove domain_init and domain_free iommu_ops

 drivers/iommu/amd_iommu.c       | 84 +++++++++++++++++++++------------------
 drivers/iommu/amd_iommu_types.h |  7 ++--
 drivers/iommu/arm-smmu.c        | 46 +++++++++++++---------
 drivers/iommu/exynos-iommu.c    | 87 ++++++++++++++++++++++-------------------
 drivers/iommu/fsl_pamu_domain.c | 60 +++++++++++++++-------------
 drivers/iommu/fsl_pamu_domain.h |  2 +-
 drivers/iommu/intel-iommu.c     | 48 +++++++++++++----------
 drivers/iommu/iommu.c           | 20 ++--------
 drivers/iommu/ipmmu-vmsa.c      | 43 +++++++++++---------
 drivers/iommu/msm_iommu.c       | 73 +++++++++++++++++-----------------
 drivers/iommu/omap-iommu.c      | 49 +++++++++++++----------
 drivers/iommu/rockchip-iommu.c  | 40 +++++++++++--------
 drivers/iommu/shmobile-iommu.c  | 40 +++++++++++--------
 drivers/iommu/tegra-gart.c      | 67 +++++++++++++++++++++----------
 drivers/iommu/tegra-smmu.c      | 41 ++++++++++---------
 include/linux/iommu.h           | 17 ++++++--
 16 files changed, 407 insertions(+), 317 deletions(-)

-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 01/15] iommu: Introduce domain_alloc and domain_free iommu_ops
  2015-01-26 23:51 ` Joerg Roedel
  (?)
@ 2015-01-26 23:51     ` Joerg Roedel
  -1 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA
  Cc: Will Deacon, Kukjin Kim, David Woodhouse, Heiko Stuebner,
	Hiroshi Doyu, Stephen Warren, Thierry Reding, Alexandre Courbot,
	Alex Williamson, Arnd Bergmann,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r,
	linux-samsung-soc-u79uwXL29TY76Z2rM5mHXA,
	linux-rockchip-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r,
	linux-tegra-u79uwXL29TY76Z2rM5mHXA, Joerg Roedel,
	jroedel-l3A5Bk7waGM

From: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>

These new call-backs defer the allocation and destruction of
'struct iommu_domain' to the iommu driver. This allows
drivers to embed this struct into their private domain
structures and to get rid of the domain_init and
domain_destroy call-backs when all drivers have been
converted.

Signed-off-by: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>
---
 drivers/iommu/iommu.c | 29 +++++++++++++++++++++--------
 include/linux/iommu.h |  5 +++++
 2 files changed, 26 insertions(+), 8 deletions(-)

diff --git a/drivers/iommu/iommu.c b/drivers/iommu/iommu.c
index f7718d7..684efc0 100644
--- a/drivers/iommu/iommu.c
+++ b/drivers/iommu/iommu.c
@@ -900,26 +900,34 @@ EXPORT_SYMBOL_GPL(iommu_set_fault_handler);
 
 struct iommu_domain *iommu_domain_alloc(struct bus_type *bus)
 {
+	const struct iommu_ops *ops;
 	struct iommu_domain *domain;
-	int ret;
 
 	if (bus == NULL || bus->iommu_ops == NULL)
 		return NULL;
 
-	domain = kzalloc(sizeof(*domain), GFP_KERNEL);
+	ops = bus->iommu_ops;
+
+	if (ops->domain_alloc)
+		domain = ops->domain_alloc();
+	else
+		domain = kzalloc(sizeof(*domain), GFP_KERNEL);
+
 	if (!domain)
 		return NULL;
 
 	domain->ops = bus->iommu_ops;
 
-	ret = domain->ops->domain_init(domain);
-	if (ret)
+	if (ops->domain_init && domain->ops->domain_init(domain))
 		goto out_free;
 
 	return domain;
 
 out_free:
-	kfree(domain);
+	if (ops->domain_free)
+		ops->domain_free(domain);
+	else
+		kfree(domain);
 
 	return NULL;
 }
@@ -927,10 +935,15 @@ EXPORT_SYMBOL_GPL(iommu_domain_alloc);
 
 void iommu_domain_free(struct iommu_domain *domain)
 {
-	if (likely(domain->ops->domain_destroy != NULL))
-		domain->ops->domain_destroy(domain);
+	const struct iommu_ops *ops = domain->ops;
 
-	kfree(domain);
+	if (likely(ops->domain_destroy != NULL))
+		ops->domain_destroy(domain);
+
+	if (ops->domain_free)
+		ops->domain_free(domain);
+	else
+		kfree(domain);
 }
 EXPORT_SYMBOL_GPL(iommu_domain_free);
 
diff --git a/include/linux/iommu.h b/include/linux/iommu.h
index 38daa45..69d1d12 100644
--- a/include/linux/iommu.h
+++ b/include/linux/iommu.h
@@ -115,6 +115,11 @@ struct iommu_ops {
 	bool (*capable)(enum iommu_cap);
 	int (*domain_init)(struct iommu_domain *domain);
 	void (*domain_destroy)(struct iommu_domain *domain);
+
+	/* Domain allocation and freeing by the iommu driver */
+	struct iommu_domain *(*domain_alloc)(void);
+	void (*domain_free)(struct iommu_domain *);
+
 	int (*attach_dev)(struct iommu_domain *domain, struct device *dev);
 	void (*detach_dev)(struct iommu_domain *domain, struct device *dev);
 	int (*map)(struct iommu_domain *domain, unsigned long iova,
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 01/15] iommu: Introduce domain_alloc and domain_free iommu_ops
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu
  Cc: Will Deacon, Kukjin Kim, David Woodhouse, Heiko Stuebner,
	Hiroshi Doyu, Stephen Warren, Thierry Reding, Alexandre Courbot,
	Alex Williamson, Arnd Bergmann, linux-kernel, linux-arm-kernel,
	linux-samsung-soc, linux-rockchip, linux-tegra, Joerg Roedel,
	jroedel

From: Joerg Roedel <jroedel@suse.de>

These new call-backs defer the allocation and destruction of
'struct iommu_domain' to the iommu driver. This allows
drivers to embed this struct into their private domain
structures and to get rid of the domain_init and
domain_destroy call-backs when all drivers have been
converted.

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

diff --git a/drivers/iommu/iommu.c b/drivers/iommu/iommu.c
index f7718d7..684efc0 100644
--- a/drivers/iommu/iommu.c
+++ b/drivers/iommu/iommu.c
@@ -900,26 +900,34 @@ EXPORT_SYMBOL_GPL(iommu_set_fault_handler);
 
 struct iommu_domain *iommu_domain_alloc(struct bus_type *bus)
 {
+	const struct iommu_ops *ops;
 	struct iommu_domain *domain;
-	int ret;
 
 	if (bus == NULL || bus->iommu_ops == NULL)
 		return NULL;
 
-	domain = kzalloc(sizeof(*domain), GFP_KERNEL);
+	ops = bus->iommu_ops;
+
+	if (ops->domain_alloc)
+		domain = ops->domain_alloc();
+	else
+		domain = kzalloc(sizeof(*domain), GFP_KERNEL);
+
 	if (!domain)
 		return NULL;
 
 	domain->ops = bus->iommu_ops;
 
-	ret = domain->ops->domain_init(domain);
-	if (ret)
+	if (ops->domain_init && domain->ops->domain_init(domain))
 		goto out_free;
 
 	return domain;
 
 out_free:
-	kfree(domain);
+	if (ops->domain_free)
+		ops->domain_free(domain);
+	else
+		kfree(domain);
 
 	return NULL;
 }
@@ -927,10 +935,15 @@ EXPORT_SYMBOL_GPL(iommu_domain_alloc);
 
 void iommu_domain_free(struct iommu_domain *domain)
 {
-	if (likely(domain->ops->domain_destroy != NULL))
-		domain->ops->domain_destroy(domain);
+	const struct iommu_ops *ops = domain->ops;
 
-	kfree(domain);
+	if (likely(ops->domain_destroy != NULL))
+		ops->domain_destroy(domain);
+
+	if (ops->domain_free)
+		ops->domain_free(domain);
+	else
+		kfree(domain);
 }
 EXPORT_SYMBOL_GPL(iommu_domain_free);
 
diff --git a/include/linux/iommu.h b/include/linux/iommu.h
index 38daa45..69d1d12 100644
--- a/include/linux/iommu.h
+++ b/include/linux/iommu.h
@@ -115,6 +115,11 @@ struct iommu_ops {
 	bool (*capable)(enum iommu_cap);
 	int (*domain_init)(struct iommu_domain *domain);
 	void (*domain_destroy)(struct iommu_domain *domain);
+
+	/* Domain allocation and freeing by the iommu driver */
+	struct iommu_domain *(*domain_alloc)(void);
+	void (*domain_free)(struct iommu_domain *);
+
 	int (*attach_dev)(struct iommu_domain *domain, struct device *dev);
 	void (*detach_dev)(struct iommu_domain *domain, struct device *dev);
 	int (*map)(struct iommu_domain *domain, unsigned long iova,
-- 
1.8.4.5


^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 01/15] iommu: Introduce domain_alloc and domain_free iommu_ops
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: linux-arm-kernel

From: Joerg Roedel <jroedel@suse.de>

These new call-backs defer the allocation and destruction of
'struct iommu_domain' to the iommu driver. This allows
drivers to embed this struct into their private domain
structures and to get rid of the domain_init and
domain_destroy call-backs when all drivers have been
converted.

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

diff --git a/drivers/iommu/iommu.c b/drivers/iommu/iommu.c
index f7718d7..684efc0 100644
--- a/drivers/iommu/iommu.c
+++ b/drivers/iommu/iommu.c
@@ -900,26 +900,34 @@ EXPORT_SYMBOL_GPL(iommu_set_fault_handler);
 
 struct iommu_domain *iommu_domain_alloc(struct bus_type *bus)
 {
+	const struct iommu_ops *ops;
 	struct iommu_domain *domain;
-	int ret;
 
 	if (bus == NULL || bus->iommu_ops == NULL)
 		return NULL;
 
-	domain = kzalloc(sizeof(*domain), GFP_KERNEL);
+	ops = bus->iommu_ops;
+
+	if (ops->domain_alloc)
+		domain = ops->domain_alloc();
+	else
+		domain = kzalloc(sizeof(*domain), GFP_KERNEL);
+
 	if (!domain)
 		return NULL;
 
 	domain->ops = bus->iommu_ops;
 
-	ret = domain->ops->domain_init(domain);
-	if (ret)
+	if (ops->domain_init && domain->ops->domain_init(domain))
 		goto out_free;
 
 	return domain;
 
 out_free:
-	kfree(domain);
+	if (ops->domain_free)
+		ops->domain_free(domain);
+	else
+		kfree(domain);
 
 	return NULL;
 }
@@ -927,10 +935,15 @@ EXPORT_SYMBOL_GPL(iommu_domain_alloc);
 
 void iommu_domain_free(struct iommu_domain *domain)
 {
-	if (likely(domain->ops->domain_destroy != NULL))
-		domain->ops->domain_destroy(domain);
+	const struct iommu_ops *ops = domain->ops;
 
-	kfree(domain);
+	if (likely(ops->domain_destroy != NULL))
+		ops->domain_destroy(domain);
+
+	if (ops->domain_free)
+		ops->domain_free(domain);
+	else
+		kfree(domain);
 }
 EXPORT_SYMBOL_GPL(iommu_domain_free);
 
diff --git a/include/linux/iommu.h b/include/linux/iommu.h
index 38daa45..69d1d12 100644
--- a/include/linux/iommu.h
+++ b/include/linux/iommu.h
@@ -115,6 +115,11 @@ struct iommu_ops {
 	bool (*capable)(enum iommu_cap);
 	int (*domain_init)(struct iommu_domain *domain);
 	void (*domain_destroy)(struct iommu_domain *domain);
+
+	/* Domain allocation and freeing by the iommu driver */
+	struct iommu_domain *(*domain_alloc)(void);
+	void (*domain_free)(struct iommu_domain *);
+
 	int (*attach_dev)(struct iommu_domain *domain, struct device *dev);
 	void (*detach_dev)(struct iommu_domain *domain, struct device *dev);
 	int (*map)(struct iommu_domain *domain, unsigned long iova,
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 02/15] iommu: Introduce iommu domain types
  2015-01-26 23:51 ` Joerg Roedel
  (?)
@ 2015-01-26 23:51     ` Joerg Roedel
  -1 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA
  Cc: Alexandre Courbot, linux-samsung-soc-u79uwXL29TY76Z2rM5mHXA,
	Heiko Stuebner, Arnd Bergmann, Stephen Warren, Will Deacon,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-rockchip-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Kukjin Kim,
	Thierry Reding, jroedel-l3A5Bk7waGM,
	linux-tegra-u79uwXL29TY76Z2rM5mHXA, David Woodhouse,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r

From: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>

This allows to handle domains differently based on their
type in the future. An IOMMU driver can implement certain
optimizations for DMA-API domains for example.

Signed-off-by: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>
---
 drivers/iommu/iommu.c |  5 +++--
 include/linux/iommu.h | 11 ++++++++++-
 2 files changed, 13 insertions(+), 3 deletions(-)

diff --git a/drivers/iommu/iommu.c b/drivers/iommu/iommu.c
index 684efc0..ab24d77 100644
--- a/drivers/iommu/iommu.c
+++ b/drivers/iommu/iommu.c
@@ -909,14 +909,15 @@ struct iommu_domain *iommu_domain_alloc(struct bus_type *bus)
 	ops = bus->iommu_ops;
 
 	if (ops->domain_alloc)
-		domain = ops->domain_alloc();
+		domain = ops->domain_alloc(IOMMU_DOMAIN_UNMANAGED);
 	else
 		domain = kzalloc(sizeof(*domain), GFP_KERNEL);
 
 	if (!domain)
 		return NULL;
 
-	domain->ops = bus->iommu_ops;
+	domain->ops  = bus->iommu_ops;
+	domain->type = IOMMU_DOMAIN_UNMANAGED;
 
 	if (ops->domain_init && domain->ops->domain_init(domain))
 		goto out_free;
diff --git a/include/linux/iommu.h b/include/linux/iommu.h
index 69d1d12..0b67f65 100644
--- a/include/linux/iommu.h
+++ b/include/linux/iommu.h
@@ -51,7 +51,16 @@ struct iommu_domain_geometry {
 	bool force_aperture;       /* DMA only allowed in mappable range? */
 };
 
+/* This are the possible domain-types */
+enum iommu_domain_type {
+	IOMMU_DOMAIN_DMA,	/* Domain used for DMA-API */
+	IOMMU_DOMAIN_IDENTITY,	/* Identity mapped domain  */
+	IOMMU_DOMAIN_UNMANAGED, /* Domain mappings are managed by a third party
+				   user (like KVM or VFIO) */
+};
+
 struct iommu_domain {
+	enum iommu_domain_type type;
 	const struct iommu_ops *ops;
 	void *priv;
 	iommu_fault_handler_t handler;
@@ -117,7 +126,7 @@ struct iommu_ops {
 	void (*domain_destroy)(struct iommu_domain *domain);
 
 	/* Domain allocation and freeing by the iommu driver */
-	struct iommu_domain *(*domain_alloc)(void);
+	struct iommu_domain *(*domain_alloc)(enum iommu_domain_type);
 	void (*domain_free)(struct iommu_domain *);
 
 	int (*attach_dev)(struct iommu_domain *domain, struct device *dev);
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 02/15] iommu: Introduce iommu domain types
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu
  Cc: Will Deacon, Kukjin Kim, David Woodhouse, Heiko Stuebner,
	Hiroshi Doyu, Stephen Warren, Thierry Reding, Alexandre Courbot,
	Alex Williamson, Arnd Bergmann, linux-kernel, linux-arm-kernel,
	linux-samsung-soc, linux-rockchip, linux-tegra, Joerg Roedel,
	jroedel

From: Joerg Roedel <jroedel@suse.de>

This allows to handle domains differently based on their
type in the future. An IOMMU driver can implement certain
optimizations for DMA-API domains for example.

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

diff --git a/drivers/iommu/iommu.c b/drivers/iommu/iommu.c
index 684efc0..ab24d77 100644
--- a/drivers/iommu/iommu.c
+++ b/drivers/iommu/iommu.c
@@ -909,14 +909,15 @@ struct iommu_domain *iommu_domain_alloc(struct bus_type *bus)
 	ops = bus->iommu_ops;
 
 	if (ops->domain_alloc)
-		domain = ops->domain_alloc();
+		domain = ops->domain_alloc(IOMMU_DOMAIN_UNMANAGED);
 	else
 		domain = kzalloc(sizeof(*domain), GFP_KERNEL);
 
 	if (!domain)
 		return NULL;
 
-	domain->ops = bus->iommu_ops;
+	domain->ops  = bus->iommu_ops;
+	domain->type = IOMMU_DOMAIN_UNMANAGED;
 
 	if (ops->domain_init && domain->ops->domain_init(domain))
 		goto out_free;
diff --git a/include/linux/iommu.h b/include/linux/iommu.h
index 69d1d12..0b67f65 100644
--- a/include/linux/iommu.h
+++ b/include/linux/iommu.h
@@ -51,7 +51,16 @@ struct iommu_domain_geometry {
 	bool force_aperture;       /* DMA only allowed in mappable range? */
 };
 
+/* This are the possible domain-types */
+enum iommu_domain_type {
+	IOMMU_DOMAIN_DMA,	/* Domain used for DMA-API */
+	IOMMU_DOMAIN_IDENTITY,	/* Identity mapped domain  */
+	IOMMU_DOMAIN_UNMANAGED, /* Domain mappings are managed by a third party
+				   user (like KVM or VFIO) */
+};
+
 struct iommu_domain {
+	enum iommu_domain_type type;
 	const struct iommu_ops *ops;
 	void *priv;
 	iommu_fault_handler_t handler;
@@ -117,7 +126,7 @@ struct iommu_ops {
 	void (*domain_destroy)(struct iommu_domain *domain);
 
 	/* Domain allocation and freeing by the iommu driver */
-	struct iommu_domain *(*domain_alloc)(void);
+	struct iommu_domain *(*domain_alloc)(enum iommu_domain_type);
 	void (*domain_free)(struct iommu_domain *);
 
 	int (*attach_dev)(struct iommu_domain *domain, struct device *dev);
-- 
1.8.4.5


^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 02/15] iommu: Introduce iommu domain types
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: linux-arm-kernel

From: Joerg Roedel <jroedel@suse.de>

This allows to handle domains differently based on their
type in the future. An IOMMU driver can implement certain
optimizations for DMA-API domains for example.

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

diff --git a/drivers/iommu/iommu.c b/drivers/iommu/iommu.c
index 684efc0..ab24d77 100644
--- a/drivers/iommu/iommu.c
+++ b/drivers/iommu/iommu.c
@@ -909,14 +909,15 @@ struct iommu_domain *iommu_domain_alloc(struct bus_type *bus)
 	ops = bus->iommu_ops;
 
 	if (ops->domain_alloc)
-		domain = ops->domain_alloc();
+		domain = ops->domain_alloc(IOMMU_DOMAIN_UNMANAGED);
 	else
 		domain = kzalloc(sizeof(*domain), GFP_KERNEL);
 
 	if (!domain)
 		return NULL;
 
-	domain->ops = bus->iommu_ops;
+	domain->ops  = bus->iommu_ops;
+	domain->type = IOMMU_DOMAIN_UNMANAGED;
 
 	if (ops->domain_init && domain->ops->domain_init(domain))
 		goto out_free;
diff --git a/include/linux/iommu.h b/include/linux/iommu.h
index 69d1d12..0b67f65 100644
--- a/include/linux/iommu.h
+++ b/include/linux/iommu.h
@@ -51,7 +51,16 @@ struct iommu_domain_geometry {
 	bool force_aperture;       /* DMA only allowed in mappable range? */
 };
 
+/* This are the possible domain-types */
+enum iommu_domain_type {
+	IOMMU_DOMAIN_DMA,	/* Domain used for DMA-API */
+	IOMMU_DOMAIN_IDENTITY,	/* Identity mapped domain  */
+	IOMMU_DOMAIN_UNMANAGED, /* Domain mappings are managed by a third party
+				   user (like KVM or VFIO) */
+};
+
 struct iommu_domain {
+	enum iommu_domain_type type;
 	const struct iommu_ops *ops;
 	void *priv;
 	iommu_fault_handler_t handler;
@@ -117,7 +126,7 @@ struct iommu_ops {
 	void (*domain_destroy)(struct iommu_domain *domain);
 
 	/* Domain allocation and freeing by the iommu driver */
-	struct iommu_domain *(*domain_alloc)(void);
+	struct iommu_domain *(*domain_alloc)(enum iommu_domain_type);
 	void (*domain_free)(struct iommu_domain *);
 
 	int (*attach_dev)(struct iommu_domain *domain, struct device *dev);
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 03/15] iommu/amd: Make use of domain_alloc and domain_free
  2015-01-26 23:51 ` Joerg Roedel
  (?)
@ 2015-01-26 23:51     ` Joerg Roedel
  -1 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA
  Cc: Alexandre Courbot, linux-samsung-soc-u79uwXL29TY76Z2rM5mHXA,
	Heiko Stuebner, Arnd Bergmann, Stephen Warren, Will Deacon,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-rockchip-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Kukjin Kim,
	Thierry Reding, jroedel-l3A5Bk7waGM,
	linux-tegra-u79uwXL29TY76Z2rM5mHXA, David Woodhouse,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r

From: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>

Implement the new iommu-ops function pointers and remove the
obsolete domain_init and domain_destroy functions.

Signed-off-by: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>
---
 drivers/iommu/amd_iommu.c       | 84 ++++++++++++++++++++++-------------------
 drivers/iommu/amd_iommu_types.h |  7 ++--
 2 files changed, 48 insertions(+), 43 deletions(-)

diff --git a/drivers/iommu/amd_iommu.c b/drivers/iommu/amd_iommu.c
index 9802485..dfcddf5 100644
--- a/drivers/iommu/amd_iommu.c
+++ b/drivers/iommu/amd_iommu.c
@@ -126,6 +126,11 @@ static int __init alloc_passthrough_domain(void);
  *
  ****************************************************************************/
 
+static struct protection_domain *to_pdomain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct protection_domain, domain);
+}
+
 static struct iommu_dev_data *alloc_dev_data(u16 devid)
 {
 	struct iommu_dev_data *dev_data;
@@ -3236,42 +3241,45 @@ static int __init alloc_passthrough_domain(void)
 
 	return 0;
 }
-static int amd_iommu_domain_init(struct iommu_domain *dom)
+
+static struct iommu_domain *amd_iommu_domain_alloc(enum iommu_domain_type type)
 {
-	struct protection_domain *domain;
+	struct protection_domain *pdomain;
 
-	domain = protection_domain_alloc();
-	if (!domain)
-		goto out_free;
+	/* We only support unmanaged domains for now */
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
 
-	domain->mode    = PAGE_MODE_3_LEVEL;
-	domain->pt_root = (void *)get_zeroed_page(GFP_KERNEL);
-	if (!domain->pt_root)
+	pdomain = protection_domain_alloc();
+	if (!pdomain)
 		goto out_free;
 
-	domain->iommu_domain = dom;
-
-	dom->priv = domain;
+	pdomain->mode    = PAGE_MODE_3_LEVEL;
+	pdomain->pt_root = (void *)get_zeroed_page(GFP_KERNEL);
+	if (!pdomain->pt_root)
+		goto out_free;
 
-	dom->geometry.aperture_start = 0;
-	dom->geometry.aperture_end   = ~0ULL;
-	dom->geometry.force_aperture = true;
+	pdomain->domain.geometry.aperture_start = 0;
+	pdomain->domain.geometry.aperture_end   = ~0ULL;
+	pdomain->domain.geometry.force_aperture = true;
 
-	return 0;
+	return &pdomain->domain;
 
 out_free:
-	protection_domain_free(domain);
+	protection_domain_free(pdomain);
 
-	return -ENOMEM;
+	return NULL;
 }
 
-static void amd_iommu_domain_destroy(struct iommu_domain *dom)
+static void amd_iommu_domain_free(struct iommu_domain *dom)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain;
 
-	if (!domain)
+	if (!dom)
 		return;
 
+	domain = to_pdomain(dom);
+
 	if (domain->dev_cnt > 0)
 		cleanup_domain(domain);
 
@@ -3284,8 +3292,6 @@ static void amd_iommu_domain_destroy(struct iommu_domain *dom)
 		free_gcr3_table(domain);
 
 	protection_domain_free(domain);
-
-	dom->priv = NULL;
 }
 
 static void amd_iommu_detach_device(struct iommu_domain *dom,
@@ -3313,7 +3319,7 @@ static void amd_iommu_detach_device(struct iommu_domain *dom,
 static int amd_iommu_attach_device(struct iommu_domain *dom,
 				   struct device *dev)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	struct iommu_dev_data *dev_data;
 	struct amd_iommu *iommu;
 	int ret;
@@ -3340,7 +3346,7 @@ static int amd_iommu_attach_device(struct iommu_domain *dom,
 static int amd_iommu_map(struct iommu_domain *dom, unsigned long iova,
 			 phys_addr_t paddr, size_t page_size, int iommu_prot)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	int prot = 0;
 	int ret;
 
@@ -3362,7 +3368,7 @@ static int amd_iommu_map(struct iommu_domain *dom, unsigned long iova,
 static size_t amd_iommu_unmap(struct iommu_domain *dom, unsigned long iova,
 			   size_t page_size)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	size_t unmap_size;
 
 	if (domain->mode == PAGE_MODE_NONE)
@@ -3380,7 +3386,7 @@ static size_t amd_iommu_unmap(struct iommu_domain *dom, unsigned long iova,
 static phys_addr_t amd_iommu_iova_to_phys(struct iommu_domain *dom,
 					  dma_addr_t iova)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	unsigned long offset_mask;
 	phys_addr_t paddr;
 	u64 *pte, __pte;
@@ -3420,8 +3426,8 @@ static bool amd_iommu_capable(enum iommu_cap cap)
 
 static const struct iommu_ops amd_iommu_ops = {
 	.capable = amd_iommu_capable,
-	.domain_init = amd_iommu_domain_init,
-	.domain_destroy = amd_iommu_domain_destroy,
+	.domain_alloc = amd_iommu_domain_alloc,
+	.domain_free  = amd_iommu_domain_free,
 	.attach_dev = amd_iommu_attach_device,
 	.detach_dev = amd_iommu_detach_device,
 	.map = amd_iommu_map,
@@ -3483,7 +3489,7 @@ EXPORT_SYMBOL(amd_iommu_unregister_ppr_notifier);
 
 void amd_iommu_domain_direct_map(struct iommu_domain *dom)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	unsigned long flags;
 
 	spin_lock_irqsave(&domain->lock, flags);
@@ -3504,7 +3510,7 @@ EXPORT_SYMBOL(amd_iommu_domain_direct_map);
 
 int amd_iommu_domain_enable_v2(struct iommu_domain *dom, int pasids)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	unsigned long flags;
 	int levels, ret;
 
@@ -3616,7 +3622,7 @@ static int __amd_iommu_flush_page(struct protection_domain *domain, int pasid,
 int amd_iommu_flush_page(struct iommu_domain *dom, int pasid,
 			 u64 address)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	unsigned long flags;
 	int ret;
 
@@ -3638,7 +3644,7 @@ static int __amd_iommu_flush_tlb(struct protection_domain *domain, int pasid)
 
 int amd_iommu_flush_tlb(struct iommu_domain *dom, int pasid)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	unsigned long flags;
 	int ret;
 
@@ -3718,7 +3724,7 @@ static int __clear_gcr3(struct protection_domain *domain, int pasid)
 int amd_iommu_domain_set_gcr3(struct iommu_domain *dom, int pasid,
 			      unsigned long cr3)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	unsigned long flags;
 	int ret;
 
@@ -3732,7 +3738,7 @@ EXPORT_SYMBOL(amd_iommu_domain_set_gcr3);
 
 int amd_iommu_domain_clear_gcr3(struct iommu_domain *dom, int pasid)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	unsigned long flags;
 	int ret;
 
@@ -3765,17 +3771,17 @@ EXPORT_SYMBOL(amd_iommu_complete_ppr);
 
 struct iommu_domain *amd_iommu_get_v2_domain(struct pci_dev *pdev)
 {
-	struct protection_domain *domain;
+	struct protection_domain *pdomain;
 
-	domain = get_domain(&pdev->dev);
-	if (IS_ERR(domain))
+	pdomain = get_domain(&pdev->dev);
+	if (IS_ERR(pdomain))
 		return NULL;
 
 	/* Only return IOMMUv2 domains */
-	if (!(domain->flags & PD_IOMMUV2_MASK))
+	if (!(pdomain->flags & PD_IOMMUV2_MASK))
 		return NULL;
 
-	return domain->iommu_domain;
+	return &pdomain->domain;
 }
 EXPORT_SYMBOL(amd_iommu_get_v2_domain);
 
diff --git a/drivers/iommu/amd_iommu_types.h b/drivers/iommu/amd_iommu_types.h
index cec51a8..b029654 100644
--- a/drivers/iommu/amd_iommu_types.h
+++ b/drivers/iommu/amd_iommu_types.h
@@ -400,6 +400,8 @@ struct iommu_domain;
 struct protection_domain {
 	struct list_head list;  /* for list of all protection domains */
 	struct list_head dev_list; /* List of all devices in this domain */
+	struct iommu_domain domain; /* generic domain handle used by
+				       iommu core code */
 	spinlock_t lock;	/* mostly used to lock the page table*/
 	struct mutex api_lock;	/* protect page tables in the iommu-api path */
 	u16 id;			/* the domain id written to the device table */
@@ -411,10 +413,7 @@ struct protection_domain {
 	bool updated;		/* complete domain flush required */
 	unsigned dev_cnt;	/* devices assigned to this domain */
 	unsigned dev_iommu[MAX_IOMMUS]; /* per-IOMMU reference count */
-	void *priv;		/* private data */
-	struct iommu_domain *iommu_domain; /* Pointer to generic
-					      domain structure */
-
+	void *priv;             /* private data */
 };
 
 /*
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 03/15] iommu/amd: Make use of domain_alloc and domain_free
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu
  Cc: Will Deacon, Kukjin Kim, David Woodhouse, Heiko Stuebner,
	Hiroshi Doyu, Stephen Warren, Thierry Reding, Alexandre Courbot,
	Alex Williamson, Arnd Bergmann, linux-kernel, linux-arm-kernel,
	linux-samsung-soc, linux-rockchip, linux-tegra, Joerg Roedel,
	jroedel

From: Joerg Roedel <jroedel@suse.de>

Implement the new iommu-ops function pointers and remove the
obsolete domain_init and domain_destroy functions.

Signed-off-by: Joerg Roedel <jroedel@suse.de>
---
 drivers/iommu/amd_iommu.c       | 84 ++++++++++++++++++++++-------------------
 drivers/iommu/amd_iommu_types.h |  7 ++--
 2 files changed, 48 insertions(+), 43 deletions(-)

diff --git a/drivers/iommu/amd_iommu.c b/drivers/iommu/amd_iommu.c
index 9802485..dfcddf5 100644
--- a/drivers/iommu/amd_iommu.c
+++ b/drivers/iommu/amd_iommu.c
@@ -126,6 +126,11 @@ static int __init alloc_passthrough_domain(void);
  *
  ****************************************************************************/
 
+static struct protection_domain *to_pdomain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct protection_domain, domain);
+}
+
 static struct iommu_dev_data *alloc_dev_data(u16 devid)
 {
 	struct iommu_dev_data *dev_data;
@@ -3236,42 +3241,45 @@ static int __init alloc_passthrough_domain(void)
 
 	return 0;
 }
-static int amd_iommu_domain_init(struct iommu_domain *dom)
+
+static struct iommu_domain *amd_iommu_domain_alloc(enum iommu_domain_type type)
 {
-	struct protection_domain *domain;
+	struct protection_domain *pdomain;
 
-	domain = protection_domain_alloc();
-	if (!domain)
-		goto out_free;
+	/* We only support unmanaged domains for now */
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
 
-	domain->mode    = PAGE_MODE_3_LEVEL;
-	domain->pt_root = (void *)get_zeroed_page(GFP_KERNEL);
-	if (!domain->pt_root)
+	pdomain = protection_domain_alloc();
+	if (!pdomain)
 		goto out_free;
 
-	domain->iommu_domain = dom;
-
-	dom->priv = domain;
+	pdomain->mode    = PAGE_MODE_3_LEVEL;
+	pdomain->pt_root = (void *)get_zeroed_page(GFP_KERNEL);
+	if (!pdomain->pt_root)
+		goto out_free;
 
-	dom->geometry.aperture_start = 0;
-	dom->geometry.aperture_end   = ~0ULL;
-	dom->geometry.force_aperture = true;
+	pdomain->domain.geometry.aperture_start = 0;
+	pdomain->domain.geometry.aperture_end   = ~0ULL;
+	pdomain->domain.geometry.force_aperture = true;
 
-	return 0;
+	return &pdomain->domain;
 
 out_free:
-	protection_domain_free(domain);
+	protection_domain_free(pdomain);
 
-	return -ENOMEM;
+	return NULL;
 }
 
-static void amd_iommu_domain_destroy(struct iommu_domain *dom)
+static void amd_iommu_domain_free(struct iommu_domain *dom)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain;
 
-	if (!domain)
+	if (!dom)
 		return;
 
+	domain = to_pdomain(dom);
+
 	if (domain->dev_cnt > 0)
 		cleanup_domain(domain);
 
@@ -3284,8 +3292,6 @@ static void amd_iommu_domain_destroy(struct iommu_domain *dom)
 		free_gcr3_table(domain);
 
 	protection_domain_free(domain);
-
-	dom->priv = NULL;
 }
 
 static void amd_iommu_detach_device(struct iommu_domain *dom,
@@ -3313,7 +3319,7 @@ static void amd_iommu_detach_device(struct iommu_domain *dom,
 static int amd_iommu_attach_device(struct iommu_domain *dom,
 				   struct device *dev)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	struct iommu_dev_data *dev_data;
 	struct amd_iommu *iommu;
 	int ret;
@@ -3340,7 +3346,7 @@ static int amd_iommu_attach_device(struct iommu_domain *dom,
 static int amd_iommu_map(struct iommu_domain *dom, unsigned long iova,
 			 phys_addr_t paddr, size_t page_size, int iommu_prot)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	int prot = 0;
 	int ret;
 
@@ -3362,7 +3368,7 @@ static int amd_iommu_map(struct iommu_domain *dom, unsigned long iova,
 static size_t amd_iommu_unmap(struct iommu_domain *dom, unsigned long iova,
 			   size_t page_size)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	size_t unmap_size;
 
 	if (domain->mode == PAGE_MODE_NONE)
@@ -3380,7 +3386,7 @@ static size_t amd_iommu_unmap(struct iommu_domain *dom, unsigned long iova,
 static phys_addr_t amd_iommu_iova_to_phys(struct iommu_domain *dom,
 					  dma_addr_t iova)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	unsigned long offset_mask;
 	phys_addr_t paddr;
 	u64 *pte, __pte;
@@ -3420,8 +3426,8 @@ static bool amd_iommu_capable(enum iommu_cap cap)
 
 static const struct iommu_ops amd_iommu_ops = {
 	.capable = amd_iommu_capable,
-	.domain_init = amd_iommu_domain_init,
-	.domain_destroy = amd_iommu_domain_destroy,
+	.domain_alloc = amd_iommu_domain_alloc,
+	.domain_free  = amd_iommu_domain_free,
 	.attach_dev = amd_iommu_attach_device,
 	.detach_dev = amd_iommu_detach_device,
 	.map = amd_iommu_map,
@@ -3483,7 +3489,7 @@ EXPORT_SYMBOL(amd_iommu_unregister_ppr_notifier);
 
 void amd_iommu_domain_direct_map(struct iommu_domain *dom)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	unsigned long flags;
 
 	spin_lock_irqsave(&domain->lock, flags);
@@ -3504,7 +3510,7 @@ EXPORT_SYMBOL(amd_iommu_domain_direct_map);
 
 int amd_iommu_domain_enable_v2(struct iommu_domain *dom, int pasids)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	unsigned long flags;
 	int levels, ret;
 
@@ -3616,7 +3622,7 @@ static int __amd_iommu_flush_page(struct protection_domain *domain, int pasid,
 int amd_iommu_flush_page(struct iommu_domain *dom, int pasid,
 			 u64 address)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	unsigned long flags;
 	int ret;
 
@@ -3638,7 +3644,7 @@ static int __amd_iommu_flush_tlb(struct protection_domain *domain, int pasid)
 
 int amd_iommu_flush_tlb(struct iommu_domain *dom, int pasid)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	unsigned long flags;
 	int ret;
 
@@ -3718,7 +3724,7 @@ static int __clear_gcr3(struct protection_domain *domain, int pasid)
 int amd_iommu_domain_set_gcr3(struct iommu_domain *dom, int pasid,
 			      unsigned long cr3)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	unsigned long flags;
 	int ret;
 
@@ -3732,7 +3738,7 @@ EXPORT_SYMBOL(amd_iommu_domain_set_gcr3);
 
 int amd_iommu_domain_clear_gcr3(struct iommu_domain *dom, int pasid)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	unsigned long flags;
 	int ret;
 
@@ -3765,17 +3771,17 @@ EXPORT_SYMBOL(amd_iommu_complete_ppr);
 
 struct iommu_domain *amd_iommu_get_v2_domain(struct pci_dev *pdev)
 {
-	struct protection_domain *domain;
+	struct protection_domain *pdomain;
 
-	domain = get_domain(&pdev->dev);
-	if (IS_ERR(domain))
+	pdomain = get_domain(&pdev->dev);
+	if (IS_ERR(pdomain))
 		return NULL;
 
 	/* Only return IOMMUv2 domains */
-	if (!(domain->flags & PD_IOMMUV2_MASK))
+	if (!(pdomain->flags & PD_IOMMUV2_MASK))
 		return NULL;
 
-	return domain->iommu_domain;
+	return &pdomain->domain;
 }
 EXPORT_SYMBOL(amd_iommu_get_v2_domain);
 
diff --git a/drivers/iommu/amd_iommu_types.h b/drivers/iommu/amd_iommu_types.h
index cec51a8..b029654 100644
--- a/drivers/iommu/amd_iommu_types.h
+++ b/drivers/iommu/amd_iommu_types.h
@@ -400,6 +400,8 @@ struct iommu_domain;
 struct protection_domain {
 	struct list_head list;  /* for list of all protection domains */
 	struct list_head dev_list; /* List of all devices in this domain */
+	struct iommu_domain domain; /* generic domain handle used by
+				       iommu core code */
 	spinlock_t lock;	/* mostly used to lock the page table*/
 	struct mutex api_lock;	/* protect page tables in the iommu-api path */
 	u16 id;			/* the domain id written to the device table */
@@ -411,10 +413,7 @@ struct protection_domain {
 	bool updated;		/* complete domain flush required */
 	unsigned dev_cnt;	/* devices assigned to this domain */
 	unsigned dev_iommu[MAX_IOMMUS]; /* per-IOMMU reference count */
-	void *priv;		/* private data */
-	struct iommu_domain *iommu_domain; /* Pointer to generic
-					      domain structure */
-
+	void *priv;             /* private data */
 };
 
 /*
-- 
1.8.4.5


^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 03/15] iommu/amd: Make use of domain_alloc and domain_free
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: linux-arm-kernel

From: Joerg Roedel <jroedel@suse.de>

Implement the new iommu-ops function pointers and remove the
obsolete domain_init and domain_destroy functions.

Signed-off-by: Joerg Roedel <jroedel@suse.de>
---
 drivers/iommu/amd_iommu.c       | 84 ++++++++++++++++++++++-------------------
 drivers/iommu/amd_iommu_types.h |  7 ++--
 2 files changed, 48 insertions(+), 43 deletions(-)

diff --git a/drivers/iommu/amd_iommu.c b/drivers/iommu/amd_iommu.c
index 9802485..dfcddf5 100644
--- a/drivers/iommu/amd_iommu.c
+++ b/drivers/iommu/amd_iommu.c
@@ -126,6 +126,11 @@ static int __init alloc_passthrough_domain(void);
  *
  ****************************************************************************/
 
+static struct protection_domain *to_pdomain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct protection_domain, domain);
+}
+
 static struct iommu_dev_data *alloc_dev_data(u16 devid)
 {
 	struct iommu_dev_data *dev_data;
@@ -3236,42 +3241,45 @@ static int __init alloc_passthrough_domain(void)
 
 	return 0;
 }
-static int amd_iommu_domain_init(struct iommu_domain *dom)
+
+static struct iommu_domain *amd_iommu_domain_alloc(enum iommu_domain_type type)
 {
-	struct protection_domain *domain;
+	struct protection_domain *pdomain;
 
-	domain = protection_domain_alloc();
-	if (!domain)
-		goto out_free;
+	/* We only support unmanaged domains for now */
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
 
-	domain->mode    = PAGE_MODE_3_LEVEL;
-	domain->pt_root = (void *)get_zeroed_page(GFP_KERNEL);
-	if (!domain->pt_root)
+	pdomain = protection_domain_alloc();
+	if (!pdomain)
 		goto out_free;
 
-	domain->iommu_domain = dom;
-
-	dom->priv = domain;
+	pdomain->mode    = PAGE_MODE_3_LEVEL;
+	pdomain->pt_root = (void *)get_zeroed_page(GFP_KERNEL);
+	if (!pdomain->pt_root)
+		goto out_free;
 
-	dom->geometry.aperture_start = 0;
-	dom->geometry.aperture_end   = ~0ULL;
-	dom->geometry.force_aperture = true;
+	pdomain->domain.geometry.aperture_start = 0;
+	pdomain->domain.geometry.aperture_end   = ~0ULL;
+	pdomain->domain.geometry.force_aperture = true;
 
-	return 0;
+	return &pdomain->domain;
 
 out_free:
-	protection_domain_free(domain);
+	protection_domain_free(pdomain);
 
-	return -ENOMEM;
+	return NULL;
 }
 
-static void amd_iommu_domain_destroy(struct iommu_domain *dom)
+static void amd_iommu_domain_free(struct iommu_domain *dom)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain;
 
-	if (!domain)
+	if (!dom)
 		return;
 
+	domain = to_pdomain(dom);
+
 	if (domain->dev_cnt > 0)
 		cleanup_domain(domain);
 
@@ -3284,8 +3292,6 @@ static void amd_iommu_domain_destroy(struct iommu_domain *dom)
 		free_gcr3_table(domain);
 
 	protection_domain_free(domain);
-
-	dom->priv = NULL;
 }
 
 static void amd_iommu_detach_device(struct iommu_domain *dom,
@@ -3313,7 +3319,7 @@ static void amd_iommu_detach_device(struct iommu_domain *dom,
 static int amd_iommu_attach_device(struct iommu_domain *dom,
 				   struct device *dev)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	struct iommu_dev_data *dev_data;
 	struct amd_iommu *iommu;
 	int ret;
@@ -3340,7 +3346,7 @@ static int amd_iommu_attach_device(struct iommu_domain *dom,
 static int amd_iommu_map(struct iommu_domain *dom, unsigned long iova,
 			 phys_addr_t paddr, size_t page_size, int iommu_prot)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	int prot = 0;
 	int ret;
 
@@ -3362,7 +3368,7 @@ static int amd_iommu_map(struct iommu_domain *dom, unsigned long iova,
 static size_t amd_iommu_unmap(struct iommu_domain *dom, unsigned long iova,
 			   size_t page_size)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	size_t unmap_size;
 
 	if (domain->mode == PAGE_MODE_NONE)
@@ -3380,7 +3386,7 @@ static size_t amd_iommu_unmap(struct iommu_domain *dom, unsigned long iova,
 static phys_addr_t amd_iommu_iova_to_phys(struct iommu_domain *dom,
 					  dma_addr_t iova)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	unsigned long offset_mask;
 	phys_addr_t paddr;
 	u64 *pte, __pte;
@@ -3420,8 +3426,8 @@ static bool amd_iommu_capable(enum iommu_cap cap)
 
 static const struct iommu_ops amd_iommu_ops = {
 	.capable = amd_iommu_capable,
-	.domain_init = amd_iommu_domain_init,
-	.domain_destroy = amd_iommu_domain_destroy,
+	.domain_alloc = amd_iommu_domain_alloc,
+	.domain_free  = amd_iommu_domain_free,
 	.attach_dev = amd_iommu_attach_device,
 	.detach_dev = amd_iommu_detach_device,
 	.map = amd_iommu_map,
@@ -3483,7 +3489,7 @@ EXPORT_SYMBOL(amd_iommu_unregister_ppr_notifier);
 
 void amd_iommu_domain_direct_map(struct iommu_domain *dom)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	unsigned long flags;
 
 	spin_lock_irqsave(&domain->lock, flags);
@@ -3504,7 +3510,7 @@ EXPORT_SYMBOL(amd_iommu_domain_direct_map);
 
 int amd_iommu_domain_enable_v2(struct iommu_domain *dom, int pasids)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	unsigned long flags;
 	int levels, ret;
 
@@ -3616,7 +3622,7 @@ static int __amd_iommu_flush_page(struct protection_domain *domain, int pasid,
 int amd_iommu_flush_page(struct iommu_domain *dom, int pasid,
 			 u64 address)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	unsigned long flags;
 	int ret;
 
@@ -3638,7 +3644,7 @@ static int __amd_iommu_flush_tlb(struct protection_domain *domain, int pasid)
 
 int amd_iommu_flush_tlb(struct iommu_domain *dom, int pasid)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	unsigned long flags;
 	int ret;
 
@@ -3718,7 +3724,7 @@ static int __clear_gcr3(struct protection_domain *domain, int pasid)
 int amd_iommu_domain_set_gcr3(struct iommu_domain *dom, int pasid,
 			      unsigned long cr3)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	unsigned long flags;
 	int ret;
 
@@ -3732,7 +3738,7 @@ EXPORT_SYMBOL(amd_iommu_domain_set_gcr3);
 
 int amd_iommu_domain_clear_gcr3(struct iommu_domain *dom, int pasid)
 {
-	struct protection_domain *domain = dom->priv;
+	struct protection_domain *domain = to_pdomain(dom);
 	unsigned long flags;
 	int ret;
 
@@ -3765,17 +3771,17 @@ EXPORT_SYMBOL(amd_iommu_complete_ppr);
 
 struct iommu_domain *amd_iommu_get_v2_domain(struct pci_dev *pdev)
 {
-	struct protection_domain *domain;
+	struct protection_domain *pdomain;
 
-	domain = get_domain(&pdev->dev);
-	if (IS_ERR(domain))
+	pdomain = get_domain(&pdev->dev);
+	if (IS_ERR(pdomain))
 		return NULL;
 
 	/* Only return IOMMUv2 domains */
-	if (!(domain->flags & PD_IOMMUV2_MASK))
+	if (!(pdomain->flags & PD_IOMMUV2_MASK))
 		return NULL;
 
-	return domain->iommu_domain;
+	return &pdomain->domain;
 }
 EXPORT_SYMBOL(amd_iommu_get_v2_domain);
 
diff --git a/drivers/iommu/amd_iommu_types.h b/drivers/iommu/amd_iommu_types.h
index cec51a8..b029654 100644
--- a/drivers/iommu/amd_iommu_types.h
+++ b/drivers/iommu/amd_iommu_types.h
@@ -400,6 +400,8 @@ struct iommu_domain;
 struct protection_domain {
 	struct list_head list;  /* for list of all protection domains */
 	struct list_head dev_list; /* List of all devices in this domain */
+	struct iommu_domain domain; /* generic domain handle used by
+				       iommu core code */
 	spinlock_t lock;	/* mostly used to lock the page table*/
 	struct mutex api_lock;	/* protect page tables in the iommu-api path */
 	u16 id;			/* the domain id written to the device table */
@@ -411,10 +413,7 @@ struct protection_domain {
 	bool updated;		/* complete domain flush required */
 	unsigned dev_cnt;	/* devices assigned to this domain */
 	unsigned dev_iommu[MAX_IOMMUS]; /* per-IOMMU reference count */
-	void *priv;		/* private data */
-	struct iommu_domain *iommu_domain; /* Pointer to generic
-					      domain structure */
-
+	void *priv;             /* private data */
 };
 
 /*
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 04/15] iommu/vt-d: Make use of domain_alloc and domain_free
  2015-01-26 23:51 ` Joerg Roedel
  (?)
@ 2015-01-26 23:51     ` Joerg Roedel
  -1 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA
  Cc: Alexandre Courbot, linux-samsung-soc-u79uwXL29TY76Z2rM5mHXA,
	Heiko Stuebner, Arnd Bergmann, Stephen Warren, Will Deacon,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-rockchip-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Kukjin Kim,
	Thierry Reding, jroedel-l3A5Bk7waGM,
	linux-tegra-u79uwXL29TY76Z2rM5mHXA, David Woodhouse,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r

From: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>

Get rid of domain_init and domain_destroy and implement
domain_alloc/domain_free instead.

Signed-off-by: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>
---
 drivers/iommu/intel-iommu.c | 48 ++++++++++++++++++++++++++-------------------
 1 file changed, 28 insertions(+), 20 deletions(-)

diff --git a/drivers/iommu/intel-iommu.c b/drivers/iommu/intel-iommu.c
index 40dfbc0..f3e979f 100644
--- a/drivers/iommu/intel-iommu.c
+++ b/drivers/iommu/intel-iommu.c
@@ -336,7 +336,7 @@ struct dmar_domain {
 	DECLARE_BITMAP(iommu_bmp, DMAR_UNITS_SUPPORTED);
 					/* bitmap of iommus this domain uses*/
 
-	struct list_head devices; 	/* all devices' list */
+	struct list_head devices;	/* all devices' list */
 	struct iova_domain iovad;	/* iova's that belong to this domain */
 
 	struct dma_pte	*pgd;		/* virtual address */
@@ -355,6 +355,9 @@ struct dmar_domain {
 					   2 == 1GiB, 3 == 512GiB, 4 == 1TiB */
 	spinlock_t	iommu_lock;	/* protect iommu set in domain */
 	u64		max_addr;	/* maximum mapped address */
+
+	struct iommu_domain domain;	/* generic domain data structure for
+					   iommu core */
 };
 
 /* PCI domain-device relationship */
@@ -446,6 +449,12 @@ static LIST_HEAD(device_domain_list);
 
 static const struct iommu_ops intel_iommu_ops;
 
+/* Convert generic 'struct iommu_domain to private struct dmar_domain */
+static struct dmar_domain *to_dmar_domain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct dmar_domain, domain);
+}
+
 static int __init intel_iommu_setup(char *str)
 {
 	if (!str)
@@ -4363,44 +4372,45 @@ static int md_domain_init(struct dmar_domain *domain, int guest_width)
 	return 0;
 }
 
-static int intel_iommu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *intel_iommu_domain_alloc(enum iommu_domain_type type)
 {
 	struct dmar_domain *dmar_domain;
+	struct iommu_domain *domain;
+
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
 
 	dmar_domain = alloc_domain(DOMAIN_FLAG_VIRTUAL_MACHINE);
 	if (!dmar_domain) {
 		printk(KERN_ERR
 			"intel_iommu_domain_init: dmar_domain == NULL\n");
-		return -ENOMEM;
+		return NULL;
 	}
 	if (md_domain_init(dmar_domain, DEFAULT_DOMAIN_ADDRESS_WIDTH)) {
 		printk(KERN_ERR
 			"intel_iommu_domain_init() failed\n");
 		domain_exit(dmar_domain);
-		return -ENOMEM;
+		return NULL;
 	}
 	domain_update_iommu_cap(dmar_domain);
-	domain->priv = dmar_domain;
 
+	domain = &dmar_domain->domain;
 	domain->geometry.aperture_start = 0;
 	domain->geometry.aperture_end   = __DOMAIN_MAX_ADDR(dmar_domain->gaw);
 	domain->geometry.force_aperture = true;
 
-	return 0;
+	return domain;
 }
 
-static void intel_iommu_domain_destroy(struct iommu_domain *domain)
+static void intel_iommu_domain_free(struct iommu_domain *domain)
 {
-	struct dmar_domain *dmar_domain = domain->priv;
-
-	domain->priv = NULL;
-	domain_exit(dmar_domain);
+	domain_exit(to_dmar_domain(domain));
 }
 
 static int intel_iommu_attach_device(struct iommu_domain *domain,
 				     struct device *dev)
 {
-	struct dmar_domain *dmar_domain = domain->priv;
+	struct dmar_domain *dmar_domain = to_dmar_domain(domain);
 	struct intel_iommu *iommu;
 	int addr_width;
 	u8 bus, devfn;
@@ -4465,16 +4475,14 @@ static int intel_iommu_attach_device(struct iommu_domain *domain,
 static void intel_iommu_detach_device(struct iommu_domain *domain,
 				      struct device *dev)
 {
-	struct dmar_domain *dmar_domain = domain->priv;
-
-	domain_remove_one_dev_info(dmar_domain, dev);
+	domain_remove_one_dev_info(to_dmar_domain(domain), dev);
 }
 
 static int intel_iommu_map(struct iommu_domain *domain,
 			   unsigned long iova, phys_addr_t hpa,
 			   size_t size, int iommu_prot)
 {
-	struct dmar_domain *dmar_domain = domain->priv;
+	struct dmar_domain *dmar_domain = to_dmar_domain(domain);
 	u64 max_addr;
 	int prot = 0;
 	int ret;
@@ -4511,7 +4519,7 @@ static int intel_iommu_map(struct iommu_domain *domain,
 static size_t intel_iommu_unmap(struct iommu_domain *domain,
 				unsigned long iova, size_t size)
 {
-	struct dmar_domain *dmar_domain = domain->priv;
+	struct dmar_domain *dmar_domain = to_dmar_domain(domain);
 	struct page *freelist = NULL;
 	struct intel_iommu *iommu;
 	unsigned long start_pfn, last_pfn;
@@ -4559,7 +4567,7 @@ static size_t intel_iommu_unmap(struct iommu_domain *domain,
 static phys_addr_t intel_iommu_iova_to_phys(struct iommu_domain *domain,
 					    dma_addr_t iova)
 {
-	struct dmar_domain *dmar_domain = domain->priv;
+	struct dmar_domain *dmar_domain = to_dmar_domain(domain);
 	struct dma_pte *pte;
 	int level = 0;
 	u64 phys = 0;
@@ -4618,8 +4626,8 @@ static void intel_iommu_remove_device(struct device *dev)
 
 static const struct iommu_ops intel_iommu_ops = {
 	.capable	= intel_iommu_capable,
-	.domain_init	= intel_iommu_domain_init,
-	.domain_destroy = intel_iommu_domain_destroy,
+	.domain_alloc	= intel_iommu_domain_alloc,
+	.domain_free	= intel_iommu_domain_free,
 	.attach_dev	= intel_iommu_attach_device,
 	.detach_dev	= intel_iommu_detach_device,
 	.map		= intel_iommu_map,
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 04/15] iommu/vt-d: Make use of domain_alloc and domain_free
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu
  Cc: Will Deacon, Kukjin Kim, David Woodhouse, Heiko Stuebner,
	Hiroshi Doyu, Stephen Warren, Thierry Reding, Alexandre Courbot,
	Alex Williamson, Arnd Bergmann, linux-kernel, linux-arm-kernel,
	linux-samsung-soc, linux-rockchip, linux-tegra, Joerg Roedel,
	jroedel

From: Joerg Roedel <jroedel@suse.de>

Get rid of domain_init and domain_destroy and implement
domain_alloc/domain_free instead.

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

diff --git a/drivers/iommu/intel-iommu.c b/drivers/iommu/intel-iommu.c
index 40dfbc0..f3e979f 100644
--- a/drivers/iommu/intel-iommu.c
+++ b/drivers/iommu/intel-iommu.c
@@ -336,7 +336,7 @@ struct dmar_domain {
 	DECLARE_BITMAP(iommu_bmp, DMAR_UNITS_SUPPORTED);
 					/* bitmap of iommus this domain uses*/
 
-	struct list_head devices; 	/* all devices' list */
+	struct list_head devices;	/* all devices' list */
 	struct iova_domain iovad;	/* iova's that belong to this domain */
 
 	struct dma_pte	*pgd;		/* virtual address */
@@ -355,6 +355,9 @@ struct dmar_domain {
 					   2 == 1GiB, 3 == 512GiB, 4 == 1TiB */
 	spinlock_t	iommu_lock;	/* protect iommu set in domain */
 	u64		max_addr;	/* maximum mapped address */
+
+	struct iommu_domain domain;	/* generic domain data structure for
+					   iommu core */
 };
 
 /* PCI domain-device relationship */
@@ -446,6 +449,12 @@ static LIST_HEAD(device_domain_list);
 
 static const struct iommu_ops intel_iommu_ops;
 
+/* Convert generic 'struct iommu_domain to private struct dmar_domain */
+static struct dmar_domain *to_dmar_domain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct dmar_domain, domain);
+}
+
 static int __init intel_iommu_setup(char *str)
 {
 	if (!str)
@@ -4363,44 +4372,45 @@ static int md_domain_init(struct dmar_domain *domain, int guest_width)
 	return 0;
 }
 
-static int intel_iommu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *intel_iommu_domain_alloc(enum iommu_domain_type type)
 {
 	struct dmar_domain *dmar_domain;
+	struct iommu_domain *domain;
+
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
 
 	dmar_domain = alloc_domain(DOMAIN_FLAG_VIRTUAL_MACHINE);
 	if (!dmar_domain) {
 		printk(KERN_ERR
 			"intel_iommu_domain_init: dmar_domain == NULL\n");
-		return -ENOMEM;
+		return NULL;
 	}
 	if (md_domain_init(dmar_domain, DEFAULT_DOMAIN_ADDRESS_WIDTH)) {
 		printk(KERN_ERR
 			"intel_iommu_domain_init() failed\n");
 		domain_exit(dmar_domain);
-		return -ENOMEM;
+		return NULL;
 	}
 	domain_update_iommu_cap(dmar_domain);
-	domain->priv = dmar_domain;
 
+	domain = &dmar_domain->domain;
 	domain->geometry.aperture_start = 0;
 	domain->geometry.aperture_end   = __DOMAIN_MAX_ADDR(dmar_domain->gaw);
 	domain->geometry.force_aperture = true;
 
-	return 0;
+	return domain;
 }
 
-static void intel_iommu_domain_destroy(struct iommu_domain *domain)
+static void intel_iommu_domain_free(struct iommu_domain *domain)
 {
-	struct dmar_domain *dmar_domain = domain->priv;
-
-	domain->priv = NULL;
-	domain_exit(dmar_domain);
+	domain_exit(to_dmar_domain(domain));
 }
 
 static int intel_iommu_attach_device(struct iommu_domain *domain,
 				     struct device *dev)
 {
-	struct dmar_domain *dmar_domain = domain->priv;
+	struct dmar_domain *dmar_domain = to_dmar_domain(domain);
 	struct intel_iommu *iommu;
 	int addr_width;
 	u8 bus, devfn;
@@ -4465,16 +4475,14 @@ static int intel_iommu_attach_device(struct iommu_domain *domain,
 static void intel_iommu_detach_device(struct iommu_domain *domain,
 				      struct device *dev)
 {
-	struct dmar_domain *dmar_domain = domain->priv;
-
-	domain_remove_one_dev_info(dmar_domain, dev);
+	domain_remove_one_dev_info(to_dmar_domain(domain), dev);
 }
 
 static int intel_iommu_map(struct iommu_domain *domain,
 			   unsigned long iova, phys_addr_t hpa,
 			   size_t size, int iommu_prot)
 {
-	struct dmar_domain *dmar_domain = domain->priv;
+	struct dmar_domain *dmar_domain = to_dmar_domain(domain);
 	u64 max_addr;
 	int prot = 0;
 	int ret;
@@ -4511,7 +4519,7 @@ static int intel_iommu_map(struct iommu_domain *domain,
 static size_t intel_iommu_unmap(struct iommu_domain *domain,
 				unsigned long iova, size_t size)
 {
-	struct dmar_domain *dmar_domain = domain->priv;
+	struct dmar_domain *dmar_domain = to_dmar_domain(domain);
 	struct page *freelist = NULL;
 	struct intel_iommu *iommu;
 	unsigned long start_pfn, last_pfn;
@@ -4559,7 +4567,7 @@ static size_t intel_iommu_unmap(struct iommu_domain *domain,
 static phys_addr_t intel_iommu_iova_to_phys(struct iommu_domain *domain,
 					    dma_addr_t iova)
 {
-	struct dmar_domain *dmar_domain = domain->priv;
+	struct dmar_domain *dmar_domain = to_dmar_domain(domain);
 	struct dma_pte *pte;
 	int level = 0;
 	u64 phys = 0;
@@ -4618,8 +4626,8 @@ static void intel_iommu_remove_device(struct device *dev)
 
 static const struct iommu_ops intel_iommu_ops = {
 	.capable	= intel_iommu_capable,
-	.domain_init	= intel_iommu_domain_init,
-	.domain_destroy = intel_iommu_domain_destroy,
+	.domain_alloc	= intel_iommu_domain_alloc,
+	.domain_free	= intel_iommu_domain_free,
 	.attach_dev	= intel_iommu_attach_device,
 	.detach_dev	= intel_iommu_detach_device,
 	.map		= intel_iommu_map,
-- 
1.8.4.5


^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 04/15] iommu/vt-d: Make use of domain_alloc and domain_free
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: linux-arm-kernel

From: Joerg Roedel <jroedel@suse.de>

Get rid of domain_init and domain_destroy and implement
domain_alloc/domain_free instead.

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

diff --git a/drivers/iommu/intel-iommu.c b/drivers/iommu/intel-iommu.c
index 40dfbc0..f3e979f 100644
--- a/drivers/iommu/intel-iommu.c
+++ b/drivers/iommu/intel-iommu.c
@@ -336,7 +336,7 @@ struct dmar_domain {
 	DECLARE_BITMAP(iommu_bmp, DMAR_UNITS_SUPPORTED);
 					/* bitmap of iommus this domain uses*/
 
-	struct list_head devices; 	/* all devices' list */
+	struct list_head devices;	/* all devices' list */
 	struct iova_domain iovad;	/* iova's that belong to this domain */
 
 	struct dma_pte	*pgd;		/* virtual address */
@@ -355,6 +355,9 @@ struct dmar_domain {
 					   2 == 1GiB, 3 == 512GiB, 4 == 1TiB */
 	spinlock_t	iommu_lock;	/* protect iommu set in domain */
 	u64		max_addr;	/* maximum mapped address */
+
+	struct iommu_domain domain;	/* generic domain data structure for
+					   iommu core */
 };
 
 /* PCI domain-device relationship */
@@ -446,6 +449,12 @@ static LIST_HEAD(device_domain_list);
 
 static const struct iommu_ops intel_iommu_ops;
 
+/* Convert generic 'struct iommu_domain to private struct dmar_domain */
+static struct dmar_domain *to_dmar_domain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct dmar_domain, domain);
+}
+
 static int __init intel_iommu_setup(char *str)
 {
 	if (!str)
@@ -4363,44 +4372,45 @@ static int md_domain_init(struct dmar_domain *domain, int guest_width)
 	return 0;
 }
 
-static int intel_iommu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *intel_iommu_domain_alloc(enum iommu_domain_type type)
 {
 	struct dmar_domain *dmar_domain;
+	struct iommu_domain *domain;
+
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
 
 	dmar_domain = alloc_domain(DOMAIN_FLAG_VIRTUAL_MACHINE);
 	if (!dmar_domain) {
 		printk(KERN_ERR
 			"intel_iommu_domain_init: dmar_domain == NULL\n");
-		return -ENOMEM;
+		return NULL;
 	}
 	if (md_domain_init(dmar_domain, DEFAULT_DOMAIN_ADDRESS_WIDTH)) {
 		printk(KERN_ERR
 			"intel_iommu_domain_init() failed\n");
 		domain_exit(dmar_domain);
-		return -ENOMEM;
+		return NULL;
 	}
 	domain_update_iommu_cap(dmar_domain);
-	domain->priv = dmar_domain;
 
+	domain = &dmar_domain->domain;
 	domain->geometry.aperture_start = 0;
 	domain->geometry.aperture_end   = __DOMAIN_MAX_ADDR(dmar_domain->gaw);
 	domain->geometry.force_aperture = true;
 
-	return 0;
+	return domain;
 }
 
-static void intel_iommu_domain_destroy(struct iommu_domain *domain)
+static void intel_iommu_domain_free(struct iommu_domain *domain)
 {
-	struct dmar_domain *dmar_domain = domain->priv;
-
-	domain->priv = NULL;
-	domain_exit(dmar_domain);
+	domain_exit(to_dmar_domain(domain));
 }
 
 static int intel_iommu_attach_device(struct iommu_domain *domain,
 				     struct device *dev)
 {
-	struct dmar_domain *dmar_domain = domain->priv;
+	struct dmar_domain *dmar_domain = to_dmar_domain(domain);
 	struct intel_iommu *iommu;
 	int addr_width;
 	u8 bus, devfn;
@@ -4465,16 +4475,14 @@ static int intel_iommu_attach_device(struct iommu_domain *domain,
 static void intel_iommu_detach_device(struct iommu_domain *domain,
 				      struct device *dev)
 {
-	struct dmar_domain *dmar_domain = domain->priv;
-
-	domain_remove_one_dev_info(dmar_domain, dev);
+	domain_remove_one_dev_info(to_dmar_domain(domain), dev);
 }
 
 static int intel_iommu_map(struct iommu_domain *domain,
 			   unsigned long iova, phys_addr_t hpa,
 			   size_t size, int iommu_prot)
 {
-	struct dmar_domain *dmar_domain = domain->priv;
+	struct dmar_domain *dmar_domain = to_dmar_domain(domain);
 	u64 max_addr;
 	int prot = 0;
 	int ret;
@@ -4511,7 +4519,7 @@ static int intel_iommu_map(struct iommu_domain *domain,
 static size_t intel_iommu_unmap(struct iommu_domain *domain,
 				unsigned long iova, size_t size)
 {
-	struct dmar_domain *dmar_domain = domain->priv;
+	struct dmar_domain *dmar_domain = to_dmar_domain(domain);
 	struct page *freelist = NULL;
 	struct intel_iommu *iommu;
 	unsigned long start_pfn, last_pfn;
@@ -4559,7 +4567,7 @@ static size_t intel_iommu_unmap(struct iommu_domain *domain,
 static phys_addr_t intel_iommu_iova_to_phys(struct iommu_domain *domain,
 					    dma_addr_t iova)
 {
-	struct dmar_domain *dmar_domain = domain->priv;
+	struct dmar_domain *dmar_domain = to_dmar_domain(domain);
 	struct dma_pte *pte;
 	int level = 0;
 	u64 phys = 0;
@@ -4618,8 +4626,8 @@ static void intel_iommu_remove_device(struct device *dev)
 
 static const struct iommu_ops intel_iommu_ops = {
 	.capable	= intel_iommu_capable,
-	.domain_init	= intel_iommu_domain_init,
-	.domain_destroy = intel_iommu_domain_destroy,
+	.domain_alloc	= intel_iommu_domain_alloc,
+	.domain_free	= intel_iommu_domain_free,
 	.attach_dev	= intel_iommu_attach_device,
 	.detach_dev	= intel_iommu_detach_device,
 	.map		= intel_iommu_map,
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 05/15] iommu/omap: Make use of domain_alloc and domain_free
  2015-01-26 23:51 ` Joerg Roedel
  (?)
@ 2015-01-26 23:51     ` Joerg Roedel
  -1 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA
  Cc: Alexandre Courbot, linux-samsung-soc-u79uwXL29TY76Z2rM5mHXA,
	Heiko Stuebner, Arnd Bergmann, Stephen Warren, Will Deacon,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-rockchip-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Kukjin Kim,
	Thierry Reding, jroedel-l3A5Bk7waGM,
	linux-tegra-u79uwXL29TY76Z2rM5mHXA, David Woodhouse,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r

From: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>

Implement the new domain_alloc and domain_free call-backs
and remove the old domain_init/destroy ones.

Signed-off-by: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>
---
 drivers/iommu/omap-iommu.c | 49 +++++++++++++++++++++++++++-------------------
 1 file changed, 29 insertions(+), 20 deletions(-)

diff --git a/drivers/iommu/omap-iommu.c b/drivers/iommu/omap-iommu.c
index f59f857..f10af50 100644
--- a/drivers/iommu/omap-iommu.c
+++ b/drivers/iommu/omap-iommu.c
@@ -59,6 +59,7 @@ struct omap_iommu_domain {
 	struct omap_iommu *iommu_dev;
 	struct device *dev;
 	spinlock_t lock;
+	struct iommu_domain domain;
 };
 
 #define MMU_LOCK_BASE_SHIFT	10
@@ -80,6 +81,15 @@ static struct platform_driver omap_iommu_driver;
 static struct kmem_cache *iopte_cachep;
 
 /**
+ * to_omap_domain - Get struct omap_iommu_domain from generic iommu_domain
+ * @dom:	generic iommu domain handle
+ **/
+static struct omap_iommu_domain *to_omap_domain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct omap_iommu_domain, domain);
+}
+
+/**
  * omap_iommu_save_ctx - Save registers for pm off-mode support
  * @dev:	client device
  **/
@@ -901,7 +911,7 @@ static irqreturn_t iommu_fault_handler(int irq, void *data)
 	u32 *iopgd, *iopte;
 	struct omap_iommu *obj = data;
 	struct iommu_domain *domain = obj->domain;
-	struct omap_iommu_domain *omap_domain = domain->priv;
+	struct omap_iommu_domain *omap_domain = to_omap_domain(domain);
 
 	if (!omap_domain->iommu_dev)
 		return IRQ_NONE;
@@ -1113,7 +1123,7 @@ static u32 iotlb_init_entry(struct iotlb_entry *e, u32 da, u32 pa, int pgsz)
 static int omap_iommu_map(struct iommu_domain *domain, unsigned long da,
 			 phys_addr_t pa, size_t bytes, int prot)
 {
-	struct omap_iommu_domain *omap_domain = domain->priv;
+	struct omap_iommu_domain *omap_domain = to_omap_domain(domain);
 	struct omap_iommu *oiommu = omap_domain->iommu_dev;
 	struct device *dev = oiommu->dev;
 	struct iotlb_entry e;
@@ -1140,7 +1150,7 @@ static int omap_iommu_map(struct iommu_domain *domain, unsigned long da,
 static size_t omap_iommu_unmap(struct iommu_domain *domain, unsigned long da,
 			    size_t size)
 {
-	struct omap_iommu_domain *omap_domain = domain->priv;
+	struct omap_iommu_domain *omap_domain = to_omap_domain(domain);
 	struct omap_iommu *oiommu = omap_domain->iommu_dev;
 	struct device *dev = oiommu->dev;
 
@@ -1152,7 +1162,7 @@ static size_t omap_iommu_unmap(struct iommu_domain *domain, unsigned long da,
 static int
 omap_iommu_attach_dev(struct iommu_domain *domain, struct device *dev)
 {
-	struct omap_iommu_domain *omap_domain = domain->priv;
+	struct omap_iommu_domain *omap_domain = to_omap_domain(domain);
 	struct omap_iommu *oiommu;
 	struct omap_iommu_arch_data *arch_data = dev->archdata.iommu;
 	int ret = 0;
@@ -1212,17 +1222,20 @@ static void _omap_iommu_detach_dev(struct omap_iommu_domain *omap_domain,
 static void omap_iommu_detach_dev(struct iommu_domain *domain,
 				 struct device *dev)
 {
-	struct omap_iommu_domain *omap_domain = domain->priv;
+	struct omap_iommu_domain *omap_domain = to_omap_domain(domain);
 
 	spin_lock(&omap_domain->lock);
 	_omap_iommu_detach_dev(omap_domain, dev);
 	spin_unlock(&omap_domain->lock);
 }
 
-static int omap_iommu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *omap_iommu_domain_alloc(enum iommu_domain_type type)
 {
 	struct omap_iommu_domain *omap_domain;
 
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
+
 	omap_domain = kzalloc(sizeof(*omap_domain), GFP_KERNEL);
 	if (!omap_domain) {
 		pr_err("kzalloc failed\n");
@@ -1244,25 +1257,21 @@ static int omap_iommu_domain_init(struct iommu_domain *domain)
 	clean_dcache_area(omap_domain->pgtable, IOPGD_TABLE_SIZE);
 	spin_lock_init(&omap_domain->lock);
 
-	domain->priv = omap_domain;
+	omap_domain->domain.geometry.aperture_start = 0;
+	omap_domain->domain.geometry.aperture_end   = (1ULL << 32) - 1;
+	omap_domain->domain.geometry.force_aperture = true;
 
-	domain->geometry.aperture_start = 0;
-	domain->geometry.aperture_end   = (1ULL << 32) - 1;
-	domain->geometry.force_aperture = true;
-
-	return 0;
+	return &omap_domain->domain;
 
 fail_nomem:
 	kfree(omap_domain);
 out:
-	return -ENOMEM;
+	return NULL;
 }
 
-static void omap_iommu_domain_destroy(struct iommu_domain *domain)
+static void omap_iommu_domain_free(struct iommu_domain *domain)
 {
-	struct omap_iommu_domain *omap_domain = domain->priv;
-
-	domain->priv = NULL;
+	struct omap_iommu_domain *omap_domain = to_omap_domain(domain);
 
 	/*
 	 * An iommu device is still attached
@@ -1278,7 +1287,7 @@ static void omap_iommu_domain_destroy(struct iommu_domain *domain)
 static phys_addr_t omap_iommu_iova_to_phys(struct iommu_domain *domain,
 					  dma_addr_t da)
 {
-	struct omap_iommu_domain *omap_domain = domain->priv;
+	struct omap_iommu_domain *omap_domain = to_omap_domain(domain);
 	struct omap_iommu *oiommu = omap_domain->iommu_dev;
 	struct device *dev = oiommu->dev;
 	u32 *pgd, *pte;
@@ -1358,8 +1367,8 @@ static void omap_iommu_remove_device(struct device *dev)
 }
 
 static const struct iommu_ops omap_iommu_ops = {
-	.domain_init	= omap_iommu_domain_init,
-	.domain_destroy	= omap_iommu_domain_destroy,
+	.domain_alloc	= omap_iommu_domain_alloc,
+	.domain_free	= omap_iommu_domain_free,
 	.attach_dev	= omap_iommu_attach_dev,
 	.detach_dev	= omap_iommu_detach_dev,
 	.map		= omap_iommu_map,
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 05/15] iommu/omap: Make use of domain_alloc and domain_free
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu
  Cc: Will Deacon, Kukjin Kim, David Woodhouse, Heiko Stuebner,
	Hiroshi Doyu, Stephen Warren, Thierry Reding, Alexandre Courbot,
	Alex Williamson, Arnd Bergmann, linux-kernel, linux-arm-kernel,
	linux-samsung-soc, linux-rockchip, linux-tegra, Joerg Roedel,
	jroedel

From: Joerg Roedel <jroedel@suse.de>

Implement the new domain_alloc and domain_free call-backs
and remove the old domain_init/destroy ones.

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

diff --git a/drivers/iommu/omap-iommu.c b/drivers/iommu/omap-iommu.c
index f59f857..f10af50 100644
--- a/drivers/iommu/omap-iommu.c
+++ b/drivers/iommu/omap-iommu.c
@@ -59,6 +59,7 @@ struct omap_iommu_domain {
 	struct omap_iommu *iommu_dev;
 	struct device *dev;
 	spinlock_t lock;
+	struct iommu_domain domain;
 };
 
 #define MMU_LOCK_BASE_SHIFT	10
@@ -80,6 +81,15 @@ static struct platform_driver omap_iommu_driver;
 static struct kmem_cache *iopte_cachep;
 
 /**
+ * to_omap_domain - Get struct omap_iommu_domain from generic iommu_domain
+ * @dom:	generic iommu domain handle
+ **/
+static struct omap_iommu_domain *to_omap_domain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct omap_iommu_domain, domain);
+}
+
+/**
  * omap_iommu_save_ctx - Save registers for pm off-mode support
  * @dev:	client device
  **/
@@ -901,7 +911,7 @@ static irqreturn_t iommu_fault_handler(int irq, void *data)
 	u32 *iopgd, *iopte;
 	struct omap_iommu *obj = data;
 	struct iommu_domain *domain = obj->domain;
-	struct omap_iommu_domain *omap_domain = domain->priv;
+	struct omap_iommu_domain *omap_domain = to_omap_domain(domain);
 
 	if (!omap_domain->iommu_dev)
 		return IRQ_NONE;
@@ -1113,7 +1123,7 @@ static u32 iotlb_init_entry(struct iotlb_entry *e, u32 da, u32 pa, int pgsz)
 static int omap_iommu_map(struct iommu_domain *domain, unsigned long da,
 			 phys_addr_t pa, size_t bytes, int prot)
 {
-	struct omap_iommu_domain *omap_domain = domain->priv;
+	struct omap_iommu_domain *omap_domain = to_omap_domain(domain);
 	struct omap_iommu *oiommu = omap_domain->iommu_dev;
 	struct device *dev = oiommu->dev;
 	struct iotlb_entry e;
@@ -1140,7 +1150,7 @@ static int omap_iommu_map(struct iommu_domain *domain, unsigned long da,
 static size_t omap_iommu_unmap(struct iommu_domain *domain, unsigned long da,
 			    size_t size)
 {
-	struct omap_iommu_domain *omap_domain = domain->priv;
+	struct omap_iommu_domain *omap_domain = to_omap_domain(domain);
 	struct omap_iommu *oiommu = omap_domain->iommu_dev;
 	struct device *dev = oiommu->dev;
 
@@ -1152,7 +1162,7 @@ static size_t omap_iommu_unmap(struct iommu_domain *domain, unsigned long da,
 static int
 omap_iommu_attach_dev(struct iommu_domain *domain, struct device *dev)
 {
-	struct omap_iommu_domain *omap_domain = domain->priv;
+	struct omap_iommu_domain *omap_domain = to_omap_domain(domain);
 	struct omap_iommu *oiommu;
 	struct omap_iommu_arch_data *arch_data = dev->archdata.iommu;
 	int ret = 0;
@@ -1212,17 +1222,20 @@ static void _omap_iommu_detach_dev(struct omap_iommu_domain *omap_domain,
 static void omap_iommu_detach_dev(struct iommu_domain *domain,
 				 struct device *dev)
 {
-	struct omap_iommu_domain *omap_domain = domain->priv;
+	struct omap_iommu_domain *omap_domain = to_omap_domain(domain);
 
 	spin_lock(&omap_domain->lock);
 	_omap_iommu_detach_dev(omap_domain, dev);
 	spin_unlock(&omap_domain->lock);
 }
 
-static int omap_iommu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *omap_iommu_domain_alloc(enum iommu_domain_type type)
 {
 	struct omap_iommu_domain *omap_domain;
 
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
+
 	omap_domain = kzalloc(sizeof(*omap_domain), GFP_KERNEL);
 	if (!omap_domain) {
 		pr_err("kzalloc failed\n");
@@ -1244,25 +1257,21 @@ static int omap_iommu_domain_init(struct iommu_domain *domain)
 	clean_dcache_area(omap_domain->pgtable, IOPGD_TABLE_SIZE);
 	spin_lock_init(&omap_domain->lock);
 
-	domain->priv = omap_domain;
+	omap_domain->domain.geometry.aperture_start = 0;
+	omap_domain->domain.geometry.aperture_end   = (1ULL << 32) - 1;
+	omap_domain->domain.geometry.force_aperture = true;
 
-	domain->geometry.aperture_start = 0;
-	domain->geometry.aperture_end   = (1ULL << 32) - 1;
-	domain->geometry.force_aperture = true;
-
-	return 0;
+	return &omap_domain->domain;
 
 fail_nomem:
 	kfree(omap_domain);
 out:
-	return -ENOMEM;
+	return NULL;
 }
 
-static void omap_iommu_domain_destroy(struct iommu_domain *domain)
+static void omap_iommu_domain_free(struct iommu_domain *domain)
 {
-	struct omap_iommu_domain *omap_domain = domain->priv;
-
-	domain->priv = NULL;
+	struct omap_iommu_domain *omap_domain = to_omap_domain(domain);
 
 	/*
 	 * An iommu device is still attached
@@ -1278,7 +1287,7 @@ static void omap_iommu_domain_destroy(struct iommu_domain *domain)
 static phys_addr_t omap_iommu_iova_to_phys(struct iommu_domain *domain,
 					  dma_addr_t da)
 {
-	struct omap_iommu_domain *omap_domain = domain->priv;
+	struct omap_iommu_domain *omap_domain = to_omap_domain(domain);
 	struct omap_iommu *oiommu = omap_domain->iommu_dev;
 	struct device *dev = oiommu->dev;
 	u32 *pgd, *pte;
@@ -1358,8 +1367,8 @@ static void omap_iommu_remove_device(struct device *dev)
 }
 
 static const struct iommu_ops omap_iommu_ops = {
-	.domain_init	= omap_iommu_domain_init,
-	.domain_destroy	= omap_iommu_domain_destroy,
+	.domain_alloc	= omap_iommu_domain_alloc,
+	.domain_free	= omap_iommu_domain_free,
 	.attach_dev	= omap_iommu_attach_dev,
 	.detach_dev	= omap_iommu_detach_dev,
 	.map		= omap_iommu_map,
-- 
1.8.4.5


^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 05/15] iommu/omap: Make use of domain_alloc and domain_free
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: linux-arm-kernel

From: Joerg Roedel <jroedel@suse.de>

Implement the new domain_alloc and domain_free call-backs
and remove the old domain_init/destroy ones.

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

diff --git a/drivers/iommu/omap-iommu.c b/drivers/iommu/omap-iommu.c
index f59f857..f10af50 100644
--- a/drivers/iommu/omap-iommu.c
+++ b/drivers/iommu/omap-iommu.c
@@ -59,6 +59,7 @@ struct omap_iommu_domain {
 	struct omap_iommu *iommu_dev;
 	struct device *dev;
 	spinlock_t lock;
+	struct iommu_domain domain;
 };
 
 #define MMU_LOCK_BASE_SHIFT	10
@@ -80,6 +81,15 @@ static struct platform_driver omap_iommu_driver;
 static struct kmem_cache *iopte_cachep;
 
 /**
+ * to_omap_domain - Get struct omap_iommu_domain from generic iommu_domain
+ * @dom:	generic iommu domain handle
+ **/
+static struct omap_iommu_domain *to_omap_domain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct omap_iommu_domain, domain);
+}
+
+/**
  * omap_iommu_save_ctx - Save registers for pm off-mode support
  * @dev:	client device
  **/
@@ -901,7 +911,7 @@ static irqreturn_t iommu_fault_handler(int irq, void *data)
 	u32 *iopgd, *iopte;
 	struct omap_iommu *obj = data;
 	struct iommu_domain *domain = obj->domain;
-	struct omap_iommu_domain *omap_domain = domain->priv;
+	struct omap_iommu_domain *omap_domain = to_omap_domain(domain);
 
 	if (!omap_domain->iommu_dev)
 		return IRQ_NONE;
@@ -1113,7 +1123,7 @@ static u32 iotlb_init_entry(struct iotlb_entry *e, u32 da, u32 pa, int pgsz)
 static int omap_iommu_map(struct iommu_domain *domain, unsigned long da,
 			 phys_addr_t pa, size_t bytes, int prot)
 {
-	struct omap_iommu_domain *omap_domain = domain->priv;
+	struct omap_iommu_domain *omap_domain = to_omap_domain(domain);
 	struct omap_iommu *oiommu = omap_domain->iommu_dev;
 	struct device *dev = oiommu->dev;
 	struct iotlb_entry e;
@@ -1140,7 +1150,7 @@ static int omap_iommu_map(struct iommu_domain *domain, unsigned long da,
 static size_t omap_iommu_unmap(struct iommu_domain *domain, unsigned long da,
 			    size_t size)
 {
-	struct omap_iommu_domain *omap_domain = domain->priv;
+	struct omap_iommu_domain *omap_domain = to_omap_domain(domain);
 	struct omap_iommu *oiommu = omap_domain->iommu_dev;
 	struct device *dev = oiommu->dev;
 
@@ -1152,7 +1162,7 @@ static size_t omap_iommu_unmap(struct iommu_domain *domain, unsigned long da,
 static int
 omap_iommu_attach_dev(struct iommu_domain *domain, struct device *dev)
 {
-	struct omap_iommu_domain *omap_domain = domain->priv;
+	struct omap_iommu_domain *omap_domain = to_omap_domain(domain);
 	struct omap_iommu *oiommu;
 	struct omap_iommu_arch_data *arch_data = dev->archdata.iommu;
 	int ret = 0;
@@ -1212,17 +1222,20 @@ static void _omap_iommu_detach_dev(struct omap_iommu_domain *omap_domain,
 static void omap_iommu_detach_dev(struct iommu_domain *domain,
 				 struct device *dev)
 {
-	struct omap_iommu_domain *omap_domain = domain->priv;
+	struct omap_iommu_domain *omap_domain = to_omap_domain(domain);
 
 	spin_lock(&omap_domain->lock);
 	_omap_iommu_detach_dev(omap_domain, dev);
 	spin_unlock(&omap_domain->lock);
 }
 
-static int omap_iommu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *omap_iommu_domain_alloc(enum iommu_domain_type type)
 {
 	struct omap_iommu_domain *omap_domain;
 
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
+
 	omap_domain = kzalloc(sizeof(*omap_domain), GFP_KERNEL);
 	if (!omap_domain) {
 		pr_err("kzalloc failed\n");
@@ -1244,25 +1257,21 @@ static int omap_iommu_domain_init(struct iommu_domain *domain)
 	clean_dcache_area(omap_domain->pgtable, IOPGD_TABLE_SIZE);
 	spin_lock_init(&omap_domain->lock);
 
-	domain->priv = omap_domain;
+	omap_domain->domain.geometry.aperture_start = 0;
+	omap_domain->domain.geometry.aperture_end   = (1ULL << 32) - 1;
+	omap_domain->domain.geometry.force_aperture = true;
 
-	domain->geometry.aperture_start = 0;
-	domain->geometry.aperture_end   = (1ULL << 32) - 1;
-	domain->geometry.force_aperture = true;
-
-	return 0;
+	return &omap_domain->domain;
 
 fail_nomem:
 	kfree(omap_domain);
 out:
-	return -ENOMEM;
+	return NULL;
 }
 
-static void omap_iommu_domain_destroy(struct iommu_domain *domain)
+static void omap_iommu_domain_free(struct iommu_domain *domain)
 {
-	struct omap_iommu_domain *omap_domain = domain->priv;
-
-	domain->priv = NULL;
+	struct omap_iommu_domain *omap_domain = to_omap_domain(domain);
 
 	/*
 	 * An iommu device is still attached
@@ -1278,7 +1287,7 @@ static void omap_iommu_domain_destroy(struct iommu_domain *domain)
 static phys_addr_t omap_iommu_iova_to_phys(struct iommu_domain *domain,
 					  dma_addr_t da)
 {
-	struct omap_iommu_domain *omap_domain = domain->priv;
+	struct omap_iommu_domain *omap_domain = to_omap_domain(domain);
 	struct omap_iommu *oiommu = omap_domain->iommu_dev;
 	struct device *dev = oiommu->dev;
 	u32 *pgd, *pte;
@@ -1358,8 +1367,8 @@ static void omap_iommu_remove_device(struct device *dev)
 }
 
 static const struct iommu_ops omap_iommu_ops = {
-	.domain_init	= omap_iommu_domain_init,
-	.domain_destroy	= omap_iommu_domain_destroy,
+	.domain_alloc	= omap_iommu_domain_alloc,
+	.domain_free	= omap_iommu_domain_free,
 	.attach_dev	= omap_iommu_attach_dev,
 	.detach_dev	= omap_iommu_detach_dev,
 	.map		= omap_iommu_map,
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 06/15] iommu/arm-smmu: Make use of domain_alloc and domain_free
  2015-01-26 23:51 ` Joerg Roedel
  (?)
@ 2015-01-26 23:51     ` Joerg Roedel
  -1 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA
  Cc: Alexandre Courbot, linux-samsung-soc-u79uwXL29TY76Z2rM5mHXA,
	Heiko Stuebner, Arnd Bergmann, Stephen Warren, Will Deacon,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-rockchip-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Kukjin Kim,
	Thierry Reding, jroedel-l3A5Bk7waGM,
	linux-tegra-u79uwXL29TY76Z2rM5mHXA, David Woodhouse,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r

From: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>

Implement domain_alloc and domain_free iommu-ops as a
replacement for domain_init/domain_destroy.

Signed-off-by: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>
---
 drivers/iommu/arm-smmu.c | 46 +++++++++++++++++++++++++++-------------------
 1 file changed, 27 insertions(+), 19 deletions(-)

diff --git a/drivers/iommu/arm-smmu.c b/drivers/iommu/arm-smmu.c
index 6cd47b7..dd62669 100644
--- a/drivers/iommu/arm-smmu.c
+++ b/drivers/iommu/arm-smmu.c
@@ -415,6 +415,7 @@ struct arm_smmu_domain {
 	struct arm_smmu_cfg		cfg;
 	enum arm_smmu_domain_stage	stage;
 	spinlock_t			lock;
+	struct iommu_domain		domain;
 };
 
 static DEFINE_SPINLOCK(arm_smmu_devices_lock);
@@ -430,6 +431,11 @@ static struct arm_smmu_option_prop arm_smmu_options[] = {
 	{ 0, NULL},
 };
 
+static struct arm_smmu_domain *to_smmu_domain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct arm_smmu_domain, domain);
+}
+
 static void parse_driver_options(struct arm_smmu_device *smmu)
 {
 	int i = 0;
@@ -641,7 +647,7 @@ static irqreturn_t arm_smmu_context_fault(int irq, void *dev)
 	u32 fsr, far, fsynr, resume;
 	unsigned long iova;
 	struct iommu_domain *domain = dev;
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 	struct arm_smmu_cfg *cfg = &smmu_domain->cfg;
 	struct arm_smmu_device *smmu = smmu_domain->smmu;
 	void __iomem *cb_base;
@@ -906,7 +912,7 @@ static int arm_smmu_init_domain_context(struct iommu_domain *domain,
 {
 	int irq, start, ret = 0;
 	unsigned long flags;
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 	struct arm_smmu_cfg *cfg = &smmu_domain->cfg;
 
 	spin_lock_irqsave(&smmu_domain->lock, flags);
@@ -990,7 +996,7 @@ out_unlock:
 
 static void arm_smmu_destroy_domain_context(struct iommu_domain *domain)
 {
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 	struct arm_smmu_device *smmu = smmu_domain->smmu;
 	struct arm_smmu_cfg *cfg = &smmu_domain->cfg;
 	void __iomem *cb_base;
@@ -1012,11 +1018,13 @@ static void arm_smmu_destroy_domain_context(struct iommu_domain *domain)
 	__arm_smmu_free_bitmap(smmu->context_map, cfg->cbndx);
 }
 
-static int arm_smmu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *arm_smmu_domain_alloc(enum iommu_domain_type type)
 {
 	struct arm_smmu_domain *smmu_domain;
 	pgd_t *pgd;
 
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
 	/*
 	 * Allocate the domain and initialise some of its data structures.
 	 * We can't really do anything meaningful until we've added a
@@ -1024,7 +1032,7 @@ static int arm_smmu_domain_init(struct iommu_domain *domain)
 	 */
 	smmu_domain = kzalloc(sizeof(*smmu_domain), GFP_KERNEL);
 	if (!smmu_domain)
-		return -ENOMEM;
+		return NULL;
 
 	pgd = kcalloc(PTRS_PER_PGD, sizeof(pgd_t), GFP_KERNEL);
 	if (!pgd)
@@ -1032,12 +1040,12 @@ static int arm_smmu_domain_init(struct iommu_domain *domain)
 	smmu_domain->cfg.pgd = pgd;
 
 	spin_lock_init(&smmu_domain->lock);
-	domain->priv = smmu_domain;
-	return 0;
+
+	return &smmu_domain->domain;
 
 out_free_domain:
 	kfree(smmu_domain);
-	return -ENOMEM;
+	return NULL;
 }
 
 static void arm_smmu_free_ptes(pmd_t *pmd)
@@ -1103,9 +1111,9 @@ static void arm_smmu_free_pgtables(struct arm_smmu_domain *smmu_domain)
 	kfree(pgd_base);
 }
 
-static void arm_smmu_domain_destroy(struct iommu_domain *domain)
+static void arm_smmu_domain_free(struct iommu_domain *domain)
 {
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 
 	/*
 	 * Free the domain resources. We assume that all devices have
@@ -1243,7 +1251,7 @@ static void arm_smmu_domain_remove_master(struct arm_smmu_domain *smmu_domain,
 static int arm_smmu_attach_dev(struct iommu_domain *domain, struct device *dev)
 {
 	int ret;
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 	struct arm_smmu_device *smmu, *dom_smmu;
 	struct arm_smmu_master_cfg *cfg;
 
@@ -1292,7 +1300,7 @@ static int arm_smmu_attach_dev(struct iommu_domain *domain, struct device *dev)
 
 static void arm_smmu_detach_dev(struct iommu_domain *domain, struct device *dev)
 {
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 	struct arm_smmu_master_cfg *cfg;
 
 	cfg = find_smmu_master_cfg(dev);
@@ -1540,7 +1548,7 @@ out_unlock:
 static int arm_smmu_map(struct iommu_domain *domain, unsigned long iova,
 			phys_addr_t paddr, size_t size, int prot)
 {
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 
 	if (!smmu_domain)
 		return -ENODEV;
@@ -1552,7 +1560,7 @@ static size_t arm_smmu_unmap(struct iommu_domain *domain, unsigned long iova,
 			     size_t size)
 {
 	int ret;
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 
 	ret = arm_smmu_handle_mapping(smmu_domain, iova, 0, size, 0);
 	arm_smmu_tlb_inv_context(smmu_domain);
@@ -1566,7 +1574,7 @@ static phys_addr_t arm_smmu_iova_to_phys(struct iommu_domain *domain,
 	pud_t pud;
 	pmd_t pmd;
 	pte_t pte;
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 	struct arm_smmu_cfg *cfg = &smmu_domain->cfg;
 
 	pgdp = cfg->pgd;
@@ -1684,7 +1692,7 @@ static void arm_smmu_remove_device(struct device *dev)
 static int arm_smmu_domain_get_attr(struct iommu_domain *domain,
 				    enum iommu_attr attr, void *data)
 {
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 
 	switch (attr) {
 	case DOMAIN_ATTR_NESTING:
@@ -1698,7 +1706,7 @@ static int arm_smmu_domain_get_attr(struct iommu_domain *domain,
 static int arm_smmu_domain_set_attr(struct iommu_domain *domain,
 				    enum iommu_attr attr, void *data)
 {
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 
 	switch (attr) {
 	case DOMAIN_ATTR_NESTING:
@@ -1717,8 +1725,8 @@ static int arm_smmu_domain_set_attr(struct iommu_domain *domain,
 
 static const struct iommu_ops arm_smmu_ops = {
 	.capable		= arm_smmu_capable,
-	.domain_init		= arm_smmu_domain_init,
-	.domain_destroy		= arm_smmu_domain_destroy,
+	.domain_alloc		= arm_smmu_domain_alloc,
+	.domain_free		= arm_smmu_domain_free,
 	.attach_dev		= arm_smmu_attach_dev,
 	.detach_dev		= arm_smmu_detach_dev,
 	.map			= arm_smmu_map,
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 06/15] iommu/arm-smmu: Make use of domain_alloc and domain_free
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu
  Cc: Will Deacon, Kukjin Kim, David Woodhouse, Heiko Stuebner,
	Hiroshi Doyu, Stephen Warren, Thierry Reding, Alexandre Courbot,
	Alex Williamson, Arnd Bergmann, linux-kernel, linux-arm-kernel,
	linux-samsung-soc, linux-rockchip, linux-tegra, Joerg Roedel,
	jroedel

From: Joerg Roedel <jroedel@suse.de>

Implement domain_alloc and domain_free iommu-ops as a
replacement for domain_init/domain_destroy.

Signed-off-by: Joerg Roedel <jroedel@suse.de>
---
 drivers/iommu/arm-smmu.c | 46 +++++++++++++++++++++++++++-------------------
 1 file changed, 27 insertions(+), 19 deletions(-)

diff --git a/drivers/iommu/arm-smmu.c b/drivers/iommu/arm-smmu.c
index 6cd47b7..dd62669 100644
--- a/drivers/iommu/arm-smmu.c
+++ b/drivers/iommu/arm-smmu.c
@@ -415,6 +415,7 @@ struct arm_smmu_domain {
 	struct arm_smmu_cfg		cfg;
 	enum arm_smmu_domain_stage	stage;
 	spinlock_t			lock;
+	struct iommu_domain		domain;
 };
 
 static DEFINE_SPINLOCK(arm_smmu_devices_lock);
@@ -430,6 +431,11 @@ static struct arm_smmu_option_prop arm_smmu_options[] = {
 	{ 0, NULL},
 };
 
+static struct arm_smmu_domain *to_smmu_domain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct arm_smmu_domain, domain);
+}
+
 static void parse_driver_options(struct arm_smmu_device *smmu)
 {
 	int i = 0;
@@ -641,7 +647,7 @@ static irqreturn_t arm_smmu_context_fault(int irq, void *dev)
 	u32 fsr, far, fsynr, resume;
 	unsigned long iova;
 	struct iommu_domain *domain = dev;
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 	struct arm_smmu_cfg *cfg = &smmu_domain->cfg;
 	struct arm_smmu_device *smmu = smmu_domain->smmu;
 	void __iomem *cb_base;
@@ -906,7 +912,7 @@ static int arm_smmu_init_domain_context(struct iommu_domain *domain,
 {
 	int irq, start, ret = 0;
 	unsigned long flags;
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 	struct arm_smmu_cfg *cfg = &smmu_domain->cfg;
 
 	spin_lock_irqsave(&smmu_domain->lock, flags);
@@ -990,7 +996,7 @@ out_unlock:
 
 static void arm_smmu_destroy_domain_context(struct iommu_domain *domain)
 {
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 	struct arm_smmu_device *smmu = smmu_domain->smmu;
 	struct arm_smmu_cfg *cfg = &smmu_domain->cfg;
 	void __iomem *cb_base;
@@ -1012,11 +1018,13 @@ static void arm_smmu_destroy_domain_context(struct iommu_domain *domain)
 	__arm_smmu_free_bitmap(smmu->context_map, cfg->cbndx);
 }
 
-static int arm_smmu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *arm_smmu_domain_alloc(enum iommu_domain_type type)
 {
 	struct arm_smmu_domain *smmu_domain;
 	pgd_t *pgd;
 
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
 	/*
 	 * Allocate the domain and initialise some of its data structures.
 	 * We can't really do anything meaningful until we've added a
@@ -1024,7 +1032,7 @@ static int arm_smmu_domain_init(struct iommu_domain *domain)
 	 */
 	smmu_domain = kzalloc(sizeof(*smmu_domain), GFP_KERNEL);
 	if (!smmu_domain)
-		return -ENOMEM;
+		return NULL;
 
 	pgd = kcalloc(PTRS_PER_PGD, sizeof(pgd_t), GFP_KERNEL);
 	if (!pgd)
@@ -1032,12 +1040,12 @@ static int arm_smmu_domain_init(struct iommu_domain *domain)
 	smmu_domain->cfg.pgd = pgd;
 
 	spin_lock_init(&smmu_domain->lock);
-	domain->priv = smmu_domain;
-	return 0;
+
+	return &smmu_domain->domain;
 
 out_free_domain:
 	kfree(smmu_domain);
-	return -ENOMEM;
+	return NULL;
 }
 
 static void arm_smmu_free_ptes(pmd_t *pmd)
@@ -1103,9 +1111,9 @@ static void arm_smmu_free_pgtables(struct arm_smmu_domain *smmu_domain)
 	kfree(pgd_base);
 }
 
-static void arm_smmu_domain_destroy(struct iommu_domain *domain)
+static void arm_smmu_domain_free(struct iommu_domain *domain)
 {
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 
 	/*
 	 * Free the domain resources. We assume that all devices have
@@ -1243,7 +1251,7 @@ static void arm_smmu_domain_remove_master(struct arm_smmu_domain *smmu_domain,
 static int arm_smmu_attach_dev(struct iommu_domain *domain, struct device *dev)
 {
 	int ret;
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 	struct arm_smmu_device *smmu, *dom_smmu;
 	struct arm_smmu_master_cfg *cfg;
 
@@ -1292,7 +1300,7 @@ static int arm_smmu_attach_dev(struct iommu_domain *domain, struct device *dev)
 
 static void arm_smmu_detach_dev(struct iommu_domain *domain, struct device *dev)
 {
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 	struct arm_smmu_master_cfg *cfg;
 
 	cfg = find_smmu_master_cfg(dev);
@@ -1540,7 +1548,7 @@ out_unlock:
 static int arm_smmu_map(struct iommu_domain *domain, unsigned long iova,
 			phys_addr_t paddr, size_t size, int prot)
 {
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 
 	if (!smmu_domain)
 		return -ENODEV;
@@ -1552,7 +1560,7 @@ static size_t arm_smmu_unmap(struct iommu_domain *domain, unsigned long iova,
 			     size_t size)
 {
 	int ret;
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 
 	ret = arm_smmu_handle_mapping(smmu_domain, iova, 0, size, 0);
 	arm_smmu_tlb_inv_context(smmu_domain);
@@ -1566,7 +1574,7 @@ static phys_addr_t arm_smmu_iova_to_phys(struct iommu_domain *domain,
 	pud_t pud;
 	pmd_t pmd;
 	pte_t pte;
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 	struct arm_smmu_cfg *cfg = &smmu_domain->cfg;
 
 	pgdp = cfg->pgd;
@@ -1684,7 +1692,7 @@ static void arm_smmu_remove_device(struct device *dev)
 static int arm_smmu_domain_get_attr(struct iommu_domain *domain,
 				    enum iommu_attr attr, void *data)
 {
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 
 	switch (attr) {
 	case DOMAIN_ATTR_NESTING:
@@ -1698,7 +1706,7 @@ static int arm_smmu_domain_get_attr(struct iommu_domain *domain,
 static int arm_smmu_domain_set_attr(struct iommu_domain *domain,
 				    enum iommu_attr attr, void *data)
 {
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 
 	switch (attr) {
 	case DOMAIN_ATTR_NESTING:
@@ -1717,8 +1725,8 @@ static int arm_smmu_domain_set_attr(struct iommu_domain *domain,
 
 static const struct iommu_ops arm_smmu_ops = {
 	.capable		= arm_smmu_capable,
-	.domain_init		= arm_smmu_domain_init,
-	.domain_destroy		= arm_smmu_domain_destroy,
+	.domain_alloc		= arm_smmu_domain_alloc,
+	.domain_free		= arm_smmu_domain_free,
 	.attach_dev		= arm_smmu_attach_dev,
 	.detach_dev		= arm_smmu_detach_dev,
 	.map			= arm_smmu_map,
-- 
1.8.4.5


^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 06/15] iommu/arm-smmu: Make use of domain_alloc and domain_free
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: linux-arm-kernel

From: Joerg Roedel <jroedel@suse.de>

Implement domain_alloc and domain_free iommu-ops as a
replacement for domain_init/domain_destroy.

Signed-off-by: Joerg Roedel <jroedel@suse.de>
---
 drivers/iommu/arm-smmu.c | 46 +++++++++++++++++++++++++++-------------------
 1 file changed, 27 insertions(+), 19 deletions(-)

diff --git a/drivers/iommu/arm-smmu.c b/drivers/iommu/arm-smmu.c
index 6cd47b7..dd62669 100644
--- a/drivers/iommu/arm-smmu.c
+++ b/drivers/iommu/arm-smmu.c
@@ -415,6 +415,7 @@ struct arm_smmu_domain {
 	struct arm_smmu_cfg		cfg;
 	enum arm_smmu_domain_stage	stage;
 	spinlock_t			lock;
+	struct iommu_domain		domain;
 };
 
 static DEFINE_SPINLOCK(arm_smmu_devices_lock);
@@ -430,6 +431,11 @@ static struct arm_smmu_option_prop arm_smmu_options[] = {
 	{ 0, NULL},
 };
 
+static struct arm_smmu_domain *to_smmu_domain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct arm_smmu_domain, domain);
+}
+
 static void parse_driver_options(struct arm_smmu_device *smmu)
 {
 	int i = 0;
@@ -641,7 +647,7 @@ static irqreturn_t arm_smmu_context_fault(int irq, void *dev)
 	u32 fsr, far, fsynr, resume;
 	unsigned long iova;
 	struct iommu_domain *domain = dev;
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 	struct arm_smmu_cfg *cfg = &smmu_domain->cfg;
 	struct arm_smmu_device *smmu = smmu_domain->smmu;
 	void __iomem *cb_base;
@@ -906,7 +912,7 @@ static int arm_smmu_init_domain_context(struct iommu_domain *domain,
 {
 	int irq, start, ret = 0;
 	unsigned long flags;
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 	struct arm_smmu_cfg *cfg = &smmu_domain->cfg;
 
 	spin_lock_irqsave(&smmu_domain->lock, flags);
@@ -990,7 +996,7 @@ out_unlock:
 
 static void arm_smmu_destroy_domain_context(struct iommu_domain *domain)
 {
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 	struct arm_smmu_device *smmu = smmu_domain->smmu;
 	struct arm_smmu_cfg *cfg = &smmu_domain->cfg;
 	void __iomem *cb_base;
@@ -1012,11 +1018,13 @@ static void arm_smmu_destroy_domain_context(struct iommu_domain *domain)
 	__arm_smmu_free_bitmap(smmu->context_map, cfg->cbndx);
 }
 
-static int arm_smmu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *arm_smmu_domain_alloc(enum iommu_domain_type type)
 {
 	struct arm_smmu_domain *smmu_domain;
 	pgd_t *pgd;
 
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
 	/*
 	 * Allocate the domain and initialise some of its data structures.
 	 * We can't really do anything meaningful until we've added a
@@ -1024,7 +1032,7 @@ static int arm_smmu_domain_init(struct iommu_domain *domain)
 	 */
 	smmu_domain = kzalloc(sizeof(*smmu_domain), GFP_KERNEL);
 	if (!smmu_domain)
-		return -ENOMEM;
+		return NULL;
 
 	pgd = kcalloc(PTRS_PER_PGD, sizeof(pgd_t), GFP_KERNEL);
 	if (!pgd)
@@ -1032,12 +1040,12 @@ static int arm_smmu_domain_init(struct iommu_domain *domain)
 	smmu_domain->cfg.pgd = pgd;
 
 	spin_lock_init(&smmu_domain->lock);
-	domain->priv = smmu_domain;
-	return 0;
+
+	return &smmu_domain->domain;
 
 out_free_domain:
 	kfree(smmu_domain);
-	return -ENOMEM;
+	return NULL;
 }
 
 static void arm_smmu_free_ptes(pmd_t *pmd)
@@ -1103,9 +1111,9 @@ static void arm_smmu_free_pgtables(struct arm_smmu_domain *smmu_domain)
 	kfree(pgd_base);
 }
 
-static void arm_smmu_domain_destroy(struct iommu_domain *domain)
+static void arm_smmu_domain_free(struct iommu_domain *domain)
 {
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 
 	/*
 	 * Free the domain resources. We assume that all devices have
@@ -1243,7 +1251,7 @@ static void arm_smmu_domain_remove_master(struct arm_smmu_domain *smmu_domain,
 static int arm_smmu_attach_dev(struct iommu_domain *domain, struct device *dev)
 {
 	int ret;
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 	struct arm_smmu_device *smmu, *dom_smmu;
 	struct arm_smmu_master_cfg *cfg;
 
@@ -1292,7 +1300,7 @@ static int arm_smmu_attach_dev(struct iommu_domain *domain, struct device *dev)
 
 static void arm_smmu_detach_dev(struct iommu_domain *domain, struct device *dev)
 {
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 	struct arm_smmu_master_cfg *cfg;
 
 	cfg = find_smmu_master_cfg(dev);
@@ -1540,7 +1548,7 @@ out_unlock:
 static int arm_smmu_map(struct iommu_domain *domain, unsigned long iova,
 			phys_addr_t paddr, size_t size, int prot)
 {
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 
 	if (!smmu_domain)
 		return -ENODEV;
@@ -1552,7 +1560,7 @@ static size_t arm_smmu_unmap(struct iommu_domain *domain, unsigned long iova,
 			     size_t size)
 {
 	int ret;
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 
 	ret = arm_smmu_handle_mapping(smmu_domain, iova, 0, size, 0);
 	arm_smmu_tlb_inv_context(smmu_domain);
@@ -1566,7 +1574,7 @@ static phys_addr_t arm_smmu_iova_to_phys(struct iommu_domain *domain,
 	pud_t pud;
 	pmd_t pmd;
 	pte_t pte;
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 	struct arm_smmu_cfg *cfg = &smmu_domain->cfg;
 
 	pgdp = cfg->pgd;
@@ -1684,7 +1692,7 @@ static void arm_smmu_remove_device(struct device *dev)
 static int arm_smmu_domain_get_attr(struct iommu_domain *domain,
 				    enum iommu_attr attr, void *data)
 {
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 
 	switch (attr) {
 	case DOMAIN_ATTR_NESTING:
@@ -1698,7 +1706,7 @@ static int arm_smmu_domain_get_attr(struct iommu_domain *domain,
 static int arm_smmu_domain_set_attr(struct iommu_domain *domain,
 				    enum iommu_attr attr, void *data)
 {
-	struct arm_smmu_domain *smmu_domain = domain->priv;
+	struct arm_smmu_domain *smmu_domain = to_smmu_domain(domain);
 
 	switch (attr) {
 	case DOMAIN_ATTR_NESTING:
@@ -1717,8 +1725,8 @@ static int arm_smmu_domain_set_attr(struct iommu_domain *domain,
 
 static const struct iommu_ops arm_smmu_ops = {
 	.capable		= arm_smmu_capable,
-	.domain_init		= arm_smmu_domain_init,
-	.domain_destroy		= arm_smmu_domain_destroy,
+	.domain_alloc		= arm_smmu_domain_alloc,
+	.domain_free		= arm_smmu_domain_free,
 	.attach_dev		= arm_smmu_attach_dev,
 	.detach_dev		= arm_smmu_detach_dev,
 	.map			= arm_smmu_map,
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 07/15] iommu/exynos: Make use of domain_alloc and domain_free
  2015-01-26 23:51 ` Joerg Roedel
  (?)
@ 2015-01-26 23:51     ` Joerg Roedel
  -1 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA
  Cc: Alexandre Courbot, linux-samsung-soc-u79uwXL29TY76Z2rM5mHXA,
	Heiko Stuebner, Arnd Bergmann, Stephen Warren, Will Deacon,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-rockchip-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Kukjin Kim,
	Thierry Reding, jroedel-l3A5Bk7waGM,
	linux-tegra-u79uwXL29TY76Z2rM5mHXA, David Woodhouse,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r

From: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>

Implement domain_alloc and domain_free iommu-ops as a
replacement for domain_init/domain_destroy.

Signed-off-by: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>
---
 drivers/iommu/exynos-iommu.c | 87 ++++++++++++++++++++++++--------------------
 1 file changed, 47 insertions(+), 40 deletions(-)

diff --git a/drivers/iommu/exynos-iommu.c b/drivers/iommu/exynos-iommu.c
index 7ce5273..d103cbf 100644
--- a/drivers/iommu/exynos-iommu.c
+++ b/drivers/iommu/exynos-iommu.c
@@ -200,6 +200,7 @@ struct exynos_iommu_domain {
 	short *lv2entcnt; /* free lv2 entry counter for each section */
 	spinlock_t lock; /* lock for this structure */
 	spinlock_t pgtablelock; /* lock for modifying page table @ pgtable */
+	struct iommu_domain domain; /* generic domain data structure */
 };
 
 struct sysmmu_drvdata {
@@ -214,6 +215,11 @@ struct sysmmu_drvdata {
 	phys_addr_t pgtable;
 };
 
+static struct exynos_iommu_domain *to_exynos_domain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct exynos_iommu_domain, domain);
+}
+
 static bool set_sysmmu_active(struct sysmmu_drvdata *data)
 {
 	/* return true if the System MMU was not active previously
@@ -696,58 +702,60 @@ static inline void pgtable_flush(void *vastart, void *vaend)
 				virt_to_phys(vaend));
 }
 
-static int exynos_iommu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *exynos_iommu_domain_alloc(enum iommu_domain_type type)
 {
-	struct exynos_iommu_domain *priv;
+	struct exynos_iommu_domain *exynos_domain;
 	int i;
 
-	priv = kzalloc(sizeof(*priv), GFP_KERNEL);
-	if (!priv)
-		return -ENOMEM;
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
+
+	exynos_domain = kzalloc(sizeof(*exynos_domain), GFP_KERNEL);
+	if (!exynos_domain)
+		return NULL;
 
-	priv->pgtable = (sysmmu_pte_t *)__get_free_pages(GFP_KERNEL, 2);
-	if (!priv->pgtable)
+	exynos_domain->pgtable = (sysmmu_pte_t *)__get_free_pages(GFP_KERNEL, 2);
+	if (!exynos_domain->pgtable)
 		goto err_pgtable;
 
-	priv->lv2entcnt = (short *)__get_free_pages(GFP_KERNEL | __GFP_ZERO, 1);
-	if (!priv->lv2entcnt)
+	exynos_domain->lv2entcnt = (short *)__get_free_pages(GFP_KERNEL | __GFP_ZERO, 1);
+	if (!exynos_domain->lv2entcnt)
 		goto err_counter;
 
 	/* Workaround for System MMU v3.3 to prevent caching 1MiB mapping */
 	for (i = 0; i < NUM_LV1ENTRIES; i += 8) {
-		priv->pgtable[i + 0] = ZERO_LV2LINK;
-		priv->pgtable[i + 1] = ZERO_LV2LINK;
-		priv->pgtable[i + 2] = ZERO_LV2LINK;
-		priv->pgtable[i + 3] = ZERO_LV2LINK;
-		priv->pgtable[i + 4] = ZERO_LV2LINK;
-		priv->pgtable[i + 5] = ZERO_LV2LINK;
-		priv->pgtable[i + 6] = ZERO_LV2LINK;
-		priv->pgtable[i + 7] = ZERO_LV2LINK;
+		exynos_domain->pgtable[i + 0] = ZERO_LV2LINK;
+		exynos_domain->pgtable[i + 1] = ZERO_LV2LINK;
+		exynos_domain->pgtable[i + 2] = ZERO_LV2LINK;
+		exynos_domain->pgtable[i + 3] = ZERO_LV2LINK;
+		exynos_domain->pgtable[i + 4] = ZERO_LV2LINK;
+		exynos_domain->pgtable[i + 5] = ZERO_LV2LINK;
+		exynos_domain->pgtable[i + 6] = ZERO_LV2LINK;
+		exynos_domain->pgtable[i + 7] = ZERO_LV2LINK;
 	}
 
-	pgtable_flush(priv->pgtable, priv->pgtable + NUM_LV1ENTRIES);
+	pgtable_flush(exynos_domain->pgtable, exynos_domain->pgtable + NUM_LV1ENTRIES);
 
-	spin_lock_init(&priv->lock);
-	spin_lock_init(&priv->pgtablelock);
-	INIT_LIST_HEAD(&priv->clients);
+	spin_lock_init(&exynos_domain->lock);
+	spin_lock_init(&exynos_domain->pgtablelock);
+	INIT_LIST_HEAD(&exynos_domain->clients);
 
-	domain->geometry.aperture_start = 0;
-	domain->geometry.aperture_end   = ~0UL;
-	domain->geometry.force_aperture = true;
+	exynos_domain->domain.geometry.aperture_start = 0;
+	exynos_domain->domain.geometry.aperture_end   = ~0UL;
+	exynos_domain->domain.geometry.force_aperture = true;
 
-	domain->priv = priv;
-	return 0;
+	return &exynos_domain->domain;
 
 err_counter:
-	free_pages((unsigned long)priv->pgtable, 2);
+	free_pages((unsigned long)exynos_domain->pgtable, 2);
 err_pgtable:
-	kfree(priv);
-	return -ENOMEM;
+	kfree(exynos_domain);
+	return NULL;
 }
 
-static void exynos_iommu_domain_destroy(struct iommu_domain *domain)
+static void exynos_iommu_domain_free(struct iommu_domain *domain)
 {
-	struct exynos_iommu_domain *priv = domain->priv;
+	struct exynos_iommu_domain *priv = to_exynos_domain(domain);
 	struct exynos_iommu_owner *owner;
 	unsigned long flags;
 	int i;
@@ -773,15 +781,14 @@ static void exynos_iommu_domain_destroy(struct iommu_domain *domain)
 
 	free_pages((unsigned long)priv->pgtable, 2);
 	free_pages((unsigned long)priv->lv2entcnt, 1);
-	kfree(domain->priv);
-	domain->priv = NULL;
+	kfree(priv);
 }
 
 static int exynos_iommu_attach_device(struct iommu_domain *domain,
 				   struct device *dev)
 {
 	struct exynos_iommu_owner *owner = dev->archdata.iommu;
-	struct exynos_iommu_domain *priv = domain->priv;
+	struct exynos_iommu_domain *priv = to_exynos_domain(domain);
 	phys_addr_t pagetable = virt_to_phys(priv->pgtable);
 	unsigned long flags;
 	int ret;
@@ -812,7 +819,7 @@ static void exynos_iommu_detach_device(struct iommu_domain *domain,
 				    struct device *dev)
 {
 	struct exynos_iommu_owner *owner;
-	struct exynos_iommu_domain *priv = domain->priv;
+	struct exynos_iommu_domain *priv = to_exynos_domain(domain);
 	phys_addr_t pagetable = virt_to_phys(priv->pgtable);
 	unsigned long flags;
 
@@ -988,7 +995,7 @@ static int lv2set_page(sysmmu_pte_t *pent, phys_addr_t paddr, size_t size,
 static int exynos_iommu_map(struct iommu_domain *domain, unsigned long l_iova,
 			 phys_addr_t paddr, size_t size, int prot)
 {
-	struct exynos_iommu_domain *priv = domain->priv;
+	struct exynos_iommu_domain *priv = to_exynos_domain(domain);
 	sysmmu_pte_t *entry;
 	sysmmu_iova_t iova = (sysmmu_iova_t)l_iova;
 	unsigned long flags;
@@ -1042,7 +1049,7 @@ static void exynos_iommu_tlb_invalidate_entry(struct exynos_iommu_domain *priv,
 static size_t exynos_iommu_unmap(struct iommu_domain *domain,
 					unsigned long l_iova, size_t size)
 {
-	struct exynos_iommu_domain *priv = domain->priv;
+	struct exynos_iommu_domain *priv = to_exynos_domain(domain);
 	sysmmu_iova_t iova = (sysmmu_iova_t)l_iova;
 	sysmmu_pte_t *ent;
 	size_t err_pgsize;
@@ -1119,7 +1126,7 @@ err:
 static phys_addr_t exynos_iommu_iova_to_phys(struct iommu_domain *domain,
 					  dma_addr_t iova)
 {
-	struct exynos_iommu_domain *priv = domain->priv;
+	struct exynos_iommu_domain *priv = to_exynos_domain(domain);
 	sysmmu_pte_t *entry;
 	unsigned long flags;
 	phys_addr_t phys = 0;
@@ -1171,8 +1178,8 @@ static void exynos_iommu_remove_device(struct device *dev)
 }
 
 static const struct iommu_ops exynos_iommu_ops = {
-	.domain_init = exynos_iommu_domain_init,
-	.domain_destroy = exynos_iommu_domain_destroy,
+	.domain_alloc = exynos_iommu_domain_alloc,
+	.domain_free = exynos_iommu_domain_free,
 	.attach_dev = exynos_iommu_attach_device,
 	.detach_dev = exynos_iommu_detach_device,
 	.map = exynos_iommu_map,
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 07/15] iommu/exynos: Make use of domain_alloc and domain_free
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu
  Cc: Will Deacon, Kukjin Kim, David Woodhouse, Heiko Stuebner,
	Hiroshi Doyu, Stephen Warren, Thierry Reding, Alexandre Courbot,
	Alex Williamson, Arnd Bergmann, linux-kernel, linux-arm-kernel,
	linux-samsung-soc, linux-rockchip, linux-tegra, Joerg Roedel,
	jroedel

From: Joerg Roedel <jroedel@suse.de>

Implement domain_alloc and domain_free iommu-ops as a
replacement for domain_init/domain_destroy.

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

diff --git a/drivers/iommu/exynos-iommu.c b/drivers/iommu/exynos-iommu.c
index 7ce5273..d103cbf 100644
--- a/drivers/iommu/exynos-iommu.c
+++ b/drivers/iommu/exynos-iommu.c
@@ -200,6 +200,7 @@ struct exynos_iommu_domain {
 	short *lv2entcnt; /* free lv2 entry counter for each section */
 	spinlock_t lock; /* lock for this structure */
 	spinlock_t pgtablelock; /* lock for modifying page table @ pgtable */
+	struct iommu_domain domain; /* generic domain data structure */
 };
 
 struct sysmmu_drvdata {
@@ -214,6 +215,11 @@ struct sysmmu_drvdata {
 	phys_addr_t pgtable;
 };
 
+static struct exynos_iommu_domain *to_exynos_domain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct exynos_iommu_domain, domain);
+}
+
 static bool set_sysmmu_active(struct sysmmu_drvdata *data)
 {
 	/* return true if the System MMU was not active previously
@@ -696,58 +702,60 @@ static inline void pgtable_flush(void *vastart, void *vaend)
 				virt_to_phys(vaend));
 }
 
-static int exynos_iommu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *exynos_iommu_domain_alloc(enum iommu_domain_type type)
 {
-	struct exynos_iommu_domain *priv;
+	struct exynos_iommu_domain *exynos_domain;
 	int i;
 
-	priv = kzalloc(sizeof(*priv), GFP_KERNEL);
-	if (!priv)
-		return -ENOMEM;
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
+
+	exynos_domain = kzalloc(sizeof(*exynos_domain), GFP_KERNEL);
+	if (!exynos_domain)
+		return NULL;
 
-	priv->pgtable = (sysmmu_pte_t *)__get_free_pages(GFP_KERNEL, 2);
-	if (!priv->pgtable)
+	exynos_domain->pgtable = (sysmmu_pte_t *)__get_free_pages(GFP_KERNEL, 2);
+	if (!exynos_domain->pgtable)
 		goto err_pgtable;
 
-	priv->lv2entcnt = (short *)__get_free_pages(GFP_KERNEL | __GFP_ZERO, 1);
-	if (!priv->lv2entcnt)
+	exynos_domain->lv2entcnt = (short *)__get_free_pages(GFP_KERNEL | __GFP_ZERO, 1);
+	if (!exynos_domain->lv2entcnt)
 		goto err_counter;
 
 	/* Workaround for System MMU v3.3 to prevent caching 1MiB mapping */
 	for (i = 0; i < NUM_LV1ENTRIES; i += 8) {
-		priv->pgtable[i + 0] = ZERO_LV2LINK;
-		priv->pgtable[i + 1] = ZERO_LV2LINK;
-		priv->pgtable[i + 2] = ZERO_LV2LINK;
-		priv->pgtable[i + 3] = ZERO_LV2LINK;
-		priv->pgtable[i + 4] = ZERO_LV2LINK;
-		priv->pgtable[i + 5] = ZERO_LV2LINK;
-		priv->pgtable[i + 6] = ZERO_LV2LINK;
-		priv->pgtable[i + 7] = ZERO_LV2LINK;
+		exynos_domain->pgtable[i + 0] = ZERO_LV2LINK;
+		exynos_domain->pgtable[i + 1] = ZERO_LV2LINK;
+		exynos_domain->pgtable[i + 2] = ZERO_LV2LINK;
+		exynos_domain->pgtable[i + 3] = ZERO_LV2LINK;
+		exynos_domain->pgtable[i + 4] = ZERO_LV2LINK;
+		exynos_domain->pgtable[i + 5] = ZERO_LV2LINK;
+		exynos_domain->pgtable[i + 6] = ZERO_LV2LINK;
+		exynos_domain->pgtable[i + 7] = ZERO_LV2LINK;
 	}
 
-	pgtable_flush(priv->pgtable, priv->pgtable + NUM_LV1ENTRIES);
+	pgtable_flush(exynos_domain->pgtable, exynos_domain->pgtable + NUM_LV1ENTRIES);
 
-	spin_lock_init(&priv->lock);
-	spin_lock_init(&priv->pgtablelock);
-	INIT_LIST_HEAD(&priv->clients);
+	spin_lock_init(&exynos_domain->lock);
+	spin_lock_init(&exynos_domain->pgtablelock);
+	INIT_LIST_HEAD(&exynos_domain->clients);
 
-	domain->geometry.aperture_start = 0;
-	domain->geometry.aperture_end   = ~0UL;
-	domain->geometry.force_aperture = true;
+	exynos_domain->domain.geometry.aperture_start = 0;
+	exynos_domain->domain.geometry.aperture_end   = ~0UL;
+	exynos_domain->domain.geometry.force_aperture = true;
 
-	domain->priv = priv;
-	return 0;
+	return &exynos_domain->domain;
 
 err_counter:
-	free_pages((unsigned long)priv->pgtable, 2);
+	free_pages((unsigned long)exynos_domain->pgtable, 2);
 err_pgtable:
-	kfree(priv);
-	return -ENOMEM;
+	kfree(exynos_domain);
+	return NULL;
 }
 
-static void exynos_iommu_domain_destroy(struct iommu_domain *domain)
+static void exynos_iommu_domain_free(struct iommu_domain *domain)
 {
-	struct exynos_iommu_domain *priv = domain->priv;
+	struct exynos_iommu_domain *priv = to_exynos_domain(domain);
 	struct exynos_iommu_owner *owner;
 	unsigned long flags;
 	int i;
@@ -773,15 +781,14 @@ static void exynos_iommu_domain_destroy(struct iommu_domain *domain)
 
 	free_pages((unsigned long)priv->pgtable, 2);
 	free_pages((unsigned long)priv->lv2entcnt, 1);
-	kfree(domain->priv);
-	domain->priv = NULL;
+	kfree(priv);
 }
 
 static int exynos_iommu_attach_device(struct iommu_domain *domain,
 				   struct device *dev)
 {
 	struct exynos_iommu_owner *owner = dev->archdata.iommu;
-	struct exynos_iommu_domain *priv = domain->priv;
+	struct exynos_iommu_domain *priv = to_exynos_domain(domain);
 	phys_addr_t pagetable = virt_to_phys(priv->pgtable);
 	unsigned long flags;
 	int ret;
@@ -812,7 +819,7 @@ static void exynos_iommu_detach_device(struct iommu_domain *domain,
 				    struct device *dev)
 {
 	struct exynos_iommu_owner *owner;
-	struct exynos_iommu_domain *priv = domain->priv;
+	struct exynos_iommu_domain *priv = to_exynos_domain(domain);
 	phys_addr_t pagetable = virt_to_phys(priv->pgtable);
 	unsigned long flags;
 
@@ -988,7 +995,7 @@ static int lv2set_page(sysmmu_pte_t *pent, phys_addr_t paddr, size_t size,
 static int exynos_iommu_map(struct iommu_domain *domain, unsigned long l_iova,
 			 phys_addr_t paddr, size_t size, int prot)
 {
-	struct exynos_iommu_domain *priv = domain->priv;
+	struct exynos_iommu_domain *priv = to_exynos_domain(domain);
 	sysmmu_pte_t *entry;
 	sysmmu_iova_t iova = (sysmmu_iova_t)l_iova;
 	unsigned long flags;
@@ -1042,7 +1049,7 @@ static void exynos_iommu_tlb_invalidate_entry(struct exynos_iommu_domain *priv,
 static size_t exynos_iommu_unmap(struct iommu_domain *domain,
 					unsigned long l_iova, size_t size)
 {
-	struct exynos_iommu_domain *priv = domain->priv;
+	struct exynos_iommu_domain *priv = to_exynos_domain(domain);
 	sysmmu_iova_t iova = (sysmmu_iova_t)l_iova;
 	sysmmu_pte_t *ent;
 	size_t err_pgsize;
@@ -1119,7 +1126,7 @@ err:
 static phys_addr_t exynos_iommu_iova_to_phys(struct iommu_domain *domain,
 					  dma_addr_t iova)
 {
-	struct exynos_iommu_domain *priv = domain->priv;
+	struct exynos_iommu_domain *priv = to_exynos_domain(domain);
 	sysmmu_pte_t *entry;
 	unsigned long flags;
 	phys_addr_t phys = 0;
@@ -1171,8 +1178,8 @@ static void exynos_iommu_remove_device(struct device *dev)
 }
 
 static const struct iommu_ops exynos_iommu_ops = {
-	.domain_init = exynos_iommu_domain_init,
-	.domain_destroy = exynos_iommu_domain_destroy,
+	.domain_alloc = exynos_iommu_domain_alloc,
+	.domain_free = exynos_iommu_domain_free,
 	.attach_dev = exynos_iommu_attach_device,
 	.detach_dev = exynos_iommu_detach_device,
 	.map = exynos_iommu_map,
-- 
1.8.4.5


^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 07/15] iommu/exynos: Make use of domain_alloc and domain_free
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: linux-arm-kernel

From: Joerg Roedel <jroedel@suse.de>

Implement domain_alloc and domain_free iommu-ops as a
replacement for domain_init/domain_destroy.

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

diff --git a/drivers/iommu/exynos-iommu.c b/drivers/iommu/exynos-iommu.c
index 7ce5273..d103cbf 100644
--- a/drivers/iommu/exynos-iommu.c
+++ b/drivers/iommu/exynos-iommu.c
@@ -200,6 +200,7 @@ struct exynos_iommu_domain {
 	short *lv2entcnt; /* free lv2 entry counter for each section */
 	spinlock_t lock; /* lock for this structure */
 	spinlock_t pgtablelock; /* lock for modifying page table @ pgtable */
+	struct iommu_domain domain; /* generic domain data structure */
 };
 
 struct sysmmu_drvdata {
@@ -214,6 +215,11 @@ struct sysmmu_drvdata {
 	phys_addr_t pgtable;
 };
 
+static struct exynos_iommu_domain *to_exynos_domain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct exynos_iommu_domain, domain);
+}
+
 static bool set_sysmmu_active(struct sysmmu_drvdata *data)
 {
 	/* return true if the System MMU was not active previously
@@ -696,58 +702,60 @@ static inline void pgtable_flush(void *vastart, void *vaend)
 				virt_to_phys(vaend));
 }
 
-static int exynos_iommu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *exynos_iommu_domain_alloc(enum iommu_domain_type type)
 {
-	struct exynos_iommu_domain *priv;
+	struct exynos_iommu_domain *exynos_domain;
 	int i;
 
-	priv = kzalloc(sizeof(*priv), GFP_KERNEL);
-	if (!priv)
-		return -ENOMEM;
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
+
+	exynos_domain = kzalloc(sizeof(*exynos_domain), GFP_KERNEL);
+	if (!exynos_domain)
+		return NULL;
 
-	priv->pgtable = (sysmmu_pte_t *)__get_free_pages(GFP_KERNEL, 2);
-	if (!priv->pgtable)
+	exynos_domain->pgtable = (sysmmu_pte_t *)__get_free_pages(GFP_KERNEL, 2);
+	if (!exynos_domain->pgtable)
 		goto err_pgtable;
 
-	priv->lv2entcnt = (short *)__get_free_pages(GFP_KERNEL | __GFP_ZERO, 1);
-	if (!priv->lv2entcnt)
+	exynos_domain->lv2entcnt = (short *)__get_free_pages(GFP_KERNEL | __GFP_ZERO, 1);
+	if (!exynos_domain->lv2entcnt)
 		goto err_counter;
 
 	/* Workaround for System MMU v3.3 to prevent caching 1MiB mapping */
 	for (i = 0; i < NUM_LV1ENTRIES; i += 8) {
-		priv->pgtable[i + 0] = ZERO_LV2LINK;
-		priv->pgtable[i + 1] = ZERO_LV2LINK;
-		priv->pgtable[i + 2] = ZERO_LV2LINK;
-		priv->pgtable[i + 3] = ZERO_LV2LINK;
-		priv->pgtable[i + 4] = ZERO_LV2LINK;
-		priv->pgtable[i + 5] = ZERO_LV2LINK;
-		priv->pgtable[i + 6] = ZERO_LV2LINK;
-		priv->pgtable[i + 7] = ZERO_LV2LINK;
+		exynos_domain->pgtable[i + 0] = ZERO_LV2LINK;
+		exynos_domain->pgtable[i + 1] = ZERO_LV2LINK;
+		exynos_domain->pgtable[i + 2] = ZERO_LV2LINK;
+		exynos_domain->pgtable[i + 3] = ZERO_LV2LINK;
+		exynos_domain->pgtable[i + 4] = ZERO_LV2LINK;
+		exynos_domain->pgtable[i + 5] = ZERO_LV2LINK;
+		exynos_domain->pgtable[i + 6] = ZERO_LV2LINK;
+		exynos_domain->pgtable[i + 7] = ZERO_LV2LINK;
 	}
 
-	pgtable_flush(priv->pgtable, priv->pgtable + NUM_LV1ENTRIES);
+	pgtable_flush(exynos_domain->pgtable, exynos_domain->pgtable + NUM_LV1ENTRIES);
 
-	spin_lock_init(&priv->lock);
-	spin_lock_init(&priv->pgtablelock);
-	INIT_LIST_HEAD(&priv->clients);
+	spin_lock_init(&exynos_domain->lock);
+	spin_lock_init(&exynos_domain->pgtablelock);
+	INIT_LIST_HEAD(&exynos_domain->clients);
 
-	domain->geometry.aperture_start = 0;
-	domain->geometry.aperture_end   = ~0UL;
-	domain->geometry.force_aperture = true;
+	exynos_domain->domain.geometry.aperture_start = 0;
+	exynos_domain->domain.geometry.aperture_end   = ~0UL;
+	exynos_domain->domain.geometry.force_aperture = true;
 
-	domain->priv = priv;
-	return 0;
+	return &exynos_domain->domain;
 
 err_counter:
-	free_pages((unsigned long)priv->pgtable, 2);
+	free_pages((unsigned long)exynos_domain->pgtable, 2);
 err_pgtable:
-	kfree(priv);
-	return -ENOMEM;
+	kfree(exynos_domain);
+	return NULL;
 }
 
-static void exynos_iommu_domain_destroy(struct iommu_domain *domain)
+static void exynos_iommu_domain_free(struct iommu_domain *domain)
 {
-	struct exynos_iommu_domain *priv = domain->priv;
+	struct exynos_iommu_domain *priv = to_exynos_domain(domain);
 	struct exynos_iommu_owner *owner;
 	unsigned long flags;
 	int i;
@@ -773,15 +781,14 @@ static void exynos_iommu_domain_destroy(struct iommu_domain *domain)
 
 	free_pages((unsigned long)priv->pgtable, 2);
 	free_pages((unsigned long)priv->lv2entcnt, 1);
-	kfree(domain->priv);
-	domain->priv = NULL;
+	kfree(priv);
 }
 
 static int exynos_iommu_attach_device(struct iommu_domain *domain,
 				   struct device *dev)
 {
 	struct exynos_iommu_owner *owner = dev->archdata.iommu;
-	struct exynos_iommu_domain *priv = domain->priv;
+	struct exynos_iommu_domain *priv = to_exynos_domain(domain);
 	phys_addr_t pagetable = virt_to_phys(priv->pgtable);
 	unsigned long flags;
 	int ret;
@@ -812,7 +819,7 @@ static void exynos_iommu_detach_device(struct iommu_domain *domain,
 				    struct device *dev)
 {
 	struct exynos_iommu_owner *owner;
-	struct exynos_iommu_domain *priv = domain->priv;
+	struct exynos_iommu_domain *priv = to_exynos_domain(domain);
 	phys_addr_t pagetable = virt_to_phys(priv->pgtable);
 	unsigned long flags;
 
@@ -988,7 +995,7 @@ static int lv2set_page(sysmmu_pte_t *pent, phys_addr_t paddr, size_t size,
 static int exynos_iommu_map(struct iommu_domain *domain, unsigned long l_iova,
 			 phys_addr_t paddr, size_t size, int prot)
 {
-	struct exynos_iommu_domain *priv = domain->priv;
+	struct exynos_iommu_domain *priv = to_exynos_domain(domain);
 	sysmmu_pte_t *entry;
 	sysmmu_iova_t iova = (sysmmu_iova_t)l_iova;
 	unsigned long flags;
@@ -1042,7 +1049,7 @@ static void exynos_iommu_tlb_invalidate_entry(struct exynos_iommu_domain *priv,
 static size_t exynos_iommu_unmap(struct iommu_domain *domain,
 					unsigned long l_iova, size_t size)
 {
-	struct exynos_iommu_domain *priv = domain->priv;
+	struct exynos_iommu_domain *priv = to_exynos_domain(domain);
 	sysmmu_iova_t iova = (sysmmu_iova_t)l_iova;
 	sysmmu_pte_t *ent;
 	size_t err_pgsize;
@@ -1119,7 +1126,7 @@ err:
 static phys_addr_t exynos_iommu_iova_to_phys(struct iommu_domain *domain,
 					  dma_addr_t iova)
 {
-	struct exynos_iommu_domain *priv = domain->priv;
+	struct exynos_iommu_domain *priv = to_exynos_domain(domain);
 	sysmmu_pte_t *entry;
 	unsigned long flags;
 	phys_addr_t phys = 0;
@@ -1171,8 +1178,8 @@ static void exynos_iommu_remove_device(struct device *dev)
 }
 
 static const struct iommu_ops exynos_iommu_ops = {
-	.domain_init = exynos_iommu_domain_init,
-	.domain_destroy = exynos_iommu_domain_destroy,
+	.domain_alloc = exynos_iommu_domain_alloc,
+	.domain_free = exynos_iommu_domain_free,
 	.attach_dev = exynos_iommu_attach_device,
 	.detach_dev = exynos_iommu_detach_device,
 	.map = exynos_iommu_map,
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 08/15] iommu/tegra-smmu: Make use of domain_alloc and domain_free
  2015-01-26 23:51 ` Joerg Roedel
  (?)
@ 2015-01-26 23:51     ` Joerg Roedel
  -1 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA
  Cc: Alexandre Courbot, linux-samsung-soc-u79uwXL29TY76Z2rM5mHXA,
	Heiko Stuebner, Arnd Bergmann, Stephen Warren, Will Deacon,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-rockchip-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Kukjin Kim,
	Thierry Reding, jroedel-l3A5Bk7waGM,
	linux-tegra-u79uwXL29TY76Z2rM5mHXA, David Woodhouse,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r

From: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>

Implement domain_alloc and domain_free iommu-ops as a
replacement for domain_init/domain_destroy.

Signed-off-by: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>
---
 drivers/iommu/tegra-smmu.c | 41 +++++++++++++++++++++++------------------
 1 file changed, 23 insertions(+), 18 deletions(-)

diff --git a/drivers/iommu/tegra-smmu.c b/drivers/iommu/tegra-smmu.c
index 6e134c7..f1bf84a 100644
--- a/drivers/iommu/tegra-smmu.c
+++ b/drivers/iommu/tegra-smmu.c
@@ -31,7 +31,7 @@ struct tegra_smmu {
 };
 
 struct tegra_smmu_as {
-	struct iommu_domain *domain;
+	struct iommu_domain domain;
 	struct tegra_smmu *smmu;
 	unsigned int use_count;
 	struct page *count;
@@ -40,6 +40,11 @@ struct tegra_smmu_as {
 	u32 attr;
 };
 
+static struct tegra_smmu_as *to_smmu_as(struct iommu_domain *dom)
+{
+	return container_of(dom, struct tegra_smmu_as, domain);
+}
+
 static inline void smmu_writel(struct tegra_smmu *smmu, u32 value,
 			       unsigned long offset)
 {
@@ -224,30 +229,32 @@ static bool tegra_smmu_capable(enum iommu_cap cap)
 	return false;
 }
 
-static int tegra_smmu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *tegra_smmu_domain_alloc(enum iommu_domain_type type)
 {
 	struct tegra_smmu_as *as;
 	unsigned int i;
 	uint32_t *pd;
 
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
+
 	as = kzalloc(sizeof(*as), GFP_KERNEL);
 	if (!as)
-		return -ENOMEM;
+		return NULL;
 
 	as->attr = SMMU_PD_READABLE | SMMU_PD_WRITABLE | SMMU_PD_NONSECURE;
-	as->domain = domain;
 
 	as->pd = alloc_page(GFP_KERNEL | __GFP_DMA);
 	if (!as->pd) {
 		kfree(as);
-		return -ENOMEM;
+		return NULL;
 	}
 
 	as->count = alloc_page(GFP_KERNEL);
 	if (!as->count) {
 		__free_page(as->pd);
 		kfree(as);
-		return -ENOMEM;
+		return NULL;
 	}
 
 	/* clear PDEs */
@@ -264,14 +271,12 @@ static int tegra_smmu_domain_init(struct iommu_domain *domain)
 	for (i = 0; i < SMMU_NUM_PDE; i++)
 		pd[i] = 0;
 
-	domain->priv = as;
-
-	return 0;
+	return &as->domain;
 }
 
-static void tegra_smmu_domain_destroy(struct iommu_domain *domain)
+static void tegra_smmu_domain_free(struct iommu_domain *domain)
 {
-	struct tegra_smmu_as *as = domain->priv;
+	struct tegra_smmu_as *as = to_smmu_as(domain);
 
 	/* TODO: free page directory and page tables */
 	ClearPageReserved(as->pd);
@@ -395,7 +400,7 @@ static int tegra_smmu_attach_dev(struct iommu_domain *domain,
 				 struct device *dev)
 {
 	struct tegra_smmu *smmu = dev->archdata.iommu;
-	struct tegra_smmu_as *as = domain->priv;
+	struct tegra_smmu_as *as = to_smmu_as(domain);
 	struct device_node *np = dev->of_node;
 	struct of_phandle_args args;
 	unsigned int index = 0;
@@ -428,7 +433,7 @@ static int tegra_smmu_attach_dev(struct iommu_domain *domain,
 
 static void tegra_smmu_detach_dev(struct iommu_domain *domain, struct device *dev)
 {
-	struct tegra_smmu_as *as = domain->priv;
+	struct tegra_smmu_as *as = to_smmu_as(domain);
 	struct device_node *np = dev->of_node;
 	struct tegra_smmu *smmu = as->smmu;
 	struct of_phandle_args args;
@@ -524,7 +529,7 @@ static void as_put_pte(struct tegra_smmu_as *as, dma_addr_t iova)
 static int tegra_smmu_map(struct iommu_domain *domain, unsigned long iova,
 			  phys_addr_t paddr, size_t size, int prot)
 {
-	struct tegra_smmu_as *as = domain->priv;
+	struct tegra_smmu_as *as = to_smmu_as(domain);
 	struct tegra_smmu *smmu = as->smmu;
 	unsigned long offset;
 	struct page *page;
@@ -548,7 +553,7 @@ static int tegra_smmu_map(struct iommu_domain *domain, unsigned long iova,
 static size_t tegra_smmu_unmap(struct iommu_domain *domain, unsigned long iova,
 			       size_t size)
 {
-	struct tegra_smmu_as *as = domain->priv;
+	struct tegra_smmu_as *as = to_smmu_as(domain);
 	struct tegra_smmu *smmu = as->smmu;
 	unsigned long offset;
 	struct page *page;
@@ -572,7 +577,7 @@ static size_t tegra_smmu_unmap(struct iommu_domain *domain, unsigned long iova,
 static phys_addr_t tegra_smmu_iova_to_phys(struct iommu_domain *domain,
 					   dma_addr_t iova)
 {
-	struct tegra_smmu_as *as = domain->priv;
+	struct tegra_smmu_as *as = to_smmu_as(domain);
 	struct page *page;
 	unsigned long pfn;
 	u32 *pte;
@@ -633,8 +638,8 @@ static void tegra_smmu_remove_device(struct device *dev)
 
 static const struct iommu_ops tegra_smmu_ops = {
 	.capable = tegra_smmu_capable,
-	.domain_init = tegra_smmu_domain_init,
-	.domain_destroy = tegra_smmu_domain_destroy,
+	.domain_alloc = tegra_smmu_domain_alloc,
+	.domain_free = tegra_smmu_domain_free,
 	.attach_dev = tegra_smmu_attach_dev,
 	.detach_dev = tegra_smmu_detach_dev,
 	.add_device = tegra_smmu_add_device,
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 08/15] iommu/tegra-smmu: Make use of domain_alloc and domain_free
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu
  Cc: Will Deacon, Kukjin Kim, David Woodhouse, Heiko Stuebner,
	Hiroshi Doyu, Stephen Warren, Thierry Reding, Alexandre Courbot,
	Alex Williamson, Arnd Bergmann, linux-kernel, linux-arm-kernel,
	linux-samsung-soc, linux-rockchip, linux-tegra, Joerg Roedel,
	jroedel

From: Joerg Roedel <jroedel@suse.de>

Implement domain_alloc and domain_free iommu-ops as a
replacement for domain_init/domain_destroy.

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

diff --git a/drivers/iommu/tegra-smmu.c b/drivers/iommu/tegra-smmu.c
index 6e134c7..f1bf84a 100644
--- a/drivers/iommu/tegra-smmu.c
+++ b/drivers/iommu/tegra-smmu.c
@@ -31,7 +31,7 @@ struct tegra_smmu {
 };
 
 struct tegra_smmu_as {
-	struct iommu_domain *domain;
+	struct iommu_domain domain;
 	struct tegra_smmu *smmu;
 	unsigned int use_count;
 	struct page *count;
@@ -40,6 +40,11 @@ struct tegra_smmu_as {
 	u32 attr;
 };
 
+static struct tegra_smmu_as *to_smmu_as(struct iommu_domain *dom)
+{
+	return container_of(dom, struct tegra_smmu_as, domain);
+}
+
 static inline void smmu_writel(struct tegra_smmu *smmu, u32 value,
 			       unsigned long offset)
 {
@@ -224,30 +229,32 @@ static bool tegra_smmu_capable(enum iommu_cap cap)
 	return false;
 }
 
-static int tegra_smmu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *tegra_smmu_domain_alloc(enum iommu_domain_type type)
 {
 	struct tegra_smmu_as *as;
 	unsigned int i;
 	uint32_t *pd;
 
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
+
 	as = kzalloc(sizeof(*as), GFP_KERNEL);
 	if (!as)
-		return -ENOMEM;
+		return NULL;
 
 	as->attr = SMMU_PD_READABLE | SMMU_PD_WRITABLE | SMMU_PD_NONSECURE;
-	as->domain = domain;
 
 	as->pd = alloc_page(GFP_KERNEL | __GFP_DMA);
 	if (!as->pd) {
 		kfree(as);
-		return -ENOMEM;
+		return NULL;
 	}
 
 	as->count = alloc_page(GFP_KERNEL);
 	if (!as->count) {
 		__free_page(as->pd);
 		kfree(as);
-		return -ENOMEM;
+		return NULL;
 	}
 
 	/* clear PDEs */
@@ -264,14 +271,12 @@ static int tegra_smmu_domain_init(struct iommu_domain *domain)
 	for (i = 0; i < SMMU_NUM_PDE; i++)
 		pd[i] = 0;
 
-	domain->priv = as;
-
-	return 0;
+	return &as->domain;
 }
 
-static void tegra_smmu_domain_destroy(struct iommu_domain *domain)
+static void tegra_smmu_domain_free(struct iommu_domain *domain)
 {
-	struct tegra_smmu_as *as = domain->priv;
+	struct tegra_smmu_as *as = to_smmu_as(domain);
 
 	/* TODO: free page directory and page tables */
 	ClearPageReserved(as->pd);
@@ -395,7 +400,7 @@ static int tegra_smmu_attach_dev(struct iommu_domain *domain,
 				 struct device *dev)
 {
 	struct tegra_smmu *smmu = dev->archdata.iommu;
-	struct tegra_smmu_as *as = domain->priv;
+	struct tegra_smmu_as *as = to_smmu_as(domain);
 	struct device_node *np = dev->of_node;
 	struct of_phandle_args args;
 	unsigned int index = 0;
@@ -428,7 +433,7 @@ static int tegra_smmu_attach_dev(struct iommu_domain *domain,
 
 static void tegra_smmu_detach_dev(struct iommu_domain *domain, struct device *dev)
 {
-	struct tegra_smmu_as *as = domain->priv;
+	struct tegra_smmu_as *as = to_smmu_as(domain);
 	struct device_node *np = dev->of_node;
 	struct tegra_smmu *smmu = as->smmu;
 	struct of_phandle_args args;
@@ -524,7 +529,7 @@ static void as_put_pte(struct tegra_smmu_as *as, dma_addr_t iova)
 static int tegra_smmu_map(struct iommu_domain *domain, unsigned long iova,
 			  phys_addr_t paddr, size_t size, int prot)
 {
-	struct tegra_smmu_as *as = domain->priv;
+	struct tegra_smmu_as *as = to_smmu_as(domain);
 	struct tegra_smmu *smmu = as->smmu;
 	unsigned long offset;
 	struct page *page;
@@ -548,7 +553,7 @@ static int tegra_smmu_map(struct iommu_domain *domain, unsigned long iova,
 static size_t tegra_smmu_unmap(struct iommu_domain *domain, unsigned long iova,
 			       size_t size)
 {
-	struct tegra_smmu_as *as = domain->priv;
+	struct tegra_smmu_as *as = to_smmu_as(domain);
 	struct tegra_smmu *smmu = as->smmu;
 	unsigned long offset;
 	struct page *page;
@@ -572,7 +577,7 @@ static size_t tegra_smmu_unmap(struct iommu_domain *domain, unsigned long iova,
 static phys_addr_t tegra_smmu_iova_to_phys(struct iommu_domain *domain,
 					   dma_addr_t iova)
 {
-	struct tegra_smmu_as *as = domain->priv;
+	struct tegra_smmu_as *as = to_smmu_as(domain);
 	struct page *page;
 	unsigned long pfn;
 	u32 *pte;
@@ -633,8 +638,8 @@ static void tegra_smmu_remove_device(struct device *dev)
 
 static const struct iommu_ops tegra_smmu_ops = {
 	.capable = tegra_smmu_capable,
-	.domain_init = tegra_smmu_domain_init,
-	.domain_destroy = tegra_smmu_domain_destroy,
+	.domain_alloc = tegra_smmu_domain_alloc,
+	.domain_free = tegra_smmu_domain_free,
 	.attach_dev = tegra_smmu_attach_dev,
 	.detach_dev = tegra_smmu_detach_dev,
 	.add_device = tegra_smmu_add_device,
-- 
1.8.4.5


^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 08/15] iommu/tegra-smmu: Make use of domain_alloc and domain_free
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: linux-arm-kernel

From: Joerg Roedel <jroedel@suse.de>

Implement domain_alloc and domain_free iommu-ops as a
replacement for domain_init/domain_destroy.

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

diff --git a/drivers/iommu/tegra-smmu.c b/drivers/iommu/tegra-smmu.c
index 6e134c7..f1bf84a 100644
--- a/drivers/iommu/tegra-smmu.c
+++ b/drivers/iommu/tegra-smmu.c
@@ -31,7 +31,7 @@ struct tegra_smmu {
 };
 
 struct tegra_smmu_as {
-	struct iommu_domain *domain;
+	struct iommu_domain domain;
 	struct tegra_smmu *smmu;
 	unsigned int use_count;
 	struct page *count;
@@ -40,6 +40,11 @@ struct tegra_smmu_as {
 	u32 attr;
 };
 
+static struct tegra_smmu_as *to_smmu_as(struct iommu_domain *dom)
+{
+	return container_of(dom, struct tegra_smmu_as, domain);
+}
+
 static inline void smmu_writel(struct tegra_smmu *smmu, u32 value,
 			       unsigned long offset)
 {
@@ -224,30 +229,32 @@ static bool tegra_smmu_capable(enum iommu_cap cap)
 	return false;
 }
 
-static int tegra_smmu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *tegra_smmu_domain_alloc(enum iommu_domain_type type)
 {
 	struct tegra_smmu_as *as;
 	unsigned int i;
 	uint32_t *pd;
 
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
+
 	as = kzalloc(sizeof(*as), GFP_KERNEL);
 	if (!as)
-		return -ENOMEM;
+		return NULL;
 
 	as->attr = SMMU_PD_READABLE | SMMU_PD_WRITABLE | SMMU_PD_NONSECURE;
-	as->domain = domain;
 
 	as->pd = alloc_page(GFP_KERNEL | __GFP_DMA);
 	if (!as->pd) {
 		kfree(as);
-		return -ENOMEM;
+		return NULL;
 	}
 
 	as->count = alloc_page(GFP_KERNEL);
 	if (!as->count) {
 		__free_page(as->pd);
 		kfree(as);
-		return -ENOMEM;
+		return NULL;
 	}
 
 	/* clear PDEs */
@@ -264,14 +271,12 @@ static int tegra_smmu_domain_init(struct iommu_domain *domain)
 	for (i = 0; i < SMMU_NUM_PDE; i++)
 		pd[i] = 0;
 
-	domain->priv = as;
-
-	return 0;
+	return &as->domain;
 }
 
-static void tegra_smmu_domain_destroy(struct iommu_domain *domain)
+static void tegra_smmu_domain_free(struct iommu_domain *domain)
 {
-	struct tegra_smmu_as *as = domain->priv;
+	struct tegra_smmu_as *as = to_smmu_as(domain);
 
 	/* TODO: free page directory and page tables */
 	ClearPageReserved(as->pd);
@@ -395,7 +400,7 @@ static int tegra_smmu_attach_dev(struct iommu_domain *domain,
 				 struct device *dev)
 {
 	struct tegra_smmu *smmu = dev->archdata.iommu;
-	struct tegra_smmu_as *as = domain->priv;
+	struct tegra_smmu_as *as = to_smmu_as(domain);
 	struct device_node *np = dev->of_node;
 	struct of_phandle_args args;
 	unsigned int index = 0;
@@ -428,7 +433,7 @@ static int tegra_smmu_attach_dev(struct iommu_domain *domain,
 
 static void tegra_smmu_detach_dev(struct iommu_domain *domain, struct device *dev)
 {
-	struct tegra_smmu_as *as = domain->priv;
+	struct tegra_smmu_as *as = to_smmu_as(domain);
 	struct device_node *np = dev->of_node;
 	struct tegra_smmu *smmu = as->smmu;
 	struct of_phandle_args args;
@@ -524,7 +529,7 @@ static void as_put_pte(struct tegra_smmu_as *as, dma_addr_t iova)
 static int tegra_smmu_map(struct iommu_domain *domain, unsigned long iova,
 			  phys_addr_t paddr, size_t size, int prot)
 {
-	struct tegra_smmu_as *as = domain->priv;
+	struct tegra_smmu_as *as = to_smmu_as(domain);
 	struct tegra_smmu *smmu = as->smmu;
 	unsigned long offset;
 	struct page *page;
@@ -548,7 +553,7 @@ static int tegra_smmu_map(struct iommu_domain *domain, unsigned long iova,
 static size_t tegra_smmu_unmap(struct iommu_domain *domain, unsigned long iova,
 			       size_t size)
 {
-	struct tegra_smmu_as *as = domain->priv;
+	struct tegra_smmu_as *as = to_smmu_as(domain);
 	struct tegra_smmu *smmu = as->smmu;
 	unsigned long offset;
 	struct page *page;
@@ -572,7 +577,7 @@ static size_t tegra_smmu_unmap(struct iommu_domain *domain, unsigned long iova,
 static phys_addr_t tegra_smmu_iova_to_phys(struct iommu_domain *domain,
 					   dma_addr_t iova)
 {
-	struct tegra_smmu_as *as = domain->priv;
+	struct tegra_smmu_as *as = to_smmu_as(domain);
 	struct page *page;
 	unsigned long pfn;
 	u32 *pte;
@@ -633,8 +638,8 @@ static void tegra_smmu_remove_device(struct device *dev)
 
 static const struct iommu_ops tegra_smmu_ops = {
 	.capable = tegra_smmu_capable,
-	.domain_init = tegra_smmu_domain_init,
-	.domain_destroy = tegra_smmu_domain_destroy,
+	.domain_alloc = tegra_smmu_domain_alloc,
+	.domain_free = tegra_smmu_domain_free,
 	.attach_dev = tegra_smmu_attach_dev,
 	.detach_dev = tegra_smmu_detach_dev,
 	.add_device = tegra_smmu_add_device,
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 09/15] iommu/tegra-gart: Make use of domain_alloc and domain_free
  2015-01-26 23:51 ` Joerg Roedel
  (?)
@ 2015-01-26 23:51     ` Joerg Roedel
  -1 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA
  Cc: Alexandre Courbot, linux-samsung-soc-u79uwXL29TY76Z2rM5mHXA,
	Heiko Stuebner, Arnd Bergmann, Stephen Warren, Will Deacon,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-rockchip-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Kukjin Kim,
	Thierry Reding, jroedel-l3A5Bk7waGM,
	linux-tegra-u79uwXL29TY76Z2rM5mHXA, David Woodhouse,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r

From: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>

Implement domain_alloc and domain_free iommu-ops as a
replacement for domain_init/domain_destroy.

Signed-off-by: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>
---
 drivers/iommu/tegra-gart.c | 67 +++++++++++++++++++++++++++++++---------------
 1 file changed, 46 insertions(+), 21 deletions(-)

diff --git a/drivers/iommu/tegra-gart.c b/drivers/iommu/tegra-gart.c
index f722a0c..34ca333 100644
--- a/drivers/iommu/tegra-gart.c
+++ b/drivers/iommu/tegra-gart.c
@@ -63,11 +63,21 @@ struct gart_device {
 	struct device		*dev;
 };
 
+struct gart_domain {
+	struct iommu_domain domain;		/* generic domain handle */
+	struct gart_device *gart;		/* link to gart device   */
+};
+
 static struct gart_device *gart_handle; /* unique for a system */
 
 #define GART_PTE(_pfn)						\
 	(GART_ENTRY_PHYS_ADDR_VALID | ((_pfn) << PAGE_SHIFT))
 
+static struct gart_domain *to_gart_domain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct gart_domain, domain);
+}
+
 /*
  * Any interaction between any block on PPSB and a block on APB or AHB
  * must have these read-back to ensure the APB/AHB bus transaction is
@@ -156,6 +166,7 @@ static inline bool gart_iova_range_valid(struct gart_device *gart,
 static int gart_iommu_attach_dev(struct iommu_domain *domain,
 				 struct device *dev)
 {
+	struct gart_domain *gart_domain = to_gart_domain(domain);
 	struct gart_device *gart;
 	struct gart_client *client, *c;
 	int err = 0;
@@ -163,7 +174,7 @@ static int gart_iommu_attach_dev(struct iommu_domain *domain,
 	gart = gart_handle;
 	if (!gart)
 		return -EINVAL;
-	domain->priv = gart;
+	gart_domain->gart = gart;
 
 	domain->geometry.aperture_start = gart->iovmm_base;
 	domain->geometry.aperture_end   = gart->iovmm_base +
@@ -198,7 +209,8 @@ fail:
 static void gart_iommu_detach_dev(struct iommu_domain *domain,
 				  struct device *dev)
 {
-	struct gart_device *gart = domain->priv;
+	struct gart_domain *gart_domain = to_gart_domain(domain);
+	struct gart_device *gart = gart_domain->gart;
 	struct gart_client *c;
 
 	spin_lock(&gart->client_lock);
@@ -216,33 +228,44 @@ out:
 	spin_unlock(&gart->client_lock);
 }
 
-static int gart_iommu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *gart_iommu_domain_alloc(enum iommu_domain_type type)
 {
-	return 0;
+	struct gart_domain *gart_domain;
+
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
+
+	gart_domain = kzalloc(sizeof(*gart_domain), GFP_KERNEL);
+	if (!gart_domain)
+		return NULL;
+
+	return &gart_domain->domain;
 }
 
-static void gart_iommu_domain_destroy(struct iommu_domain *domain)
+static void gart_iommu_domain_free(struct iommu_domain *domain)
 {
-	struct gart_device *gart = domain->priv;
-
-	if (!gart)
-		return;
+	struct gart_domain *gart_domain = to_gart_domain(domain);
+	struct gart_device *gart = gart_domain->gart;
 
-	spin_lock(&gart->client_lock);
-	if (!list_empty(&gart->client)) {
-		struct gart_client *c;
+	if (gart) {
+		spin_lock(&gart->client_lock);
+		if (!list_empty(&gart->client)) {
+			struct gart_client *c;
 
-		list_for_each_entry(c, &gart->client, list)
-			gart_iommu_detach_dev(domain, c->dev);
+			list_for_each_entry(c, &gart->client, list)
+				gart_iommu_detach_dev(domain, c->dev);
+		}
+		spin_unlock(&gart->client_lock);
 	}
-	spin_unlock(&gart->client_lock);
-	domain->priv = NULL;
+
+	kfree(gart_domain);
 }
 
 static int gart_iommu_map(struct iommu_domain *domain, unsigned long iova,
 			  phys_addr_t pa, size_t bytes, int prot)
 {
-	struct gart_device *gart = domain->priv;
+	struct gart_domain *gart_domain = to_gart_domain(domain);
+	struct gart_device *gart = gart_domain->gart;
 	unsigned long flags;
 	unsigned long pfn;
 
@@ -265,7 +288,8 @@ static int gart_iommu_map(struct iommu_domain *domain, unsigned long iova,
 static size_t gart_iommu_unmap(struct iommu_domain *domain, unsigned long iova,
 			       size_t bytes)
 {
-	struct gart_device *gart = domain->priv;
+	struct gart_domain *gart_domain = to_gart_domain(domain);
+	struct gart_device *gart = gart_domain->gart;
 	unsigned long flags;
 
 	if (!gart_iova_range_valid(gart, iova, bytes))
@@ -281,7 +305,8 @@ static size_t gart_iommu_unmap(struct iommu_domain *domain, unsigned long iova,
 static phys_addr_t gart_iommu_iova_to_phys(struct iommu_domain *domain,
 					   dma_addr_t iova)
 {
-	struct gart_device *gart = domain->priv;
+	struct gart_domain *gart_domain = to_gart_domain(domain);
+	struct gart_device *gart = gart_domain->gart;
 	unsigned long pte;
 	phys_addr_t pa;
 	unsigned long flags;
@@ -310,8 +335,8 @@ static bool gart_iommu_capable(enum iommu_cap cap)
 
 static const struct iommu_ops gart_iommu_ops = {
 	.capable	= gart_iommu_capable,
-	.domain_init	= gart_iommu_domain_init,
-	.domain_destroy	= gart_iommu_domain_destroy,
+	.domain_alloc	= gart_iommu_domain_alloc,
+	.domain_free	= gart_iommu_domain_free,
 	.attach_dev	= gart_iommu_attach_dev,
 	.detach_dev	= gart_iommu_detach_dev,
 	.map		= gart_iommu_map,
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 09/15] iommu/tegra-gart: Make use of domain_alloc and domain_free
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu
  Cc: Will Deacon, Kukjin Kim, David Woodhouse, Heiko Stuebner,
	Hiroshi Doyu, Stephen Warren, Thierry Reding, Alexandre Courbot,
	Alex Williamson, Arnd Bergmann, linux-kernel, linux-arm-kernel,
	linux-samsung-soc, linux-rockchip, linux-tegra, Joerg Roedel,
	jroedel

From: Joerg Roedel <jroedel@suse.de>

Implement domain_alloc and domain_free iommu-ops as a
replacement for domain_init/domain_destroy.

Signed-off-by: Joerg Roedel <jroedel@suse.de>
---
 drivers/iommu/tegra-gart.c | 67 +++++++++++++++++++++++++++++++---------------
 1 file changed, 46 insertions(+), 21 deletions(-)

diff --git a/drivers/iommu/tegra-gart.c b/drivers/iommu/tegra-gart.c
index f722a0c..34ca333 100644
--- a/drivers/iommu/tegra-gart.c
+++ b/drivers/iommu/tegra-gart.c
@@ -63,11 +63,21 @@ struct gart_device {
 	struct device		*dev;
 };
 
+struct gart_domain {
+	struct iommu_domain domain;		/* generic domain handle */
+	struct gart_device *gart;		/* link to gart device   */
+};
+
 static struct gart_device *gart_handle; /* unique for a system */
 
 #define GART_PTE(_pfn)						\
 	(GART_ENTRY_PHYS_ADDR_VALID | ((_pfn) << PAGE_SHIFT))
 
+static struct gart_domain *to_gart_domain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct gart_domain, domain);
+}
+
 /*
  * Any interaction between any block on PPSB and a block on APB or AHB
  * must have these read-back to ensure the APB/AHB bus transaction is
@@ -156,6 +166,7 @@ static inline bool gart_iova_range_valid(struct gart_device *gart,
 static int gart_iommu_attach_dev(struct iommu_domain *domain,
 				 struct device *dev)
 {
+	struct gart_domain *gart_domain = to_gart_domain(domain);
 	struct gart_device *gart;
 	struct gart_client *client, *c;
 	int err = 0;
@@ -163,7 +174,7 @@ static int gart_iommu_attach_dev(struct iommu_domain *domain,
 	gart = gart_handle;
 	if (!gart)
 		return -EINVAL;
-	domain->priv = gart;
+	gart_domain->gart = gart;
 
 	domain->geometry.aperture_start = gart->iovmm_base;
 	domain->geometry.aperture_end   = gart->iovmm_base +
@@ -198,7 +209,8 @@ fail:
 static void gart_iommu_detach_dev(struct iommu_domain *domain,
 				  struct device *dev)
 {
-	struct gart_device *gart = domain->priv;
+	struct gart_domain *gart_domain = to_gart_domain(domain);
+	struct gart_device *gart = gart_domain->gart;
 	struct gart_client *c;
 
 	spin_lock(&gart->client_lock);
@@ -216,33 +228,44 @@ out:
 	spin_unlock(&gart->client_lock);
 }
 
-static int gart_iommu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *gart_iommu_domain_alloc(enum iommu_domain_type type)
 {
-	return 0;
+	struct gart_domain *gart_domain;
+
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
+
+	gart_domain = kzalloc(sizeof(*gart_domain), GFP_KERNEL);
+	if (!gart_domain)
+		return NULL;
+
+	return &gart_domain->domain;
 }
 
-static void gart_iommu_domain_destroy(struct iommu_domain *domain)
+static void gart_iommu_domain_free(struct iommu_domain *domain)
 {
-	struct gart_device *gart = domain->priv;
-
-	if (!gart)
-		return;
+	struct gart_domain *gart_domain = to_gart_domain(domain);
+	struct gart_device *gart = gart_domain->gart;
 
-	spin_lock(&gart->client_lock);
-	if (!list_empty(&gart->client)) {
-		struct gart_client *c;
+	if (gart) {
+		spin_lock(&gart->client_lock);
+		if (!list_empty(&gart->client)) {
+			struct gart_client *c;
 
-		list_for_each_entry(c, &gart->client, list)
-			gart_iommu_detach_dev(domain, c->dev);
+			list_for_each_entry(c, &gart->client, list)
+				gart_iommu_detach_dev(domain, c->dev);
+		}
+		spin_unlock(&gart->client_lock);
 	}
-	spin_unlock(&gart->client_lock);
-	domain->priv = NULL;
+
+	kfree(gart_domain);
 }
 
 static int gart_iommu_map(struct iommu_domain *domain, unsigned long iova,
 			  phys_addr_t pa, size_t bytes, int prot)
 {
-	struct gart_device *gart = domain->priv;
+	struct gart_domain *gart_domain = to_gart_domain(domain);
+	struct gart_device *gart = gart_domain->gart;
 	unsigned long flags;
 	unsigned long pfn;
 
@@ -265,7 +288,8 @@ static int gart_iommu_map(struct iommu_domain *domain, unsigned long iova,
 static size_t gart_iommu_unmap(struct iommu_domain *domain, unsigned long iova,
 			       size_t bytes)
 {
-	struct gart_device *gart = domain->priv;
+	struct gart_domain *gart_domain = to_gart_domain(domain);
+	struct gart_device *gart = gart_domain->gart;
 	unsigned long flags;
 
 	if (!gart_iova_range_valid(gart, iova, bytes))
@@ -281,7 +305,8 @@ static size_t gart_iommu_unmap(struct iommu_domain *domain, unsigned long iova,
 static phys_addr_t gart_iommu_iova_to_phys(struct iommu_domain *domain,
 					   dma_addr_t iova)
 {
-	struct gart_device *gart = domain->priv;
+	struct gart_domain *gart_domain = to_gart_domain(domain);
+	struct gart_device *gart = gart_domain->gart;
 	unsigned long pte;
 	phys_addr_t pa;
 	unsigned long flags;
@@ -310,8 +335,8 @@ static bool gart_iommu_capable(enum iommu_cap cap)
 
 static const struct iommu_ops gart_iommu_ops = {
 	.capable	= gart_iommu_capable,
-	.domain_init	= gart_iommu_domain_init,
-	.domain_destroy	= gart_iommu_domain_destroy,
+	.domain_alloc	= gart_iommu_domain_alloc,
+	.domain_free	= gart_iommu_domain_free,
 	.attach_dev	= gart_iommu_attach_dev,
 	.detach_dev	= gart_iommu_detach_dev,
 	.map		= gart_iommu_map,
-- 
1.8.4.5


^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 09/15] iommu/tegra-gart: Make use of domain_alloc and domain_free
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: linux-arm-kernel

From: Joerg Roedel <jroedel@suse.de>

Implement domain_alloc and domain_free iommu-ops as a
replacement for domain_init/domain_destroy.

Signed-off-by: Joerg Roedel <jroedel@suse.de>
---
 drivers/iommu/tegra-gart.c | 67 +++++++++++++++++++++++++++++++---------------
 1 file changed, 46 insertions(+), 21 deletions(-)

diff --git a/drivers/iommu/tegra-gart.c b/drivers/iommu/tegra-gart.c
index f722a0c..34ca333 100644
--- a/drivers/iommu/tegra-gart.c
+++ b/drivers/iommu/tegra-gart.c
@@ -63,11 +63,21 @@ struct gart_device {
 	struct device		*dev;
 };
 
+struct gart_domain {
+	struct iommu_domain domain;		/* generic domain handle */
+	struct gart_device *gart;		/* link to gart device   */
+};
+
 static struct gart_device *gart_handle; /* unique for a system */
 
 #define GART_PTE(_pfn)						\
 	(GART_ENTRY_PHYS_ADDR_VALID | ((_pfn) << PAGE_SHIFT))
 
+static struct gart_domain *to_gart_domain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct gart_domain, domain);
+}
+
 /*
  * Any interaction between any block on PPSB and a block on APB or AHB
  * must have these read-back to ensure the APB/AHB bus transaction is
@@ -156,6 +166,7 @@ static inline bool gart_iova_range_valid(struct gart_device *gart,
 static int gart_iommu_attach_dev(struct iommu_domain *domain,
 				 struct device *dev)
 {
+	struct gart_domain *gart_domain = to_gart_domain(domain);
 	struct gart_device *gart;
 	struct gart_client *client, *c;
 	int err = 0;
@@ -163,7 +174,7 @@ static int gart_iommu_attach_dev(struct iommu_domain *domain,
 	gart = gart_handle;
 	if (!gart)
 		return -EINVAL;
-	domain->priv = gart;
+	gart_domain->gart = gart;
 
 	domain->geometry.aperture_start = gart->iovmm_base;
 	domain->geometry.aperture_end   = gart->iovmm_base +
@@ -198,7 +209,8 @@ fail:
 static void gart_iommu_detach_dev(struct iommu_domain *domain,
 				  struct device *dev)
 {
-	struct gart_device *gart = domain->priv;
+	struct gart_domain *gart_domain = to_gart_domain(domain);
+	struct gart_device *gart = gart_domain->gart;
 	struct gart_client *c;
 
 	spin_lock(&gart->client_lock);
@@ -216,33 +228,44 @@ out:
 	spin_unlock(&gart->client_lock);
 }
 
-static int gart_iommu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *gart_iommu_domain_alloc(enum iommu_domain_type type)
 {
-	return 0;
+	struct gart_domain *gart_domain;
+
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
+
+	gart_domain = kzalloc(sizeof(*gart_domain), GFP_KERNEL);
+	if (!gart_domain)
+		return NULL;
+
+	return &gart_domain->domain;
 }
 
-static void gart_iommu_domain_destroy(struct iommu_domain *domain)
+static void gart_iommu_domain_free(struct iommu_domain *domain)
 {
-	struct gart_device *gart = domain->priv;
-
-	if (!gart)
-		return;
+	struct gart_domain *gart_domain = to_gart_domain(domain);
+	struct gart_device *gart = gart_domain->gart;
 
-	spin_lock(&gart->client_lock);
-	if (!list_empty(&gart->client)) {
-		struct gart_client *c;
+	if (gart) {
+		spin_lock(&gart->client_lock);
+		if (!list_empty(&gart->client)) {
+			struct gart_client *c;
 
-		list_for_each_entry(c, &gart->client, list)
-			gart_iommu_detach_dev(domain, c->dev);
+			list_for_each_entry(c, &gart->client, list)
+				gart_iommu_detach_dev(domain, c->dev);
+		}
+		spin_unlock(&gart->client_lock);
 	}
-	spin_unlock(&gart->client_lock);
-	domain->priv = NULL;
+
+	kfree(gart_domain);
 }
 
 static int gart_iommu_map(struct iommu_domain *domain, unsigned long iova,
 			  phys_addr_t pa, size_t bytes, int prot)
 {
-	struct gart_device *gart = domain->priv;
+	struct gart_domain *gart_domain = to_gart_domain(domain);
+	struct gart_device *gart = gart_domain->gart;
 	unsigned long flags;
 	unsigned long pfn;
 
@@ -265,7 +288,8 @@ static int gart_iommu_map(struct iommu_domain *domain, unsigned long iova,
 static size_t gart_iommu_unmap(struct iommu_domain *domain, unsigned long iova,
 			       size_t bytes)
 {
-	struct gart_device *gart = domain->priv;
+	struct gart_domain *gart_domain = to_gart_domain(domain);
+	struct gart_device *gart = gart_domain->gart;
 	unsigned long flags;
 
 	if (!gart_iova_range_valid(gart, iova, bytes))
@@ -281,7 +305,8 @@ static size_t gart_iommu_unmap(struct iommu_domain *domain, unsigned long iova,
 static phys_addr_t gart_iommu_iova_to_phys(struct iommu_domain *domain,
 					   dma_addr_t iova)
 {
-	struct gart_device *gart = domain->priv;
+	struct gart_domain *gart_domain = to_gart_domain(domain);
+	struct gart_device *gart = gart_domain->gart;
 	unsigned long pte;
 	phys_addr_t pa;
 	unsigned long flags;
@@ -310,8 +335,8 @@ static bool gart_iommu_capable(enum iommu_cap cap)
 
 static const struct iommu_ops gart_iommu_ops = {
 	.capable	= gart_iommu_capable,
-	.domain_init	= gart_iommu_domain_init,
-	.domain_destroy	= gart_iommu_domain_destroy,
+	.domain_alloc	= gart_iommu_domain_alloc,
+	.domain_free	= gart_iommu_domain_free,
 	.attach_dev	= gart_iommu_attach_dev,
 	.detach_dev	= gart_iommu_detach_dev,
 	.map		= gart_iommu_map,
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 10/15] iommu/msm: Make use of domain_alloc and domain_free
  2015-01-26 23:51 ` Joerg Roedel
  (?)
@ 2015-01-26 23:51     ` Joerg Roedel
  -1 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA
  Cc: Alexandre Courbot, linux-samsung-soc-u79uwXL29TY76Z2rM5mHXA,
	Heiko Stuebner, Arnd Bergmann, Stephen Warren, Will Deacon,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-rockchip-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Kukjin Kim,
	Thierry Reding, jroedel-l3A5Bk7waGM,
	linux-tegra-u79uwXL29TY76Z2rM5mHXA, David Woodhouse,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r

From: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>

Implement domain_alloc and domain_free iommu-ops as a
replacement for domain_init/domain_destroy.

Signed-off-by: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>
---
 drivers/iommu/msm_iommu.c | 73 +++++++++++++++++++++++------------------------
 1 file changed, 36 insertions(+), 37 deletions(-)

diff --git a/drivers/iommu/msm_iommu.c b/drivers/iommu/msm_iommu.c
index e1b0537..f023c7a 100644
--- a/drivers/iommu/msm_iommu.c
+++ b/drivers/iommu/msm_iommu.c
@@ -52,8 +52,14 @@ DEFINE_SPINLOCK(msm_iommu_lock);
 struct msm_priv {
 	unsigned long *pgtable;
 	struct list_head list_attached;
+	struct iommu_domain domain;
 };
 
+static struct msm_priv *to_msm_priv(struct iommu_domain *dom)
+{
+	return container_of(dom, struct msm_priv, domain);
+}
+
 static int __enable_clocks(struct msm_iommu_drvdata *drvdata)
 {
 	int ret;
@@ -79,7 +85,7 @@ static void __disable_clocks(struct msm_iommu_drvdata *drvdata)
 
 static int __flush_iotlb(struct iommu_domain *domain)
 {
-	struct msm_priv *priv = domain->priv;
+	struct msm_priv *priv = to_msm_priv(domain);
 	struct msm_iommu_drvdata *iommu_drvdata;
 	struct msm_iommu_ctx_drvdata *ctx_drvdata;
 	int ret = 0;
@@ -209,10 +215,14 @@ static void __program_context(void __iomem *base, int ctx, phys_addr_t pgtable)
 	SET_M(base, ctx, 1);
 }
 
-static int msm_iommu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *msm_iommu_domain_alloc(enum iommu_domain_type type)
 {
-	struct msm_priv *priv = kzalloc(sizeof(*priv), GFP_KERNEL);
+	struct msm_priv *priv;
 
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
+
+	priv = kzalloc(sizeof(*priv), GFP_KERNEL);
 	if (!priv)
 		goto fail_nomem;
 
@@ -224,20 +234,19 @@ static int msm_iommu_domain_init(struct iommu_domain *domain)
 		goto fail_nomem;
 
 	memset(priv->pgtable, 0, SZ_16K);
-	domain->priv = priv;
 
-	domain->geometry.aperture_start = 0;
-	domain->geometry.aperture_end   = (1ULL << 32) - 1;
-	domain->geometry.force_aperture = true;
+	priv->domain.geometry.aperture_start = 0;
+	priv->domain.geometry.aperture_end   = (1ULL << 32) - 1;
+	priv->domain.geometry.force_aperture = true;
 
-	return 0;
+	return &priv->domain;
 
 fail_nomem:
 	kfree(priv);
-	return -ENOMEM;
+	return NULL;
 }
 
-static void msm_iommu_domain_destroy(struct iommu_domain *domain)
+static void msm_iommu_domain_free(struct iommu_domain *domain)
 {
 	struct msm_priv *priv;
 	unsigned long flags;
@@ -245,20 +254,17 @@ static void msm_iommu_domain_destroy(struct iommu_domain *domain)
 	int i;
 
 	spin_lock_irqsave(&msm_iommu_lock, flags);
-	priv = domain->priv;
-	domain->priv = NULL;
+	priv = to_msm_priv(domain);
 
-	if (priv) {
-		fl_table = priv->pgtable;
+	fl_table = priv->pgtable;
 
-		for (i = 0; i < NUM_FL_PTE; i++)
-			if ((fl_table[i] & 0x03) == FL_TYPE_TABLE)
-				free_page((unsigned long) __va(((fl_table[i]) &
-								FL_BASE_MASK)));
+	for (i = 0; i < NUM_FL_PTE; i++)
+		if ((fl_table[i] & 0x03) == FL_TYPE_TABLE)
+			free_page((unsigned long) __va(((fl_table[i]) &
+							FL_BASE_MASK)));
 
-		free_pages((unsigned long)priv->pgtable, get_order(SZ_16K));
-		priv->pgtable = NULL;
-	}
+	free_pages((unsigned long)priv->pgtable, get_order(SZ_16K));
+	priv->pgtable = NULL;
 
 	kfree(priv);
 	spin_unlock_irqrestore(&msm_iommu_lock, flags);
@@ -276,9 +282,9 @@ static int msm_iommu_attach_dev(struct iommu_domain *domain, struct device *dev)
 
 	spin_lock_irqsave(&msm_iommu_lock, flags);
 
-	priv = domain->priv;
+	priv = to_msm_priv(domain);
 
-	if (!priv || !dev) {
+	if (!dev) {
 		ret = -EINVAL;
 		goto fail;
 	}
@@ -330,9 +336,9 @@ static void msm_iommu_detach_dev(struct iommu_domain *domain,
 	int ret;
 
 	spin_lock_irqsave(&msm_iommu_lock, flags);
-	priv = domain->priv;
+	priv = to_msm_priv(domain);
 
-	if (!priv || !dev)
+	if (!dev)
 		goto fail;
 
 	iommu_drvdata = dev_get_drvdata(dev->parent);
@@ -382,11 +388,7 @@ static int msm_iommu_map(struct iommu_domain *domain, unsigned long va,
 		goto fail;
 	}
 
-	priv = domain->priv;
-	if (!priv) {
-		ret = -EINVAL;
-		goto fail;
-	}
+	priv = to_msm_priv(domain);
 
 	fl_table = priv->pgtable;
 
@@ -484,10 +486,7 @@ static size_t msm_iommu_unmap(struct iommu_domain *domain, unsigned long va,
 
 	spin_lock_irqsave(&msm_iommu_lock, flags);
 
-	priv = domain->priv;
-
-	if (!priv)
-		goto fail;
+	priv = to_msm_priv(domain);
 
 	fl_table = priv->pgtable;
 
@@ -566,7 +565,7 @@ static phys_addr_t msm_iommu_iova_to_phys(struct iommu_domain *domain,
 
 	spin_lock_irqsave(&msm_iommu_lock, flags);
 
-	priv = domain->priv;
+	priv = to_msm_priv(domain);
 	if (list_empty(&priv->list_attached))
 		goto fail;
 
@@ -674,8 +673,8 @@ fail:
 
 static const struct iommu_ops msm_iommu_ops = {
 	.capable = msm_iommu_capable,
-	.domain_init = msm_iommu_domain_init,
-	.domain_destroy = msm_iommu_domain_destroy,
+	.domain_alloc = msm_iommu_domain_alloc,
+	.domain_free = msm_iommu_domain_free,
 	.attach_dev = msm_iommu_attach_dev,
 	.detach_dev = msm_iommu_detach_dev,
 	.map = msm_iommu_map,
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 10/15] iommu/msm: Make use of domain_alloc and domain_free
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu
  Cc: Will Deacon, Kukjin Kim, David Woodhouse, Heiko Stuebner,
	Hiroshi Doyu, Stephen Warren, Thierry Reding, Alexandre Courbot,
	Alex Williamson, Arnd Bergmann, linux-kernel, linux-arm-kernel,
	linux-samsung-soc, linux-rockchip, linux-tegra, Joerg Roedel,
	jroedel

From: Joerg Roedel <jroedel@suse.de>

Implement domain_alloc and domain_free iommu-ops as a
replacement for domain_init/domain_destroy.

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

diff --git a/drivers/iommu/msm_iommu.c b/drivers/iommu/msm_iommu.c
index e1b0537..f023c7a 100644
--- a/drivers/iommu/msm_iommu.c
+++ b/drivers/iommu/msm_iommu.c
@@ -52,8 +52,14 @@ DEFINE_SPINLOCK(msm_iommu_lock);
 struct msm_priv {
 	unsigned long *pgtable;
 	struct list_head list_attached;
+	struct iommu_domain domain;
 };
 
+static struct msm_priv *to_msm_priv(struct iommu_domain *dom)
+{
+	return container_of(dom, struct msm_priv, domain);
+}
+
 static int __enable_clocks(struct msm_iommu_drvdata *drvdata)
 {
 	int ret;
@@ -79,7 +85,7 @@ static void __disable_clocks(struct msm_iommu_drvdata *drvdata)
 
 static int __flush_iotlb(struct iommu_domain *domain)
 {
-	struct msm_priv *priv = domain->priv;
+	struct msm_priv *priv = to_msm_priv(domain);
 	struct msm_iommu_drvdata *iommu_drvdata;
 	struct msm_iommu_ctx_drvdata *ctx_drvdata;
 	int ret = 0;
@@ -209,10 +215,14 @@ static void __program_context(void __iomem *base, int ctx, phys_addr_t pgtable)
 	SET_M(base, ctx, 1);
 }
 
-static int msm_iommu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *msm_iommu_domain_alloc(enum iommu_domain_type type)
 {
-	struct msm_priv *priv = kzalloc(sizeof(*priv), GFP_KERNEL);
+	struct msm_priv *priv;
 
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
+
+	priv = kzalloc(sizeof(*priv), GFP_KERNEL);
 	if (!priv)
 		goto fail_nomem;
 
@@ -224,20 +234,19 @@ static int msm_iommu_domain_init(struct iommu_domain *domain)
 		goto fail_nomem;
 
 	memset(priv->pgtable, 0, SZ_16K);
-	domain->priv = priv;
 
-	domain->geometry.aperture_start = 0;
-	domain->geometry.aperture_end   = (1ULL << 32) - 1;
-	domain->geometry.force_aperture = true;
+	priv->domain.geometry.aperture_start = 0;
+	priv->domain.geometry.aperture_end   = (1ULL << 32) - 1;
+	priv->domain.geometry.force_aperture = true;
 
-	return 0;
+	return &priv->domain;
 
 fail_nomem:
 	kfree(priv);
-	return -ENOMEM;
+	return NULL;
 }
 
-static void msm_iommu_domain_destroy(struct iommu_domain *domain)
+static void msm_iommu_domain_free(struct iommu_domain *domain)
 {
 	struct msm_priv *priv;
 	unsigned long flags;
@@ -245,20 +254,17 @@ static void msm_iommu_domain_destroy(struct iommu_domain *domain)
 	int i;
 
 	spin_lock_irqsave(&msm_iommu_lock, flags);
-	priv = domain->priv;
-	domain->priv = NULL;
+	priv = to_msm_priv(domain);
 
-	if (priv) {
-		fl_table = priv->pgtable;
+	fl_table = priv->pgtable;
 
-		for (i = 0; i < NUM_FL_PTE; i++)
-			if ((fl_table[i] & 0x03) == FL_TYPE_TABLE)
-				free_page((unsigned long) __va(((fl_table[i]) &
-								FL_BASE_MASK)));
+	for (i = 0; i < NUM_FL_PTE; i++)
+		if ((fl_table[i] & 0x03) == FL_TYPE_TABLE)
+			free_page((unsigned long) __va(((fl_table[i]) &
+							FL_BASE_MASK)));
 
-		free_pages((unsigned long)priv->pgtable, get_order(SZ_16K));
-		priv->pgtable = NULL;
-	}
+	free_pages((unsigned long)priv->pgtable, get_order(SZ_16K));
+	priv->pgtable = NULL;
 
 	kfree(priv);
 	spin_unlock_irqrestore(&msm_iommu_lock, flags);
@@ -276,9 +282,9 @@ static int msm_iommu_attach_dev(struct iommu_domain *domain, struct device *dev)
 
 	spin_lock_irqsave(&msm_iommu_lock, flags);
 
-	priv = domain->priv;
+	priv = to_msm_priv(domain);
 
-	if (!priv || !dev) {
+	if (!dev) {
 		ret = -EINVAL;
 		goto fail;
 	}
@@ -330,9 +336,9 @@ static void msm_iommu_detach_dev(struct iommu_domain *domain,
 	int ret;
 
 	spin_lock_irqsave(&msm_iommu_lock, flags);
-	priv = domain->priv;
+	priv = to_msm_priv(domain);
 
-	if (!priv || !dev)
+	if (!dev)
 		goto fail;
 
 	iommu_drvdata = dev_get_drvdata(dev->parent);
@@ -382,11 +388,7 @@ static int msm_iommu_map(struct iommu_domain *domain, unsigned long va,
 		goto fail;
 	}
 
-	priv = domain->priv;
-	if (!priv) {
-		ret = -EINVAL;
-		goto fail;
-	}
+	priv = to_msm_priv(domain);
 
 	fl_table = priv->pgtable;
 
@@ -484,10 +486,7 @@ static size_t msm_iommu_unmap(struct iommu_domain *domain, unsigned long va,
 
 	spin_lock_irqsave(&msm_iommu_lock, flags);
 
-	priv = domain->priv;
-
-	if (!priv)
-		goto fail;
+	priv = to_msm_priv(domain);
 
 	fl_table = priv->pgtable;
 
@@ -566,7 +565,7 @@ static phys_addr_t msm_iommu_iova_to_phys(struct iommu_domain *domain,
 
 	spin_lock_irqsave(&msm_iommu_lock, flags);
 
-	priv = domain->priv;
+	priv = to_msm_priv(domain);
 	if (list_empty(&priv->list_attached))
 		goto fail;
 
@@ -674,8 +673,8 @@ fail:
 
 static const struct iommu_ops msm_iommu_ops = {
 	.capable = msm_iommu_capable,
-	.domain_init = msm_iommu_domain_init,
-	.domain_destroy = msm_iommu_domain_destroy,
+	.domain_alloc = msm_iommu_domain_alloc,
+	.domain_free = msm_iommu_domain_free,
 	.attach_dev = msm_iommu_attach_dev,
 	.detach_dev = msm_iommu_detach_dev,
 	.map = msm_iommu_map,
-- 
1.8.4.5


^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 10/15] iommu/msm: Make use of domain_alloc and domain_free
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: linux-arm-kernel

From: Joerg Roedel <jroedel@suse.de>

Implement domain_alloc and domain_free iommu-ops as a
replacement for domain_init/domain_destroy.

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

diff --git a/drivers/iommu/msm_iommu.c b/drivers/iommu/msm_iommu.c
index e1b0537..f023c7a 100644
--- a/drivers/iommu/msm_iommu.c
+++ b/drivers/iommu/msm_iommu.c
@@ -52,8 +52,14 @@ DEFINE_SPINLOCK(msm_iommu_lock);
 struct msm_priv {
 	unsigned long *pgtable;
 	struct list_head list_attached;
+	struct iommu_domain domain;
 };
 
+static struct msm_priv *to_msm_priv(struct iommu_domain *dom)
+{
+	return container_of(dom, struct msm_priv, domain);
+}
+
 static int __enable_clocks(struct msm_iommu_drvdata *drvdata)
 {
 	int ret;
@@ -79,7 +85,7 @@ static void __disable_clocks(struct msm_iommu_drvdata *drvdata)
 
 static int __flush_iotlb(struct iommu_domain *domain)
 {
-	struct msm_priv *priv = domain->priv;
+	struct msm_priv *priv = to_msm_priv(domain);
 	struct msm_iommu_drvdata *iommu_drvdata;
 	struct msm_iommu_ctx_drvdata *ctx_drvdata;
 	int ret = 0;
@@ -209,10 +215,14 @@ static void __program_context(void __iomem *base, int ctx, phys_addr_t pgtable)
 	SET_M(base, ctx, 1);
 }
 
-static int msm_iommu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *msm_iommu_domain_alloc(enum iommu_domain_type type)
 {
-	struct msm_priv *priv = kzalloc(sizeof(*priv), GFP_KERNEL);
+	struct msm_priv *priv;
 
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
+
+	priv = kzalloc(sizeof(*priv), GFP_KERNEL);
 	if (!priv)
 		goto fail_nomem;
 
@@ -224,20 +234,19 @@ static int msm_iommu_domain_init(struct iommu_domain *domain)
 		goto fail_nomem;
 
 	memset(priv->pgtable, 0, SZ_16K);
-	domain->priv = priv;
 
-	domain->geometry.aperture_start = 0;
-	domain->geometry.aperture_end   = (1ULL << 32) - 1;
-	domain->geometry.force_aperture = true;
+	priv->domain.geometry.aperture_start = 0;
+	priv->domain.geometry.aperture_end   = (1ULL << 32) - 1;
+	priv->domain.geometry.force_aperture = true;
 
-	return 0;
+	return &priv->domain;
 
 fail_nomem:
 	kfree(priv);
-	return -ENOMEM;
+	return NULL;
 }
 
-static void msm_iommu_domain_destroy(struct iommu_domain *domain)
+static void msm_iommu_domain_free(struct iommu_domain *domain)
 {
 	struct msm_priv *priv;
 	unsigned long flags;
@@ -245,20 +254,17 @@ static void msm_iommu_domain_destroy(struct iommu_domain *domain)
 	int i;
 
 	spin_lock_irqsave(&msm_iommu_lock, flags);
-	priv = domain->priv;
-	domain->priv = NULL;
+	priv = to_msm_priv(domain);
 
-	if (priv) {
-		fl_table = priv->pgtable;
+	fl_table = priv->pgtable;
 
-		for (i = 0; i < NUM_FL_PTE; i++)
-			if ((fl_table[i] & 0x03) == FL_TYPE_TABLE)
-				free_page((unsigned long) __va(((fl_table[i]) &
-								FL_BASE_MASK)));
+	for (i = 0; i < NUM_FL_PTE; i++)
+		if ((fl_table[i] & 0x03) == FL_TYPE_TABLE)
+			free_page((unsigned long) __va(((fl_table[i]) &
+							FL_BASE_MASK)));
 
-		free_pages((unsigned long)priv->pgtable, get_order(SZ_16K));
-		priv->pgtable = NULL;
-	}
+	free_pages((unsigned long)priv->pgtable, get_order(SZ_16K));
+	priv->pgtable = NULL;
 
 	kfree(priv);
 	spin_unlock_irqrestore(&msm_iommu_lock, flags);
@@ -276,9 +282,9 @@ static int msm_iommu_attach_dev(struct iommu_domain *domain, struct device *dev)
 
 	spin_lock_irqsave(&msm_iommu_lock, flags);
 
-	priv = domain->priv;
+	priv = to_msm_priv(domain);
 
-	if (!priv || !dev) {
+	if (!dev) {
 		ret = -EINVAL;
 		goto fail;
 	}
@@ -330,9 +336,9 @@ static void msm_iommu_detach_dev(struct iommu_domain *domain,
 	int ret;
 
 	spin_lock_irqsave(&msm_iommu_lock, flags);
-	priv = domain->priv;
+	priv = to_msm_priv(domain);
 
-	if (!priv || !dev)
+	if (!dev)
 		goto fail;
 
 	iommu_drvdata = dev_get_drvdata(dev->parent);
@@ -382,11 +388,7 @@ static int msm_iommu_map(struct iommu_domain *domain, unsigned long va,
 		goto fail;
 	}
 
-	priv = domain->priv;
-	if (!priv) {
-		ret = -EINVAL;
-		goto fail;
-	}
+	priv = to_msm_priv(domain);
 
 	fl_table = priv->pgtable;
 
@@ -484,10 +486,7 @@ static size_t msm_iommu_unmap(struct iommu_domain *domain, unsigned long va,
 
 	spin_lock_irqsave(&msm_iommu_lock, flags);
 
-	priv = domain->priv;
-
-	if (!priv)
-		goto fail;
+	priv = to_msm_priv(domain);
 
 	fl_table = priv->pgtable;
 
@@ -566,7 +565,7 @@ static phys_addr_t msm_iommu_iova_to_phys(struct iommu_domain *domain,
 
 	spin_lock_irqsave(&msm_iommu_lock, flags);
 
-	priv = domain->priv;
+	priv = to_msm_priv(domain);
 	if (list_empty(&priv->list_attached))
 		goto fail;
 
@@ -674,8 +673,8 @@ fail:
 
 static const struct iommu_ops msm_iommu_ops = {
 	.capable = msm_iommu_capable,
-	.domain_init = msm_iommu_domain_init,
-	.domain_destroy = msm_iommu_domain_destroy,
+	.domain_alloc = msm_iommu_domain_alloc,
+	.domain_free = msm_iommu_domain_free,
 	.attach_dev = msm_iommu_attach_dev,
 	.detach_dev = msm_iommu_detach_dev,
 	.map = msm_iommu_map,
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 11/15] iommu/shmobile: Make use of domain_alloc and domain_free
  2015-01-26 23:51 ` Joerg Roedel
  (?)
@ 2015-01-26 23:51     ` Joerg Roedel
  -1 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA
  Cc: Alexandre Courbot, linux-samsung-soc-u79uwXL29TY76Z2rM5mHXA,
	Heiko Stuebner, Arnd Bergmann, Stephen Warren, Will Deacon,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-rockchip-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Kukjin Kim,
	Thierry Reding, jroedel-l3A5Bk7waGM,
	linux-tegra-u79uwXL29TY76Z2rM5mHXA, David Woodhouse,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r

From: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>

Implement domain_alloc and domain_free iommu-ops as a
replacement for domain_init/domain_destroy.

Signed-off-by: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>
---
 drivers/iommu/shmobile-iommu.c | 40 ++++++++++++++++++++++++----------------
 1 file changed, 24 insertions(+), 16 deletions(-)

diff --git a/drivers/iommu/shmobile-iommu.c b/drivers/iommu/shmobile-iommu.c
index f1b0077..a65601c 100644
--- a/drivers/iommu/shmobile-iommu.c
+++ b/drivers/iommu/shmobile-iommu.c
@@ -42,11 +42,17 @@ struct shmobile_iommu_domain {
 	spinlock_t map_lock;
 	spinlock_t attached_list_lock;
 	struct list_head attached_list;
+	struct iommu_domain domain;
 };
 
 static struct shmobile_iommu_archdata *ipmmu_archdata;
 static struct kmem_cache *l1cache, *l2cache;
 
+static struct shmobile_iommu_domain *to_sh_domain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct shmobile_iommu_domain, domain);
+}
+
 static int pgtable_alloc(struct shmobile_iommu_domain_pgtable *pgtable,
 			 struct kmem_cache *cache, size_t size)
 {
@@ -82,31 +88,34 @@ static void pgtable_write(struct shmobile_iommu_domain_pgtable *pgtable,
 				   sizeof(val) * count, DMA_TO_DEVICE);
 }
 
-static int shmobile_iommu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *
+shmobile_iommu_domain_alloc(enum iommu_domain_type type)
 {
 	struct shmobile_iommu_domain *sh_domain;
 	int i, ret;
 
-	sh_domain = kmalloc(sizeof(*sh_domain), GFP_KERNEL);
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
+
+	sh_domain = kzalloc(sizeof(*sh_domain), GFP_KERNEL);
 	if (!sh_domain)
-		return -ENOMEM;
+		return NULL;
 	ret = pgtable_alloc(&sh_domain->l1, l1cache, L1_SIZE);
 	if (ret < 0) {
 		kfree(sh_domain);
-		return ret;
+		return NULL;
 	}
 	for (i = 0; i < L1_LEN; i++)
 		sh_domain->l2[i].pgtable = NULL;
 	spin_lock_init(&sh_domain->map_lock);
 	spin_lock_init(&sh_domain->attached_list_lock);
 	INIT_LIST_HEAD(&sh_domain->attached_list);
-	domain->priv = sh_domain;
-	return 0;
+	return &sh_domain->domain;
 }
 
-static void shmobile_iommu_domain_destroy(struct iommu_domain *domain)
+static void shmobile_iommu_domain_free(struct iommu_domain *domain)
 {
-	struct shmobile_iommu_domain *sh_domain = domain->priv;
+	struct shmobile_iommu_domain *sh_domain = to_sh_domain(domain);
 	int i;
 
 	for (i = 0; i < L1_LEN; i++) {
@@ -115,14 +124,13 @@ static void shmobile_iommu_domain_destroy(struct iommu_domain *domain)
 	}
 	pgtable_free(&sh_domain->l1, l1cache, L1_SIZE);
 	kfree(sh_domain);
-	domain->priv = NULL;
 }
 
 static int shmobile_iommu_attach_device(struct iommu_domain *domain,
 					struct device *dev)
 {
 	struct shmobile_iommu_archdata *archdata = dev->archdata.iommu;
-	struct shmobile_iommu_domain *sh_domain = domain->priv;
+	struct shmobile_iommu_domain *sh_domain = to_sh_domain(domain);
 	int ret = -EBUSY;
 
 	if (!archdata)
@@ -151,7 +159,7 @@ static void shmobile_iommu_detach_device(struct iommu_domain *domain,
 					 struct device *dev)
 {
 	struct shmobile_iommu_archdata *archdata = dev->archdata.iommu;
-	struct shmobile_iommu_domain *sh_domain = domain->priv;
+	struct shmobile_iommu_domain *sh_domain = to_sh_domain(domain);
 
 	if (!archdata)
 		return;
@@ -214,7 +222,7 @@ static int shmobile_iommu_map(struct iommu_domain *domain, unsigned long iova,
 			      phys_addr_t paddr, size_t size, int prot)
 {
 	struct shmobile_iommu_domain_pgtable l2 = { .pgtable = NULL };
-	struct shmobile_iommu_domain *sh_domain = domain->priv;
+	struct shmobile_iommu_domain *sh_domain = to_sh_domain(domain);
 	unsigned int l1index, l2index;
 	int ret;
 
@@ -258,7 +266,7 @@ static size_t shmobile_iommu_unmap(struct iommu_domain *domain,
 				   unsigned long iova, size_t size)
 {
 	struct shmobile_iommu_domain_pgtable l2 = { .pgtable = NULL };
-	struct shmobile_iommu_domain *sh_domain = domain->priv;
+	struct shmobile_iommu_domain *sh_domain = to_sh_domain(domain);
 	unsigned int l1index, l2index;
 	uint32_t l2entry = 0;
 	size_t ret = 0;
@@ -298,7 +306,7 @@ done:
 static phys_addr_t shmobile_iommu_iova_to_phys(struct iommu_domain *domain,
 					       dma_addr_t iova)
 {
-	struct shmobile_iommu_domain *sh_domain = domain->priv;
+	struct shmobile_iommu_domain *sh_domain = to_sh_domain(domain);
 	uint32_t l1entry = 0, l2entry = 0;
 	unsigned int l1index, l2index;
 
@@ -355,8 +363,8 @@ static int shmobile_iommu_add_device(struct device *dev)
 }
 
 static const struct iommu_ops shmobile_iommu_ops = {
-	.domain_init = shmobile_iommu_domain_init,
-	.domain_destroy = shmobile_iommu_domain_destroy,
+	.domain_alloc = shmobile_iommu_domain_alloc,
+	.domain_free = shmobile_iommu_domain_free,
 	.attach_dev = shmobile_iommu_attach_device,
 	.detach_dev = shmobile_iommu_detach_device,
 	.map = shmobile_iommu_map,
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 11/15] iommu/shmobile: Make use of domain_alloc and domain_free
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu
  Cc: Will Deacon, Kukjin Kim, David Woodhouse, Heiko Stuebner,
	Hiroshi Doyu, Stephen Warren, Thierry Reding, Alexandre Courbot,
	Alex Williamson, Arnd Bergmann, linux-kernel, linux-arm-kernel,
	linux-samsung-soc, linux-rockchip, linux-tegra, Joerg Roedel,
	jroedel

From: Joerg Roedel <jroedel@suse.de>

Implement domain_alloc and domain_free iommu-ops as a
replacement for domain_init/domain_destroy.

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

diff --git a/drivers/iommu/shmobile-iommu.c b/drivers/iommu/shmobile-iommu.c
index f1b0077..a65601c 100644
--- a/drivers/iommu/shmobile-iommu.c
+++ b/drivers/iommu/shmobile-iommu.c
@@ -42,11 +42,17 @@ struct shmobile_iommu_domain {
 	spinlock_t map_lock;
 	spinlock_t attached_list_lock;
 	struct list_head attached_list;
+	struct iommu_domain domain;
 };
 
 static struct shmobile_iommu_archdata *ipmmu_archdata;
 static struct kmem_cache *l1cache, *l2cache;
 
+static struct shmobile_iommu_domain *to_sh_domain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct shmobile_iommu_domain, domain);
+}
+
 static int pgtable_alloc(struct shmobile_iommu_domain_pgtable *pgtable,
 			 struct kmem_cache *cache, size_t size)
 {
@@ -82,31 +88,34 @@ static void pgtable_write(struct shmobile_iommu_domain_pgtable *pgtable,
 				   sizeof(val) * count, DMA_TO_DEVICE);
 }
 
-static int shmobile_iommu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *
+shmobile_iommu_domain_alloc(enum iommu_domain_type type)
 {
 	struct shmobile_iommu_domain *sh_domain;
 	int i, ret;
 
-	sh_domain = kmalloc(sizeof(*sh_domain), GFP_KERNEL);
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
+
+	sh_domain = kzalloc(sizeof(*sh_domain), GFP_KERNEL);
 	if (!sh_domain)
-		return -ENOMEM;
+		return NULL;
 	ret = pgtable_alloc(&sh_domain->l1, l1cache, L1_SIZE);
 	if (ret < 0) {
 		kfree(sh_domain);
-		return ret;
+		return NULL;
 	}
 	for (i = 0; i < L1_LEN; i++)
 		sh_domain->l2[i].pgtable = NULL;
 	spin_lock_init(&sh_domain->map_lock);
 	spin_lock_init(&sh_domain->attached_list_lock);
 	INIT_LIST_HEAD(&sh_domain->attached_list);
-	domain->priv = sh_domain;
-	return 0;
+	return &sh_domain->domain;
 }
 
-static void shmobile_iommu_domain_destroy(struct iommu_domain *domain)
+static void shmobile_iommu_domain_free(struct iommu_domain *domain)
 {
-	struct shmobile_iommu_domain *sh_domain = domain->priv;
+	struct shmobile_iommu_domain *sh_domain = to_sh_domain(domain);
 	int i;
 
 	for (i = 0; i < L1_LEN; i++) {
@@ -115,14 +124,13 @@ static void shmobile_iommu_domain_destroy(struct iommu_domain *domain)
 	}
 	pgtable_free(&sh_domain->l1, l1cache, L1_SIZE);
 	kfree(sh_domain);
-	domain->priv = NULL;
 }
 
 static int shmobile_iommu_attach_device(struct iommu_domain *domain,
 					struct device *dev)
 {
 	struct shmobile_iommu_archdata *archdata = dev->archdata.iommu;
-	struct shmobile_iommu_domain *sh_domain = domain->priv;
+	struct shmobile_iommu_domain *sh_domain = to_sh_domain(domain);
 	int ret = -EBUSY;
 
 	if (!archdata)
@@ -151,7 +159,7 @@ static void shmobile_iommu_detach_device(struct iommu_domain *domain,
 					 struct device *dev)
 {
 	struct shmobile_iommu_archdata *archdata = dev->archdata.iommu;
-	struct shmobile_iommu_domain *sh_domain = domain->priv;
+	struct shmobile_iommu_domain *sh_domain = to_sh_domain(domain);
 
 	if (!archdata)
 		return;
@@ -214,7 +222,7 @@ static int shmobile_iommu_map(struct iommu_domain *domain, unsigned long iova,
 			      phys_addr_t paddr, size_t size, int prot)
 {
 	struct shmobile_iommu_domain_pgtable l2 = { .pgtable = NULL };
-	struct shmobile_iommu_domain *sh_domain = domain->priv;
+	struct shmobile_iommu_domain *sh_domain = to_sh_domain(domain);
 	unsigned int l1index, l2index;
 	int ret;
 
@@ -258,7 +266,7 @@ static size_t shmobile_iommu_unmap(struct iommu_domain *domain,
 				   unsigned long iova, size_t size)
 {
 	struct shmobile_iommu_domain_pgtable l2 = { .pgtable = NULL };
-	struct shmobile_iommu_domain *sh_domain = domain->priv;
+	struct shmobile_iommu_domain *sh_domain = to_sh_domain(domain);
 	unsigned int l1index, l2index;
 	uint32_t l2entry = 0;
 	size_t ret = 0;
@@ -298,7 +306,7 @@ done:
 static phys_addr_t shmobile_iommu_iova_to_phys(struct iommu_domain *domain,
 					       dma_addr_t iova)
 {
-	struct shmobile_iommu_domain *sh_domain = domain->priv;
+	struct shmobile_iommu_domain *sh_domain = to_sh_domain(domain);
 	uint32_t l1entry = 0, l2entry = 0;
 	unsigned int l1index, l2index;
 
@@ -355,8 +363,8 @@ static int shmobile_iommu_add_device(struct device *dev)
 }
 
 static const struct iommu_ops shmobile_iommu_ops = {
-	.domain_init = shmobile_iommu_domain_init,
-	.domain_destroy = shmobile_iommu_domain_destroy,
+	.domain_alloc = shmobile_iommu_domain_alloc,
+	.domain_free = shmobile_iommu_domain_free,
 	.attach_dev = shmobile_iommu_attach_device,
 	.detach_dev = shmobile_iommu_detach_device,
 	.map = shmobile_iommu_map,
-- 
1.8.4.5


^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 11/15] iommu/shmobile: Make use of domain_alloc and domain_free
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: linux-arm-kernel

From: Joerg Roedel <jroedel@suse.de>

Implement domain_alloc and domain_free iommu-ops as a
replacement for domain_init/domain_destroy.

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

diff --git a/drivers/iommu/shmobile-iommu.c b/drivers/iommu/shmobile-iommu.c
index f1b0077..a65601c 100644
--- a/drivers/iommu/shmobile-iommu.c
+++ b/drivers/iommu/shmobile-iommu.c
@@ -42,11 +42,17 @@ struct shmobile_iommu_domain {
 	spinlock_t map_lock;
 	spinlock_t attached_list_lock;
 	struct list_head attached_list;
+	struct iommu_domain domain;
 };
 
 static struct shmobile_iommu_archdata *ipmmu_archdata;
 static struct kmem_cache *l1cache, *l2cache;
 
+static struct shmobile_iommu_domain *to_sh_domain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct shmobile_iommu_domain, domain);
+}
+
 static int pgtable_alloc(struct shmobile_iommu_domain_pgtable *pgtable,
 			 struct kmem_cache *cache, size_t size)
 {
@@ -82,31 +88,34 @@ static void pgtable_write(struct shmobile_iommu_domain_pgtable *pgtable,
 				   sizeof(val) * count, DMA_TO_DEVICE);
 }
 
-static int shmobile_iommu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *
+shmobile_iommu_domain_alloc(enum iommu_domain_type type)
 {
 	struct shmobile_iommu_domain *sh_domain;
 	int i, ret;
 
-	sh_domain = kmalloc(sizeof(*sh_domain), GFP_KERNEL);
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
+
+	sh_domain = kzalloc(sizeof(*sh_domain), GFP_KERNEL);
 	if (!sh_domain)
-		return -ENOMEM;
+		return NULL;
 	ret = pgtable_alloc(&sh_domain->l1, l1cache, L1_SIZE);
 	if (ret < 0) {
 		kfree(sh_domain);
-		return ret;
+		return NULL;
 	}
 	for (i = 0; i < L1_LEN; i++)
 		sh_domain->l2[i].pgtable = NULL;
 	spin_lock_init(&sh_domain->map_lock);
 	spin_lock_init(&sh_domain->attached_list_lock);
 	INIT_LIST_HEAD(&sh_domain->attached_list);
-	domain->priv = sh_domain;
-	return 0;
+	return &sh_domain->domain;
 }
 
-static void shmobile_iommu_domain_destroy(struct iommu_domain *domain)
+static void shmobile_iommu_domain_free(struct iommu_domain *domain)
 {
-	struct shmobile_iommu_domain *sh_domain = domain->priv;
+	struct shmobile_iommu_domain *sh_domain = to_sh_domain(domain);
 	int i;
 
 	for (i = 0; i < L1_LEN; i++) {
@@ -115,14 +124,13 @@ static void shmobile_iommu_domain_destroy(struct iommu_domain *domain)
 	}
 	pgtable_free(&sh_domain->l1, l1cache, L1_SIZE);
 	kfree(sh_domain);
-	domain->priv = NULL;
 }
 
 static int shmobile_iommu_attach_device(struct iommu_domain *domain,
 					struct device *dev)
 {
 	struct shmobile_iommu_archdata *archdata = dev->archdata.iommu;
-	struct shmobile_iommu_domain *sh_domain = domain->priv;
+	struct shmobile_iommu_domain *sh_domain = to_sh_domain(domain);
 	int ret = -EBUSY;
 
 	if (!archdata)
@@ -151,7 +159,7 @@ static void shmobile_iommu_detach_device(struct iommu_domain *domain,
 					 struct device *dev)
 {
 	struct shmobile_iommu_archdata *archdata = dev->archdata.iommu;
-	struct shmobile_iommu_domain *sh_domain = domain->priv;
+	struct shmobile_iommu_domain *sh_domain = to_sh_domain(domain);
 
 	if (!archdata)
 		return;
@@ -214,7 +222,7 @@ static int shmobile_iommu_map(struct iommu_domain *domain, unsigned long iova,
 			      phys_addr_t paddr, size_t size, int prot)
 {
 	struct shmobile_iommu_domain_pgtable l2 = { .pgtable = NULL };
-	struct shmobile_iommu_domain *sh_domain = domain->priv;
+	struct shmobile_iommu_domain *sh_domain = to_sh_domain(domain);
 	unsigned int l1index, l2index;
 	int ret;
 
@@ -258,7 +266,7 @@ static size_t shmobile_iommu_unmap(struct iommu_domain *domain,
 				   unsigned long iova, size_t size)
 {
 	struct shmobile_iommu_domain_pgtable l2 = { .pgtable = NULL };
-	struct shmobile_iommu_domain *sh_domain = domain->priv;
+	struct shmobile_iommu_domain *sh_domain = to_sh_domain(domain);
 	unsigned int l1index, l2index;
 	uint32_t l2entry = 0;
 	size_t ret = 0;
@@ -298,7 +306,7 @@ done:
 static phys_addr_t shmobile_iommu_iova_to_phys(struct iommu_domain *domain,
 					       dma_addr_t iova)
 {
-	struct shmobile_iommu_domain *sh_domain = domain->priv;
+	struct shmobile_iommu_domain *sh_domain = to_sh_domain(domain);
 	uint32_t l1entry = 0, l2entry = 0;
 	unsigned int l1index, l2index;
 
@@ -355,8 +363,8 @@ static int shmobile_iommu_add_device(struct device *dev)
 }
 
 static const struct iommu_ops shmobile_iommu_ops = {
-	.domain_init = shmobile_iommu_domain_init,
-	.domain_destroy = shmobile_iommu_domain_destroy,
+	.domain_alloc = shmobile_iommu_domain_alloc,
+	.domain_free = shmobile_iommu_domain_free,
 	.attach_dev = shmobile_iommu_attach_device,
 	.detach_dev = shmobile_iommu_detach_device,
 	.map = shmobile_iommu_map,
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 12/15] iommu/ipmmu-vmsa: Make use of domain_alloc and domain_free
  2015-01-26 23:51 ` Joerg Roedel
  (?)
@ 2015-01-26 23:51     ` Joerg Roedel
  -1 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA
  Cc: Alexandre Courbot, linux-samsung-soc-u79uwXL29TY76Z2rM5mHXA,
	Heiko Stuebner, Arnd Bergmann, Stephen Warren, Will Deacon,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-rockchip-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Kukjin Kim,
	Thierry Reding, jroedel-l3A5Bk7waGM,
	linux-tegra-u79uwXL29TY76Z2rM5mHXA, David Woodhouse,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r

From: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>

Implement domain_alloc and domain_free iommu-ops as a
replacement for domain_init/domain_destroy.

Signed-off-by: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>
---
 drivers/iommu/ipmmu-vmsa.c | 43 ++++++++++++++++++++++++-------------------
 1 file changed, 24 insertions(+), 19 deletions(-)

diff --git a/drivers/iommu/ipmmu-vmsa.c b/drivers/iommu/ipmmu-vmsa.c
index 7486931..12270e1 100644
--- a/drivers/iommu/ipmmu-vmsa.c
+++ b/drivers/iommu/ipmmu-vmsa.c
@@ -37,7 +37,7 @@ struct ipmmu_vmsa_device {
 
 struct ipmmu_vmsa_domain {
 	struct ipmmu_vmsa_device *mmu;
-	struct iommu_domain *io_domain;
+	struct iommu_domain io_domain;
 
 	unsigned int context_id;
 	spinlock_t lock;			/* Protects mappings */
@@ -52,6 +52,11 @@ struct ipmmu_vmsa_archdata {
 static DEFINE_SPINLOCK(ipmmu_devices_lock);
 static LIST_HEAD(ipmmu_devices);
 
+static struct ipmmu_vmsa_domain *to_vmsa_domain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct ipmmu_vmsa_domain, io_domain);
+}
+
 #define TLB_LOOP_TIMEOUT		100	/* 100us */
 
 /* -----------------------------------------------------------------------------
@@ -435,7 +440,7 @@ static irqreturn_t ipmmu_domain_irq(struct ipmmu_vmsa_domain *domain)
 	 * TODO: We need to look up the faulty device based on the I/O VA. Use
 	 * the IOMMU device for now.
 	 */
-	if (!report_iommu_fault(domain->io_domain, mmu->dev, iova, 0))
+	if (!report_iommu_fault(&domain->io_domain, mmu->dev, iova, 0))
 		return IRQ_HANDLED;
 
 	dev_err_ratelimited(mmu->dev,
@@ -455,7 +460,7 @@ static irqreturn_t ipmmu_irq(int irq, void *dev)
 		return IRQ_NONE;
 
 	io_domain = mmu->mapping->domain;
-	domain = io_domain->priv;
+	domain = to_vmsa_domain(io_domain);
 
 	return ipmmu_domain_irq(domain);
 }
@@ -854,31 +859,31 @@ done:
  * IOMMU Operations
  */
 
-static int ipmmu_domain_init(struct iommu_domain *io_domain)
+static struct iommu_domain *ipmmu_domain_alloc(enum iommu_domain_type type)
 {
 	struct ipmmu_vmsa_domain *domain;
 
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
+
 	domain = kzalloc(sizeof(*domain), GFP_KERNEL);
 	if (!domain)
-		return -ENOMEM;
+		return NULL;
 
 	spin_lock_init(&domain->lock);
 
 	domain->pgd = kzalloc(IPMMU_PTRS_PER_PGD * sizeof(pgd_t), GFP_KERNEL);
 	if (!domain->pgd) {
 		kfree(domain);
-		return -ENOMEM;
+		return NULL;
 	}
 
-	io_domain->priv = domain;
-	domain->io_domain = io_domain;
-
-	return 0;
+	return &domain->io_domain;
 }
 
-static void ipmmu_domain_destroy(struct iommu_domain *io_domain)
+static void ipmmu_domain_free(struct iommu_domain *io_domain)
 {
-	struct ipmmu_vmsa_domain *domain = io_domain->priv;
+	struct ipmmu_vmsa_domain *domain = to_vmsa_domain(io_domain);
 
 	/*
 	 * Free the domain resources. We assume that all devices have already
@@ -894,7 +899,7 @@ static int ipmmu_attach_device(struct iommu_domain *io_domain,
 {
 	struct ipmmu_vmsa_archdata *archdata = dev->archdata.iommu;
 	struct ipmmu_vmsa_device *mmu = archdata->mmu;
-	struct ipmmu_vmsa_domain *domain = io_domain->priv;
+	struct ipmmu_vmsa_domain *domain = to_vmsa_domain(io_domain);
 	unsigned long flags;
 	int ret = 0;
 
@@ -933,7 +938,7 @@ static void ipmmu_detach_device(struct iommu_domain *io_domain,
 				struct device *dev)
 {
 	struct ipmmu_vmsa_archdata *archdata = dev->archdata.iommu;
-	struct ipmmu_vmsa_domain *domain = io_domain->priv;
+	struct ipmmu_vmsa_domain *domain = to_vmsa_domain(io_domain);
 
 	ipmmu_utlb_disable(domain, archdata->utlb);
 
@@ -945,7 +950,7 @@ static void ipmmu_detach_device(struct iommu_domain *io_domain,
 static int ipmmu_map(struct iommu_domain *io_domain, unsigned long iova,
 		     phys_addr_t paddr, size_t size, int prot)
 {
-	struct ipmmu_vmsa_domain *domain = io_domain->priv;
+	struct ipmmu_vmsa_domain *domain = to_vmsa_domain(io_domain);
 
 	if (!domain)
 		return -ENODEV;
@@ -956,7 +961,7 @@ static int ipmmu_map(struct iommu_domain *io_domain, unsigned long iova,
 static size_t ipmmu_unmap(struct iommu_domain *io_domain, unsigned long iova,
 			  size_t size)
 {
-	struct ipmmu_vmsa_domain *domain = io_domain->priv;
+	struct ipmmu_vmsa_domain *domain = to_vmsa_domain(io_domain);
 	int ret;
 
 	ret = ipmmu_clear_mapping(domain, iova, size);
@@ -966,7 +971,7 @@ static size_t ipmmu_unmap(struct iommu_domain *io_domain, unsigned long iova,
 static phys_addr_t ipmmu_iova_to_phys(struct iommu_domain *io_domain,
 				      dma_addr_t iova)
 {
-	struct ipmmu_vmsa_domain *domain = io_domain->priv;
+	struct ipmmu_vmsa_domain *domain = to_vmsa_domain(io_domain);
 	pgd_t pgd;
 	pud_t pud;
 	pmd_t pmd;
@@ -1121,8 +1126,8 @@ static void ipmmu_remove_device(struct device *dev)
 }
 
 static const struct iommu_ops ipmmu_ops = {
-	.domain_init = ipmmu_domain_init,
-	.domain_destroy = ipmmu_domain_destroy,
+	.domain_alloc = ipmmu_domain_alloc,
+	.domain_free = ipmmu_domain_free,
 	.attach_dev = ipmmu_attach_device,
 	.detach_dev = ipmmu_detach_device,
 	.map = ipmmu_map,
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 12/15] iommu/ipmmu-vmsa: Make use of domain_alloc and domain_free
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu
  Cc: Will Deacon, Kukjin Kim, David Woodhouse, Heiko Stuebner,
	Hiroshi Doyu, Stephen Warren, Thierry Reding, Alexandre Courbot,
	Alex Williamson, Arnd Bergmann, linux-kernel, linux-arm-kernel,
	linux-samsung-soc, linux-rockchip, linux-tegra, Joerg Roedel,
	jroedel

From: Joerg Roedel <jroedel@suse.de>

Implement domain_alloc and domain_free iommu-ops as a
replacement for domain_init/domain_destroy.

Signed-off-by: Joerg Roedel <jroedel@suse.de>
---
 drivers/iommu/ipmmu-vmsa.c | 43 ++++++++++++++++++++++++-------------------
 1 file changed, 24 insertions(+), 19 deletions(-)

diff --git a/drivers/iommu/ipmmu-vmsa.c b/drivers/iommu/ipmmu-vmsa.c
index 7486931..12270e1 100644
--- a/drivers/iommu/ipmmu-vmsa.c
+++ b/drivers/iommu/ipmmu-vmsa.c
@@ -37,7 +37,7 @@ struct ipmmu_vmsa_device {
 
 struct ipmmu_vmsa_domain {
 	struct ipmmu_vmsa_device *mmu;
-	struct iommu_domain *io_domain;
+	struct iommu_domain io_domain;
 
 	unsigned int context_id;
 	spinlock_t lock;			/* Protects mappings */
@@ -52,6 +52,11 @@ struct ipmmu_vmsa_archdata {
 static DEFINE_SPINLOCK(ipmmu_devices_lock);
 static LIST_HEAD(ipmmu_devices);
 
+static struct ipmmu_vmsa_domain *to_vmsa_domain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct ipmmu_vmsa_domain, io_domain);
+}
+
 #define TLB_LOOP_TIMEOUT		100	/* 100us */
 
 /* -----------------------------------------------------------------------------
@@ -435,7 +440,7 @@ static irqreturn_t ipmmu_domain_irq(struct ipmmu_vmsa_domain *domain)
 	 * TODO: We need to look up the faulty device based on the I/O VA. Use
 	 * the IOMMU device for now.
 	 */
-	if (!report_iommu_fault(domain->io_domain, mmu->dev, iova, 0))
+	if (!report_iommu_fault(&domain->io_domain, mmu->dev, iova, 0))
 		return IRQ_HANDLED;
 
 	dev_err_ratelimited(mmu->dev,
@@ -455,7 +460,7 @@ static irqreturn_t ipmmu_irq(int irq, void *dev)
 		return IRQ_NONE;
 
 	io_domain = mmu->mapping->domain;
-	domain = io_domain->priv;
+	domain = to_vmsa_domain(io_domain);
 
 	return ipmmu_domain_irq(domain);
 }
@@ -854,31 +859,31 @@ done:
  * IOMMU Operations
  */
 
-static int ipmmu_domain_init(struct iommu_domain *io_domain)
+static struct iommu_domain *ipmmu_domain_alloc(enum iommu_domain_type type)
 {
 	struct ipmmu_vmsa_domain *domain;
 
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
+
 	domain = kzalloc(sizeof(*domain), GFP_KERNEL);
 	if (!domain)
-		return -ENOMEM;
+		return NULL;
 
 	spin_lock_init(&domain->lock);
 
 	domain->pgd = kzalloc(IPMMU_PTRS_PER_PGD * sizeof(pgd_t), GFP_KERNEL);
 	if (!domain->pgd) {
 		kfree(domain);
-		return -ENOMEM;
+		return NULL;
 	}
 
-	io_domain->priv = domain;
-	domain->io_domain = io_domain;
-
-	return 0;
+	return &domain->io_domain;
 }
 
-static void ipmmu_domain_destroy(struct iommu_domain *io_domain)
+static void ipmmu_domain_free(struct iommu_domain *io_domain)
 {
-	struct ipmmu_vmsa_domain *domain = io_domain->priv;
+	struct ipmmu_vmsa_domain *domain = to_vmsa_domain(io_domain);
 
 	/*
 	 * Free the domain resources. We assume that all devices have already
@@ -894,7 +899,7 @@ static int ipmmu_attach_device(struct iommu_domain *io_domain,
 {
 	struct ipmmu_vmsa_archdata *archdata = dev->archdata.iommu;
 	struct ipmmu_vmsa_device *mmu = archdata->mmu;
-	struct ipmmu_vmsa_domain *domain = io_domain->priv;
+	struct ipmmu_vmsa_domain *domain = to_vmsa_domain(io_domain);
 	unsigned long flags;
 	int ret = 0;
 
@@ -933,7 +938,7 @@ static void ipmmu_detach_device(struct iommu_domain *io_domain,
 				struct device *dev)
 {
 	struct ipmmu_vmsa_archdata *archdata = dev->archdata.iommu;
-	struct ipmmu_vmsa_domain *domain = io_domain->priv;
+	struct ipmmu_vmsa_domain *domain = to_vmsa_domain(io_domain);
 
 	ipmmu_utlb_disable(domain, archdata->utlb);
 
@@ -945,7 +950,7 @@ static void ipmmu_detach_device(struct iommu_domain *io_domain,
 static int ipmmu_map(struct iommu_domain *io_domain, unsigned long iova,
 		     phys_addr_t paddr, size_t size, int prot)
 {
-	struct ipmmu_vmsa_domain *domain = io_domain->priv;
+	struct ipmmu_vmsa_domain *domain = to_vmsa_domain(io_domain);
 
 	if (!domain)
 		return -ENODEV;
@@ -956,7 +961,7 @@ static int ipmmu_map(struct iommu_domain *io_domain, unsigned long iova,
 static size_t ipmmu_unmap(struct iommu_domain *io_domain, unsigned long iova,
 			  size_t size)
 {
-	struct ipmmu_vmsa_domain *domain = io_domain->priv;
+	struct ipmmu_vmsa_domain *domain = to_vmsa_domain(io_domain);
 	int ret;
 
 	ret = ipmmu_clear_mapping(domain, iova, size);
@@ -966,7 +971,7 @@ static size_t ipmmu_unmap(struct iommu_domain *io_domain, unsigned long iova,
 static phys_addr_t ipmmu_iova_to_phys(struct iommu_domain *io_domain,
 				      dma_addr_t iova)
 {
-	struct ipmmu_vmsa_domain *domain = io_domain->priv;
+	struct ipmmu_vmsa_domain *domain = to_vmsa_domain(io_domain);
 	pgd_t pgd;
 	pud_t pud;
 	pmd_t pmd;
@@ -1121,8 +1126,8 @@ static void ipmmu_remove_device(struct device *dev)
 }
 
 static const struct iommu_ops ipmmu_ops = {
-	.domain_init = ipmmu_domain_init,
-	.domain_destroy = ipmmu_domain_destroy,
+	.domain_alloc = ipmmu_domain_alloc,
+	.domain_free = ipmmu_domain_free,
 	.attach_dev = ipmmu_attach_device,
 	.detach_dev = ipmmu_detach_device,
 	.map = ipmmu_map,
-- 
1.8.4.5


^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 12/15] iommu/ipmmu-vmsa: Make use of domain_alloc and domain_free
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: linux-arm-kernel

From: Joerg Roedel <jroedel@suse.de>

Implement domain_alloc and domain_free iommu-ops as a
replacement for domain_init/domain_destroy.

Signed-off-by: Joerg Roedel <jroedel@suse.de>
---
 drivers/iommu/ipmmu-vmsa.c | 43 ++++++++++++++++++++++++-------------------
 1 file changed, 24 insertions(+), 19 deletions(-)

diff --git a/drivers/iommu/ipmmu-vmsa.c b/drivers/iommu/ipmmu-vmsa.c
index 7486931..12270e1 100644
--- a/drivers/iommu/ipmmu-vmsa.c
+++ b/drivers/iommu/ipmmu-vmsa.c
@@ -37,7 +37,7 @@ struct ipmmu_vmsa_device {
 
 struct ipmmu_vmsa_domain {
 	struct ipmmu_vmsa_device *mmu;
-	struct iommu_domain *io_domain;
+	struct iommu_domain io_domain;
 
 	unsigned int context_id;
 	spinlock_t lock;			/* Protects mappings */
@@ -52,6 +52,11 @@ struct ipmmu_vmsa_archdata {
 static DEFINE_SPINLOCK(ipmmu_devices_lock);
 static LIST_HEAD(ipmmu_devices);
 
+static struct ipmmu_vmsa_domain *to_vmsa_domain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct ipmmu_vmsa_domain, io_domain);
+}
+
 #define TLB_LOOP_TIMEOUT		100	/* 100us */
 
 /* -----------------------------------------------------------------------------
@@ -435,7 +440,7 @@ static irqreturn_t ipmmu_domain_irq(struct ipmmu_vmsa_domain *domain)
 	 * TODO: We need to look up the faulty device based on the I/O VA. Use
 	 * the IOMMU device for now.
 	 */
-	if (!report_iommu_fault(domain->io_domain, mmu->dev, iova, 0))
+	if (!report_iommu_fault(&domain->io_domain, mmu->dev, iova, 0))
 		return IRQ_HANDLED;
 
 	dev_err_ratelimited(mmu->dev,
@@ -455,7 +460,7 @@ static irqreturn_t ipmmu_irq(int irq, void *dev)
 		return IRQ_NONE;
 
 	io_domain = mmu->mapping->domain;
-	domain = io_domain->priv;
+	domain = to_vmsa_domain(io_domain);
 
 	return ipmmu_domain_irq(domain);
 }
@@ -854,31 +859,31 @@ done:
  * IOMMU Operations
  */
 
-static int ipmmu_domain_init(struct iommu_domain *io_domain)
+static struct iommu_domain *ipmmu_domain_alloc(enum iommu_domain_type type)
 {
 	struct ipmmu_vmsa_domain *domain;
 
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
+
 	domain = kzalloc(sizeof(*domain), GFP_KERNEL);
 	if (!domain)
-		return -ENOMEM;
+		return NULL;
 
 	spin_lock_init(&domain->lock);
 
 	domain->pgd = kzalloc(IPMMU_PTRS_PER_PGD * sizeof(pgd_t), GFP_KERNEL);
 	if (!domain->pgd) {
 		kfree(domain);
-		return -ENOMEM;
+		return NULL;
 	}
 
-	io_domain->priv = domain;
-	domain->io_domain = io_domain;
-
-	return 0;
+	return &domain->io_domain;
 }
 
-static void ipmmu_domain_destroy(struct iommu_domain *io_domain)
+static void ipmmu_domain_free(struct iommu_domain *io_domain)
 {
-	struct ipmmu_vmsa_domain *domain = io_domain->priv;
+	struct ipmmu_vmsa_domain *domain = to_vmsa_domain(io_domain);
 
 	/*
 	 * Free the domain resources. We assume that all devices have already
@@ -894,7 +899,7 @@ static int ipmmu_attach_device(struct iommu_domain *io_domain,
 {
 	struct ipmmu_vmsa_archdata *archdata = dev->archdata.iommu;
 	struct ipmmu_vmsa_device *mmu = archdata->mmu;
-	struct ipmmu_vmsa_domain *domain = io_domain->priv;
+	struct ipmmu_vmsa_domain *domain = to_vmsa_domain(io_domain);
 	unsigned long flags;
 	int ret = 0;
 
@@ -933,7 +938,7 @@ static void ipmmu_detach_device(struct iommu_domain *io_domain,
 				struct device *dev)
 {
 	struct ipmmu_vmsa_archdata *archdata = dev->archdata.iommu;
-	struct ipmmu_vmsa_domain *domain = io_domain->priv;
+	struct ipmmu_vmsa_domain *domain = to_vmsa_domain(io_domain);
 
 	ipmmu_utlb_disable(domain, archdata->utlb);
 
@@ -945,7 +950,7 @@ static void ipmmu_detach_device(struct iommu_domain *io_domain,
 static int ipmmu_map(struct iommu_domain *io_domain, unsigned long iova,
 		     phys_addr_t paddr, size_t size, int prot)
 {
-	struct ipmmu_vmsa_domain *domain = io_domain->priv;
+	struct ipmmu_vmsa_domain *domain = to_vmsa_domain(io_domain);
 
 	if (!domain)
 		return -ENODEV;
@@ -956,7 +961,7 @@ static int ipmmu_map(struct iommu_domain *io_domain, unsigned long iova,
 static size_t ipmmu_unmap(struct iommu_domain *io_domain, unsigned long iova,
 			  size_t size)
 {
-	struct ipmmu_vmsa_domain *domain = io_domain->priv;
+	struct ipmmu_vmsa_domain *domain = to_vmsa_domain(io_domain);
 	int ret;
 
 	ret = ipmmu_clear_mapping(domain, iova, size);
@@ -966,7 +971,7 @@ static size_t ipmmu_unmap(struct iommu_domain *io_domain, unsigned long iova,
 static phys_addr_t ipmmu_iova_to_phys(struct iommu_domain *io_domain,
 				      dma_addr_t iova)
 {
-	struct ipmmu_vmsa_domain *domain = io_domain->priv;
+	struct ipmmu_vmsa_domain *domain = to_vmsa_domain(io_domain);
 	pgd_t pgd;
 	pud_t pud;
 	pmd_t pmd;
@@ -1121,8 +1126,8 @@ static void ipmmu_remove_device(struct device *dev)
 }
 
 static const struct iommu_ops ipmmu_ops = {
-	.domain_init = ipmmu_domain_init,
-	.domain_destroy = ipmmu_domain_destroy,
+	.domain_alloc = ipmmu_domain_alloc,
+	.domain_free = ipmmu_domain_free,
 	.attach_dev = ipmmu_attach_device,
 	.detach_dev = ipmmu_detach_device,
 	.map = ipmmu_map,
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 13/15] iommu/rockchip: Make use of domain_alloc and domain_free
  2015-01-26 23:51 ` Joerg Roedel
  (?)
@ 2015-01-26 23:51     ` Joerg Roedel
  -1 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA
  Cc: Alexandre Courbot, linux-samsung-soc-u79uwXL29TY76Z2rM5mHXA,
	Heiko Stuebner, Arnd Bergmann, Stephen Warren, Will Deacon,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-rockchip-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Kukjin Kim,
	Thierry Reding, jroedel-l3A5Bk7waGM,
	linux-tegra-u79uwXL29TY76Z2rM5mHXA, David Woodhouse,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r

From: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>

Implement domain_alloc and domain_free iommu-ops as a
replacement for domain_init/domain_destroy.

Signed-off-by: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>
---
 drivers/iommu/rockchip-iommu.c | 40 ++++++++++++++++++++++++----------------
 1 file changed, 24 insertions(+), 16 deletions(-)

diff --git a/drivers/iommu/rockchip-iommu.c b/drivers/iommu/rockchip-iommu.c
index 6a8b1ec..0646827 100644
--- a/drivers/iommu/rockchip-iommu.c
+++ b/drivers/iommu/rockchip-iommu.c
@@ -80,6 +80,8 @@ struct rk_iommu_domain {
 	u32 *dt; /* page directory table */
 	spinlock_t iommus_lock; /* lock for iommus list */
 	spinlock_t dt_lock; /* lock for modifying page directory table */
+
+	struct iommu_domain domain;
 };
 
 struct rk_iommu {
@@ -100,6 +102,11 @@ static inline void rk_table_flush(u32 *va, unsigned int count)
 	outer_flush_range(pa_start, pa_end);
 }
 
+static struct rk_iommu_domain *to_rk_domain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct rk_iommu_domain, domain);
+}
+
 /**
  * Inspired by _wait_for in intel_drv.h
  * This is NOT safe for use in interrupt context.
@@ -503,7 +510,7 @@ static irqreturn_t rk_iommu_irq(int irq, void *dev_id)
 static phys_addr_t rk_iommu_iova_to_phys(struct iommu_domain *domain,
 					 dma_addr_t iova)
 {
-	struct rk_iommu_domain *rk_domain = domain->priv;
+	struct rk_iommu_domain *rk_domain = to_rk_domain(domain);
 	unsigned long flags;
 	phys_addr_t pt_phys, phys = 0;
 	u32 dte, pte;
@@ -639,7 +646,7 @@ unwind:
 static int rk_iommu_map(struct iommu_domain *domain, unsigned long _iova,
 			phys_addr_t paddr, size_t size, int prot)
 {
-	struct rk_iommu_domain *rk_domain = domain->priv;
+	struct rk_iommu_domain *rk_domain = to_rk_domain(domain);
 	unsigned long flags;
 	dma_addr_t iova = (dma_addr_t)_iova;
 	u32 *page_table, *pte_addr;
@@ -670,7 +677,7 @@ static int rk_iommu_map(struct iommu_domain *domain, unsigned long _iova,
 static size_t rk_iommu_unmap(struct iommu_domain *domain, unsigned long _iova,
 			     size_t size)
 {
-	struct rk_iommu_domain *rk_domain = domain->priv;
+	struct rk_iommu_domain *rk_domain = to_rk_domain(domain);
 	unsigned long flags;
 	dma_addr_t iova = (dma_addr_t)_iova;
 	phys_addr_t pt_phys;
@@ -726,7 +733,7 @@ static int rk_iommu_attach_device(struct iommu_domain *domain,
 				  struct device *dev)
 {
 	struct rk_iommu *iommu;
-	struct rk_iommu_domain *rk_domain = domain->priv;
+	struct rk_iommu_domain *rk_domain = to_rk_domain(domain);
 	unsigned long flags;
 	int ret;
 	phys_addr_t dte_addr;
@@ -778,7 +785,7 @@ static void rk_iommu_detach_device(struct iommu_domain *domain,
 				   struct device *dev)
 {
 	struct rk_iommu *iommu;
-	struct rk_iommu_domain *rk_domain = domain->priv;
+	struct rk_iommu_domain *rk_domain = to_rk_domain(domain);
 	unsigned long flags;
 
 	/* Allow 'virtual devices' (eg drm) to detach from domain */
@@ -804,13 +811,16 @@ static void rk_iommu_detach_device(struct iommu_domain *domain,
 	dev_info(dev, "Detached from iommu domain\n");
 }
 
-static int rk_iommu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *rk_iommu_domain_alloc(enum iommu_domain_type type)
 {
 	struct rk_iommu_domain *rk_domain;
 
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
+
 	rk_domain = kzalloc(sizeof(*rk_domain), GFP_KERNEL);
 	if (!rk_domain)
-		return -ENOMEM;
+		return NULL;
 
 	/*
 	 * rk32xx iommus use a 2 level pagetable.
@@ -827,17 +837,16 @@ static int rk_iommu_domain_init(struct iommu_domain *domain)
 	spin_lock_init(&rk_domain->dt_lock);
 	INIT_LIST_HEAD(&rk_domain->iommus);
 
-	domain->priv = rk_domain;
+	return &rk_domain->domain;
 
-	return 0;
 err_dt:
 	kfree(rk_domain);
-	return -ENOMEM;
+	return NULL;
 }
 
-static void rk_iommu_domain_destroy(struct iommu_domain *domain)
+static void rk_iommu_domain_free(struct iommu_domain *domain)
 {
-	struct rk_iommu_domain *rk_domain = domain->priv;
+	struct rk_iommu_domain *rk_domain = to_rk_domain(domain);
 	int i;
 
 	WARN_ON(!list_empty(&rk_domain->iommus));
@@ -852,8 +861,7 @@ static void rk_iommu_domain_destroy(struct iommu_domain *domain)
 	}
 
 	free_page((unsigned long)rk_domain->dt);
-	kfree(domain->priv);
-	domain->priv = NULL;
+	kfree(rk_domain);
 }
 
 static bool rk_iommu_is_dev_iommu_master(struct device *dev)
@@ -952,8 +960,8 @@ static void rk_iommu_remove_device(struct device *dev)
 }
 
 static const struct iommu_ops rk_iommu_ops = {
-	.domain_init = rk_iommu_domain_init,
-	.domain_destroy = rk_iommu_domain_destroy,
+	.domain_alloc = rk_iommu_domain_alloc,
+	.domain_free = rk_iommu_domain_free,
 	.attach_dev = rk_iommu_attach_device,
 	.detach_dev = rk_iommu_detach_device,
 	.map = rk_iommu_map,
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 13/15] iommu/rockchip: Make use of domain_alloc and domain_free
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu
  Cc: Will Deacon, Kukjin Kim, David Woodhouse, Heiko Stuebner,
	Hiroshi Doyu, Stephen Warren, Thierry Reding, Alexandre Courbot,
	Alex Williamson, Arnd Bergmann, linux-kernel, linux-arm-kernel,
	linux-samsung-soc, linux-rockchip, linux-tegra, Joerg Roedel,
	jroedel

From: Joerg Roedel <jroedel@suse.de>

Implement domain_alloc and domain_free iommu-ops as a
replacement for domain_init/domain_destroy.

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

diff --git a/drivers/iommu/rockchip-iommu.c b/drivers/iommu/rockchip-iommu.c
index 6a8b1ec..0646827 100644
--- a/drivers/iommu/rockchip-iommu.c
+++ b/drivers/iommu/rockchip-iommu.c
@@ -80,6 +80,8 @@ struct rk_iommu_domain {
 	u32 *dt; /* page directory table */
 	spinlock_t iommus_lock; /* lock for iommus list */
 	spinlock_t dt_lock; /* lock for modifying page directory table */
+
+	struct iommu_domain domain;
 };
 
 struct rk_iommu {
@@ -100,6 +102,11 @@ static inline void rk_table_flush(u32 *va, unsigned int count)
 	outer_flush_range(pa_start, pa_end);
 }
 
+static struct rk_iommu_domain *to_rk_domain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct rk_iommu_domain, domain);
+}
+
 /**
  * Inspired by _wait_for in intel_drv.h
  * This is NOT safe for use in interrupt context.
@@ -503,7 +510,7 @@ static irqreturn_t rk_iommu_irq(int irq, void *dev_id)
 static phys_addr_t rk_iommu_iova_to_phys(struct iommu_domain *domain,
 					 dma_addr_t iova)
 {
-	struct rk_iommu_domain *rk_domain = domain->priv;
+	struct rk_iommu_domain *rk_domain = to_rk_domain(domain);
 	unsigned long flags;
 	phys_addr_t pt_phys, phys = 0;
 	u32 dte, pte;
@@ -639,7 +646,7 @@ unwind:
 static int rk_iommu_map(struct iommu_domain *domain, unsigned long _iova,
 			phys_addr_t paddr, size_t size, int prot)
 {
-	struct rk_iommu_domain *rk_domain = domain->priv;
+	struct rk_iommu_domain *rk_domain = to_rk_domain(domain);
 	unsigned long flags;
 	dma_addr_t iova = (dma_addr_t)_iova;
 	u32 *page_table, *pte_addr;
@@ -670,7 +677,7 @@ static int rk_iommu_map(struct iommu_domain *domain, unsigned long _iova,
 static size_t rk_iommu_unmap(struct iommu_domain *domain, unsigned long _iova,
 			     size_t size)
 {
-	struct rk_iommu_domain *rk_domain = domain->priv;
+	struct rk_iommu_domain *rk_domain = to_rk_domain(domain);
 	unsigned long flags;
 	dma_addr_t iova = (dma_addr_t)_iova;
 	phys_addr_t pt_phys;
@@ -726,7 +733,7 @@ static int rk_iommu_attach_device(struct iommu_domain *domain,
 				  struct device *dev)
 {
 	struct rk_iommu *iommu;
-	struct rk_iommu_domain *rk_domain = domain->priv;
+	struct rk_iommu_domain *rk_domain = to_rk_domain(domain);
 	unsigned long flags;
 	int ret;
 	phys_addr_t dte_addr;
@@ -778,7 +785,7 @@ static void rk_iommu_detach_device(struct iommu_domain *domain,
 				   struct device *dev)
 {
 	struct rk_iommu *iommu;
-	struct rk_iommu_domain *rk_domain = domain->priv;
+	struct rk_iommu_domain *rk_domain = to_rk_domain(domain);
 	unsigned long flags;
 
 	/* Allow 'virtual devices' (eg drm) to detach from domain */
@@ -804,13 +811,16 @@ static void rk_iommu_detach_device(struct iommu_domain *domain,
 	dev_info(dev, "Detached from iommu domain\n");
 }
 
-static int rk_iommu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *rk_iommu_domain_alloc(enum iommu_domain_type type)
 {
 	struct rk_iommu_domain *rk_domain;
 
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
+
 	rk_domain = kzalloc(sizeof(*rk_domain), GFP_KERNEL);
 	if (!rk_domain)
-		return -ENOMEM;
+		return NULL;
 
 	/*
 	 * rk32xx iommus use a 2 level pagetable.
@@ -827,17 +837,16 @@ static int rk_iommu_domain_init(struct iommu_domain *domain)
 	spin_lock_init(&rk_domain->dt_lock);
 	INIT_LIST_HEAD(&rk_domain->iommus);
 
-	domain->priv = rk_domain;
+	return &rk_domain->domain;
 
-	return 0;
 err_dt:
 	kfree(rk_domain);
-	return -ENOMEM;
+	return NULL;
 }
 
-static void rk_iommu_domain_destroy(struct iommu_domain *domain)
+static void rk_iommu_domain_free(struct iommu_domain *domain)
 {
-	struct rk_iommu_domain *rk_domain = domain->priv;
+	struct rk_iommu_domain *rk_domain = to_rk_domain(domain);
 	int i;
 
 	WARN_ON(!list_empty(&rk_domain->iommus));
@@ -852,8 +861,7 @@ static void rk_iommu_domain_destroy(struct iommu_domain *domain)
 	}
 
 	free_page((unsigned long)rk_domain->dt);
-	kfree(domain->priv);
-	domain->priv = NULL;
+	kfree(rk_domain);
 }
 
 static bool rk_iommu_is_dev_iommu_master(struct device *dev)
@@ -952,8 +960,8 @@ static void rk_iommu_remove_device(struct device *dev)
 }
 
 static const struct iommu_ops rk_iommu_ops = {
-	.domain_init = rk_iommu_domain_init,
-	.domain_destroy = rk_iommu_domain_destroy,
+	.domain_alloc = rk_iommu_domain_alloc,
+	.domain_free = rk_iommu_domain_free,
 	.attach_dev = rk_iommu_attach_device,
 	.detach_dev = rk_iommu_detach_device,
 	.map = rk_iommu_map,
-- 
1.8.4.5


^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 13/15] iommu/rockchip: Make use of domain_alloc and domain_free
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: linux-arm-kernel

From: Joerg Roedel <jroedel@suse.de>

Implement domain_alloc and domain_free iommu-ops as a
replacement for domain_init/domain_destroy.

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

diff --git a/drivers/iommu/rockchip-iommu.c b/drivers/iommu/rockchip-iommu.c
index 6a8b1ec..0646827 100644
--- a/drivers/iommu/rockchip-iommu.c
+++ b/drivers/iommu/rockchip-iommu.c
@@ -80,6 +80,8 @@ struct rk_iommu_domain {
 	u32 *dt; /* page directory table */
 	spinlock_t iommus_lock; /* lock for iommus list */
 	spinlock_t dt_lock; /* lock for modifying page directory table */
+
+	struct iommu_domain domain;
 };
 
 struct rk_iommu {
@@ -100,6 +102,11 @@ static inline void rk_table_flush(u32 *va, unsigned int count)
 	outer_flush_range(pa_start, pa_end);
 }
 
+static struct rk_iommu_domain *to_rk_domain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct rk_iommu_domain, domain);
+}
+
 /**
  * Inspired by _wait_for in intel_drv.h
  * This is NOT safe for use in interrupt context.
@@ -503,7 +510,7 @@ static irqreturn_t rk_iommu_irq(int irq, void *dev_id)
 static phys_addr_t rk_iommu_iova_to_phys(struct iommu_domain *domain,
 					 dma_addr_t iova)
 {
-	struct rk_iommu_domain *rk_domain = domain->priv;
+	struct rk_iommu_domain *rk_domain = to_rk_domain(domain);
 	unsigned long flags;
 	phys_addr_t pt_phys, phys = 0;
 	u32 dte, pte;
@@ -639,7 +646,7 @@ unwind:
 static int rk_iommu_map(struct iommu_domain *domain, unsigned long _iova,
 			phys_addr_t paddr, size_t size, int prot)
 {
-	struct rk_iommu_domain *rk_domain = domain->priv;
+	struct rk_iommu_domain *rk_domain = to_rk_domain(domain);
 	unsigned long flags;
 	dma_addr_t iova = (dma_addr_t)_iova;
 	u32 *page_table, *pte_addr;
@@ -670,7 +677,7 @@ static int rk_iommu_map(struct iommu_domain *domain, unsigned long _iova,
 static size_t rk_iommu_unmap(struct iommu_domain *domain, unsigned long _iova,
 			     size_t size)
 {
-	struct rk_iommu_domain *rk_domain = domain->priv;
+	struct rk_iommu_domain *rk_domain = to_rk_domain(domain);
 	unsigned long flags;
 	dma_addr_t iova = (dma_addr_t)_iova;
 	phys_addr_t pt_phys;
@@ -726,7 +733,7 @@ static int rk_iommu_attach_device(struct iommu_domain *domain,
 				  struct device *dev)
 {
 	struct rk_iommu *iommu;
-	struct rk_iommu_domain *rk_domain = domain->priv;
+	struct rk_iommu_domain *rk_domain = to_rk_domain(domain);
 	unsigned long flags;
 	int ret;
 	phys_addr_t dte_addr;
@@ -778,7 +785,7 @@ static void rk_iommu_detach_device(struct iommu_domain *domain,
 				   struct device *dev)
 {
 	struct rk_iommu *iommu;
-	struct rk_iommu_domain *rk_domain = domain->priv;
+	struct rk_iommu_domain *rk_domain = to_rk_domain(domain);
 	unsigned long flags;
 
 	/* Allow 'virtual devices' (eg drm) to detach from domain */
@@ -804,13 +811,16 @@ static void rk_iommu_detach_device(struct iommu_domain *domain,
 	dev_info(dev, "Detached from iommu domain\n");
 }
 
-static int rk_iommu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *rk_iommu_domain_alloc(enum iommu_domain_type type)
 {
 	struct rk_iommu_domain *rk_domain;
 
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
+
 	rk_domain = kzalloc(sizeof(*rk_domain), GFP_KERNEL);
 	if (!rk_domain)
-		return -ENOMEM;
+		return NULL;
 
 	/*
 	 * rk32xx iommus use a 2 level pagetable.
@@ -827,17 +837,16 @@ static int rk_iommu_domain_init(struct iommu_domain *domain)
 	spin_lock_init(&rk_domain->dt_lock);
 	INIT_LIST_HEAD(&rk_domain->iommus);
 
-	domain->priv = rk_domain;
+	return &rk_domain->domain;
 
-	return 0;
 err_dt:
 	kfree(rk_domain);
-	return -ENOMEM;
+	return NULL;
 }
 
-static void rk_iommu_domain_destroy(struct iommu_domain *domain)
+static void rk_iommu_domain_free(struct iommu_domain *domain)
 {
-	struct rk_iommu_domain *rk_domain = domain->priv;
+	struct rk_iommu_domain *rk_domain = to_rk_domain(domain);
 	int i;
 
 	WARN_ON(!list_empty(&rk_domain->iommus));
@@ -852,8 +861,7 @@ static void rk_iommu_domain_destroy(struct iommu_domain *domain)
 	}
 
 	free_page((unsigned long)rk_domain->dt);
-	kfree(domain->priv);
-	domain->priv = NULL;
+	kfree(rk_domain);
 }
 
 static bool rk_iommu_is_dev_iommu_master(struct device *dev)
@@ -952,8 +960,8 @@ static void rk_iommu_remove_device(struct device *dev)
 }
 
 static const struct iommu_ops rk_iommu_ops = {
-	.domain_init = rk_iommu_domain_init,
-	.domain_destroy = rk_iommu_domain_destroy,
+	.domain_alloc = rk_iommu_domain_alloc,
+	.domain_free = rk_iommu_domain_free,
 	.attach_dev = rk_iommu_attach_device,
 	.detach_dev = rk_iommu_detach_device,
 	.map = rk_iommu_map,
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 14/15] iommu/fsl: Make use of domain_alloc and domain_free
  2015-01-26 23:51 ` Joerg Roedel
  (?)
@ 2015-01-26 23:51     ` Joerg Roedel
  -1 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA
  Cc: Alexandre Courbot, linux-samsung-soc-u79uwXL29TY76Z2rM5mHXA,
	Heiko Stuebner, Arnd Bergmann, Stephen Warren, Will Deacon,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-rockchip-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Kukjin Kim,
	Thierry Reding, jroedel-l3A5Bk7waGM,
	linux-tegra-u79uwXL29TY76Z2rM5mHXA, David Woodhouse,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r

From: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>

Implement domain_alloc and domain_free iommu-ops as a
replacement for domain_init/domain_destroy.

Signed-off-by: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>
---
 drivers/iommu/fsl_pamu_domain.c | 60 ++++++++++++++++++++++-------------------
 drivers/iommu/fsl_pamu_domain.h |  2 +-
 2 files changed, 33 insertions(+), 29 deletions(-)

diff --git a/drivers/iommu/fsl_pamu_domain.c b/drivers/iommu/fsl_pamu_domain.c
index c828f80..7c16c80 100644
--- a/drivers/iommu/fsl_pamu_domain.c
+++ b/drivers/iommu/fsl_pamu_domain.c
@@ -49,6 +49,11 @@ static struct kmem_cache *fsl_pamu_domain_cache;
 static struct kmem_cache *iommu_devinfo_cache;
 static DEFINE_SPINLOCK(device_domain_lock);
 
+static struct fsl_dma_domain *to_fsl_dma_domain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct fsl_dma_domain, iommu_domain);
+}
+
 static int __init iommu_init_mempool(void)
 {
 
@@ -84,7 +89,7 @@ static phys_addr_t get_phys_addr(struct fsl_dma_domain *dma_domain, dma_addr_t i
 				&dma_domain->win_arr[0];
 	struct iommu_domain_geometry *geom;
 
-	geom = &dma_domain->iommu_domain->geometry;
+	geom = &dma_domain->iommu_domain.geometry;
 
 	if (!win_cnt || !dma_domain->geom_size) {
 		pr_debug("Number of windows/geometry not configured for the domain\n");
@@ -144,7 +149,7 @@ static int map_win(int liodn, struct fsl_dma_domain *dma_domain)
 {
 	int ret;
 	struct dma_window *wnd = &dma_domain->win_arr[0];
-	phys_addr_t wnd_addr = dma_domain->iommu_domain->geometry.aperture_start;
+	phys_addr_t wnd_addr = dma_domain->iommu_domain.geometry.aperture_start;
 	unsigned long flags;
 
 	spin_lock_irqsave(&iommu_lock, flags);
@@ -194,7 +199,7 @@ static int update_liodn(int liodn, struct fsl_dma_domain *dma_domain, u32 wnd_nr
 	} else {
 		phys_addr_t wnd_addr;
 
-		wnd_addr = dma_domain->iommu_domain->geometry.aperture_start;
+		wnd_addr = dma_domain->iommu_domain.geometry.aperture_start;
 
 		ret = pamu_config_ppaace(liodn, wnd_addr,
 					 wnd->size,
@@ -402,7 +407,7 @@ static void attach_device(struct fsl_dma_domain *dma_domain, int liodn, struct d
 static phys_addr_t fsl_pamu_iova_to_phys(struct iommu_domain *domain,
 					    dma_addr_t iova)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 
 	if ((iova < domain->geometry.aperture_start) ||
 		iova > (domain->geometry.aperture_end))
@@ -416,11 +421,9 @@ static bool fsl_pamu_capable(enum iommu_cap cap)
 	return cap == IOMMU_CAP_CACHE_COHERENCY;
 }
 
-static void fsl_pamu_domain_destroy(struct iommu_domain *domain)
+static void fsl_pamu_domain_free(struct iommu_domain *domain)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
-
-	domain->priv = NULL;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 
 	/* remove all the devices from the device list */
 	detach_device(NULL, dma_domain);
@@ -431,23 +434,24 @@ static void fsl_pamu_domain_destroy(struct iommu_domain *domain)
 	kmem_cache_free(fsl_pamu_domain_cache, dma_domain);
 }
 
-static int fsl_pamu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *fsl_pamu_domain_alloc(enum iommu_domain_type type)
 {
 	struct fsl_dma_domain *dma_domain;
 
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
+
 	dma_domain = iommu_alloc_dma_domain();
 	if (!dma_domain) {
 		pr_debug("dma_domain allocation failed\n");
-		return -ENOMEM;
+		return NULL;
 	}
-	domain->priv = dma_domain;
-	dma_domain->iommu_domain = domain;
 	/* defaul geometry 64 GB i.e. maximum system address */
-	domain->geometry.aperture_start = 0;
-	domain->geometry.aperture_end = (1ULL << 36) - 1;
-	domain->geometry.force_aperture = true;
+	dma_domain->iommu_domain. geometry.aperture_start = 0;
+	dma_domain->iommu_domain.geometry.aperture_end = (1ULL << 36) - 1;
+	dma_domain->iommu_domain.geometry.force_aperture = true;
 
-	return 0;
+	return &dma_domain->iommu_domain;
 }
 
 /* Configure geometry settings for all LIODNs associated with domain */
@@ -517,7 +521,7 @@ static int disable_domain_win(struct fsl_dma_domain *dma_domain, u32 wnd_nr)
 
 static void fsl_pamu_window_disable(struct iommu_domain *domain, u32 wnd_nr)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 	unsigned long flags;
 	int ret;
 
@@ -549,7 +553,7 @@ static void fsl_pamu_window_disable(struct iommu_domain *domain, u32 wnd_nr)
 static int fsl_pamu_window_enable(struct iommu_domain *domain, u32 wnd_nr,
 				  phys_addr_t paddr, u64 size, int prot)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 	struct dma_window *wnd;
 	int pamu_prot = 0;
 	int ret;
@@ -626,7 +630,7 @@ static int handle_attach_device(struct fsl_dma_domain *dma_domain,
 				 int num)
 {
 	unsigned long flags;
-	struct iommu_domain *domain = dma_domain->iommu_domain;
+	struct iommu_domain *domain = &dma_domain->iommu_domain;
 	int ret = 0;
 	int i;
 
@@ -673,7 +677,7 @@ static int handle_attach_device(struct fsl_dma_domain *dma_domain,
 static int fsl_pamu_attach_device(struct iommu_domain *domain,
 				  struct device *dev)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 	const u32 *liodn;
 	u32 liodn_cnt;
 	int len, ret = 0;
@@ -712,7 +716,7 @@ static int fsl_pamu_attach_device(struct iommu_domain *domain,
 static void fsl_pamu_detach_device(struct iommu_domain *domain,
 				      struct device *dev)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 	const u32 *prop;
 	int len;
 	struct pci_dev *pdev = NULL;
@@ -744,7 +748,7 @@ static void fsl_pamu_detach_device(struct iommu_domain *domain,
 static  int configure_domain_geometry(struct iommu_domain *domain, void *data)
 {
 	struct iommu_domain_geometry *geom_attr = data;
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 	dma_addr_t geom_size;
 	unsigned long flags;
 
@@ -835,7 +839,7 @@ static int configure_domain_dma_state(struct fsl_dma_domain *dma_domain, bool en
 static int fsl_pamu_set_domain_attr(struct iommu_domain *domain,
 				 enum iommu_attr attr_type, void *data)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 	int ret = 0;
 
 
@@ -861,7 +865,7 @@ static int fsl_pamu_set_domain_attr(struct iommu_domain *domain,
 static int fsl_pamu_get_domain_attr(struct iommu_domain *domain,
 				 enum iommu_attr attr_type, void *data)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 	int ret = 0;
 
 
@@ -1025,7 +1029,7 @@ static void fsl_pamu_remove_device(struct device *dev)
 
 static int fsl_pamu_set_windows(struct iommu_domain *domain, u32 w_count)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 	unsigned long flags;
 	int ret;
 
@@ -1073,15 +1077,15 @@ static int fsl_pamu_set_windows(struct iommu_domain *domain, u32 w_count)
 
 static u32 fsl_pamu_get_windows(struct iommu_domain *domain)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 
 	return dma_domain->win_cnt;
 }
 
 static const struct iommu_ops fsl_pamu_ops = {
 	.capable	= fsl_pamu_capable,
-	.domain_init	= fsl_pamu_domain_init,
-	.domain_destroy = fsl_pamu_domain_destroy,
+	.domain_alloc	= fsl_pamu_domain_alloc,
+	.domain_free    = fsl_pamu_domain_free,
 	.attach_dev	= fsl_pamu_attach_device,
 	.detach_dev	= fsl_pamu_detach_device,
 	.domain_window_enable = fsl_pamu_window_enable,
diff --git a/drivers/iommu/fsl_pamu_domain.h b/drivers/iommu/fsl_pamu_domain.h
index c90293f..f2b0f74 100644
--- a/drivers/iommu/fsl_pamu_domain.h
+++ b/drivers/iommu/fsl_pamu_domain.h
@@ -71,7 +71,7 @@ struct fsl_dma_domain {
 	u32				stash_id;
 	struct pamu_stash_attribute	dma_stash;
 	u32				snoop_id;
-	struct iommu_domain		*iommu_domain;
+	struct iommu_domain		iommu_domain;
 	spinlock_t			domain_lock;
 };
 
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 14/15] iommu/fsl: Make use of domain_alloc and domain_free
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu
  Cc: Will Deacon, Kukjin Kim, David Woodhouse, Heiko Stuebner,
	Hiroshi Doyu, Stephen Warren, Thierry Reding, Alexandre Courbot,
	Alex Williamson, Arnd Bergmann, linux-kernel, linux-arm-kernel,
	linux-samsung-soc, linux-rockchip, linux-tegra, Joerg Roedel,
	jroedel

From: Joerg Roedel <jroedel@suse.de>

Implement domain_alloc and domain_free iommu-ops as a
replacement for domain_init/domain_destroy.

Signed-off-by: Joerg Roedel <jroedel@suse.de>
---
 drivers/iommu/fsl_pamu_domain.c | 60 ++++++++++++++++++++++-------------------
 drivers/iommu/fsl_pamu_domain.h |  2 +-
 2 files changed, 33 insertions(+), 29 deletions(-)

diff --git a/drivers/iommu/fsl_pamu_domain.c b/drivers/iommu/fsl_pamu_domain.c
index c828f80..7c16c80 100644
--- a/drivers/iommu/fsl_pamu_domain.c
+++ b/drivers/iommu/fsl_pamu_domain.c
@@ -49,6 +49,11 @@ static struct kmem_cache *fsl_pamu_domain_cache;
 static struct kmem_cache *iommu_devinfo_cache;
 static DEFINE_SPINLOCK(device_domain_lock);
 
+static struct fsl_dma_domain *to_fsl_dma_domain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct fsl_dma_domain, iommu_domain);
+}
+
 static int __init iommu_init_mempool(void)
 {
 
@@ -84,7 +89,7 @@ static phys_addr_t get_phys_addr(struct fsl_dma_domain *dma_domain, dma_addr_t i
 				&dma_domain->win_arr[0];
 	struct iommu_domain_geometry *geom;
 
-	geom = &dma_domain->iommu_domain->geometry;
+	geom = &dma_domain->iommu_domain.geometry;
 
 	if (!win_cnt || !dma_domain->geom_size) {
 		pr_debug("Number of windows/geometry not configured for the domain\n");
@@ -144,7 +149,7 @@ static int map_win(int liodn, struct fsl_dma_domain *dma_domain)
 {
 	int ret;
 	struct dma_window *wnd = &dma_domain->win_arr[0];
-	phys_addr_t wnd_addr = dma_domain->iommu_domain->geometry.aperture_start;
+	phys_addr_t wnd_addr = dma_domain->iommu_domain.geometry.aperture_start;
 	unsigned long flags;
 
 	spin_lock_irqsave(&iommu_lock, flags);
@@ -194,7 +199,7 @@ static int update_liodn(int liodn, struct fsl_dma_domain *dma_domain, u32 wnd_nr
 	} else {
 		phys_addr_t wnd_addr;
 
-		wnd_addr = dma_domain->iommu_domain->geometry.aperture_start;
+		wnd_addr = dma_domain->iommu_domain.geometry.aperture_start;
 
 		ret = pamu_config_ppaace(liodn, wnd_addr,
 					 wnd->size,
@@ -402,7 +407,7 @@ static void attach_device(struct fsl_dma_domain *dma_domain, int liodn, struct d
 static phys_addr_t fsl_pamu_iova_to_phys(struct iommu_domain *domain,
 					    dma_addr_t iova)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 
 	if ((iova < domain->geometry.aperture_start) ||
 		iova > (domain->geometry.aperture_end))
@@ -416,11 +421,9 @@ static bool fsl_pamu_capable(enum iommu_cap cap)
 	return cap == IOMMU_CAP_CACHE_COHERENCY;
 }
 
-static void fsl_pamu_domain_destroy(struct iommu_domain *domain)
+static void fsl_pamu_domain_free(struct iommu_domain *domain)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
-
-	domain->priv = NULL;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 
 	/* remove all the devices from the device list */
 	detach_device(NULL, dma_domain);
@@ -431,23 +434,24 @@ static void fsl_pamu_domain_destroy(struct iommu_domain *domain)
 	kmem_cache_free(fsl_pamu_domain_cache, dma_domain);
 }
 
-static int fsl_pamu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *fsl_pamu_domain_alloc(enum iommu_domain_type type)
 {
 	struct fsl_dma_domain *dma_domain;
 
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
+
 	dma_domain = iommu_alloc_dma_domain();
 	if (!dma_domain) {
 		pr_debug("dma_domain allocation failed\n");
-		return -ENOMEM;
+		return NULL;
 	}
-	domain->priv = dma_domain;
-	dma_domain->iommu_domain = domain;
 	/* defaul geometry 64 GB i.e. maximum system address */
-	domain->geometry.aperture_start = 0;
-	domain->geometry.aperture_end = (1ULL << 36) - 1;
-	domain->geometry.force_aperture = true;
+	dma_domain->iommu_domain. geometry.aperture_start = 0;
+	dma_domain->iommu_domain.geometry.aperture_end = (1ULL << 36) - 1;
+	dma_domain->iommu_domain.geometry.force_aperture = true;
 
-	return 0;
+	return &dma_domain->iommu_domain;
 }
 
 /* Configure geometry settings for all LIODNs associated with domain */
@@ -517,7 +521,7 @@ static int disable_domain_win(struct fsl_dma_domain *dma_domain, u32 wnd_nr)
 
 static void fsl_pamu_window_disable(struct iommu_domain *domain, u32 wnd_nr)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 	unsigned long flags;
 	int ret;
 
@@ -549,7 +553,7 @@ static void fsl_pamu_window_disable(struct iommu_domain *domain, u32 wnd_nr)
 static int fsl_pamu_window_enable(struct iommu_domain *domain, u32 wnd_nr,
 				  phys_addr_t paddr, u64 size, int prot)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 	struct dma_window *wnd;
 	int pamu_prot = 0;
 	int ret;
@@ -626,7 +630,7 @@ static int handle_attach_device(struct fsl_dma_domain *dma_domain,
 				 int num)
 {
 	unsigned long flags;
-	struct iommu_domain *domain = dma_domain->iommu_domain;
+	struct iommu_domain *domain = &dma_domain->iommu_domain;
 	int ret = 0;
 	int i;
 
@@ -673,7 +677,7 @@ static int handle_attach_device(struct fsl_dma_domain *dma_domain,
 static int fsl_pamu_attach_device(struct iommu_domain *domain,
 				  struct device *dev)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 	const u32 *liodn;
 	u32 liodn_cnt;
 	int len, ret = 0;
@@ -712,7 +716,7 @@ static int fsl_pamu_attach_device(struct iommu_domain *domain,
 static void fsl_pamu_detach_device(struct iommu_domain *domain,
 				      struct device *dev)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 	const u32 *prop;
 	int len;
 	struct pci_dev *pdev = NULL;
@@ -744,7 +748,7 @@ static void fsl_pamu_detach_device(struct iommu_domain *domain,
 static  int configure_domain_geometry(struct iommu_domain *domain, void *data)
 {
 	struct iommu_domain_geometry *geom_attr = data;
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 	dma_addr_t geom_size;
 	unsigned long flags;
 
@@ -835,7 +839,7 @@ static int configure_domain_dma_state(struct fsl_dma_domain *dma_domain, bool en
 static int fsl_pamu_set_domain_attr(struct iommu_domain *domain,
 				 enum iommu_attr attr_type, void *data)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 	int ret = 0;
 
 
@@ -861,7 +865,7 @@ static int fsl_pamu_set_domain_attr(struct iommu_domain *domain,
 static int fsl_pamu_get_domain_attr(struct iommu_domain *domain,
 				 enum iommu_attr attr_type, void *data)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 	int ret = 0;
 
 
@@ -1025,7 +1029,7 @@ static void fsl_pamu_remove_device(struct device *dev)
 
 static int fsl_pamu_set_windows(struct iommu_domain *domain, u32 w_count)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 	unsigned long flags;
 	int ret;
 
@@ -1073,15 +1077,15 @@ static int fsl_pamu_set_windows(struct iommu_domain *domain, u32 w_count)
 
 static u32 fsl_pamu_get_windows(struct iommu_domain *domain)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 
 	return dma_domain->win_cnt;
 }
 
 static const struct iommu_ops fsl_pamu_ops = {
 	.capable	= fsl_pamu_capable,
-	.domain_init	= fsl_pamu_domain_init,
-	.domain_destroy = fsl_pamu_domain_destroy,
+	.domain_alloc	= fsl_pamu_domain_alloc,
+	.domain_free    = fsl_pamu_domain_free,
 	.attach_dev	= fsl_pamu_attach_device,
 	.detach_dev	= fsl_pamu_detach_device,
 	.domain_window_enable = fsl_pamu_window_enable,
diff --git a/drivers/iommu/fsl_pamu_domain.h b/drivers/iommu/fsl_pamu_domain.h
index c90293f..f2b0f74 100644
--- a/drivers/iommu/fsl_pamu_domain.h
+++ b/drivers/iommu/fsl_pamu_domain.h
@@ -71,7 +71,7 @@ struct fsl_dma_domain {
 	u32				stash_id;
 	struct pamu_stash_attribute	dma_stash;
 	u32				snoop_id;
-	struct iommu_domain		*iommu_domain;
+	struct iommu_domain		iommu_domain;
 	spinlock_t			domain_lock;
 };
 
-- 
1.8.4.5


^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 14/15] iommu/fsl: Make use of domain_alloc and domain_free
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: linux-arm-kernel

From: Joerg Roedel <jroedel@suse.de>

Implement domain_alloc and domain_free iommu-ops as a
replacement for domain_init/domain_destroy.

Signed-off-by: Joerg Roedel <jroedel@suse.de>
---
 drivers/iommu/fsl_pamu_domain.c | 60 ++++++++++++++++++++++-------------------
 drivers/iommu/fsl_pamu_domain.h |  2 +-
 2 files changed, 33 insertions(+), 29 deletions(-)

diff --git a/drivers/iommu/fsl_pamu_domain.c b/drivers/iommu/fsl_pamu_domain.c
index c828f80..7c16c80 100644
--- a/drivers/iommu/fsl_pamu_domain.c
+++ b/drivers/iommu/fsl_pamu_domain.c
@@ -49,6 +49,11 @@ static struct kmem_cache *fsl_pamu_domain_cache;
 static struct kmem_cache *iommu_devinfo_cache;
 static DEFINE_SPINLOCK(device_domain_lock);
 
+static struct fsl_dma_domain *to_fsl_dma_domain(struct iommu_domain *dom)
+{
+	return container_of(dom, struct fsl_dma_domain, iommu_domain);
+}
+
 static int __init iommu_init_mempool(void)
 {
 
@@ -84,7 +89,7 @@ static phys_addr_t get_phys_addr(struct fsl_dma_domain *dma_domain, dma_addr_t i
 				&dma_domain->win_arr[0];
 	struct iommu_domain_geometry *geom;
 
-	geom = &dma_domain->iommu_domain->geometry;
+	geom = &dma_domain->iommu_domain.geometry;
 
 	if (!win_cnt || !dma_domain->geom_size) {
 		pr_debug("Number of windows/geometry not configured for the domain\n");
@@ -144,7 +149,7 @@ static int map_win(int liodn, struct fsl_dma_domain *dma_domain)
 {
 	int ret;
 	struct dma_window *wnd = &dma_domain->win_arr[0];
-	phys_addr_t wnd_addr = dma_domain->iommu_domain->geometry.aperture_start;
+	phys_addr_t wnd_addr = dma_domain->iommu_domain.geometry.aperture_start;
 	unsigned long flags;
 
 	spin_lock_irqsave(&iommu_lock, flags);
@@ -194,7 +199,7 @@ static int update_liodn(int liodn, struct fsl_dma_domain *dma_domain, u32 wnd_nr
 	} else {
 		phys_addr_t wnd_addr;
 
-		wnd_addr = dma_domain->iommu_domain->geometry.aperture_start;
+		wnd_addr = dma_domain->iommu_domain.geometry.aperture_start;
 
 		ret = pamu_config_ppaace(liodn, wnd_addr,
 					 wnd->size,
@@ -402,7 +407,7 @@ static void attach_device(struct fsl_dma_domain *dma_domain, int liodn, struct d
 static phys_addr_t fsl_pamu_iova_to_phys(struct iommu_domain *domain,
 					    dma_addr_t iova)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 
 	if ((iova < domain->geometry.aperture_start) ||
 		iova > (domain->geometry.aperture_end))
@@ -416,11 +421,9 @@ static bool fsl_pamu_capable(enum iommu_cap cap)
 	return cap == IOMMU_CAP_CACHE_COHERENCY;
 }
 
-static void fsl_pamu_domain_destroy(struct iommu_domain *domain)
+static void fsl_pamu_domain_free(struct iommu_domain *domain)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
-
-	domain->priv = NULL;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 
 	/* remove all the devices from the device list */
 	detach_device(NULL, dma_domain);
@@ -431,23 +434,24 @@ static void fsl_pamu_domain_destroy(struct iommu_domain *domain)
 	kmem_cache_free(fsl_pamu_domain_cache, dma_domain);
 }
 
-static int fsl_pamu_domain_init(struct iommu_domain *domain)
+static struct iommu_domain *fsl_pamu_domain_alloc(enum iommu_domain_type type)
 {
 	struct fsl_dma_domain *dma_domain;
 
+	if (type != IOMMU_DOMAIN_UNMANAGED)
+		return NULL;
+
 	dma_domain = iommu_alloc_dma_domain();
 	if (!dma_domain) {
 		pr_debug("dma_domain allocation failed\n");
-		return -ENOMEM;
+		return NULL;
 	}
-	domain->priv = dma_domain;
-	dma_domain->iommu_domain = domain;
 	/* defaul geometry 64 GB i.e. maximum system address */
-	domain->geometry.aperture_start = 0;
-	domain->geometry.aperture_end = (1ULL << 36) - 1;
-	domain->geometry.force_aperture = true;
+	dma_domain->iommu_domain. geometry.aperture_start = 0;
+	dma_domain->iommu_domain.geometry.aperture_end = (1ULL << 36) - 1;
+	dma_domain->iommu_domain.geometry.force_aperture = true;
 
-	return 0;
+	return &dma_domain->iommu_domain;
 }
 
 /* Configure geometry settings for all LIODNs associated with domain */
@@ -517,7 +521,7 @@ static int disable_domain_win(struct fsl_dma_domain *dma_domain, u32 wnd_nr)
 
 static void fsl_pamu_window_disable(struct iommu_domain *domain, u32 wnd_nr)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 	unsigned long flags;
 	int ret;
 
@@ -549,7 +553,7 @@ static void fsl_pamu_window_disable(struct iommu_domain *domain, u32 wnd_nr)
 static int fsl_pamu_window_enable(struct iommu_domain *domain, u32 wnd_nr,
 				  phys_addr_t paddr, u64 size, int prot)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 	struct dma_window *wnd;
 	int pamu_prot = 0;
 	int ret;
@@ -626,7 +630,7 @@ static int handle_attach_device(struct fsl_dma_domain *dma_domain,
 				 int num)
 {
 	unsigned long flags;
-	struct iommu_domain *domain = dma_domain->iommu_domain;
+	struct iommu_domain *domain = &dma_domain->iommu_domain;
 	int ret = 0;
 	int i;
 
@@ -673,7 +677,7 @@ static int handle_attach_device(struct fsl_dma_domain *dma_domain,
 static int fsl_pamu_attach_device(struct iommu_domain *domain,
 				  struct device *dev)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 	const u32 *liodn;
 	u32 liodn_cnt;
 	int len, ret = 0;
@@ -712,7 +716,7 @@ static int fsl_pamu_attach_device(struct iommu_domain *domain,
 static void fsl_pamu_detach_device(struct iommu_domain *domain,
 				      struct device *dev)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 	const u32 *prop;
 	int len;
 	struct pci_dev *pdev = NULL;
@@ -744,7 +748,7 @@ static void fsl_pamu_detach_device(struct iommu_domain *domain,
 static  int configure_domain_geometry(struct iommu_domain *domain, void *data)
 {
 	struct iommu_domain_geometry *geom_attr = data;
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 	dma_addr_t geom_size;
 	unsigned long flags;
 
@@ -835,7 +839,7 @@ static int configure_domain_dma_state(struct fsl_dma_domain *dma_domain, bool en
 static int fsl_pamu_set_domain_attr(struct iommu_domain *domain,
 				 enum iommu_attr attr_type, void *data)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 	int ret = 0;
 
 
@@ -861,7 +865,7 @@ static int fsl_pamu_set_domain_attr(struct iommu_domain *domain,
 static int fsl_pamu_get_domain_attr(struct iommu_domain *domain,
 				 enum iommu_attr attr_type, void *data)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 	int ret = 0;
 
 
@@ -1025,7 +1029,7 @@ static void fsl_pamu_remove_device(struct device *dev)
 
 static int fsl_pamu_set_windows(struct iommu_domain *domain, u32 w_count)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 	unsigned long flags;
 	int ret;
 
@@ -1073,15 +1077,15 @@ static int fsl_pamu_set_windows(struct iommu_domain *domain, u32 w_count)
 
 static u32 fsl_pamu_get_windows(struct iommu_domain *domain)
 {
-	struct fsl_dma_domain *dma_domain = domain->priv;
+	struct fsl_dma_domain *dma_domain = to_fsl_dma_domain(domain);
 
 	return dma_domain->win_cnt;
 }
 
 static const struct iommu_ops fsl_pamu_ops = {
 	.capable	= fsl_pamu_capable,
-	.domain_init	= fsl_pamu_domain_init,
-	.domain_destroy = fsl_pamu_domain_destroy,
+	.domain_alloc	= fsl_pamu_domain_alloc,
+	.domain_free    = fsl_pamu_domain_free,
 	.attach_dev	= fsl_pamu_attach_device,
 	.detach_dev	= fsl_pamu_detach_device,
 	.domain_window_enable = fsl_pamu_window_enable,
diff --git a/drivers/iommu/fsl_pamu_domain.h b/drivers/iommu/fsl_pamu_domain.h
index c90293f..f2b0f74 100644
--- a/drivers/iommu/fsl_pamu_domain.h
+++ b/drivers/iommu/fsl_pamu_domain.h
@@ -71,7 +71,7 @@ struct fsl_dma_domain {
 	u32				stash_id;
 	struct pamu_stash_attribute	dma_stash;
 	u32				snoop_id;
-	struct iommu_domain		*iommu_domain;
+	struct iommu_domain		iommu_domain;
 	spinlock_t			domain_lock;
 };
 
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 15/15] iommu: Remove domain_init and domain_free iommu_ops
  2015-01-26 23:51 ` Joerg Roedel
  (?)
@ 2015-01-26 23:51     ` Joerg Roedel
  -1 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA
  Cc: Alexandre Courbot, linux-samsung-soc-u79uwXL29TY76Z2rM5mHXA,
	Heiko Stuebner, Arnd Bergmann, Stephen Warren, Will Deacon,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-rockchip-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Kukjin Kim,
	Thierry Reding, jroedel-l3A5Bk7waGM,
	linux-tegra-u79uwXL29TY76Z2rM5mHXA, David Woodhouse,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r

From: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>

All drivers have been converted to the new domain_alloc and
domain_free iommu-ops. So remove the old ones and get rid of
iommu_domain->priv too, as this is no longer needed when the
struct iommu_domain is embedded in the private structures of
the iommu drivers.

Signed-off-by: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>
---
 drivers/iommu/iommu.c | 30 ++----------------------------
 include/linux/iommu.h |  3 ---
 2 files changed, 2 insertions(+), 31 deletions(-)

diff --git a/drivers/iommu/iommu.c b/drivers/iommu/iommu.c
index ab24d77..e66cc08 100644
--- a/drivers/iommu/iommu.c
+++ b/drivers/iommu/iommu.c
@@ -900,51 +900,25 @@ EXPORT_SYMBOL_GPL(iommu_set_fault_handler);
 
 struct iommu_domain *iommu_domain_alloc(struct bus_type *bus)
 {
-	const struct iommu_ops *ops;
 	struct iommu_domain *domain;
 
 	if (bus == NULL || bus->iommu_ops == NULL)
 		return NULL;
 
-	ops = bus->iommu_ops;
-
-	if (ops->domain_alloc)
-		domain = ops->domain_alloc(IOMMU_DOMAIN_UNMANAGED);
-	else
-		domain = kzalloc(sizeof(*domain), GFP_KERNEL);
-
+	domain = bus->iommu_ops->domain_alloc(IOMMU_DOMAIN_UNMANAGED);
 	if (!domain)
 		return NULL;
 
 	domain->ops  = bus->iommu_ops;
 	domain->type = IOMMU_DOMAIN_UNMANAGED;
 
-	if (ops->domain_init && domain->ops->domain_init(domain))
-		goto out_free;
-
 	return domain;
-
-out_free:
-	if (ops->domain_free)
-		ops->domain_free(domain);
-	else
-		kfree(domain);
-
-	return NULL;
 }
 EXPORT_SYMBOL_GPL(iommu_domain_alloc);
 
 void iommu_domain_free(struct iommu_domain *domain)
 {
-	const struct iommu_ops *ops = domain->ops;
-
-	if (likely(ops->domain_destroy != NULL))
-		ops->domain_destroy(domain);
-
-	if (ops->domain_free)
-		ops->domain_free(domain);
-	else
-		kfree(domain);
+	domain->ops->domain_free(domain);
 }
 EXPORT_SYMBOL_GPL(iommu_domain_free);
 
diff --git a/include/linux/iommu.h b/include/linux/iommu.h
index 0b67f65..2951dca 100644
--- a/include/linux/iommu.h
+++ b/include/linux/iommu.h
@@ -62,7 +62,6 @@ enum iommu_domain_type {
 struct iommu_domain {
 	enum iommu_domain_type type;
 	const struct iommu_ops *ops;
-	void *priv;
 	iommu_fault_handler_t handler;
 	void *handler_token;
 	struct iommu_domain_geometry geometry;
@@ -122,8 +121,6 @@ enum iommu_attr {
  */
 struct iommu_ops {
 	bool (*capable)(enum iommu_cap);
-	int (*domain_init)(struct iommu_domain *domain);
-	void (*domain_destroy)(struct iommu_domain *domain);
 
 	/* Domain allocation and freeing by the iommu driver */
 	struct iommu_domain *(*domain_alloc)(enum iommu_domain_type);
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 15/15] iommu: Remove domain_init and domain_free iommu_ops
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: iommu
  Cc: Will Deacon, Kukjin Kim, David Woodhouse, Heiko Stuebner,
	Hiroshi Doyu, Stephen Warren, Thierry Reding, Alexandre Courbot,
	Alex Williamson, Arnd Bergmann, linux-kernel, linux-arm-kernel,
	linux-samsung-soc, linux-rockchip, linux-tegra, Joerg Roedel,
	jroedel

From: Joerg Roedel <jroedel@suse.de>

All drivers have been converted to the new domain_alloc and
domain_free iommu-ops. So remove the old ones and get rid of
iommu_domain->priv too, as this is no longer needed when the
struct iommu_domain is embedded in the private structures of
the iommu drivers.

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

diff --git a/drivers/iommu/iommu.c b/drivers/iommu/iommu.c
index ab24d77..e66cc08 100644
--- a/drivers/iommu/iommu.c
+++ b/drivers/iommu/iommu.c
@@ -900,51 +900,25 @@ EXPORT_SYMBOL_GPL(iommu_set_fault_handler);
 
 struct iommu_domain *iommu_domain_alloc(struct bus_type *bus)
 {
-	const struct iommu_ops *ops;
 	struct iommu_domain *domain;
 
 	if (bus == NULL || bus->iommu_ops == NULL)
 		return NULL;
 
-	ops = bus->iommu_ops;
-
-	if (ops->domain_alloc)
-		domain = ops->domain_alloc(IOMMU_DOMAIN_UNMANAGED);
-	else
-		domain = kzalloc(sizeof(*domain), GFP_KERNEL);
-
+	domain = bus->iommu_ops->domain_alloc(IOMMU_DOMAIN_UNMANAGED);
 	if (!domain)
 		return NULL;
 
 	domain->ops  = bus->iommu_ops;
 	domain->type = IOMMU_DOMAIN_UNMANAGED;
 
-	if (ops->domain_init && domain->ops->domain_init(domain))
-		goto out_free;
-
 	return domain;
-
-out_free:
-	if (ops->domain_free)
-		ops->domain_free(domain);
-	else
-		kfree(domain);
-
-	return NULL;
 }
 EXPORT_SYMBOL_GPL(iommu_domain_alloc);
 
 void iommu_domain_free(struct iommu_domain *domain)
 {
-	const struct iommu_ops *ops = domain->ops;
-
-	if (likely(ops->domain_destroy != NULL))
-		ops->domain_destroy(domain);
-
-	if (ops->domain_free)
-		ops->domain_free(domain);
-	else
-		kfree(domain);
+	domain->ops->domain_free(domain);
 }
 EXPORT_SYMBOL_GPL(iommu_domain_free);
 
diff --git a/include/linux/iommu.h b/include/linux/iommu.h
index 0b67f65..2951dca 100644
--- a/include/linux/iommu.h
+++ b/include/linux/iommu.h
@@ -62,7 +62,6 @@ enum iommu_domain_type {
 struct iommu_domain {
 	enum iommu_domain_type type;
 	const struct iommu_ops *ops;
-	void *priv;
 	iommu_fault_handler_t handler;
 	void *handler_token;
 	struct iommu_domain_geometry geometry;
@@ -122,8 +121,6 @@ enum iommu_attr {
  */
 struct iommu_ops {
 	bool (*capable)(enum iommu_cap);
-	int (*domain_init)(struct iommu_domain *domain);
-	void (*domain_destroy)(struct iommu_domain *domain);
 
 	/* Domain allocation and freeing by the iommu driver */
 	struct iommu_domain *(*domain_alloc)(enum iommu_domain_type);
-- 
1.8.4.5


^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 15/15] iommu: Remove domain_init and domain_free iommu_ops
@ 2015-01-26 23:51     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-26 23:51 UTC (permalink / raw)
  To: linux-arm-kernel

From: Joerg Roedel <jroedel@suse.de>

All drivers have been converted to the new domain_alloc and
domain_free iommu-ops. So remove the old ones and get rid of
iommu_domain->priv too, as this is no longer needed when the
struct iommu_domain is embedded in the private structures of
the iommu drivers.

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

diff --git a/drivers/iommu/iommu.c b/drivers/iommu/iommu.c
index ab24d77..e66cc08 100644
--- a/drivers/iommu/iommu.c
+++ b/drivers/iommu/iommu.c
@@ -900,51 +900,25 @@ EXPORT_SYMBOL_GPL(iommu_set_fault_handler);
 
 struct iommu_domain *iommu_domain_alloc(struct bus_type *bus)
 {
-	const struct iommu_ops *ops;
 	struct iommu_domain *domain;
 
 	if (bus == NULL || bus->iommu_ops == NULL)
 		return NULL;
 
-	ops = bus->iommu_ops;
-
-	if (ops->domain_alloc)
-		domain = ops->domain_alloc(IOMMU_DOMAIN_UNMANAGED);
-	else
-		domain = kzalloc(sizeof(*domain), GFP_KERNEL);
-
+	domain = bus->iommu_ops->domain_alloc(IOMMU_DOMAIN_UNMANAGED);
 	if (!domain)
 		return NULL;
 
 	domain->ops  = bus->iommu_ops;
 	domain->type = IOMMU_DOMAIN_UNMANAGED;
 
-	if (ops->domain_init && domain->ops->domain_init(domain))
-		goto out_free;
-
 	return domain;
-
-out_free:
-	if (ops->domain_free)
-		ops->domain_free(domain);
-	else
-		kfree(domain);
-
-	return NULL;
 }
 EXPORT_SYMBOL_GPL(iommu_domain_alloc);
 
 void iommu_domain_free(struct iommu_domain *domain)
 {
-	const struct iommu_ops *ops = domain->ops;
-
-	if (likely(ops->domain_destroy != NULL))
-		ops->domain_destroy(domain);
-
-	if (ops->domain_free)
-		ops->domain_free(domain);
-	else
-		kfree(domain);
+	domain->ops->domain_free(domain);
 }
 EXPORT_SYMBOL_GPL(iommu_domain_free);
 
diff --git a/include/linux/iommu.h b/include/linux/iommu.h
index 0b67f65..2951dca 100644
--- a/include/linux/iommu.h
+++ b/include/linux/iommu.h
@@ -62,7 +62,6 @@ enum iommu_domain_type {
 struct iommu_domain {
 	enum iommu_domain_type type;
 	const struct iommu_ops *ops;
-	void *priv;
 	iommu_fault_handler_t handler;
 	void *handler_token;
 	struct iommu_domain_geometry geometry;
@@ -122,8 +121,6 @@ enum iommu_attr {
  */
 struct iommu_ops {
 	bool (*capable)(enum iommu_cap);
-	int (*domain_init)(struct iommu_domain *domain);
-	void (*domain_destroy)(struct iommu_domain *domain);
 
 	/* Domain allocation and freeing by the iommu driver */
 	struct iommu_domain *(*domain_alloc)(enum iommu_domain_type);
-- 
1.8.4.5

^ permalink raw reply	[flat|nested] 62+ messages in thread

* Re: [PATCH 02/15] iommu: Introduce iommu domain types
  2015-01-26 23:51     ` Joerg Roedel
  (?)
@ 2015-01-28 14:19         ` Will Deacon
  -1 siblings, 0 replies; 62+ messages in thread
From: Will Deacon @ 2015-01-28 14:19 UTC (permalink / raw)
  To: Joerg Roedel
  Cc: Alexandre Courbot, linux-samsung-soc-u79uwXL29TY76Z2rM5mHXA,
	Heiko Stuebner, Arnd Bergmann, Stephen Warren,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-rockchip-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r,
	iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA, Kukjin Kim,
	Thierry Reding, jroedel-l3A5Bk7waGM,
	linux-tegra-u79uwXL29TY76Z2rM5mHXA, David Woodhouse,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r

Hi Joerg,

Thanks for posting this!

On Mon, Jan 26, 2015 at 11:51:32PM +0000, Joerg Roedel wrote:
> From: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>
> 
> This allows to handle domains differently based on their
> type in the future. An IOMMU driver can implement certain
> optimizations for DMA-API domains for example.
> 
> Signed-off-by: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>
> ---
>  drivers/iommu/iommu.c |  5 +++--
>  include/linux/iommu.h | 11 ++++++++++-
>  2 files changed, 13 insertions(+), 3 deletions(-)
> 
> diff --git a/drivers/iommu/iommu.c b/drivers/iommu/iommu.c
> index 684efc0..ab24d77 100644
> --- a/drivers/iommu/iommu.c
> +++ b/drivers/iommu/iommu.c
> @@ -909,14 +909,15 @@ struct iommu_domain *iommu_domain_alloc(struct bus_type *bus)
>  	ops = bus->iommu_ops;
>  
>  	if (ops->domain_alloc)
> -		domain = ops->domain_alloc();
> +		domain = ops->domain_alloc(IOMMU_DOMAIN_UNMANAGED);
>  	else
>  		domain = kzalloc(sizeof(*domain), GFP_KERNEL);
>  
>  	if (!domain)
>  		return NULL;
>  
> -	domain->ops = bus->iommu_ops;
> +	domain->ops  = bus->iommu_ops;
> +	domain->type = IOMMU_DOMAIN_UNMANAGED;
>  
>  	if (ops->domain_init && domain->ops->domain_init(domain))
>  		goto out_free;
> diff --git a/include/linux/iommu.h b/include/linux/iommu.h
> index 69d1d12..0b67f65 100644
> --- a/include/linux/iommu.h
> +++ b/include/linux/iommu.h
> @@ -51,7 +51,16 @@ struct iommu_domain_geometry {
>  	bool force_aperture;       /* DMA only allowed in mappable range? */
>  };
>  
> +/* This are the possible domain-types */
> +enum iommu_domain_type {
> +	IOMMU_DOMAIN_DMA,	/* Domain used for DMA-API */
> +	IOMMU_DOMAIN_IDENTITY,	/* Identity mapped domain  */

What happens if somebody calls map or unmap on an identity-mapping domain?
Can we catch that in the IOMMU core before calling the IOMMU driver? That
also implies we need something extra to parameterise the attributes for
the mapping (e.g. cacheable, read-only) and also potentially the address
range.

> +	IOMMU_DOMAIN_UNMANAGED, /* Domain mappings are managed by a third party
> +				   user (like KVM or VFIO) */

We already have the domain attributes (iommu_attr) to describe features
of a domain. Is there really a need for this extra type, or can we extend
the attribute set and allow for domain allocation with attributes?

Will

^ permalink raw reply	[flat|nested] 62+ messages in thread

* Re: [PATCH 02/15] iommu: Introduce iommu domain types
@ 2015-01-28 14:19         ` Will Deacon
  0 siblings, 0 replies; 62+ messages in thread
From: Will Deacon @ 2015-01-28 14:19 UTC (permalink / raw)
  To: Joerg Roedel
  Cc: iommu, Kukjin Kim, David Woodhouse, Heiko Stuebner, Hiroshi Doyu,
	Stephen Warren, Thierry Reding, Alexandre Courbot,
	Alex Williamson, Arnd Bergmann, linux-kernel, linux-arm-kernel,
	linux-samsung-soc, linux-rockchip, linux-tegra, jroedel

Hi Joerg,

Thanks for posting this!

On Mon, Jan 26, 2015 at 11:51:32PM +0000, Joerg Roedel wrote:
> From: Joerg Roedel <jroedel@suse.de>
> 
> This allows to handle domains differently based on their
> type in the future. An IOMMU driver can implement certain
> optimizations for DMA-API domains for example.
> 
> Signed-off-by: Joerg Roedel <jroedel@suse.de>
> ---
>  drivers/iommu/iommu.c |  5 +++--
>  include/linux/iommu.h | 11 ++++++++++-
>  2 files changed, 13 insertions(+), 3 deletions(-)
> 
> diff --git a/drivers/iommu/iommu.c b/drivers/iommu/iommu.c
> index 684efc0..ab24d77 100644
> --- a/drivers/iommu/iommu.c
> +++ b/drivers/iommu/iommu.c
> @@ -909,14 +909,15 @@ struct iommu_domain *iommu_domain_alloc(struct bus_type *bus)
>  	ops = bus->iommu_ops;
>  
>  	if (ops->domain_alloc)
> -		domain = ops->domain_alloc();
> +		domain = ops->domain_alloc(IOMMU_DOMAIN_UNMANAGED);
>  	else
>  		domain = kzalloc(sizeof(*domain), GFP_KERNEL);
>  
>  	if (!domain)
>  		return NULL;
>  
> -	domain->ops = bus->iommu_ops;
> +	domain->ops  = bus->iommu_ops;
> +	domain->type = IOMMU_DOMAIN_UNMANAGED;
>  
>  	if (ops->domain_init && domain->ops->domain_init(domain))
>  		goto out_free;
> diff --git a/include/linux/iommu.h b/include/linux/iommu.h
> index 69d1d12..0b67f65 100644
> --- a/include/linux/iommu.h
> +++ b/include/linux/iommu.h
> @@ -51,7 +51,16 @@ struct iommu_domain_geometry {
>  	bool force_aperture;       /* DMA only allowed in mappable range? */
>  };
>  
> +/* This are the possible domain-types */
> +enum iommu_domain_type {
> +	IOMMU_DOMAIN_DMA,	/* Domain used for DMA-API */
> +	IOMMU_DOMAIN_IDENTITY,	/* Identity mapped domain  */

What happens if somebody calls map or unmap on an identity-mapping domain?
Can we catch that in the IOMMU core before calling the IOMMU driver? That
also implies we need something extra to parameterise the attributes for
the mapping (e.g. cacheable, read-only) and also potentially the address
range.

> +	IOMMU_DOMAIN_UNMANAGED, /* Domain mappings are managed by a third party
> +				   user (like KVM or VFIO) */

We already have the domain attributes (iommu_attr) to describe features
of a domain. Is there really a need for this extra type, or can we extend
the attribute set and allow for domain allocation with attributes?

Will

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 02/15] iommu: Introduce iommu domain types
@ 2015-01-28 14:19         ` Will Deacon
  0 siblings, 0 replies; 62+ messages in thread
From: Will Deacon @ 2015-01-28 14:19 UTC (permalink / raw)
  To: linux-arm-kernel

Hi Joerg,

Thanks for posting this!

On Mon, Jan 26, 2015 at 11:51:32PM +0000, Joerg Roedel wrote:
> From: Joerg Roedel <jroedel@suse.de>
> 
> This allows to handle domains differently based on their
> type in the future. An IOMMU driver can implement certain
> optimizations for DMA-API domains for example.
> 
> Signed-off-by: Joerg Roedel <jroedel@suse.de>
> ---
>  drivers/iommu/iommu.c |  5 +++--
>  include/linux/iommu.h | 11 ++++++++++-
>  2 files changed, 13 insertions(+), 3 deletions(-)
> 
> diff --git a/drivers/iommu/iommu.c b/drivers/iommu/iommu.c
> index 684efc0..ab24d77 100644
> --- a/drivers/iommu/iommu.c
> +++ b/drivers/iommu/iommu.c
> @@ -909,14 +909,15 @@ struct iommu_domain *iommu_domain_alloc(struct bus_type *bus)
>  	ops = bus->iommu_ops;
>  
>  	if (ops->domain_alloc)
> -		domain = ops->domain_alloc();
> +		domain = ops->domain_alloc(IOMMU_DOMAIN_UNMANAGED);
>  	else
>  		domain = kzalloc(sizeof(*domain), GFP_KERNEL);
>  
>  	if (!domain)
>  		return NULL;
>  
> -	domain->ops = bus->iommu_ops;
> +	domain->ops  = bus->iommu_ops;
> +	domain->type = IOMMU_DOMAIN_UNMANAGED;
>  
>  	if (ops->domain_init && domain->ops->domain_init(domain))
>  		goto out_free;
> diff --git a/include/linux/iommu.h b/include/linux/iommu.h
> index 69d1d12..0b67f65 100644
> --- a/include/linux/iommu.h
> +++ b/include/linux/iommu.h
> @@ -51,7 +51,16 @@ struct iommu_domain_geometry {
>  	bool force_aperture;       /* DMA only allowed in mappable range? */
>  };
>  
> +/* This are the possible domain-types */
> +enum iommu_domain_type {
> +	IOMMU_DOMAIN_DMA,	/* Domain used for DMA-API */
> +	IOMMU_DOMAIN_IDENTITY,	/* Identity mapped domain  */

What happens if somebody calls map or unmap on an identity-mapping domain?
Can we catch that in the IOMMU core before calling the IOMMU driver? That
also implies we need something extra to parameterise the attributes for
the mapping (e.g. cacheable, read-only) and also potentially the address
range.

> +	IOMMU_DOMAIN_UNMANAGED, /* Domain mappings are managed by a third party
> +				   user (like KVM or VFIO) */

We already have the domain attributes (iommu_attr) to describe features
of a domain. Is there really a need for this extra type, or can we extend
the attribute set and allow for domain allocation with attributes?

Will

^ permalink raw reply	[flat|nested] 62+ messages in thread

* Re: [PATCH 02/15] iommu: Introduce iommu domain types
  2015-01-28 14:19         ` Will Deacon
  (?)
@ 2015-01-30 12:22             ` Joerg Roedel
  -1 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-30 12:22 UTC (permalink / raw)
  To: Will Deacon
  Cc: Alexandre Courbot, linux-samsung-soc-u79uwXL29TY76Z2rM5mHXA,
	Heiko Stuebner, Arnd Bergmann, Stephen Warren,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-rockchip-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r,
	iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA, Kukjin Kim,
	Thierry Reding, jroedel-l3A5Bk7waGM,
	linux-tegra-u79uwXL29TY76Z2rM5mHXA, David Woodhouse,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r

Hi Will,

On Wed, Jan 28, 2015 at 02:19:34PM +0000, Will Deacon wrote:
> > +/* This are the possible domain-types */
> > +enum iommu_domain_type {
> > +	IOMMU_DOMAIN_DMA,	/* Domain used for DMA-API */
> > +	IOMMU_DOMAIN_IDENTITY,	/* Identity mapped domain  */
> 
> What happens if somebody calls map or unmap on an identity-mapping domain?
> Can we catch that in the IOMMU core before calling the IOMMU driver? That
> also implies we need something extra to parameterise the attributes for
> the mapping (e.g. cacheable, read-only) and also potentially the address
> range.

The domain type is only used by the IOMMU drivers to do be able to enter
special allocation paths (the AMD-Vi driver for example could allocate a
special internal domain type for IOMMU_DOMAIN_DMA).
But I think you are right, a couple of the current domain attributes we
have could be moved here, turning the domain-type into a bit-field. So
we could have bits for PAGING, CACHABLE, DMA_API and NESTING and build
the domain types above from those bits.

> > +	IOMMU_DOMAIN_UNMANAGED, /* Domain mappings are managed by a third party
> > +				   user (like KVM or VFIO) */
> 
> We already have the domain attributes (iommu_attr) to describe features
> of a domain. Is there really a need for this extra type, or can we extend
> the attribute set and allow for domain allocation with attributes?

I don't think that domains attributed will become obsolete with this
domain-type field. Some of the attributes should stay there for now,
like all the PAMU specific stuff. But I agree, some could be moved over.

	
	Joerg

^ permalink raw reply	[flat|nested] 62+ messages in thread

* Re: [PATCH 02/15] iommu: Introduce iommu domain types
@ 2015-01-30 12:22             ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-30 12:22 UTC (permalink / raw)
  To: Will Deacon
  Cc: iommu, Kukjin Kim, David Woodhouse, Heiko Stuebner, Hiroshi Doyu,
	Stephen Warren, Thierry Reding, Alexandre Courbot,
	Alex Williamson, Arnd Bergmann, linux-kernel, linux-arm-kernel,
	linux-samsung-soc, linux-rockchip, linux-tegra, jroedel

Hi Will,

On Wed, Jan 28, 2015 at 02:19:34PM +0000, Will Deacon wrote:
> > +/* This are the possible domain-types */
> > +enum iommu_domain_type {
> > +	IOMMU_DOMAIN_DMA,	/* Domain used for DMA-API */
> > +	IOMMU_DOMAIN_IDENTITY,	/* Identity mapped domain  */
> 
> What happens if somebody calls map or unmap on an identity-mapping domain?
> Can we catch that in the IOMMU core before calling the IOMMU driver? That
> also implies we need something extra to parameterise the attributes for
> the mapping (e.g. cacheable, read-only) and also potentially the address
> range.

The domain type is only used by the IOMMU drivers to do be able to enter
special allocation paths (the AMD-Vi driver for example could allocate a
special internal domain type for IOMMU_DOMAIN_DMA).
But I think you are right, a couple of the current domain attributes we
have could be moved here, turning the domain-type into a bit-field. So
we could have bits for PAGING, CACHABLE, DMA_API and NESTING and build
the domain types above from those bits.

> > +	IOMMU_DOMAIN_UNMANAGED, /* Domain mappings are managed by a third party
> > +				   user (like KVM or VFIO) */
> 
> We already have the domain attributes (iommu_attr) to describe features
> of a domain. Is there really a need for this extra type, or can we extend
> the attribute set and allow for domain allocation with attributes?

I don't think that domains attributed will become obsolete with this
domain-type field. Some of the attributes should stay there for now,
like all the PAMU specific stuff. But I agree, some could be moved over.

	
	Joerg


^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 02/15] iommu: Introduce iommu domain types
@ 2015-01-30 12:22             ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-01-30 12:22 UTC (permalink / raw)
  To: linux-arm-kernel

Hi Will,

On Wed, Jan 28, 2015 at 02:19:34PM +0000, Will Deacon wrote:
> > +/* This are the possible domain-types */
> > +enum iommu_domain_type {
> > +	IOMMU_DOMAIN_DMA,	/* Domain used for DMA-API */
> > +	IOMMU_DOMAIN_IDENTITY,	/* Identity mapped domain  */
> 
> What happens if somebody calls map or unmap on an identity-mapping domain?
> Can we catch that in the IOMMU core before calling the IOMMU driver? That
> also implies we need something extra to parameterise the attributes for
> the mapping (e.g. cacheable, read-only) and also potentially the address
> range.

The domain type is only used by the IOMMU drivers to do be able to enter
special allocation paths (the AMD-Vi driver for example could allocate a
special internal domain type for IOMMU_DOMAIN_DMA).
But I think you are right, a couple of the current domain attributes we
have could be moved here, turning the domain-type into a bit-field. So
we could have bits for PAGING, CACHABLE, DMA_API and NESTING and build
the domain types above from those bits.

> > +	IOMMU_DOMAIN_UNMANAGED, /* Domain mappings are managed by a third party
> > +				   user (like KVM or VFIO) */
> 
> We already have the domain attributes (iommu_attr) to describe features
> of a domain. Is there really a need for this extra type, or can we extend
> the attribute set and allow for domain allocation with attributes?

I don't think that domains attributed will become obsolete with this
domain-type field. Some of the attributes should stay there for now,
like all the PAMU specific stuff. But I agree, some could be moved over.

	
	Joerg

^ permalink raw reply	[flat|nested] 62+ messages in thread

* Re: [PATCH 00/15] iommu: Move domain allocation into drivers
  2015-01-26 23:51 ` Joerg Roedel
@ 2015-03-20  9:24   ` Yingjoe Chen
  -1 siblings, 0 replies; 62+ messages in thread
From: Yingjoe Chen @ 2015-03-20  9:24 UTC (permalink / raw)
  To: Joerg Roedel
  Cc: iommu, Alexandre Courbot, linux-samsung-soc, Heiko Stuebner,
	Arnd Bergmann, Stephen Warren, Will Deacon, linux-kernel,
	linux-rockchip, Alex Williamson, Kukjin Kim, Thierry Reding,
	jroedel, linux-tegra, David Woodhouse, linux-arm-kernel,
	Hiroshi Doyu, Tomasz Figa, Yong Wu (吴勇),
	Robin Murphy

On Tue, 2015-01-27 at 00:51 +0100, Joerg Roedel wrote:
> From: Joerg Roedel <jroedel@suse.de>
> 
> Hi,
> 
> here is patch-set to replace the existing domain_init and
> domain_destroy iommu-ops with the new domain_alloc and
> domain_free callbacks
> 
> The new callbacks move the allocation of iommu domains into
> the iommu driver, allowing them to put a generic
> iommu_domain struct into their own domain struct. This makes
> domain handling in the drivers more cache efficient and
> prepares the introduction of default domains in another
> patch-set.

Hi Joerg,

What's the status of this patchset?
While porting MTK IOMMU driver[1], we need to use a global variable
because we need to do dma_alloc_coherent in our domain_init. I think we
can remove that global variable if we base on this series.

Joe.C

[1]
http://lists.infradead.org/pipermail/linux-arm-kernel/2015-March/328461.html

^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 00/15] iommu: Move domain allocation into drivers
@ 2015-03-20  9:24   ` Yingjoe Chen
  0 siblings, 0 replies; 62+ messages in thread
From: Yingjoe Chen @ 2015-03-20  9:24 UTC (permalink / raw)
  To: linux-arm-kernel

On Tue, 2015-01-27 at 00:51 +0100, Joerg Roedel wrote:
> From: Joerg Roedel <jroedel@suse.de>
> 
> Hi,
> 
> here is patch-set to replace the existing domain_init and
> domain_destroy iommu-ops with the new domain_alloc and
> domain_free callbacks
> 
> The new callbacks move the allocation of iommu domains into
> the iommu driver, allowing them to put a generic
> iommu_domain struct into their own domain struct. This makes
> domain handling in the drivers more cache efficient and
> prepares the introduction of default domains in another
> patch-set.

Hi Joerg,

What's the status of this patchset?
While porting MTK IOMMU driver[1], we need to use a global variable
because we need to do dma_alloc_coherent in our domain_init. I think we
can remove that global variable if we base on this series.

Joe.C

[1]
http://lists.infradead.org/pipermail/linux-arm-kernel/2015-March/328461.html

^ permalink raw reply	[flat|nested] 62+ messages in thread

* Re: [PATCH 00/15] iommu: Move domain allocation into drivers
  2015-03-20  9:24   ` Yingjoe Chen
  (?)
@ 2015-03-23 11:49     ` Joerg Roedel
  -1 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-03-23 11:49 UTC (permalink / raw)
  To: Yingjoe Chen
  Cc: iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA,
	Alexandre Courbot, linux-samsung-soc-u79uwXL29TY76Z2rM5mHXA,
	Heiko Stuebner, Arnd Bergmann, Stephen Warren, Will Deacon,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-rockchip-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Alex Williamson,
	Kukjin Kim, Thierry Reding, jroedel-l3A5Bk7waGM,
	linux-tegra-u79uwXL29TY76Z2rM5mHXA, David Woodhouse,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Hiroshi Doyu,
	Tomasz Figa, Yong Wu (吴勇),
	Robin Murphy

Hi Yingjoe,

On Fri, Mar 20, 2015 at 05:24:18PM +0800, Yingjoe Chen wrote:
> What's the status of this patchset?
> While porting MTK IOMMU driver[1], we need to use a global variable
> because we need to do dma_alloc_coherent in our domain_init. I think we
> can remove that global variable if we base on this series.

I plan to send out a new version this week.


	Joerg

^ permalink raw reply	[flat|nested] 62+ messages in thread

* Re: [PATCH 00/15] iommu: Move domain allocation into drivers
@ 2015-03-23 11:49     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-03-23 11:49 UTC (permalink / raw)
  To: Yingjoe Chen
  Cc: iommu, Alexandre Courbot, linux-samsung-soc, Heiko Stuebner,
	Arnd Bergmann, Stephen Warren, Will Deacon, linux-kernel,
	linux-rockchip, Alex Williamson, Kukjin Kim, Thierry Reding,
	jroedel, linux-tegra, David Woodhouse, linux-arm-kernel,
	Hiroshi Doyu, Tomasz Figa, Yong Wu (吴勇),
	Robin Murphy

Hi Yingjoe,

On Fri, Mar 20, 2015 at 05:24:18PM +0800, Yingjoe Chen wrote:
> What's the status of this patchset?
> While porting MTK IOMMU driver[1], we need to use a global variable
> because we need to do dma_alloc_coherent in our domain_init. I think we
> can remove that global variable if we base on this series.

I plan to send out a new version this week.


	Joerg


^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 00/15] iommu: Move domain allocation into drivers
@ 2015-03-23 11:49     ` Joerg Roedel
  0 siblings, 0 replies; 62+ messages in thread
From: Joerg Roedel @ 2015-03-23 11:49 UTC (permalink / raw)
  To: linux-arm-kernel

Hi Yingjoe,

On Fri, Mar 20, 2015 at 05:24:18PM +0800, Yingjoe Chen wrote:
> What's the status of this patchset?
> While porting MTK IOMMU driver[1], we need to use a global variable
> because we need to do dma_alloc_coherent in our domain_init. I think we
> can remove that global variable if we base on this series.

I plan to send out a new version this week.


	Joerg

^ permalink raw reply	[flat|nested] 62+ messages in thread

* Re: [PATCH 00/15] iommu: Move domain allocation into drivers
  2015-03-23 11:49     ` Joerg Roedel
  (?)
@ 2015-03-23 13:35         ` Yingjoe Chen
  -1 siblings, 0 replies; 62+ messages in thread
From: Yingjoe Chen @ 2015-03-23 13:35 UTC (permalink / raw)
  To: Joerg Roedel
  Cc: iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA,
	Alexandre Courbot, linux-samsung-soc-u79uwXL29TY76Z2rM5mHXA,
	Heiko Stuebner, Arnd Bergmann, Stephen Warren, Will Deacon,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-rockchip-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Alex Williamson,
	Kukjin Kim, Thierry Reding, jroedel-l3A5Bk7waGM,
	linux-tegra-u79uwXL29TY76Z2rM5mHXA, David Woodhouse,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Hiroshi Doyu,
	Tomasz Figa, Yong Wu (吴勇),
	Robin Murphy

On Mon, 2015-03-23 at 12:49 +0100, Joerg Roedel wrote:
> Hi Yingjoe,
> 
> On Fri, Mar 20, 2015 at 05:24:18PM +0800, Yingjoe Chen wrote:
> > What's the status of this patchset?
> > While porting MTK IOMMU driver[1], we need to use a global variable
> > because we need to do dma_alloc_coherent in our domain_init. I think we
> > can remove that global variable if we base on this series.
> 
> I plan to send out a new version this week.

Hi Joerg,

That's great.
Thanks for the update :)

Joe.C

^ permalink raw reply	[flat|nested] 62+ messages in thread

* Re: [PATCH 00/15] iommu: Move domain allocation into drivers
@ 2015-03-23 13:35         ` Yingjoe Chen
  0 siblings, 0 replies; 62+ messages in thread
From: Yingjoe Chen @ 2015-03-23 13:35 UTC (permalink / raw)
  To: Joerg Roedel
  Cc: iommu, Alexandre Courbot, linux-samsung-soc, Heiko Stuebner,
	Arnd Bergmann, Stephen Warren, Will Deacon, linux-kernel,
	linux-rockchip, Alex Williamson, Kukjin Kim, Thierry Reding,
	jroedel, linux-tegra, David Woodhouse, linux-arm-kernel,
	Hiroshi Doyu, Tomasz Figa, Yong Wu (吴勇),
	Robin Murphy

On Mon, 2015-03-23 at 12:49 +0100, Joerg Roedel wrote:
> Hi Yingjoe,
> 
> On Fri, Mar 20, 2015 at 05:24:18PM +0800, Yingjoe Chen wrote:
> > What's the status of this patchset?
> > While porting MTK IOMMU driver[1], we need to use a global variable
> > because we need to do dma_alloc_coherent in our domain_init. I think we
> > can remove that global variable if we base on this series.
> 
> I plan to send out a new version this week.

Hi Joerg,

That's great.
Thanks for the update :)

Joe.C



^ permalink raw reply	[flat|nested] 62+ messages in thread

* [PATCH 00/15] iommu: Move domain allocation into drivers
@ 2015-03-23 13:35         ` Yingjoe Chen
  0 siblings, 0 replies; 62+ messages in thread
From: Yingjoe Chen @ 2015-03-23 13:35 UTC (permalink / raw)
  To: linux-arm-kernel

On Mon, 2015-03-23 at 12:49 +0100, Joerg Roedel wrote:
> Hi Yingjoe,
> 
> On Fri, Mar 20, 2015 at 05:24:18PM +0800, Yingjoe Chen wrote:
> > What's the status of this patchset?
> > While porting MTK IOMMU driver[1], we need to use a global variable
> > because we need to do dma_alloc_coherent in our domain_init. I think we
> > can remove that global variable if we base on this series.
> 
> I plan to send out a new version this week.

Hi Joerg,

That's great.
Thanks for the update :)

Joe.C

^ permalink raw reply	[flat|nested] 62+ messages in thread

end of thread, other threads:[~2015-03-23 13:37 UTC | newest]

Thread overview: 62+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2015-01-26 23:51 [PATCH 00/15] iommu: Move domain allocation into drivers Joerg Roedel
2015-01-26 23:51 ` Joerg Roedel
2015-01-26 23:51 ` Joerg Roedel
     [not found] ` <1422316305-19216-1-git-send-email-joro-zLv9SwRftAIdnm+yROfE0A@public.gmane.org>
2015-01-26 23:51   ` [PATCH 01/15] iommu: Introduce domain_alloc and domain_free iommu_ops Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51   ` [PATCH 02/15] iommu: Introduce iommu domain types Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
     [not found]     ` <1422316305-19216-3-git-send-email-joro-zLv9SwRftAIdnm+yROfE0A@public.gmane.org>
2015-01-28 14:19       ` Will Deacon
2015-01-28 14:19         ` Will Deacon
2015-01-28 14:19         ` Will Deacon
     [not found]         ` <20150128141934.GP1569-5wv7dgnIgG8@public.gmane.org>
2015-01-30 12:22           ` Joerg Roedel
2015-01-30 12:22             ` Joerg Roedel
2015-01-30 12:22             ` Joerg Roedel
2015-01-26 23:51   ` [PATCH 03/15] iommu/amd: Make use of domain_alloc and domain_free Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51   ` [PATCH 04/15] iommu/vt-d: " Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51   ` [PATCH 05/15] iommu/omap: " Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51   ` [PATCH 06/15] iommu/arm-smmu: " Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51   ` [PATCH 07/15] iommu/exynos: " Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51   ` [PATCH 08/15] iommu/tegra-smmu: " Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51   ` [PATCH 09/15] iommu/tegra-gart: " Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51   ` [PATCH 10/15] iommu/msm: " Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51   ` [PATCH 11/15] iommu/shmobile: " Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51   ` [PATCH 12/15] iommu/ipmmu-vmsa: " Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51   ` [PATCH 13/15] iommu/rockchip: " Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51   ` [PATCH 14/15] iommu/fsl: " Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51   ` [PATCH 15/15] iommu: Remove domain_init and domain_free iommu_ops Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-01-26 23:51     ` Joerg Roedel
2015-03-20  9:24 ` [PATCH 00/15] iommu: Move domain allocation into drivers Yingjoe Chen
2015-03-20  9:24   ` Yingjoe Chen
2015-03-23 11:49   ` Joerg Roedel
2015-03-23 11:49     ` Joerg Roedel
2015-03-23 11:49     ` Joerg Roedel
     [not found]     ` <20150323114921.GM4441-zLv9SwRftAIdnm+yROfE0A@public.gmane.org>
2015-03-23 13:35       ` Yingjoe Chen
2015-03-23 13:35         ` Yingjoe Chen
2015-03-23 13:35         ` Yingjoe Chen

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.