Re: [PATCH] ARM: Exynos4: integrate SYSMMU driver with DMA-mapping interface

2012-04-12 Thread Subash Patel

Hello Marek,

On 04/11/2012 08:06 PM, Marek Szyprowski wrote:

This patch provides an provides setup code which assigns IOMMU controllers
to FIMC and MFC devices and enables IOMMU aware DMA-mapping for them.
It has been tested on Samsung Exynos4 platform, NURI board.

Most of the work is done in the s5p_sysmmu_late_init() function, which
first assigns SYSMMU controller to respective client device and then
creates IO address space mapping structures. In this example 128 MiB of
address space is created at 0x2000 for most of the devices. IO address
allocation precision is set to 2^4 pages, so all small allocations will be
aligned to 64 pages. This reduces the size of the io address space bitmap
to 4 KiB.

To solve the clock dependency issues, parent clocks have been added to each
SYSMMU controller bus clock. This models the true hardware behavior,
because client's device bus clock also gates the respective sysmmu bus
clock.

Signed-off-by: Marek Szyprowskim.szyprow...@samsung.com
Acked-by: Kyungmin Parkkyungmin.p...@samsung.com
---
  arch/arm/mach-exynos/Kconfig   |1 +
  arch/arm/mach-exynos/clock-exynos4.c   |   64 +++-
  arch/arm/mach-exynos/dev-sysmmu.c  |   44 +++
  arch/arm/mach-exynos/include/mach/sysmmu.h |3 +
  drivers/iommu/Kconfig  |1 +
  5 files changed, 84 insertions(+), 29 deletions(-)

diff --git a/arch/arm/mach-exynos/Kconfig b/arch/arm/mach-exynos/Kconfig
index 801c738..25b9ba5 100644
--- a/arch/arm/mach-exynos/Kconfig
+++ b/arch/arm/mach-exynos/Kconfig
@@ -288,6 +288,7 @@ config MACH_NURI
select S5P_DEV_USB_EHCI
select S5P_SETUP_MIPIPHY
select EXYNOS4_DEV_DMA
+   select EXYNOS_DEV_SYSMMU
select EXYNOS4_SETUP_FIMC
select EXYNOS4_SETUP_FIMD0
select EXYNOS4_SETUP_I2C1
diff --git a/arch/arm/mach-exynos/clock-exynos4.c 
b/arch/arm/mach-exynos/clock-exynos4.c
index 29ae4df..fe459a3 100644
--- a/arch/arm/mach-exynos/clock-exynos4.c
+++ b/arch/arm/mach-exynos/clock-exynos4.c
@@ -497,29 +497,6 @@ static struct clk *exynos4_gate_clocks[] = {

  static struct clk exynos4_init_clocks_off[] = {
{
-   .name   = timers,
-   .parent =exynos4_clk_aclk_100.clk,
-   .enable = exynos4_clk_ip_peril_ctrl,
-   .ctrlbit= (124),
-   }, {
-   .name   = csis,
-   .devname= s5p-mipi-csis.0,
-   .enable = exynos4_clk_ip_cam_ctrl,
-   .ctrlbit= (1  4),
-   .parent =exynos4_clk_gate_cam,
-   }, {
-   .name   = csis,
-   .devname= s5p-mipi-csis.1,
-   .enable = exynos4_clk_ip_cam_ctrl,
-   .ctrlbit= (1  5),
-   .parent =exynos4_clk_gate_cam,
-   }, {
-   .name   = jpeg,
-   .id = 0,
-   .enable = exynos4_clk_ip_cam_ctrl,
-   .ctrlbit= (1  6),
-   .parent =exynos4_clk_gate_cam,
-   }, {
.name   = fimc,
.devname= exynos4-fimc.0,
.enable = exynos4_clk_ip_cam_ctrl,
@@ -544,6 +521,35 @@ static struct clk exynos4_init_clocks_off[] = {
.ctrlbit= (1  3),
.parent =exynos4_clk_gate_cam,
}, {
+   .name   = mfc,
+   .devname= s5p-mfc,
+   .enable = exynos4_clk_ip_mfc_ctrl,
+   .ctrlbit= (1  0),
+   .parent =exynos4_clk_gate_mfc,
+   }, {
+   .name   = timers,
+   .parent =exynos4_clk_aclk_100.clk,
+   .enable = exynos4_clk_ip_peril_ctrl,
+   .ctrlbit= (124),
+   }, {
+   .name   = csis,
+   .devname= s5p-mipi-csis.0,
+   .enable = exynos4_clk_ip_cam_ctrl,
+   .ctrlbit= (1  4),
+   .parent =exynos4_clk_gate_cam,
+   }, {
+   .name   = csis,
+   .devname= s5p-mipi-csis.1,
+   .enable = exynos4_clk_ip_cam_ctrl,
+   .ctrlbit= (1  5),
+   .parent =exynos4_clk_gate_cam,
+   }, {
+   .name   = jpeg,
+   .id = 0,
+   .enable = exynos4_clk_ip_cam_ctrl,
+   .ctrlbit= (1  6),
+   .parent =exynos4_clk_gate_cam,
+   }, {
.name   = hsmmc,
.devname= exynos4-sdhci.0,
.parent =exynos4_clk_aclk_133.clk,
@@ -674,12 +680,6 @@ static struct clk exynos4_init_clocks_off[] = {
.ctrlbit= (1  0),

RE: [PATCH] ARM: Exynos4: integrate SYSMMU driver with DMA-mapping interface

2012-04-12 Thread Marek Szyprowski
Hi Subash,

On Thursday, April 12, 2012 11:06 AM Subash Patel wrote:

 On 04/11/2012 08:06 PM, Marek Szyprowski wrote:
  This patch provides an provides setup code which assigns IOMMU controllers
  to FIMC and MFC devices and enables IOMMU aware DMA-mapping for them.
  It has been tested on Samsung Exynos4 platform, NURI board.
 
  Most of the work is done in the s5p_sysmmu_late_init() function, which
  first assigns SYSMMU controller to respective client device and then
  creates IO address space mapping structures. In this example 128 MiB of
  address space is created at 0x2000 for most of the devices. IO address
  allocation precision is set to 2^4 pages, so all small allocations will be
  aligned to 64 pages. This reduces the size of the io address space bitmap
  to 4 KiB.
 
  To solve the clock dependency issues, parent clocks have been added to each
  SYSMMU controller bus clock. This models the true hardware behavior,
  because client's device bus clock also gates the respective sysmmu bus
  clock.
 
  Signed-off-by: Marek Szyprowskim.szyprow...@samsung.com
  Acked-by: Kyungmin Parkkyungmin.p...@samsung.com
  ---
arch/arm/mach-exynos/Kconfig   |1 +
arch/arm/mach-exynos/clock-exynos4.c   |   64 
  +++-
arch/arm/mach-exynos/dev-sysmmu.c  |   44 +++
arch/arm/mach-exynos/include/mach/sysmmu.h |3 +
drivers/iommu/Kconfig  |1 +
5 files changed, 84 insertions(+), 29 deletions(-)
 
  diff --git a/arch/arm/mach-exynos/Kconfig b/arch/arm/mach-exynos/Kconfig
  index 801c738..25b9ba5 100644
  --- a/arch/arm/mach-exynos/Kconfig
  +++ b/arch/arm/mach-exynos/Kconfig
  @@ -288,6 +288,7 @@ config MACH_NURI
  select S5P_DEV_USB_EHCI
  select S5P_SETUP_MIPIPHY
  select EXYNOS4_DEV_DMA
  +   select EXYNOS_DEV_SYSMMU
  select EXYNOS4_SETUP_FIMC
  select EXYNOS4_SETUP_FIMD0
  select EXYNOS4_SETUP_I2C1
  diff --git a/arch/arm/mach-exynos/clock-exynos4.c 
  b/arch/arm/mach-exynos/clock-exynos4.c
  index 29ae4df..fe459a3 100644
  --- a/arch/arm/mach-exynos/clock-exynos4.c
  +++ b/arch/arm/mach-exynos/clock-exynos4.c
  @@ -497,29 +497,6 @@ static struct clk *exynos4_gate_clocks[] = {
 
static struct clk exynos4_init_clocks_off[] = {
  {
  -   .name   = timers,
  -   .parent =exynos4_clk_aclk_100.clk,
  -   .enable = exynos4_clk_ip_peril_ctrl,
  -   .ctrlbit= (124),
  -   }, {
  -   .name   = csis,
  -   .devname= s5p-mipi-csis.0,
  -   .enable = exynos4_clk_ip_cam_ctrl,
  -   .ctrlbit= (1  4),
  -   .parent =exynos4_clk_gate_cam,
  -   }, {
  -   .name   = csis,
  -   .devname= s5p-mipi-csis.1,
  -   .enable = exynos4_clk_ip_cam_ctrl,
  -   .ctrlbit= (1  5),
  -   .parent =exynos4_clk_gate_cam,
  -   }, {
  -   .name   = jpeg,
  -   .id = 0,
  -   .enable = exynos4_clk_ip_cam_ctrl,
  -   .ctrlbit= (1  6),
  -   .parent =exynos4_clk_gate_cam,
  -   }, {
  .name   = fimc,
  .devname= exynos4-fimc.0,
  .enable = exynos4_clk_ip_cam_ctrl,
  @@ -544,6 +521,35 @@ static struct clk exynos4_init_clocks_off[] = {
  .ctrlbit= (1  3),
  .parent =exynos4_clk_gate_cam,
  }, {
  +   .name   = mfc,
  +   .devname= s5p-mfc,
  +   .enable = exynos4_clk_ip_mfc_ctrl,
  +   .ctrlbit= (1  0),
  +   .parent =exynos4_clk_gate_mfc,
  +   }, {
  +   .name   = timers,
  +   .parent =exynos4_clk_aclk_100.clk,
  +   .enable = exynos4_clk_ip_peril_ctrl,
  +   .ctrlbit= (124),
  +   }, {
  +   .name   = csis,
  +   .devname= s5p-mipi-csis.0,
  +   .enable = exynos4_clk_ip_cam_ctrl,
  +   .ctrlbit= (1  4),
  +   .parent =exynos4_clk_gate_cam,
  +   }, {
  +   .name   = csis,
  +   .devname= s5p-mipi-csis.1,
  +   .enable = exynos4_clk_ip_cam_ctrl,
  +   .ctrlbit= (1  5),
  +   .parent =exynos4_clk_gate_cam,
  +   }, {
  +   .name   = jpeg,
  +   .id = 0,
  +   .enable = exynos4_clk_ip_cam_ctrl,
  +   .ctrlbit= (1  6),
  +   .parent =exynos4_clk_gate_cam,
  +   }, {
  .name   = hsmmc,
  .devname= exynos4-sdhci.0,
  .parent =exynos4_clk_aclk_133.clk,
  @@ -674,12 +680,6 @@ static struct clk exynos4_init_clocks_off[] = {
  .ctrlbit= (1  0),
   

Re: [PATCH] ARM: Exynos4: integrate SYSMMU driver with DMA-mapping interface

2012-04-12 Thread Arnd Bergmann
On Thursday 12 April 2012, Marek Szyprowski wrote:
 +
   +/*
   + * s5p_sysmmu_late_init
   + * Create DMA-mapping IOMMU context for specified devices. This function 
   must
   + * be called later, once SYSMMU driver gets registered and probed.
   + */
   +static int __init s5p_sysmmu_late_init(void)
   +{
   +   platform_set_sysmmu(SYSMMU_PLATDEV(fimc0).dev,s5p_device_fimc0.dev);
   +   platform_set_sysmmu(SYSMMU_PLATDEV(fimc1).dev,s5p_device_fimc1.dev);
   +   platform_set_sysmmu(SYSMMU_PLATDEV(fimc2).dev,s5p_device_fimc2.dev);
   +   platform_set_sysmmu(SYSMMU_PLATDEV(fimc3).dev,s5p_device_fimc3.dev);
   +   platform_set_sysmmu(SYSMMU_PLATDEV(mfc_l).dev,s5p_device_mfc_l.dev);
   +   platform_set_sysmmu(SYSMMU_PLATDEV(mfc_r).dev,s5p_device_mfc_r.dev);
   +
   +   s5p_create_iommu_mapping(s5p_device_fimc0.dev, 0x2000, SZ_128M, 
   4);
   +   s5p_create_iommu_mapping(s5p_device_fimc1.dev, 0x2000, SZ_128M, 
   4);
   +   s5p_create_iommu_mapping(s5p_device_fimc2.dev, 0x2000, SZ_128M, 
   4);
   +   s5p_create_iommu_mapping(s5p_device_fimc3.dev, 0x2000, SZ_128M, 
   4);
   +   s5p_create_iommu_mapping(s5p_device_mfc_l.dev, 0x2000, SZ_128M, 
   4);
   +   s5p_create_iommu_mapping(s5p_device_mfc_r.dev, 0x4000, SZ_128M, 
   4);
   +
   +   return 0;
   +}
   +device_initcall(s5p_sysmmu_late_init);
  
  Shouldn't these things be specific to a SoC? With this RFC, it happens
  that you will predefine the IOMMU attachment and mapping information for
  devices in common location (dev-sysmmu.c)? This may lead to problems
  because there are some IP's with SYSMMU support in exynos5, but not
  available in exynos4 (eg: GSC, FIMC-LITE, FIMC-ISP) Previously we used
  to do above declaration in individual machine file, which I think was
  more meaningful.
 
 Right, I simplified the code too much. Keeping these definitions inside 
 machine 
 files was a better idea. I completely forgot that Exynos sub-platform now 
 covers
 both Exynos4 and Exynos5 SoC families.

Ideally the information about iommu attachment should come from the
device tree. We have the dma-ranges properties that define how a dma
address space is mapped. I am not entirely sure how that works when you
have multiple IOMMUs and if that requires defining addititional properties,
but I think we should make it so that we don't have to hardcode specific
devices in the source.

Arnd
___
iommu mailing list
iommu@lists.linux-foundation.org
https://lists.linuxfoundation.org/mailman/listinfo/iommu


RE: [PATCH] ARM: Exynos4: integrate SYSMMU driver with DMA-mapping interface

2012-04-12 Thread Marek Szyprowski




 -Original Message-
 From: Arnd Bergmann [mailto:a...@arndb.de]
 Sent: Thursday, April 12, 2012 1:09 PM
 To: Marek Szyprowski
 Cc: 'Subash Patel'; linux-arm-ker...@lists.infradead.org; 
 linaro-mm-...@lists.linaro.org;
 linux...@kvack.org; linux-a...@vger.kernel.org; 
 iommu@lists.linux-foundation.org; 'Kyungmin
 Park'; 'Joerg Roedel'; 'Russell King - ARM Linux'; 'Chunsang Jeong'; 'Krishna 
 Reddy'; 'KyongHo
 Cho'; Andrzej Pietrasiewicz; 'Benjamin Herrenschmidt'; 'Konrad Rzeszutek 
 Wilk'; 'Hiroshi Doyu'
 Subject: Re: [PATCH] ARM: Exynos4: integrate SYSMMU driver with DMA-mapping 
 interface
 
 On Thursday 12 April 2012, Marek Szyprowski wrote:
  +
+/*
+ * s5p_sysmmu_late_init
+ * Create DMA-mapping IOMMU context for specified devices. This 
function must
+ * be called later, once SYSMMU driver gets registered and probed.
+ */
+static int __init s5p_sysmmu_late_init(void)
+{
+   
platform_set_sysmmu(SYSMMU_PLATDEV(fimc0).dev,s5p_device_fimc0.dev);
+   
platform_set_sysmmu(SYSMMU_PLATDEV(fimc1).dev,s5p_device_fimc1.dev);
+   
platform_set_sysmmu(SYSMMU_PLATDEV(fimc2).dev,s5p_device_fimc2.dev);
+   
platform_set_sysmmu(SYSMMU_PLATDEV(fimc3).dev,s5p_device_fimc3.dev);
+   
platform_set_sysmmu(SYSMMU_PLATDEV(mfc_l).dev,s5p_device_mfc_l.dev);
+   
platform_set_sysmmu(SYSMMU_PLATDEV(mfc_r).dev,s5p_device_mfc_r.dev);
+
+   s5p_create_iommu_mapping(s5p_device_fimc0.dev, 0x2000, 
SZ_128M, 4);
+   s5p_create_iommu_mapping(s5p_device_fimc1.dev, 0x2000, 
SZ_128M, 4);
+   s5p_create_iommu_mapping(s5p_device_fimc2.dev, 0x2000, 
SZ_128M, 4);
+   s5p_create_iommu_mapping(s5p_device_fimc3.dev, 0x2000, 
SZ_128M, 4);
+   s5p_create_iommu_mapping(s5p_device_mfc_l.dev, 0x2000, 
SZ_128M, 4);
+   s5p_create_iommu_mapping(s5p_device_mfc_r.dev, 0x4000, 
SZ_128M, 4);
+
+   return 0;
+}
+device_initcall(s5p_sysmmu_late_init);
  
   Shouldn't these things be specific to a SoC? With this RFC, it happens
   that you will predefine the IOMMU attachment and mapping information for
   devices in common location (dev-sysmmu.c)? This may lead to problems
   because there are some IP's with SYSMMU support in exynos5, but not
   available in exynos4 (eg: GSC, FIMC-LITE, FIMC-ISP) Previously we used
   to do above declaration in individual machine file, which I think was
   more meaningful.
 
  Right, I simplified the code too much. Keeping these definitions inside 
  machine
  files was a better idea. I completely forgot that Exynos sub-platform now 
  covers
  both Exynos4 and Exynos5 SoC families.
 
 Ideally the information about iommu attachment should come from the
 device tree. We have the dma-ranges properties that define how a dma
 address space is mapped. I am not entirely sure how that works when you
 have multiple IOMMUs and if that requires defining addititional properties,
 but I think we should make it so that we don't have to hardcode specific
 devices in the source.

Right, until that time machine/board files are imho ok.

Best regards
-- 
Marek Szyprowski
Samsung Poland RD Center


___
iommu mailing list
iommu@lists.linux-foundation.org
https://lists.linuxfoundation.org/mailman/listinfo/iommu


Re: [PATCH] ARM: Exynos4: integrate SYSMMU driver with DMA-mapping interface

2012-04-12 Thread Hiroshi Doyu
From: Marek Szyprowski m.szyprow...@samsung.com
Subject: RE: [PATCH] ARM: Exynos4: integrate SYSMMU driver with DMA-mapping 
interface
Date: Thu, 12 Apr 2012 14:13:37 +0200
Message-ID: 028f01cd18a5$b0721770$11564650$%szyprow...@samsung.com





  -Original Message-
  From: Arnd Bergmann [mailto:a...@arndb.de]
  Sent: Thursday, April 12, 2012 1:09 PM
  To: Marek Szyprowski
  Cc: 'Subash Patel'; linux-arm-ker...@lists.infradead.org; 
  linaro-mm-...@lists.linaro.org;
  linux...@kvack.org; linux-a...@vger.kernel.org; 
  iommu@lists.linux-foundation.org; 'Kyungmin
  Park'; 'Joerg Roedel'; 'Russell King - ARM Linux'; 'Chunsang Jeong'; 
  'Krishna Reddy'; 'KyongHo
  Cho'; Andrzej Pietrasiewicz; 'Benjamin Herrenschmidt'; 'Konrad Rzeszutek 
  Wilk'; 'Hiroshi Doyu'
  Subject: Re: [PATCH] ARM: Exynos4: integrate SYSMMU driver with DMA-mapping 
  interface
 
  On Thursday 12 April 2012, Marek Szyprowski wrote:
   +
 +/*
 + * s5p_sysmmu_late_init
 + * Create DMA-mapping IOMMU context for specified devices. This 
 function must
 + * be called later, once SYSMMU driver gets registered and probed.
 + */
 +static int __init s5p_sysmmu_late_init(void)
 +{
 +   
 platform_set_sysmmu(SYSMMU_PLATDEV(fimc0).dev,s5p_device_fimc0.dev);
 +   
 platform_set_sysmmu(SYSMMU_PLATDEV(fimc1).dev,s5p_device_fimc1.dev);
 +   
 platform_set_sysmmu(SYSMMU_PLATDEV(fimc2).dev,s5p_device_fimc2.dev);
 +   
 platform_set_sysmmu(SYSMMU_PLATDEV(fimc3).dev,s5p_device_fimc3.dev);
 +   
 platform_set_sysmmu(SYSMMU_PLATDEV(mfc_l).dev,s5p_device_mfc_l.dev);
 +   
 platform_set_sysmmu(SYSMMU_PLATDEV(mfc_r).dev,s5p_device_mfc_r.dev);
 +
 +   s5p_create_iommu_mapping(s5p_device_fimc0.dev, 0x2000, 
 SZ_128M, 4);
 +   s5p_create_iommu_mapping(s5p_device_fimc1.dev, 0x2000, 
 SZ_128M, 4);
 +   s5p_create_iommu_mapping(s5p_device_fimc2.dev, 0x2000, 
 SZ_128M, 4);
 +   s5p_create_iommu_mapping(s5p_device_fimc3.dev, 0x2000, 
 SZ_128M, 4);
 +   s5p_create_iommu_mapping(s5p_device_mfc_l.dev, 0x2000, 
 SZ_128M, 4);
 +   s5p_create_iommu_mapping(s5p_device_mfc_r.dev, 0x4000, 
 SZ_128M, 4);
 +
 +   return 0;
 +}
 +device_initcall(s5p_sysmmu_late_init);
   
Shouldn't these things be specific to a SoC? With this RFC, it happens
that you will predefine the IOMMU attachment and mapping information for
devices in common location (dev-sysmmu.c)? This may lead to problems
because there are some IP's with SYSMMU support in exynos5, but not
available in exynos4 (eg: GSC, FIMC-LITE, FIMC-ISP) Previously we used
to do above declaration in individual machine file, which I think was
more meaningful.
  
   Right, I simplified the code too much. Keeping these definitions inside 
   machine
   files was a better idea. I completely forgot that Exynos sub-platform now 
   covers
   both Exynos4 and Exynos5 SoC families.
 
  Ideally the information about iommu attachment should come from the
  device tree. We have the dma-ranges properties that define how a dma
  address space is mapped. I am not entirely sure how that works when you
  have multiple IOMMUs and if that requires defining addititional properties,
  but I think we should make it so that we don't have to hardcode specific
  devices in the source.

 Right, until that time machine/board files are imho ok.

In Tegra30, there are quite many IOMMU attachable (platform)devices,
and it's quite nice for us to configure them (un)attached with address
range and IOMMU device ID(ASID) in DT in advance rather than inserting
the code to attach those devices here and there.

Experimentally I added some hook in platform_device_add() as below,
but apparently this won't be accepted.

From cb34373ebbf025e42ec6d8fea2e19e74ba41231e Mon Sep 17 00:00:00 2001
From: Hiroshi DOYU hd...@nvidia.com
Date: Thu, 22 Mar 2012 16:06:27 +0200
Subject: [PATCH 1/1] ARM: dma-mapping: All platform_device DMA API'able

Signed-off-by: Hiroshi DOYU hd...@nvidia.com
---
 arch/arm/mach-tegra/board-cardhu.c |7 ++-
 arch/arm/mm/dma-mapping.c  |5 -
 drivers/base/platform.c|   11 +--
 include/linux/device.h |2 ++
 4 files changed, 21 insertions(+), 4 deletions(-)

diff --git a/arch/arm/mach-tegra/board-cardhu.c 
b/arch/arm/mach-tegra/board-cardhu.c
index 339011e..38f5292 100644
diff --git a/arch/arm/mm/dma-mapping.c b/arch/arm/mm/dma-mapping.c
index ca5544e..5e6dbe0 100644
--- a/arch/arm/mm/dma-mapping.c
+++ b/arch/arm/mm/dma-mapping.c
@@ -758,6 +758,9 @@ size_t arm_iommu_iova_avail(struct device *dev)
size_t size = 0;
unsigned long start = 0;

+   BUG_ON(!dev);
+   BUG_ON(!mapping);
+
spin_lock_irqsave(mapping-lock, flags);
while (1) {
unsigned long end;
@@ -1513,7 +1516,7 @@ arm_iommu_create_mapping(struct bus_type *bus, dma_addr_t 
base, size_t size