linux-kernel.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH net-next v2 0/4] net: ipa: I/O map SMEM and IMEM
@ 2020-05-04 17:58 Alex Elder
  2020-05-04 17:58 ` [PATCH net-next v2 1/4] dt-bindings: net: add IPA iommus property Alex Elder
                   ` (4 more replies)
  0 siblings, 5 replies; 10+ messages in thread
From: Alex Elder @ 2020-05-04 17:58 UTC (permalink / raw)
  To: davem
  Cc: evgreen, subashab, cpratapa, bjorn.andersson, agross, robh+dt,
	netdev, devicetree, linux-arm-msm, linux-kernel

This series adds the definition of two memory regions that must be
mapped for IPA to access through an SMMU.  It requires the SMMU to
be defined in the IPA node in the SoC's Device Tree file.

There is no change since version 1 to the content of the code in
these patches, *however* this time the first patch is an update to
the binding definition rather than an update to a DTS file.

					-Alex

Alex Elder (4):
  dt-bindings: net: add IPA iommus property
  net: ipa: redefine struct ipa_mem_data
  net: ipa: define IMEM memory region for IPA
  net: ipa: define SMEM memory region for IPA

 .../devicetree/bindings/net/qcom,ipa.yaml     |  10 +-
 drivers/net/ipa/ipa.h                         |  10 +
 drivers/net/ipa/ipa_data-sc7180.c             |  14 +-
 drivers/net/ipa/ipa_data-sdm845.c             |  14 +-
 drivers/net/ipa/ipa_data.h                    |  23 +-
 drivers/net/ipa/ipa_main.c                    |   2 +-
 drivers/net/ipa/ipa_mem.c                     | 209 +++++++++++++++++-
 drivers/net/ipa/ipa_mem.h                     |   3 +-
 8 files changed, 263 insertions(+), 22 deletions(-)

-- 
2.20.1


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

* [PATCH net-next v2 1/4] dt-bindings: net: add IPA iommus property
  2020-05-04 17:58 [PATCH net-next v2 0/4] net: ipa: I/O map SMEM and IMEM Alex Elder
@ 2020-05-04 17:58 ` Alex Elder
  2020-05-04 18:30   ` Bjorn Andersson
  2020-05-04 18:52   ` Rob Herring
  2020-05-04 17:58 ` [PATCH net-next v2 2/4] net: ipa: redefine struct ipa_mem_data Alex Elder
                   ` (3 subsequent siblings)
  4 siblings, 2 replies; 10+ messages in thread
From: Alex Elder @ 2020-05-04 17:58 UTC (permalink / raw)
  To: robh+dt, davem
  Cc: evgreen, subashab, cpratapa, bjorn.andersson, agross, devicetree,
	netdev, linux-arm-msm, linux-kernel

The IPA accesses "IMEM" and main system memory through an SMMU, so
its DT node requires an iommus property to define range of stream IDs
it uses.

Signed-off-by: Alex Elder <elder@linaro.org>
---
 Documentation/devicetree/bindings/net/qcom,ipa.yaml | 10 +++++++++-
 1 file changed, 9 insertions(+), 1 deletion(-)

diff --git a/Documentation/devicetree/bindings/net/qcom,ipa.yaml b/Documentation/devicetree/bindings/net/qcom,ipa.yaml
index 140f15245654..7b749fc04c32 100644
--- a/Documentation/devicetree/bindings/net/qcom,ipa.yaml
+++ b/Documentation/devicetree/bindings/net/qcom,ipa.yaml
@@ -20,7 +20,10 @@ description:
   The GSI is an integral part of the IPA, but it is logically isolated
   and has a distinct interrupt and a separately-defined address space.
 
-  See also soc/qcom/qcom,smp2p.txt and interconnect/interconnect.txt.
+  See also soc/qcom/qcom,smp2p.txt and interconnect/interconnect.txt.  See
+  iommu/iommu.txt and iommu/arm,smmu.yaml for more information about SMMU
+  bindings.
+
 
   - |
     --------             ---------
@@ -54,6 +57,9 @@ properties:
       - const: ipa-shared
       - const: gsi
 
+  iommus:
+    maxItems: 1
+
   clocks:
     maxItems: 1
 
@@ -126,6 +132,7 @@ properties:
 
 required:
   - compatible
+  - iommus
   - reg
   - clocks
   - interrupts
@@ -164,6 +171,7 @@ examples:
                 modem-init;
                 modem-remoteproc = <&mss_pil>;
 
+                iommus = <&apps_smmu 0x720 0x3>;
                 reg = <0 0x1e40000 0 0x7000>,
                         <0 0x1e47000 0 0x2000>,
                         <0 0x1e04000 0 0x2c000>;
-- 
2.20.1


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

* [PATCH net-next v2 2/4] net: ipa: redefine struct ipa_mem_data
  2020-05-04 17:58 [PATCH net-next v2 0/4] net: ipa: I/O map SMEM and IMEM Alex Elder
  2020-05-04 17:58 ` [PATCH net-next v2 1/4] dt-bindings: net: add IPA iommus property Alex Elder
@ 2020-05-04 17:58 ` Alex Elder
  2020-05-04 18:31   ` Bjorn Andersson
  2020-05-04 17:58 ` [PATCH net-next v2 3/4] net: ipa: define IMEM memory region for IPA Alex Elder
                   ` (2 subsequent siblings)
  4 siblings, 1 reply; 10+ messages in thread
From: Alex Elder @ 2020-05-04 17:58 UTC (permalink / raw)
  To: davem
  Cc: evgreen, subashab, cpratapa, bjorn.andersson, agross, robh+dt,
	netdev, devicetree, linux-arm-msm, linux-kernel

The ipa_mem_data structure type was never actually used.  Instead,
the IPA memory regions were defined using the ipa_mem structure.

Redefine struct ipa_mem_data so it encapsulates the array of IPA-local
memory region descriptors along with the count of entries in that
array.  Pass just an ipa_mem structure pointer to ipa_mem_init().

Rename the ipa_mem_data[] array ipa_mem_local_data[] to emphasize
that the memory regions it defines are IPA-local memory.

Signed-off-by: Alex Elder <elder@linaro.org>
---
 drivers/net/ipa/ipa_data-sc7180.c | 10 +++++++---
 drivers/net/ipa/ipa_data-sdm845.c | 10 +++++++---
 drivers/net/ipa/ipa_data.h        | 13 +++++--------
 drivers/net/ipa/ipa_main.c        |  2 +-
 drivers/net/ipa/ipa_mem.c         |  9 +++++----
 drivers/net/ipa/ipa_mem.h         |  3 ++-
 6 files changed, 27 insertions(+), 20 deletions(-)

diff --git a/drivers/net/ipa/ipa_data-sc7180.c b/drivers/net/ipa/ipa_data-sc7180.c
index 042b5fc3c135..f97e7e4e61c1 100644
--- a/drivers/net/ipa/ipa_data-sc7180.c
+++ b/drivers/net/ipa/ipa_data-sc7180.c
@@ -193,7 +193,7 @@ static const struct ipa_resource_data ipa_resource_data = {
 };
 
 /* IPA-resident memory region configuration for the SC7180 SoC. */
-static const struct ipa_mem ipa_mem_data[] = {
+static const struct ipa_mem ipa_mem_local_data[] = {
 	[IPA_MEM_UC_SHARED] = {
 		.offset		= 0x0000,
 		.size		= 0x0080,
@@ -296,12 +296,16 @@ static const struct ipa_mem ipa_mem_data[] = {
 	},
 };
 
+static struct ipa_mem_data ipa_mem_data = {
+	.local_count	= ARRAY_SIZE(ipa_mem_local_data),
+	.local		= ipa_mem_local_data,
+};
+
 /* Configuration data for the SC7180 SoC. */
 const struct ipa_data ipa_data_sc7180 = {
 	.version	= IPA_VERSION_4_2,
 	.endpoint_count	= ARRAY_SIZE(ipa_gsi_endpoint_data),
 	.endpoint_data	= ipa_gsi_endpoint_data,
 	.resource_data	= &ipa_resource_data,
-	.mem_count	= ARRAY_SIZE(ipa_mem_data),
-	.mem_data	= ipa_mem_data,
+	.mem_data	= &ipa_mem_data,
 };
diff --git a/drivers/net/ipa/ipa_data-sdm845.c b/drivers/net/ipa/ipa_data-sdm845.c
index 0d9c36e1e806..c55507e94559 100644
--- a/drivers/net/ipa/ipa_data-sdm845.c
+++ b/drivers/net/ipa/ipa_data-sdm845.c
@@ -235,7 +235,7 @@ static const struct ipa_resource_data ipa_resource_data = {
 };
 
 /* IPA-resident memory region configuration for the SDM845 SoC. */
-static const struct ipa_mem ipa_mem_data[] = {
+static const struct ipa_mem ipa_mem_local_data[] = {
 	[IPA_MEM_UC_SHARED] = {
 		.offset		= 0x0000,
 		.size		= 0x0080,
@@ -318,12 +318,16 @@ static const struct ipa_mem ipa_mem_data[] = {
 	},
 };
 
+static struct ipa_mem_data ipa_mem_data = {
+	.local_count	= ARRAY_SIZE(ipa_mem_local_data),
+	.local		= ipa_mem_local_data,
+};
+
 /* Configuration data for the SDM845 SoC. */
 const struct ipa_data ipa_data_sdm845 = {
 	.version	= IPA_VERSION_3_5_1,
 	.endpoint_count	= ARRAY_SIZE(ipa_gsi_endpoint_data),
 	.endpoint_data	= ipa_gsi_endpoint_data,
 	.resource_data	= &ipa_resource_data,
-	.mem_count	= ARRAY_SIZE(ipa_mem_data),
-	.mem_data	= ipa_mem_data,
+	.mem_data	= &ipa_mem_data,
 };
diff --git a/drivers/net/ipa/ipa_data.h b/drivers/net/ipa/ipa_data.h
index 7110de2de817..51d8e5a6f23a 100644
--- a/drivers/net/ipa/ipa_data.h
+++ b/drivers/net/ipa/ipa_data.h
@@ -246,14 +246,12 @@ struct ipa_resource_data {
 
 /**
  * struct ipa_mem - IPA-local memory region description
- * @offset:		offset in IPA memory space to base of the region
- * @size:		size in bytes base of the region
- * @canary_count:	number of 32-bit "canary" values that precede region
+ * @local_count:	number of regions defined in the local[] array
+ * @local:		array of IPA-local memory region descriptors
  */
 struct ipa_mem_data {
-	u32 offset;
-	u16 size;
-	u16 canary_count;
+	u32 local_count;
+	const struct ipa_mem *local;
 };
 
 /**
@@ -270,8 +268,7 @@ struct ipa_data {
 	u32 endpoint_count;	/* # entries in endpoint_data[] */
 	const struct ipa_gsi_endpoint_data *endpoint_data;
 	const struct ipa_resource_data *resource_data;
-	u32 mem_count;		/* # entries in mem_data[] */
-	const struct ipa_mem *mem_data;
+	const struct ipa_mem_data *mem_data;
 };
 
 extern const struct ipa_data ipa_data_sdm845;
diff --git a/drivers/net/ipa/ipa_main.c b/drivers/net/ipa/ipa_main.c
index 28998dcce3d2..9295a9122e8e 100644
--- a/drivers/net/ipa/ipa_main.c
+++ b/drivers/net/ipa/ipa_main.c
@@ -778,7 +778,7 @@ static int ipa_probe(struct platform_device *pdev)
 	if (ret)
 		goto err_kfree_ipa;
 
-	ret = ipa_mem_init(ipa, data->mem_count, data->mem_data);
+	ret = ipa_mem_init(ipa, data->mem_data);
 	if (ret)
 		goto err_reg_exit;
 
diff --git a/drivers/net/ipa/ipa_mem.c b/drivers/net/ipa/ipa_mem.c
index 42d2c29d9f0c..fb4de2a12796 100644
--- a/drivers/net/ipa/ipa_mem.c
+++ b/drivers/net/ipa/ipa_mem.c
@@ -12,6 +12,7 @@
 
 #include "ipa.h"
 #include "ipa_reg.h"
+#include "ipa_data.h"
 #include "ipa_cmd.h"
 #include "ipa_mem.h"
 #include "ipa_data.h"
@@ -266,15 +267,15 @@ int ipa_mem_zero_modem(struct ipa *ipa)
 }
 
 /* Perform memory region-related initialization */
-int ipa_mem_init(struct ipa *ipa, u32 count, const struct ipa_mem *mem)
+int ipa_mem_init(struct ipa *ipa, const struct ipa_mem_data *mem_data)
 {
 	struct device *dev = &ipa->pdev->dev;
 	struct resource *res;
 	int ret;
 
-	if (count > IPA_MEM_COUNT) {
+	if (mem_data->local_count > IPA_MEM_COUNT) {
 		dev_err(dev, "to many memory regions (%u > %u)\n",
-			count, IPA_MEM_COUNT);
+			mem_data->local_count, IPA_MEM_COUNT);
 		return -EINVAL;
 	}
 
@@ -302,7 +303,7 @@ int ipa_mem_init(struct ipa *ipa, u32 count, const struct ipa_mem *mem)
 	ipa->mem_size = resource_size(res);
 
 	/* The ipa->mem[] array is indexed by enum ipa_mem_id values */
-	ipa->mem = mem;
+	ipa->mem = mem_data->local;
 
 	return 0;
 }
diff --git a/drivers/net/ipa/ipa_mem.h b/drivers/net/ipa/ipa_mem.h
index 065cb499ebe5..f99180f84f0d 100644
--- a/drivers/net/ipa/ipa_mem.h
+++ b/drivers/net/ipa/ipa_mem.h
@@ -7,6 +7,7 @@
 #define _IPA_MEM_H_
 
 struct ipa;
+struct ipa_mem_data;
 
 /**
  * DOC: IPA Local Memory
@@ -84,7 +85,7 @@ void ipa_mem_teardown(struct ipa *ipa);
 
 int ipa_mem_zero_modem(struct ipa *ipa);
 
-int ipa_mem_init(struct ipa *ipa, u32 count, const struct ipa_mem *mem);
+int ipa_mem_init(struct ipa *ipa, const struct ipa_mem_data *mem_data);
 void ipa_mem_exit(struct ipa *ipa);
 
 #endif /* _IPA_MEM_H_ */
-- 
2.20.1


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

* [PATCH net-next v2 3/4] net: ipa: define IMEM memory region for IPA
  2020-05-04 17:58 [PATCH net-next v2 0/4] net: ipa: I/O map SMEM and IMEM Alex Elder
  2020-05-04 17:58 ` [PATCH net-next v2 1/4] dt-bindings: net: add IPA iommus property Alex Elder
  2020-05-04 17:58 ` [PATCH net-next v2 2/4] net: ipa: redefine struct ipa_mem_data Alex Elder
@ 2020-05-04 17:58 ` Alex Elder
  2020-05-04 18:28   ` Bjorn Andersson
  2020-05-04 17:58 ` [PATCH net-next v2 4/4] net: ipa: define SMEM " Alex Elder
  2020-05-04 18:27 ` [PATCH net-next v2 0/4] net: ipa: I/O map SMEM and IMEM David Miller
  4 siblings, 1 reply; 10+ messages in thread
From: Alex Elder @ 2020-05-04 17:58 UTC (permalink / raw)
  To: davem
  Cc: evgreen, subashab, cpratapa, bjorn.andersson, agross, robh+dt,
	netdev, devicetree, linux-arm-msm, linux-kernel

Define a region of IMEM memory available for use by IPA in the
platform configuration data.  Initialize it from ipa_mem_init().
The memory must be mapped for access through an SMMU.

Signed-off-by: Alex Elder <elder@linaro.org>
---
 drivers/net/ipa/ipa.h             |  5 ++
 drivers/net/ipa/ipa_data-sc7180.c |  2 +
 drivers/net/ipa/ipa_data-sdm845.c |  2 +
 drivers/net/ipa/ipa_data.h        |  6 ++-
 drivers/net/ipa/ipa_mem.c         | 84 +++++++++++++++++++++++++++++++
 5 files changed, 98 insertions(+), 1 deletion(-)

diff --git a/drivers/net/ipa/ipa.h b/drivers/net/ipa/ipa.h
index 23fb29889e5a..32f6dfafdb05 100644
--- a/drivers/net/ipa/ipa.h
+++ b/drivers/net/ipa/ipa.h
@@ -47,6 +47,8 @@ struct ipa_interrupt;
  * @mem_offset:		Offset from @mem_virt used for access to IPA memory
  * @mem_size:		Total size (bytes) of memory at @mem_virt
  * @mem:		Array of IPA-local memory region descriptors
+ * @imem_iova:		I/O virtual address of IPA region in IMEM
+ * @imem_size;		Size of IMEM region
  * @zero_addr:		DMA address of preallocated zero-filled memory
  * @zero_virt:		Virtual address of preallocated zero-filled memory
  * @zero_size:		Size (bytes) of preallocated zero-filled memory
@@ -88,6 +90,9 @@ struct ipa {
 	u32 mem_size;
 	const struct ipa_mem *mem;
 
+	unsigned long imem_iova;
+	size_t imem_size;
+
 	dma_addr_t zero_addr;
 	void *zero_virt;
 	size_t zero_size;
diff --git a/drivers/net/ipa/ipa_data-sc7180.c b/drivers/net/ipa/ipa_data-sc7180.c
index f97e7e4e61c1..e9007d151c68 100644
--- a/drivers/net/ipa/ipa_data-sc7180.c
+++ b/drivers/net/ipa/ipa_data-sc7180.c
@@ -299,6 +299,8 @@ static const struct ipa_mem ipa_mem_local_data[] = {
 static struct ipa_mem_data ipa_mem_data = {
 	.local_count	= ARRAY_SIZE(ipa_mem_local_data),
 	.local		= ipa_mem_local_data,
+	.imem_addr	= 0x146a8000,
+	.imem_size	= 0x00002000,
 };
 
 /* Configuration data for the SC7180 SoC. */
diff --git a/drivers/net/ipa/ipa_data-sdm845.c b/drivers/net/ipa/ipa_data-sdm845.c
index c55507e94559..c0e207085550 100644
--- a/drivers/net/ipa/ipa_data-sdm845.c
+++ b/drivers/net/ipa/ipa_data-sdm845.c
@@ -321,6 +321,8 @@ static const struct ipa_mem ipa_mem_local_data[] = {
 static struct ipa_mem_data ipa_mem_data = {
 	.local_count	= ARRAY_SIZE(ipa_mem_local_data),
 	.local		= ipa_mem_local_data,
+	.imem_addr	= 0x146bd000,
+	.imem_size	= 0x00002000,
 };
 
 /* Configuration data for the SDM845 SoC. */
diff --git a/drivers/net/ipa/ipa_data.h b/drivers/net/ipa/ipa_data.h
index 51d8e5a6f23a..69957af56ccd 100644
--- a/drivers/net/ipa/ipa_data.h
+++ b/drivers/net/ipa/ipa_data.h
@@ -245,13 +245,17 @@ struct ipa_resource_data {
 };
 
 /**
- * struct ipa_mem - IPA-local memory region description
+ * struct ipa_mem - description of IPA memory regions
  * @local_count:	number of regions defined in the local[] array
  * @local:		array of IPA-local memory region descriptors
+ * @imem_addr:		physical address of IPA region within IMEM
+ * @imem_size:		size in bytes of IPA IMEM region
  */
 struct ipa_mem_data {
 	u32 local_count;
 	const struct ipa_mem *local;
+	u32 imem_addr;
+	u32 imem_size;
 };
 
 /**
diff --git a/drivers/net/ipa/ipa_mem.c b/drivers/net/ipa/ipa_mem.c
index fb4de2a12796..3c0916597fe1 100644
--- a/drivers/net/ipa/ipa_mem.c
+++ b/drivers/net/ipa/ipa_mem.c
@@ -8,6 +8,7 @@
 #include <linux/bitfield.h>
 #include <linux/bug.h>
 #include <linux/dma-mapping.h>
+#include <linux/iommu.h>
 #include <linux/io.h>
 
 #include "ipa.h"
@@ -266,6 +267,79 @@ int ipa_mem_zero_modem(struct ipa *ipa)
 	return 0;
 }
 
+/**
+ * ipa_imem_init() - Initialize IMEM memory used by the IPA
+ * @ipa:	IPA pointer
+ * @addr:	Physical address of the IPA region in IMEM
+ * @size:	Size (bytes) of the IPA region in IMEM
+ *
+ * IMEM is a block of shared memory separate from system DRAM, and
+ * a portion of this memory is available for the IPA to use.  The
+ * modem accesses this memory directly, but the IPA accesses it
+ * via the IOMMU, using the AP's credentials.
+ *
+ * If this region exists (size > 0) we map it for read/write access
+ * through the IOMMU using the IPA device.
+ *
+ * Note: @addr and @size are not guaranteed to be page-aligned.
+ */
+static int ipa_imem_init(struct ipa *ipa, unsigned long addr, size_t size)
+{
+	struct device *dev = &ipa->pdev->dev;
+	struct iommu_domain *domain;
+	unsigned long iova;
+	phys_addr_t phys;
+	int ret;
+
+	if (!size)
+		return 0;	/* IMEM memory not used */
+
+	domain = iommu_get_domain_for_dev(dev);
+	if (!domain) {
+		dev_err(dev, "no IOMMU domain found for IMEM\n");
+		return -EINVAL;
+	}
+
+	/* Align the address down and the size up to page boundaries */
+	phys = addr & PAGE_MASK;
+	size = PAGE_ALIGN(size + addr - phys);
+	iova = phys;	/* We just want a direct mapping */
+
+	ret = iommu_map(domain, iova, phys, size, IOMMU_READ | IOMMU_WRITE);
+	if (ret)
+		return ret;
+
+	ipa->imem_iova = iova;
+	ipa->imem_size = size;
+
+	return 0;
+}
+
+static void ipa_imem_exit(struct ipa *ipa)
+{
+	struct iommu_domain *domain;
+	struct device *dev;
+
+	if (!ipa->imem_size)
+		return;
+
+	dev = &ipa->pdev->dev;
+	domain = iommu_get_domain_for_dev(dev);
+	if (domain) {
+		size_t size;
+
+		size = iommu_unmap(domain, ipa->imem_iova, ipa->imem_size);
+		if (size != ipa->imem_size)
+			dev_warn(dev, "unmapped %zu IMEM bytes, expected %lu\n",
+				 size, ipa->imem_size);
+	} else {
+		dev_err(dev, "couldn't get IPA IOMMU domain for IMEM\n");
+	}
+
+	ipa->imem_size = 0;
+	ipa->imem_iova = 0;
+}
+
 /* Perform memory region-related initialization */
 int ipa_mem_init(struct ipa *ipa, const struct ipa_mem_data *mem_data)
 {
@@ -305,11 +379,21 @@ int ipa_mem_init(struct ipa *ipa, const struct ipa_mem_data *mem_data)
 	/* The ipa->mem[] array is indexed by enum ipa_mem_id values */
 	ipa->mem = mem_data->local;
 
+	ret = ipa_imem_init(ipa, mem_data->imem_addr, mem_data->imem_size);
+	if (ret)
+		goto err_unmap;
+
 	return 0;
+
+err_unmap:
+	memunmap(ipa->mem_virt);
+
+	return ret;
 }
 
 /* Inverse of ipa_mem_init() */
 void ipa_mem_exit(struct ipa *ipa)
 {
+	ipa_imem_exit(ipa);
 	memunmap(ipa->mem_virt);
 }
-- 
2.20.1


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

* [PATCH net-next v2 4/4] net: ipa: define SMEM memory region for IPA
  2020-05-04 17:58 [PATCH net-next v2 0/4] net: ipa: I/O map SMEM and IMEM Alex Elder
                   ` (2 preceding siblings ...)
  2020-05-04 17:58 ` [PATCH net-next v2 3/4] net: ipa: define IMEM memory region for IPA Alex Elder
@ 2020-05-04 17:58 ` Alex Elder
  2020-05-04 18:27 ` [PATCH net-next v2 0/4] net: ipa: I/O map SMEM and IMEM David Miller
  4 siblings, 0 replies; 10+ messages in thread
From: Alex Elder @ 2020-05-04 17:58 UTC (permalink / raw)
  To: davem
  Cc: evgreen, subashab, cpratapa, bjorn.andersson, agross, robh+dt,
	netdev, devicetree, linux-arm-msm, linux-kernel

Arrange to use an item from SMEM memory for IPA.  SMEM item number
497 is designated to be used by the IPA.  Specify the item ID and
size of the region in platform configuration data.  Allocate and get
a pointer to this region from ipa_mem_init().  The memory must be
mapped for access through an SMMU.

Signed-off-by: Alex Elder <elder@linaro.org>
---
 drivers/net/ipa/ipa.h             |   5 ++
 drivers/net/ipa/ipa_data-sc7180.c |   2 +
 drivers/net/ipa/ipa_data-sdm845.c |   2 +
 drivers/net/ipa/ipa_data.h        |   4 ++
 drivers/net/ipa/ipa_mem.c         | 116 ++++++++++++++++++++++++++++++
 5 files changed, 129 insertions(+)

diff --git a/drivers/net/ipa/ipa.h b/drivers/net/ipa/ipa.h
index 32f6dfafdb05..b10a85392952 100644
--- a/drivers/net/ipa/ipa.h
+++ b/drivers/net/ipa/ipa.h
@@ -49,6 +49,8 @@ struct ipa_interrupt;
  * @mem:		Array of IPA-local memory region descriptors
  * @imem_iova:		I/O virtual address of IPA region in IMEM
  * @imem_size;		Size of IMEM region
+ * @smem_iova:		I/O virtual address of IPA region in SMEM
+ * @smem_size;		Size of SMEM region
  * @zero_addr:		DMA address of preallocated zero-filled memory
  * @zero_virt:		Virtual address of preallocated zero-filled memory
  * @zero_size:		Size (bytes) of preallocated zero-filled memory
@@ -93,6 +95,9 @@ struct ipa {
 	unsigned long imem_iova;
 	size_t imem_size;
 
+	unsigned long smem_iova;
+	size_t smem_size;
+
 	dma_addr_t zero_addr;
 	void *zero_virt;
 	size_t zero_size;
diff --git a/drivers/net/ipa/ipa_data-sc7180.c b/drivers/net/ipa/ipa_data-sc7180.c
index e9007d151c68..43faa35ae726 100644
--- a/drivers/net/ipa/ipa_data-sc7180.c
+++ b/drivers/net/ipa/ipa_data-sc7180.c
@@ -301,6 +301,8 @@ static struct ipa_mem_data ipa_mem_data = {
 	.local		= ipa_mem_local_data,
 	.imem_addr	= 0x146a8000,
 	.imem_size	= 0x00002000,
+	.smem_id	= 497,
+	.smem_size	= 0x00002000,
 };
 
 /* Configuration data for the SC7180 SoC. */
diff --git a/drivers/net/ipa/ipa_data-sdm845.c b/drivers/net/ipa/ipa_data-sdm845.c
index c0e207085550..f7ba85717edf 100644
--- a/drivers/net/ipa/ipa_data-sdm845.c
+++ b/drivers/net/ipa/ipa_data-sdm845.c
@@ -323,6 +323,8 @@ static struct ipa_mem_data ipa_mem_data = {
 	.local		= ipa_mem_local_data,
 	.imem_addr	= 0x146bd000,
 	.imem_size	= 0x00002000,
+	.smem_id	= 497,
+	.smem_size	= 0x00002000,
 };
 
 /* Configuration data for the SDM845 SoC. */
diff --git a/drivers/net/ipa/ipa_data.h b/drivers/net/ipa/ipa_data.h
index 69957af56ccd..16dfd74717b1 100644
--- a/drivers/net/ipa/ipa_data.h
+++ b/drivers/net/ipa/ipa_data.h
@@ -250,12 +250,16 @@ struct ipa_resource_data {
  * @local:		array of IPA-local memory region descriptors
  * @imem_addr:		physical address of IPA region within IMEM
  * @imem_size:		size in bytes of IPA IMEM region
+ * @smem_id:		item identifier for IPA region within SMEM memory
+ * @imem_size:		size in bytes of the IPA SMEM region
  */
 struct ipa_mem_data {
 	u32 local_count;
 	const struct ipa_mem *local;
 	u32 imem_addr;
 	u32 imem_size;
+	u32 smem_id;
+	u32 smem_size;
 };
 
 /**
diff --git a/drivers/net/ipa/ipa_mem.c b/drivers/net/ipa/ipa_mem.c
index 3c0916597fe1..aa8f6b0f3d50 100644
--- a/drivers/net/ipa/ipa_mem.c
+++ b/drivers/net/ipa/ipa_mem.c
@@ -10,6 +10,7 @@
 #include <linux/dma-mapping.h>
 #include <linux/iommu.h>
 #include <linux/io.h>
+#include <linux/soc/qcom/smem.h>
 
 #include "ipa.h"
 #include "ipa_reg.h"
@@ -23,6 +24,9 @@
 /* "Canary" value placed between memory regions to detect overflow */
 #define IPA_MEM_CANARY_VAL		cpu_to_le32(0xdeadbeef)
 
+/* SMEM host id representing the modem. */
+#define QCOM_SMEM_HOST_MODEM	1
+
 /* Add an immediate command to a transaction that zeroes a memory region */
 static void
 ipa_mem_zero_region_add(struct gsi_trans *trans, const struct ipa_mem *mem)
@@ -340,6 +344,111 @@ static void ipa_imem_exit(struct ipa *ipa)
 	ipa->imem_iova = 0;
 }
 
+/**
+ * ipa_smem_init() - Initialize SMEM memory used by the IPA
+ * @ipa:	IPA pointer
+ * @item:	Item ID of SMEM memory
+ * @size:	Size (bytes) of SMEM memory region
+ *
+ * SMEM is a managed block of shared DRAM, from which numbered "items"
+ * can be allocated.  One item is designated for use by the IPA.
+ *
+ * The modem accesses SMEM memory directly, but the IPA accesses it
+ * via the IOMMU, using the AP's credentials.
+ *
+ * If size provided is non-zero, we allocate it and map it for
+ * access through the IOMMU.
+ *
+ * Note: @size and the item address are is not guaranteed to be page-aligned.
+ */
+static int ipa_smem_init(struct ipa *ipa, u32 item, size_t size)
+{
+	struct device *dev = &ipa->pdev->dev;
+	struct iommu_domain *domain;
+	unsigned long iova;
+	phys_addr_t phys;
+	phys_addr_t addr;
+	size_t actual;
+	void *virt;
+	int ret;
+
+	if (!size)
+		return 0;	/* SMEM memory not used */
+
+	/* SMEM is memory shared between the AP and another system entity
+	 * (in this case, the modem).  An allocation from SMEM is persistent
+	 * until the AP reboots; there is no way to free an allocated SMEM
+	 * region.  Allocation only reserves the space; to use it you need
+	 * to "get" a pointer it (this implies no reference counting).
+	 * The item might have already been allocated, in which case we
+	 * use it unless the size isn't what we expect.
+	 */
+	ret = qcom_smem_alloc(QCOM_SMEM_HOST_MODEM, item, size);
+	if (ret && ret != -EEXIST) {
+		dev_err(dev, "error %d allocating size %zu SMEM item %u\n",
+			ret, size, item);
+		return ret;
+	}
+
+	/* Now get the address of the SMEM memory region */
+	virt = qcom_smem_get(QCOM_SMEM_HOST_MODEM, item, &actual);
+	if (IS_ERR(virt)) {
+		ret = PTR_ERR(virt);
+		dev_err(dev, "error %d getting SMEM item %u\n", ret, item);
+		return ret;
+	}
+
+	/* In case the region was already allocated, verify the size */
+	if (ret && actual != size) {
+		dev_err(dev, "SMEM item %u has size %zu, expected %zu\n",
+			item, actual, size);
+		return -EINVAL;
+	}
+
+	domain = iommu_get_domain_for_dev(dev);
+	if (!domain) {
+		dev_err(dev, "no IOMMU domain found for SMEM\n");
+		return -EINVAL;
+	}
+
+	/* Align the address down and the size up to a page boundary */
+	addr = qcom_smem_virt_to_phys(virt) & PAGE_MASK;
+	phys = addr & PAGE_MASK;
+	size = PAGE_ALIGN(size + addr - phys);
+	iova = phys;	/* We just want a direct mapping */
+
+	ret = iommu_map(domain, iova, phys, size, IOMMU_READ | IOMMU_WRITE);
+	if (ret)
+		return ret;
+
+	ipa->smem_iova = iova;
+	ipa->smem_size = size;
+
+	return 0;
+}
+
+static void ipa_smem_exit(struct ipa *ipa)
+{
+	struct device *dev = &ipa->pdev->dev;
+	struct iommu_domain *domain;
+
+	domain = iommu_get_domain_for_dev(dev);
+	if (domain) {
+		size_t size;
+
+		size = iommu_unmap(domain, ipa->smem_iova, ipa->smem_size);
+		if (size != ipa->smem_size)
+			dev_warn(dev, "unmapped %zu SMEM bytes, expected %lu\n",
+				 size, ipa->smem_size);
+
+	} else {
+		dev_err(dev, "couldn't get IPA IOMMU domain for SMEM\n");
+	}
+
+	ipa->smem_size = 0;
+	ipa->smem_iova = 0;
+}
+
 /* Perform memory region-related initialization */
 int ipa_mem_init(struct ipa *ipa, const struct ipa_mem_data *mem_data)
 {
@@ -383,8 +492,14 @@ int ipa_mem_init(struct ipa *ipa, const struct ipa_mem_data *mem_data)
 	if (ret)
 		goto err_unmap;
 
+	ret = ipa_smem_init(ipa, mem_data->smem_id, mem_data->smem_size);
+	if (ret)
+		goto err_imem_exit;
+
 	return 0;
 
+err_imem_exit:
+	ipa_imem_exit(ipa);
 err_unmap:
 	memunmap(ipa->mem_virt);
 
@@ -394,6 +509,7 @@ int ipa_mem_init(struct ipa *ipa, const struct ipa_mem_data *mem_data)
 /* Inverse of ipa_mem_init() */
 void ipa_mem_exit(struct ipa *ipa)
 {
+	ipa_smem_exit(ipa);
 	ipa_imem_exit(ipa);
 	memunmap(ipa->mem_virt);
 }
-- 
2.20.1


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

* Re: [PATCH net-next v2 0/4] net: ipa: I/O map SMEM and IMEM
  2020-05-04 17:58 [PATCH net-next v2 0/4] net: ipa: I/O map SMEM and IMEM Alex Elder
                   ` (3 preceding siblings ...)
  2020-05-04 17:58 ` [PATCH net-next v2 4/4] net: ipa: define SMEM " Alex Elder
@ 2020-05-04 18:27 ` David Miller
  4 siblings, 0 replies; 10+ messages in thread
From: David Miller @ 2020-05-04 18:27 UTC (permalink / raw)
  To: elder
  Cc: evgreen, subashab, cpratapa, bjorn.andersson, agross, robh+dt,
	netdev, devicetree, linux-arm-msm, linux-kernel

From: Alex Elder <elder@linaro.org>
Date: Mon,  4 May 2020 12:58:55 -0500

> This series adds the definition of two memory regions that must be
> mapped for IPA to access through an SMMU.  It requires the SMMU to
> be defined in the IPA node in the SoC's Device Tree file.
> 
> There is no change since version 1 to the content of the code in
> these patches, *however* this time the first patch is an update to
> the binding definition rather than an update to a DTS file.

Series applied, thanks Alex.

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

* Re: [PATCH net-next v2 3/4] net: ipa: define IMEM memory region for IPA
  2020-05-04 17:58 ` [PATCH net-next v2 3/4] net: ipa: define IMEM memory region for IPA Alex Elder
@ 2020-05-04 18:28   ` Bjorn Andersson
  0 siblings, 0 replies; 10+ messages in thread
From: Bjorn Andersson @ 2020-05-04 18:28 UTC (permalink / raw)
  To: Alex Elder
  Cc: davem, evgreen, subashab, cpratapa, agross, robh+dt, netdev,
	devicetree, linux-arm-msm, linux-kernel

On Mon 04 May 10:58 PDT 2020, Alex Elder wrote:

> Define a region of IMEM memory available for use by IPA in the
> platform configuration data.  Initialize it from ipa_mem_init().
> The memory must be mapped for access through an SMMU.
> 

Reviewed-by: Bjorn Andersson <bjorn.andersson@linaro.org>

Regards,
Bjorn

> Signed-off-by: Alex Elder <elder@linaro.org>
> ---
>  drivers/net/ipa/ipa.h             |  5 ++
>  drivers/net/ipa/ipa_data-sc7180.c |  2 +
>  drivers/net/ipa/ipa_data-sdm845.c |  2 +
>  drivers/net/ipa/ipa_data.h        |  6 ++-
>  drivers/net/ipa/ipa_mem.c         | 84 +++++++++++++++++++++++++++++++
>  5 files changed, 98 insertions(+), 1 deletion(-)
> 
> diff --git a/drivers/net/ipa/ipa.h b/drivers/net/ipa/ipa.h
> index 23fb29889e5a..32f6dfafdb05 100644
> --- a/drivers/net/ipa/ipa.h
> +++ b/drivers/net/ipa/ipa.h
> @@ -47,6 +47,8 @@ struct ipa_interrupt;
>   * @mem_offset:		Offset from @mem_virt used for access to IPA memory
>   * @mem_size:		Total size (bytes) of memory at @mem_virt
>   * @mem:		Array of IPA-local memory region descriptors
> + * @imem_iova:		I/O virtual address of IPA region in IMEM
> + * @imem_size;		Size of IMEM region
>   * @zero_addr:		DMA address of preallocated zero-filled memory
>   * @zero_virt:		Virtual address of preallocated zero-filled memory
>   * @zero_size:		Size (bytes) of preallocated zero-filled memory
> @@ -88,6 +90,9 @@ struct ipa {
>  	u32 mem_size;
>  	const struct ipa_mem *mem;
>  
> +	unsigned long imem_iova;
> +	size_t imem_size;
> +
>  	dma_addr_t zero_addr;
>  	void *zero_virt;
>  	size_t zero_size;
> diff --git a/drivers/net/ipa/ipa_data-sc7180.c b/drivers/net/ipa/ipa_data-sc7180.c
> index f97e7e4e61c1..e9007d151c68 100644
> --- a/drivers/net/ipa/ipa_data-sc7180.c
> +++ b/drivers/net/ipa/ipa_data-sc7180.c
> @@ -299,6 +299,8 @@ static const struct ipa_mem ipa_mem_local_data[] = {
>  static struct ipa_mem_data ipa_mem_data = {
>  	.local_count	= ARRAY_SIZE(ipa_mem_local_data),
>  	.local		= ipa_mem_local_data,
> +	.imem_addr	= 0x146a8000,
> +	.imem_size	= 0x00002000,
>  };
>  
>  /* Configuration data for the SC7180 SoC. */
> diff --git a/drivers/net/ipa/ipa_data-sdm845.c b/drivers/net/ipa/ipa_data-sdm845.c
> index c55507e94559..c0e207085550 100644
> --- a/drivers/net/ipa/ipa_data-sdm845.c
> +++ b/drivers/net/ipa/ipa_data-sdm845.c
> @@ -321,6 +321,8 @@ static const struct ipa_mem ipa_mem_local_data[] = {
>  static struct ipa_mem_data ipa_mem_data = {
>  	.local_count	= ARRAY_SIZE(ipa_mem_local_data),
>  	.local		= ipa_mem_local_data,
> +	.imem_addr	= 0x146bd000,
> +	.imem_size	= 0x00002000,
>  };
>  
>  /* Configuration data for the SDM845 SoC. */
> diff --git a/drivers/net/ipa/ipa_data.h b/drivers/net/ipa/ipa_data.h
> index 51d8e5a6f23a..69957af56ccd 100644
> --- a/drivers/net/ipa/ipa_data.h
> +++ b/drivers/net/ipa/ipa_data.h
> @@ -245,13 +245,17 @@ struct ipa_resource_data {
>  };
>  
>  /**
> - * struct ipa_mem - IPA-local memory region description
> + * struct ipa_mem - description of IPA memory regions
>   * @local_count:	number of regions defined in the local[] array
>   * @local:		array of IPA-local memory region descriptors
> + * @imem_addr:		physical address of IPA region within IMEM
> + * @imem_size:		size in bytes of IPA IMEM region
>   */
>  struct ipa_mem_data {
>  	u32 local_count;
>  	const struct ipa_mem *local;
> +	u32 imem_addr;
> +	u32 imem_size;
>  };
>  
>  /**
> diff --git a/drivers/net/ipa/ipa_mem.c b/drivers/net/ipa/ipa_mem.c
> index fb4de2a12796..3c0916597fe1 100644
> --- a/drivers/net/ipa/ipa_mem.c
> +++ b/drivers/net/ipa/ipa_mem.c
> @@ -8,6 +8,7 @@
>  #include <linux/bitfield.h>
>  #include <linux/bug.h>
>  #include <linux/dma-mapping.h>
> +#include <linux/iommu.h>
>  #include <linux/io.h>
>  
>  #include "ipa.h"
> @@ -266,6 +267,79 @@ int ipa_mem_zero_modem(struct ipa *ipa)
>  	return 0;
>  }
>  
> +/**
> + * ipa_imem_init() - Initialize IMEM memory used by the IPA
> + * @ipa:	IPA pointer
> + * @addr:	Physical address of the IPA region in IMEM
> + * @size:	Size (bytes) of the IPA region in IMEM
> + *
> + * IMEM is a block of shared memory separate from system DRAM, and
> + * a portion of this memory is available for the IPA to use.  The
> + * modem accesses this memory directly, but the IPA accesses it
> + * via the IOMMU, using the AP's credentials.
> + *
> + * If this region exists (size > 0) we map it for read/write access
> + * through the IOMMU using the IPA device.
> + *
> + * Note: @addr and @size are not guaranteed to be page-aligned.
> + */
> +static int ipa_imem_init(struct ipa *ipa, unsigned long addr, size_t size)
> +{
> +	struct device *dev = &ipa->pdev->dev;
> +	struct iommu_domain *domain;
> +	unsigned long iova;
> +	phys_addr_t phys;
> +	int ret;
> +
> +	if (!size)
> +		return 0;	/* IMEM memory not used */
> +
> +	domain = iommu_get_domain_for_dev(dev);
> +	if (!domain) {
> +		dev_err(dev, "no IOMMU domain found for IMEM\n");
> +		return -EINVAL;
> +	}
> +
> +	/* Align the address down and the size up to page boundaries */
> +	phys = addr & PAGE_MASK;
> +	size = PAGE_ALIGN(size + addr - phys);
> +	iova = phys;	/* We just want a direct mapping */
> +
> +	ret = iommu_map(domain, iova, phys, size, IOMMU_READ | IOMMU_WRITE);
> +	if (ret)
> +		return ret;
> +
> +	ipa->imem_iova = iova;
> +	ipa->imem_size = size;
> +
> +	return 0;
> +}
> +
> +static void ipa_imem_exit(struct ipa *ipa)
> +{
> +	struct iommu_domain *domain;
> +	struct device *dev;
> +
> +	if (!ipa->imem_size)
> +		return;
> +
> +	dev = &ipa->pdev->dev;
> +	domain = iommu_get_domain_for_dev(dev);
> +	if (domain) {
> +		size_t size;
> +
> +		size = iommu_unmap(domain, ipa->imem_iova, ipa->imem_size);
> +		if (size != ipa->imem_size)
> +			dev_warn(dev, "unmapped %zu IMEM bytes, expected %lu\n",
> +				 size, ipa->imem_size);
> +	} else {
> +		dev_err(dev, "couldn't get IPA IOMMU domain for IMEM\n");
> +	}
> +
> +	ipa->imem_size = 0;
> +	ipa->imem_iova = 0;
> +}
> +
>  /* Perform memory region-related initialization */
>  int ipa_mem_init(struct ipa *ipa, const struct ipa_mem_data *mem_data)
>  {
> @@ -305,11 +379,21 @@ int ipa_mem_init(struct ipa *ipa, const struct ipa_mem_data *mem_data)
>  	/* The ipa->mem[] array is indexed by enum ipa_mem_id values */
>  	ipa->mem = mem_data->local;
>  
> +	ret = ipa_imem_init(ipa, mem_data->imem_addr, mem_data->imem_size);
> +	if (ret)
> +		goto err_unmap;
> +
>  	return 0;
> +
> +err_unmap:
> +	memunmap(ipa->mem_virt);
> +
> +	return ret;
>  }
>  
>  /* Inverse of ipa_mem_init() */
>  void ipa_mem_exit(struct ipa *ipa)
>  {
> +	ipa_imem_exit(ipa);
>  	memunmap(ipa->mem_virt);
>  }
> -- 
> 2.20.1
> 

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

* Re: [PATCH net-next v2 1/4] dt-bindings: net: add IPA iommus property
  2020-05-04 17:58 ` [PATCH net-next v2 1/4] dt-bindings: net: add IPA iommus property Alex Elder
@ 2020-05-04 18:30   ` Bjorn Andersson
  2020-05-04 18:52   ` Rob Herring
  1 sibling, 0 replies; 10+ messages in thread
From: Bjorn Andersson @ 2020-05-04 18:30 UTC (permalink / raw)
  To: Alex Elder
  Cc: robh+dt, davem, evgreen, subashab, cpratapa, agross, devicetree,
	netdev, linux-arm-msm, linux-kernel

On Mon 04 May 10:58 PDT 2020, Alex Elder wrote:

> The IPA accesses "IMEM" and main system memory through an SMMU, so
> its DT node requires an iommus property to define range of stream IDs
> it uses.
> 
> Signed-off-by: Alex Elder <elder@linaro.org>
> ---
>  Documentation/devicetree/bindings/net/qcom,ipa.yaml | 10 +++++++++-
>  1 file changed, 9 insertions(+), 1 deletion(-)
> 
> diff --git a/Documentation/devicetree/bindings/net/qcom,ipa.yaml b/Documentation/devicetree/bindings/net/qcom,ipa.yaml
> index 140f15245654..7b749fc04c32 100644
> --- a/Documentation/devicetree/bindings/net/qcom,ipa.yaml
> +++ b/Documentation/devicetree/bindings/net/qcom,ipa.yaml
> @@ -20,7 +20,10 @@ description:
>    The GSI is an integral part of the IPA, but it is logically isolated
>    and has a distinct interrupt and a separately-defined address space.
>  
> -  See also soc/qcom/qcom,smp2p.txt and interconnect/interconnect.txt.
> +  See also soc/qcom/qcom,smp2p.txt and interconnect/interconnect.txt.  See
> +  iommu/iommu.txt and iommu/arm,smmu.yaml for more information about SMMU
> +  bindings.
> +
>  
>    - |
>      --------             ---------
> @@ -54,6 +57,9 @@ properties:
>        - const: ipa-shared
>        - const: gsi
>  
> +  iommus:
> +    maxItems: 1
> +
>    clocks:
>      maxItems: 1
>  
> @@ -126,6 +132,7 @@ properties:
>  
>  required:
>    - compatible
> +  - iommus

This technically "breaks" backwards compatibility, but the binding is
rather new and in limited use, so I think we should do this.


Reviewed-by: Bjorn Andersson <bjorn.andersson@linaro.org>

Regards,
Bjorn

>    - reg
>    - clocks
>    - interrupts
> @@ -164,6 +171,7 @@ examples:
>                  modem-init;
>                  modem-remoteproc = <&mss_pil>;
>  
> +                iommus = <&apps_smmu 0x720 0x3>;
>                  reg = <0 0x1e40000 0 0x7000>,
>                          <0 0x1e47000 0 0x2000>,
>                          <0 0x1e04000 0 0x2c000>;
> -- 
> 2.20.1
> 

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

* Re: [PATCH net-next v2 2/4] net: ipa: redefine struct ipa_mem_data
  2020-05-04 17:58 ` [PATCH net-next v2 2/4] net: ipa: redefine struct ipa_mem_data Alex Elder
@ 2020-05-04 18:31   ` Bjorn Andersson
  0 siblings, 0 replies; 10+ messages in thread
From: Bjorn Andersson @ 2020-05-04 18:31 UTC (permalink / raw)
  To: Alex Elder
  Cc: davem, evgreen, subashab, cpratapa, agross, robh+dt, netdev,
	devicetree, linux-arm-msm, linux-kernel

On Mon 04 May 10:58 PDT 2020, Alex Elder wrote:

> The ipa_mem_data structure type was never actually used.  Instead,
> the IPA memory regions were defined using the ipa_mem structure.
> 
> Redefine struct ipa_mem_data so it encapsulates the array of IPA-local
> memory region descriptors along with the count of entries in that
> array.  Pass just an ipa_mem structure pointer to ipa_mem_init().
> 
> Rename the ipa_mem_data[] array ipa_mem_local_data[] to emphasize
> that the memory regions it defines are IPA-local memory.
> 
> Signed-off-by: Alex Elder <elder@linaro.org>

Reviewed-by: Bjorn Andersson <bjorn.andersson@linaro.org>

Regards,
Bjorn

> ---
>  drivers/net/ipa/ipa_data-sc7180.c | 10 +++++++---
>  drivers/net/ipa/ipa_data-sdm845.c | 10 +++++++---
>  drivers/net/ipa/ipa_data.h        | 13 +++++--------
>  drivers/net/ipa/ipa_main.c        |  2 +-
>  drivers/net/ipa/ipa_mem.c         |  9 +++++----
>  drivers/net/ipa/ipa_mem.h         |  3 ++-
>  6 files changed, 27 insertions(+), 20 deletions(-)
> 
> diff --git a/drivers/net/ipa/ipa_data-sc7180.c b/drivers/net/ipa/ipa_data-sc7180.c
> index 042b5fc3c135..f97e7e4e61c1 100644
> --- a/drivers/net/ipa/ipa_data-sc7180.c
> +++ b/drivers/net/ipa/ipa_data-sc7180.c
> @@ -193,7 +193,7 @@ static const struct ipa_resource_data ipa_resource_data = {
>  };
>  
>  /* IPA-resident memory region configuration for the SC7180 SoC. */
> -static const struct ipa_mem ipa_mem_data[] = {
> +static const struct ipa_mem ipa_mem_local_data[] = {
>  	[IPA_MEM_UC_SHARED] = {
>  		.offset		= 0x0000,
>  		.size		= 0x0080,
> @@ -296,12 +296,16 @@ static const struct ipa_mem ipa_mem_data[] = {
>  	},
>  };
>  
> +static struct ipa_mem_data ipa_mem_data = {
> +	.local_count	= ARRAY_SIZE(ipa_mem_local_data),
> +	.local		= ipa_mem_local_data,
> +};
> +
>  /* Configuration data for the SC7180 SoC. */
>  const struct ipa_data ipa_data_sc7180 = {
>  	.version	= IPA_VERSION_4_2,
>  	.endpoint_count	= ARRAY_SIZE(ipa_gsi_endpoint_data),
>  	.endpoint_data	= ipa_gsi_endpoint_data,
>  	.resource_data	= &ipa_resource_data,
> -	.mem_count	= ARRAY_SIZE(ipa_mem_data),
> -	.mem_data	= ipa_mem_data,
> +	.mem_data	= &ipa_mem_data,
>  };
> diff --git a/drivers/net/ipa/ipa_data-sdm845.c b/drivers/net/ipa/ipa_data-sdm845.c
> index 0d9c36e1e806..c55507e94559 100644
> --- a/drivers/net/ipa/ipa_data-sdm845.c
> +++ b/drivers/net/ipa/ipa_data-sdm845.c
> @@ -235,7 +235,7 @@ static const struct ipa_resource_data ipa_resource_data = {
>  };
>  
>  /* IPA-resident memory region configuration for the SDM845 SoC. */
> -static const struct ipa_mem ipa_mem_data[] = {
> +static const struct ipa_mem ipa_mem_local_data[] = {
>  	[IPA_MEM_UC_SHARED] = {
>  		.offset		= 0x0000,
>  		.size		= 0x0080,
> @@ -318,12 +318,16 @@ static const struct ipa_mem ipa_mem_data[] = {
>  	},
>  };
>  
> +static struct ipa_mem_data ipa_mem_data = {
> +	.local_count	= ARRAY_SIZE(ipa_mem_local_data),
> +	.local		= ipa_mem_local_data,
> +};
> +
>  /* Configuration data for the SDM845 SoC. */
>  const struct ipa_data ipa_data_sdm845 = {
>  	.version	= IPA_VERSION_3_5_1,
>  	.endpoint_count	= ARRAY_SIZE(ipa_gsi_endpoint_data),
>  	.endpoint_data	= ipa_gsi_endpoint_data,
>  	.resource_data	= &ipa_resource_data,
> -	.mem_count	= ARRAY_SIZE(ipa_mem_data),
> -	.mem_data	= ipa_mem_data,
> +	.mem_data	= &ipa_mem_data,
>  };
> diff --git a/drivers/net/ipa/ipa_data.h b/drivers/net/ipa/ipa_data.h
> index 7110de2de817..51d8e5a6f23a 100644
> --- a/drivers/net/ipa/ipa_data.h
> +++ b/drivers/net/ipa/ipa_data.h
> @@ -246,14 +246,12 @@ struct ipa_resource_data {
>  
>  /**
>   * struct ipa_mem - IPA-local memory region description
> - * @offset:		offset in IPA memory space to base of the region
> - * @size:		size in bytes base of the region
> - * @canary_count:	number of 32-bit "canary" values that precede region
> + * @local_count:	number of regions defined in the local[] array
> + * @local:		array of IPA-local memory region descriptors
>   */
>  struct ipa_mem_data {
> -	u32 offset;
> -	u16 size;
> -	u16 canary_count;
> +	u32 local_count;
> +	const struct ipa_mem *local;
>  };
>  
>  /**
> @@ -270,8 +268,7 @@ struct ipa_data {
>  	u32 endpoint_count;	/* # entries in endpoint_data[] */
>  	const struct ipa_gsi_endpoint_data *endpoint_data;
>  	const struct ipa_resource_data *resource_data;
> -	u32 mem_count;		/* # entries in mem_data[] */
> -	const struct ipa_mem *mem_data;
> +	const struct ipa_mem_data *mem_data;
>  };
>  
>  extern const struct ipa_data ipa_data_sdm845;
> diff --git a/drivers/net/ipa/ipa_main.c b/drivers/net/ipa/ipa_main.c
> index 28998dcce3d2..9295a9122e8e 100644
> --- a/drivers/net/ipa/ipa_main.c
> +++ b/drivers/net/ipa/ipa_main.c
> @@ -778,7 +778,7 @@ static int ipa_probe(struct platform_device *pdev)
>  	if (ret)
>  		goto err_kfree_ipa;
>  
> -	ret = ipa_mem_init(ipa, data->mem_count, data->mem_data);
> +	ret = ipa_mem_init(ipa, data->mem_data);
>  	if (ret)
>  		goto err_reg_exit;
>  
> diff --git a/drivers/net/ipa/ipa_mem.c b/drivers/net/ipa/ipa_mem.c
> index 42d2c29d9f0c..fb4de2a12796 100644
> --- a/drivers/net/ipa/ipa_mem.c
> +++ b/drivers/net/ipa/ipa_mem.c
> @@ -12,6 +12,7 @@
>  
>  #include "ipa.h"
>  #include "ipa_reg.h"
> +#include "ipa_data.h"
>  #include "ipa_cmd.h"
>  #include "ipa_mem.h"
>  #include "ipa_data.h"
> @@ -266,15 +267,15 @@ int ipa_mem_zero_modem(struct ipa *ipa)
>  }
>  
>  /* Perform memory region-related initialization */
> -int ipa_mem_init(struct ipa *ipa, u32 count, const struct ipa_mem *mem)
> +int ipa_mem_init(struct ipa *ipa, const struct ipa_mem_data *mem_data)
>  {
>  	struct device *dev = &ipa->pdev->dev;
>  	struct resource *res;
>  	int ret;
>  
> -	if (count > IPA_MEM_COUNT) {
> +	if (mem_data->local_count > IPA_MEM_COUNT) {
>  		dev_err(dev, "to many memory regions (%u > %u)\n",
> -			count, IPA_MEM_COUNT);
> +			mem_data->local_count, IPA_MEM_COUNT);
>  		return -EINVAL;
>  	}
>  
> @@ -302,7 +303,7 @@ int ipa_mem_init(struct ipa *ipa, u32 count, const struct ipa_mem *mem)
>  	ipa->mem_size = resource_size(res);
>  
>  	/* The ipa->mem[] array is indexed by enum ipa_mem_id values */
> -	ipa->mem = mem;
> +	ipa->mem = mem_data->local;
>  
>  	return 0;
>  }
> diff --git a/drivers/net/ipa/ipa_mem.h b/drivers/net/ipa/ipa_mem.h
> index 065cb499ebe5..f99180f84f0d 100644
> --- a/drivers/net/ipa/ipa_mem.h
> +++ b/drivers/net/ipa/ipa_mem.h
> @@ -7,6 +7,7 @@
>  #define _IPA_MEM_H_
>  
>  struct ipa;
> +struct ipa_mem_data;
>  
>  /**
>   * DOC: IPA Local Memory
> @@ -84,7 +85,7 @@ void ipa_mem_teardown(struct ipa *ipa);
>  
>  int ipa_mem_zero_modem(struct ipa *ipa);
>  
> -int ipa_mem_init(struct ipa *ipa, u32 count, const struct ipa_mem *mem);
> +int ipa_mem_init(struct ipa *ipa, const struct ipa_mem_data *mem_data);
>  void ipa_mem_exit(struct ipa *ipa);
>  
>  #endif /* _IPA_MEM_H_ */
> -- 
> 2.20.1
> 

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

* Re: [PATCH net-next v2 1/4] dt-bindings: net: add IPA iommus property
  2020-05-04 17:58 ` [PATCH net-next v2 1/4] dt-bindings: net: add IPA iommus property Alex Elder
  2020-05-04 18:30   ` Bjorn Andersson
@ 2020-05-04 18:52   ` Rob Herring
  1 sibling, 0 replies; 10+ messages in thread
From: Rob Herring @ 2020-05-04 18:52 UTC (permalink / raw)
  To: Alex Elder
  Cc: David Miller, Evan Green, subashab, cpratapa, Bjorn Andersson,
	Andy Gross, devicetree, netdev, linux-arm-msm, linux-kernel

On Mon, May 4, 2020 at 12:59 PM Alex Elder <elder@linaro.org> wrote:
>
> The IPA accesses "IMEM" and main system memory through an SMMU, so
> its DT node requires an iommus property to define range of stream IDs
> it uses.
>
> Signed-off-by: Alex Elder <elder@linaro.org>
> ---
>  Documentation/devicetree/bindings/net/qcom,ipa.yaml | 10 +++++++++-
>  1 file changed, 9 insertions(+), 1 deletion(-)
>
> diff --git a/Documentation/devicetree/bindings/net/qcom,ipa.yaml b/Documentation/devicetree/bindings/net/qcom,ipa.yaml
> index 140f15245654..7b749fc04c32 100644
> --- a/Documentation/devicetree/bindings/net/qcom,ipa.yaml
> +++ b/Documentation/devicetree/bindings/net/qcom,ipa.yaml
> @@ -20,7 +20,10 @@ description:
>    The GSI is an integral part of the IPA, but it is logically isolated
>    and has a distinct interrupt and a separately-defined address space.
>
> -  See also soc/qcom/qcom,smp2p.txt and interconnect/interconnect.txt.
> +  See also soc/qcom/qcom,smp2p.txt and interconnect/interconnect.txt.  See
> +  iommu/iommu.txt and iommu/arm,smmu.yaml for more information about SMMU
> +  bindings.

I'd drop this. We don't need every binding to reference back to common
bindings. And in theory, this binding is unrelated to the Arm SMMU.
Any IOMMU could be used.

With that,

Reviewed-by: Rob Herring <robh@kernel.org>

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

end of thread, other threads:[~2020-05-04 18:52 UTC | newest]

Thread overview: 10+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2020-05-04 17:58 [PATCH net-next v2 0/4] net: ipa: I/O map SMEM and IMEM Alex Elder
2020-05-04 17:58 ` [PATCH net-next v2 1/4] dt-bindings: net: add IPA iommus property Alex Elder
2020-05-04 18:30   ` Bjorn Andersson
2020-05-04 18:52   ` Rob Herring
2020-05-04 17:58 ` [PATCH net-next v2 2/4] net: ipa: redefine struct ipa_mem_data Alex Elder
2020-05-04 18:31   ` Bjorn Andersson
2020-05-04 17:58 ` [PATCH net-next v2 3/4] net: ipa: define IMEM memory region for IPA Alex Elder
2020-05-04 18:28   ` Bjorn Andersson
2020-05-04 17:58 ` [PATCH net-next v2 4/4] net: ipa: define SMEM " Alex Elder
2020-05-04 18:27 ` [PATCH net-next v2 0/4] net: ipa: I/O map SMEM and IMEM David Miller

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).