All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH 0/4] Fix OMAP4 barrier support
@ 2015-07-15 17:46 ` Russell King - ARM Linux
  0 siblings, 0 replies; 22+ messages in thread
From: Russell King - ARM Linux @ 2015-07-15 17:46 UTC (permalink / raw)
  To: linux-arm-kernel, linux-omap
  Cc: Tony Lindgren, Barry Song, Will Deacon, Linus Walleij

OMAP4 (and other TI CPUs) allow for weak ordering of writes through
different buses in their interconnects.  In order to ensure that
accesses are performed in the correct order, we need to extend some
of the kernel barriers to ensure that the bus interconnects are
correctly ordered.

As an example, it is possible for the following code sequence:

	cpu = dma_alloc_coherent(dev, ..., &dma);

	*cpu = 1;
	writel(dma, dev_addr);

Normal kernel semantics ensures that the write to "*cpu" will become
visible at the ARM domain boundary before the write to dev_addr.

However, because of the TI interconnects, it is possible for the
write to dev_addr to hit the peripheral before the write to "*cpu"
hits memory.  Thus, if the write to the device causes the device to
attempt to read from "*cpu" (which could be via a different path)
the device won't see that write.

Hence, we need to extend the barriers to ensure proper ordering
further down the bus chain than we do already to the L2 cache.

 arch/arm/include/asm/barrier.h              |  13 ++-
 arch/arm/include/asm/outercache.h           |  17 ----
 arch/arm/kernel/irq.c                       |   1 +
 arch/arm/mach-omap2/Kconfig                 |   7 ++
 arch/arm/mach-omap2/common.c                |   1 +
 arch/arm/mach-omap2/common.h                |   9 +++
 arch/arm/mach-omap2/include/mach/barriers.h |  33 --------
 arch/arm/mach-omap2/io.c                    |   2 +
 arch/arm/mach-omap2/omap4-common.c          | 121 ++++++++++++++++++++++++++++
 arch/arm/mach-omap2/sleep44xx.S             |   8 +-
 arch/arm/mach-prima2/pm.c                   |   1 +
 arch/arm/mach-ux500/cache-l2x0.c            |   1 +
 arch/arm/mm/Kconfig                         |   4 +
 arch/arm/mm/flush.c                         |  15 ++++
 14 files changed, 175 insertions(+), 58 deletions(-)

-- 
FTTC broadband for 0.8mile line: currently at 10.5Mbps down 400kbps up
according to speedtest.net.

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

* [PATCH 0/4] Fix OMAP4 barrier support
@ 2015-07-15 17:46 ` Russell King - ARM Linux
  0 siblings, 0 replies; 22+ messages in thread
From: Russell King - ARM Linux @ 2015-07-15 17:46 UTC (permalink / raw)
  To: linux-arm-kernel

OMAP4 (and other TI CPUs) allow for weak ordering of writes through
different buses in their interconnects.  In order to ensure that
accesses are performed in the correct order, we need to extend some
of the kernel barriers to ensure that the bus interconnects are
correctly ordered.

As an example, it is possible for the following code sequence:

	cpu = dma_alloc_coherent(dev, ..., &dma);

	*cpu = 1;
	writel(dma, dev_addr);

Normal kernel semantics ensures that the write to "*cpu" will become
visible at the ARM domain boundary before the write to dev_addr.

However, because of the TI interconnects, it is possible for the
write to dev_addr to hit the peripheral before the write to "*cpu"
hits memory.  Thus, if the write to the device causes the device to
attempt to read from "*cpu" (which could be via a different path)
the device won't see that write.

Hence, we need to extend the barriers to ensure proper ordering
further down the bus chain than we do already to the L2 cache.

 arch/arm/include/asm/barrier.h              |  13 ++-
 arch/arm/include/asm/outercache.h           |  17 ----
 arch/arm/kernel/irq.c                       |   1 +
 arch/arm/mach-omap2/Kconfig                 |   7 ++
 arch/arm/mach-omap2/common.c                |   1 +
 arch/arm/mach-omap2/common.h                |   9 +++
 arch/arm/mach-omap2/include/mach/barriers.h |  33 --------
 arch/arm/mach-omap2/io.c                    |   2 +
 arch/arm/mach-omap2/omap4-common.c          | 121 ++++++++++++++++++++++++++++
 arch/arm/mach-omap2/sleep44xx.S             |   8 +-
 arch/arm/mach-prima2/pm.c                   |   1 +
 arch/arm/mach-ux500/cache-l2x0.c            |   1 +
 arch/arm/mm/Kconfig                         |   4 +
 arch/arm/mm/flush.c                         |  15 ++++
 14 files changed, 175 insertions(+), 58 deletions(-)

-- 
FTTC broadband for 0.8mile line: currently at 10.5Mbps down 400kbps up
according to speedtest.net.

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

* [PATCH 1/4] ARM: move heavy barrier support out of line
  2015-07-15 17:46 ` Russell King - ARM Linux
@ 2015-07-15 17:47   ` Russell King
  -1 siblings, 0 replies; 22+ messages in thread
From: Russell King @ 2015-07-15 17:47 UTC (permalink / raw)
  To: linux-arm-kernel, linux-omap; +Cc: Barry Song, Will Deacon, Linus Walleij

The existing memory barrier macro causes a significant amount of code
to be inserted inline at every call site.  For example, in
gpio_set_irq_type(), we have this for mb():

c0344c08:       f57ff04e        dsb     st
c0344c0c:       e59f8190        ldr     r8, [pc, #400]  ; c0344da4 <gpio_set_irq_type+0x230>
c0344c10:       e3590004        cmp     r9, #4
c0344c14:       e5983014        ldr     r3, [r8, #20]
c0344c18:       0a000054        beq     c0344d70 <gpio_set_irq_type+0x1fc>
c0344c1c:       e3530000        cmp     r3, #0
c0344c20:       0a000004        beq     c0344c38 <gpio_set_irq_type+0xc4>
c0344c24:       e50b2030        str     r2, [fp, #-48]  ; 0xffffffd0
c0344c28:       e50bc034        str     ip, [fp, #-52]  ; 0xffffffcc
c0344c2c:       e12fff33        blx     r3
c0344c30:       e51bc034        ldr     ip, [fp, #-52]  ; 0xffffffcc
c0344c34:       e51b2030        ldr     r2, [fp, #-48]  ; 0xffffffd0
c0344c38:       e5963004        ldr     r3, [r6, #4]

Moving the outer_cache_sync() call out of line reduces the impact of
the barrier:

c0344968:       f57ff04e        dsb     st
c034496c:       e35a0004        cmp     sl, #4
c0344970:       e50b2030        str     r2, [fp, #-48]  ; 0xffffffd0
c0344974:       0a000044        beq     c0344a8c <gpio_set_irq_type+0x1b8>
c0344978:       ebf363dd        bl      c001d8f4 <arm_heavy_mb>
c034497c:       e5953004        ldr     r3, [r5, #4]

This should reduce the cache footprint of this code.  Overall, this
results in a reduction of around 20K in the kernel size:

    text    data      bss      dec     hex filename
10773970  667392 10369656 21811018 14ccf4a ../build/imx6/vmlinux-old
10754219  667392 10369656 21791267 14c8223 ../build/imx6/vmlinux-new

Another advantage to this approach is that we can finally resolve the
issue of SoCs which have their own memory barrier requirements within
multiplatform kernels (such as OMAP.)  Here, the bus interconnects
need additional handling to ensure that writes become visible in the
correct order (eg, between dma_map() operations, writes to DMA
coherent memory, and MMIO accesses.)

Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
---
 arch/arm/include/asm/barrier.h    | 12 +++++++++---
 arch/arm/include/asm/outercache.h | 17 -----------------
 arch/arm/kernel/irq.c             |  1 +
 arch/arm/mach-prima2/pm.c         |  1 +
 arch/arm/mach-ux500/cache-l2x0.c  |  1 +
 arch/arm/mm/Kconfig               |  4 ++++
 arch/arm/mm/flush.c               | 11 +++++++++++
 7 files changed, 27 insertions(+), 20 deletions(-)

diff --git a/arch/arm/include/asm/barrier.h b/arch/arm/include/asm/barrier.h
index 6c2327e1c732..fea99b0e2087 100644
--- a/arch/arm/include/asm/barrier.h
+++ b/arch/arm/include/asm/barrier.h
@@ -2,7 +2,6 @@
 #define __ASM_BARRIER_H
 
 #ifndef __ASSEMBLY__
-#include <asm/outercache.h>
 
 #define nop() __asm__ __volatile__("mov\tr0,r0\t@ nop\n\t");
 
@@ -37,12 +36,19 @@
 #define dmb(x) __asm__ __volatile__ ("" : : : "memory")
 #endif
 
+#ifdef CONFIG_ARM_HEAVY_MB
+extern void arm_heavy_mb(void);
+#define __arm_heavy_mb(x...) do { dsb(x); arm_heavy_mb(); } while (0)
+#else
+#define __arm_heavy_mb(x...) dsb(x)
+#endif
+
 #ifdef CONFIG_ARCH_HAS_BARRIERS
 #include <mach/barriers.h>
 #elif defined(CONFIG_ARM_DMA_MEM_BUFFERABLE) || defined(CONFIG_SMP)
-#define mb()		do { dsb(); outer_sync(); } while (0)
+#define mb()		__arm_heavy_mb()
 #define rmb()		dsb()
-#define wmb()		do { dsb(st); outer_sync(); } while (0)
+#define wmb()		__arm_heavy_mb(st)
 #define dma_rmb()	dmb(osh)
 #define dma_wmb()	dmb(oshst)
 #else
diff --git a/arch/arm/include/asm/outercache.h b/arch/arm/include/asm/outercache.h
index 563b92fc2f41..c2bf24f40177 100644
--- a/arch/arm/include/asm/outercache.h
+++ b/arch/arm/include/asm/outercache.h
@@ -129,21 +129,4 @@ static inline void outer_resume(void) { }
 
 #endif
 
-#ifdef CONFIG_OUTER_CACHE_SYNC
-/**
- * outer_sync - perform a sync point for outer cache
- *
- * Ensure that all outer cache operations are complete and any store
- * buffers are drained.
- */
-static inline void outer_sync(void)
-{
-	if (outer_cache.sync)
-		outer_cache.sync();
-}
-#else
-static inline void outer_sync(void)
-{ }
-#endif
-
 #endif	/* __ASM_OUTERCACHE_H */
diff --git a/arch/arm/kernel/irq.c b/arch/arm/kernel/irq.c
index 350f188c92d2..b96c8ed1723a 100644
--- a/arch/arm/kernel/irq.c
+++ b/arch/arm/kernel/irq.c
@@ -39,6 +39,7 @@
 #include <linux/export.h>
 
 #include <asm/hardware/cache-l2x0.h>
+#include <asm/outercache.h>
 #include <asm/exception.h>
 #include <asm/mach/arch.h>
 #include <asm/mach/irq.h>
diff --git a/arch/arm/mach-prima2/pm.c b/arch/arm/mach-prima2/pm.c
index d99d08eeb966..83e94c95e314 100644
--- a/arch/arm/mach-prima2/pm.c
+++ b/arch/arm/mach-prima2/pm.c
@@ -16,6 +16,7 @@
 #include <linux/of_platform.h>
 #include <linux/io.h>
 #include <linux/rtc/sirfsoc_rtciobrg.h>
+#include <asm/outercache.h>
 #include <asm/suspend.h>
 #include <asm/hardware/cache-l2x0.h>
 
diff --git a/arch/arm/mach-ux500/cache-l2x0.c b/arch/arm/mach-ux500/cache-l2x0.c
index 7557bede7ae6..780bd13cd7e3 100644
--- a/arch/arm/mach-ux500/cache-l2x0.c
+++ b/arch/arm/mach-ux500/cache-l2x0.c
@@ -8,6 +8,7 @@
 #include <linux/of.h>
 #include <linux/of_address.h>
 
+#include <asm/outercache.h>
 #include <asm/hardware/cache-l2x0.h>
 
 #include "db8500-regs.h"
diff --git a/arch/arm/mm/Kconfig b/arch/arm/mm/Kconfig
index 7c6b976ab8d3..df7537f12469 100644
--- a/arch/arm/mm/Kconfig
+++ b/arch/arm/mm/Kconfig
@@ -883,6 +883,7 @@ config OUTER_CACHE
 
 config OUTER_CACHE_SYNC
 	bool
+	select ARM_HEAVY_MB
 	help
 	  The outer cache has a outer_cache_fns.sync function pointer
 	  that can be used to drain the write buffer of the outer cache.
@@ -1031,6 +1032,9 @@ config ARCH_HAS_BARRIERS
 	  This option allows the use of custom mandatory barriers
 	  included via the mach/barriers.h file.
 
+config ARM_HEAVY_MB
+	bool
+
 config ARCH_SUPPORTS_BIG_ENDIAN
 	bool
 	help
diff --git a/arch/arm/mm/flush.c b/arch/arm/mm/flush.c
index 34b66af516ea..ce6c2960d5ac 100644
--- a/arch/arm/mm/flush.c
+++ b/arch/arm/mm/flush.c
@@ -21,6 +21,17 @@
 
 #include "mm.h"
 
+#ifdef CONFIG_ARM_HEAVY_MB
+void arm_heavy_mb(void)
+{
+#ifdef CONFIG_OUTER_CACHE_SYNC
+	if (outer_cache.sync)
+		outer_cache.sync();
+#endif
+}
+EXPORT_SYMBOL(arm_heavy_mb);
+#endif
+
 #ifdef CONFIG_CPU_CACHE_VIPT
 
 static void flush_pfn_alias(unsigned long pfn, unsigned long vaddr)
-- 
2.1.0

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

* [PATCH 1/4] ARM: move heavy barrier support out of line
@ 2015-07-15 17:47   ` Russell King
  0 siblings, 0 replies; 22+ messages in thread
From: Russell King @ 2015-07-15 17:47 UTC (permalink / raw)
  To: linux-arm-kernel

The existing memory barrier macro causes a significant amount of code
to be inserted inline at every call site.  For example, in
gpio_set_irq_type(), we have this for mb():

c0344c08:       f57ff04e        dsb     st
c0344c0c:       e59f8190        ldr     r8, [pc, #400]  ; c0344da4 <gpio_set_irq_type+0x230>
c0344c10:       e3590004        cmp     r9, #4
c0344c14:       e5983014        ldr     r3, [r8, #20]
c0344c18:       0a000054        beq     c0344d70 <gpio_set_irq_type+0x1fc>
c0344c1c:       e3530000        cmp     r3, #0
c0344c20:       0a000004        beq     c0344c38 <gpio_set_irq_type+0xc4>
c0344c24:       e50b2030        str     r2, [fp, #-48]  ; 0xffffffd0
c0344c28:       e50bc034        str     ip, [fp, #-52]  ; 0xffffffcc
c0344c2c:       e12fff33        blx     r3
c0344c30:       e51bc034        ldr     ip, [fp, #-52]  ; 0xffffffcc
c0344c34:       e51b2030        ldr     r2, [fp, #-48]  ; 0xffffffd0
c0344c38:       e5963004        ldr     r3, [r6, #4]

Moving the outer_cache_sync() call out of line reduces the impact of
the barrier:

c0344968:       f57ff04e        dsb     st
c034496c:       e35a0004        cmp     sl, #4
c0344970:       e50b2030        str     r2, [fp, #-48]  ; 0xffffffd0
c0344974:       0a000044        beq     c0344a8c <gpio_set_irq_type+0x1b8>
c0344978:       ebf363dd        bl      c001d8f4 <arm_heavy_mb>
c034497c:       e5953004        ldr     r3, [r5, #4]

This should reduce the cache footprint of this code.  Overall, this
results in a reduction of around 20K in the kernel size:

    text    data      bss      dec     hex filename
10773970  667392 10369656 21811018 14ccf4a ../build/imx6/vmlinux-old
10754219  667392 10369656 21791267 14c8223 ../build/imx6/vmlinux-new

Another advantage to this approach is that we can finally resolve the
issue of SoCs which have their own memory barrier requirements within
multiplatform kernels (such as OMAP.)  Here, the bus interconnects
need additional handling to ensure that writes become visible in the
correct order (eg, between dma_map() operations, writes to DMA
coherent memory, and MMIO accesses.)

Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
---
 arch/arm/include/asm/barrier.h    | 12 +++++++++---
 arch/arm/include/asm/outercache.h | 17 -----------------
 arch/arm/kernel/irq.c             |  1 +
 arch/arm/mach-prima2/pm.c         |  1 +
 arch/arm/mach-ux500/cache-l2x0.c  |  1 +
 arch/arm/mm/Kconfig               |  4 ++++
 arch/arm/mm/flush.c               | 11 +++++++++++
 7 files changed, 27 insertions(+), 20 deletions(-)

diff --git a/arch/arm/include/asm/barrier.h b/arch/arm/include/asm/barrier.h
index 6c2327e1c732..fea99b0e2087 100644
--- a/arch/arm/include/asm/barrier.h
+++ b/arch/arm/include/asm/barrier.h
@@ -2,7 +2,6 @@
 #define __ASM_BARRIER_H
 
 #ifndef __ASSEMBLY__
-#include <asm/outercache.h>
 
 #define nop() __asm__ __volatile__("mov\tr0,r0\t@ nop\n\t");
 
@@ -37,12 +36,19 @@
 #define dmb(x) __asm__ __volatile__ ("" : : : "memory")
 #endif
 
+#ifdef CONFIG_ARM_HEAVY_MB
+extern void arm_heavy_mb(void);
+#define __arm_heavy_mb(x...) do { dsb(x); arm_heavy_mb(); } while (0)
+#else
+#define __arm_heavy_mb(x...) dsb(x)
+#endif
+
 #ifdef CONFIG_ARCH_HAS_BARRIERS
 #include <mach/barriers.h>
 #elif defined(CONFIG_ARM_DMA_MEM_BUFFERABLE) || defined(CONFIG_SMP)
-#define mb()		do { dsb(); outer_sync(); } while (0)
+#define mb()		__arm_heavy_mb()
 #define rmb()		dsb()
-#define wmb()		do { dsb(st); outer_sync(); } while (0)
+#define wmb()		__arm_heavy_mb(st)
 #define dma_rmb()	dmb(osh)
 #define dma_wmb()	dmb(oshst)
 #else
diff --git a/arch/arm/include/asm/outercache.h b/arch/arm/include/asm/outercache.h
index 563b92fc2f41..c2bf24f40177 100644
--- a/arch/arm/include/asm/outercache.h
+++ b/arch/arm/include/asm/outercache.h
@@ -129,21 +129,4 @@ static inline void outer_resume(void) { }
 
 #endif
 
-#ifdef CONFIG_OUTER_CACHE_SYNC
-/**
- * outer_sync - perform a sync point for outer cache
- *
- * Ensure that all outer cache operations are complete and any store
- * buffers are drained.
- */
-static inline void outer_sync(void)
-{
-	if (outer_cache.sync)
-		outer_cache.sync();
-}
-#else
-static inline void outer_sync(void)
-{ }
-#endif
-
 #endif	/* __ASM_OUTERCACHE_H */
diff --git a/arch/arm/kernel/irq.c b/arch/arm/kernel/irq.c
index 350f188c92d2..b96c8ed1723a 100644
--- a/arch/arm/kernel/irq.c
+++ b/arch/arm/kernel/irq.c
@@ -39,6 +39,7 @@
 #include <linux/export.h>
 
 #include <asm/hardware/cache-l2x0.h>
+#include <asm/outercache.h>
 #include <asm/exception.h>
 #include <asm/mach/arch.h>
 #include <asm/mach/irq.h>
diff --git a/arch/arm/mach-prima2/pm.c b/arch/arm/mach-prima2/pm.c
index d99d08eeb966..83e94c95e314 100644
--- a/arch/arm/mach-prima2/pm.c
+++ b/arch/arm/mach-prima2/pm.c
@@ -16,6 +16,7 @@
 #include <linux/of_platform.h>
 #include <linux/io.h>
 #include <linux/rtc/sirfsoc_rtciobrg.h>
+#include <asm/outercache.h>
 #include <asm/suspend.h>
 #include <asm/hardware/cache-l2x0.h>
 
diff --git a/arch/arm/mach-ux500/cache-l2x0.c b/arch/arm/mach-ux500/cache-l2x0.c
index 7557bede7ae6..780bd13cd7e3 100644
--- a/arch/arm/mach-ux500/cache-l2x0.c
+++ b/arch/arm/mach-ux500/cache-l2x0.c
@@ -8,6 +8,7 @@
 #include <linux/of.h>
 #include <linux/of_address.h>
 
+#include <asm/outercache.h>
 #include <asm/hardware/cache-l2x0.h>
 
 #include "db8500-regs.h"
diff --git a/arch/arm/mm/Kconfig b/arch/arm/mm/Kconfig
index 7c6b976ab8d3..df7537f12469 100644
--- a/arch/arm/mm/Kconfig
+++ b/arch/arm/mm/Kconfig
@@ -883,6 +883,7 @@ config OUTER_CACHE
 
 config OUTER_CACHE_SYNC
 	bool
+	select ARM_HEAVY_MB
 	help
 	  The outer cache has a outer_cache_fns.sync function pointer
 	  that can be used to drain the write buffer of the outer cache.
@@ -1031,6 +1032,9 @@ config ARCH_HAS_BARRIERS
 	  This option allows the use of custom mandatory barriers
 	  included via the mach/barriers.h file.
 
+config ARM_HEAVY_MB
+	bool
+
 config ARCH_SUPPORTS_BIG_ENDIAN
 	bool
 	help
diff --git a/arch/arm/mm/flush.c b/arch/arm/mm/flush.c
index 34b66af516ea..ce6c2960d5ac 100644
--- a/arch/arm/mm/flush.c
+++ b/arch/arm/mm/flush.c
@@ -21,6 +21,17 @@
 
 #include "mm.h"
 
+#ifdef CONFIG_ARM_HEAVY_MB
+void arm_heavy_mb(void)
+{
+#ifdef CONFIG_OUTER_CACHE_SYNC
+	if (outer_cache.sync)
+		outer_cache.sync();
+#endif
+}
+EXPORT_SYMBOL(arm_heavy_mb);
+#endif
+
 #ifdef CONFIG_CPU_CACHE_VIPT
 
 static void flush_pfn_alias(unsigned long pfn, unsigned long vaddr)
-- 
2.1.0

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

* [PATCH 2/4] ARM: add soc memory barrier extension
  2015-07-15 17:46 ` Russell King - ARM Linux
@ 2015-07-15 17:47   ` Russell King
  -1 siblings, 0 replies; 22+ messages in thread
From: Russell King @ 2015-07-15 17:47 UTC (permalink / raw)
  To: linux-arm-kernel, linux-omap; +Cc: Will Deacon

Add an extension to the heavy barrier code to allow a SoC specific
memory barrier function to be provided.  This is needed for platforms
where the interconnect has weak ordering, and thus needs assistance
to ensure that memory writes are properly visible in the correct order
to other parts of the system.

Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
---
 arch/arm/include/asm/barrier.h | 1 +
 arch/arm/mm/flush.c            | 4 ++++
 2 files changed, 5 insertions(+)

diff --git a/arch/arm/include/asm/barrier.h b/arch/arm/include/asm/barrier.h
index fea99b0e2087..3d8f1d3ad9a7 100644
--- a/arch/arm/include/asm/barrier.h
+++ b/arch/arm/include/asm/barrier.h
@@ -37,6 +37,7 @@
 #endif
 
 #ifdef CONFIG_ARM_HEAVY_MB
+extern void (*soc_mb)(void);
 extern void arm_heavy_mb(void);
 #define __arm_heavy_mb(x...) do { dsb(x); arm_heavy_mb(); } while (0)
 #else
diff --git a/arch/arm/mm/flush.c b/arch/arm/mm/flush.c
index ce6c2960d5ac..1ec8e7590fc6 100644
--- a/arch/arm/mm/flush.c
+++ b/arch/arm/mm/flush.c
@@ -22,12 +22,16 @@
 #include "mm.h"
 
 #ifdef CONFIG_ARM_HEAVY_MB
+void (*soc_mb)(void);
+
 void arm_heavy_mb(void)
 {
 #ifdef CONFIG_OUTER_CACHE_SYNC
 	if (outer_cache.sync)
 		outer_cache.sync();
 #endif
+	if (soc_mb)
+		soc_mb();
 }
 EXPORT_SYMBOL(arm_heavy_mb);
 #endif
-- 
2.1.0

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

* [PATCH 2/4] ARM: add soc memory barrier extension
@ 2015-07-15 17:47   ` Russell King
  0 siblings, 0 replies; 22+ messages in thread
From: Russell King @ 2015-07-15 17:47 UTC (permalink / raw)
  To: linux-arm-kernel

Add an extension to the heavy barrier code to allow a SoC specific
memory barrier function to be provided.  This is needed for platforms
where the interconnect has weak ordering, and thus needs assistance
to ensure that memory writes are properly visible in the correct order
to other parts of the system.

Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
---
 arch/arm/include/asm/barrier.h | 1 +
 arch/arm/mm/flush.c            | 4 ++++
 2 files changed, 5 insertions(+)

diff --git a/arch/arm/include/asm/barrier.h b/arch/arm/include/asm/barrier.h
index fea99b0e2087..3d8f1d3ad9a7 100644
--- a/arch/arm/include/asm/barrier.h
+++ b/arch/arm/include/asm/barrier.h
@@ -37,6 +37,7 @@
 #endif
 
 #ifdef CONFIG_ARM_HEAVY_MB
+extern void (*soc_mb)(void);
 extern void arm_heavy_mb(void);
 #define __arm_heavy_mb(x...) do { dsb(x); arm_heavy_mb(); } while (0)
 #else
diff --git a/arch/arm/mm/flush.c b/arch/arm/mm/flush.c
index ce6c2960d5ac..1ec8e7590fc6 100644
--- a/arch/arm/mm/flush.c
+++ b/arch/arm/mm/flush.c
@@ -22,12 +22,16 @@
 #include "mm.h"
 
 #ifdef CONFIG_ARM_HEAVY_MB
+void (*soc_mb)(void);
+
 void arm_heavy_mb(void)
 {
 #ifdef CONFIG_OUTER_CACHE_SYNC
 	if (outer_cache.sync)
 		outer_cache.sync();
 #endif
+	if (soc_mb)
+		soc_mb();
 }
 EXPORT_SYMBOL(arm_heavy_mb);
 #endif
-- 
2.1.0

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

* [PATCH 3/4] Revert "ARM: OMAP4: remove dead kconfig option OMAP4_ERRATA_I688"
  2015-07-15 17:46 ` Russell King - ARM Linux
@ 2015-07-15 17:47   ` Russell King
  -1 siblings, 0 replies; 22+ messages in thread
From: Russell King @ 2015-07-15 17:47 UTC (permalink / raw)
  To: linux-arm-kernel, linux-omap; +Cc: Tony Lindgren, Will Deacon

This reverts commit 606da4826b89b044b51e3a84958b802204cfe4c7.

We actually need this code for proper behaviour of OMAP4, and it needs
fixing a different way other than just removing the code.  Disabling
code which is necessary in the hopes of persuing multiplatform kernels
is a stupid approach.

Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
---
 arch/arm/mach-omap2/Kconfig        | 21 ++++++++++++
 arch/arm/mach-omap2/common.c       |  1 +
 arch/arm/mach-omap2/common.h       |  3 ++
 arch/arm/mach-omap2/io.c           |  2 ++
 arch/arm/mach-omap2/omap-secure.h  |  7 ++++
 arch/arm/mach-omap2/omap4-common.c | 69 ++++++++++++++++++++++++++++++++++++++
 arch/arm/mach-omap2/sleep44xx.S    |  2 ++
 7 files changed, 105 insertions(+)

diff --git a/arch/arm/mach-omap2/Kconfig b/arch/arm/mach-omap2/Kconfig
index ecc04ff13e95..2128441430ad 100644
--- a/arch/arm/mach-omap2/Kconfig
+++ b/arch/arm/mach-omap2/Kconfig
@@ -240,6 +240,27 @@ config OMAP3_SDRC_AC_TIMING
 	  wish to say no.  Selecting yes without understanding what is
 	  going on could result in system crashes;
 
+config OMAP4_ERRATA_I688
+	bool "OMAP4 errata: Async Bridge Corruption"
+	depends on (ARCH_OMAP4 || SOC_OMAP5) && !ARCH_MULTIPLATFORM
+	select ARCH_HAS_BARRIERS
+	help
+	  If a data is stalled inside asynchronous bridge because of back
+	  pressure, it may be accepted multiple times, creating pointer
+	  misalignment that will corrupt next transfers on that data path
+	  until next reset of the system (No recovery procedure once the
+	  issue is hit, the path remains consistently broken). Async bridge
+	  can be found on path between MPU to EMIF and MPU to L3 interconnect.
+	  This situation can happen only when the idle is initiated by a
+	  Master Request Disconnection (which is trigged by software when
+	  executing WFI on CPU).
+	  The work-around for this errata needs all the initiators connected
+	  through async bridge must ensure that data path is properly drained
+	  before issuing WFI. This condition will be met if one Strongly ordered
+	  access is performed to the target right before executing the WFI.
+	  In MPU case, L3 T2ASYNC FIFO and DDR T2ASYNC FIFO needs to be drained.
+	  IO barrier ensure that there is no synchronisation loss on initiators
+	  operating on both interconnect port simultaneously.
 endmenu
 
 endif
diff --git a/arch/arm/mach-omap2/common.c b/arch/arm/mach-omap2/common.c
index eae6a0e87c90..484cdadfb187 100644
--- a/arch/arm/mach-omap2/common.c
+++ b/arch/arm/mach-omap2/common.c
@@ -30,4 +30,5 @@ int __weak omap_secure_ram_reserve_memblock(void)
 void __init omap_reserve(void)
 {
 	omap_secure_ram_reserve_memblock();
+	omap_barrier_reserve_memblock();
 }
diff --git a/arch/arm/mach-omap2/common.h b/arch/arm/mach-omap2/common.h
index cf3cf22ecd42..46e24581d624 100644
--- a/arch/arm/mach-omap2/common.h
+++ b/arch/arm/mach-omap2/common.h
@@ -200,6 +200,9 @@ void __init omap4_map_io(void);
 void __init omap5_map_io(void);
 void __init ti81xx_map_io(void);
 
+/* omap_barriers_init() is OMAP4 only */
+void omap_barriers_init(void);
+
 /**
  * omap_test_timeout - busy-loop, testing a condition
  * @cond: condition to test until it evaluates to true
diff --git a/arch/arm/mach-omap2/io.c b/arch/arm/mach-omap2/io.c
index 820dde8b5b04..7743e3672f98 100644
--- a/arch/arm/mach-omap2/io.c
+++ b/arch/arm/mach-omap2/io.c
@@ -306,6 +306,7 @@ void __init am33xx_map_io(void)
 void __init omap4_map_io(void)
 {
 	iotable_init(omap44xx_io_desc, ARRAY_SIZE(omap44xx_io_desc));
+	omap_barriers_init();
 }
 #endif
 
@@ -313,6 +314,7 @@ void __init omap4_map_io(void)
 void __init omap5_map_io(void)
 {
 	iotable_init(omap54xx_io_desc, ARRAY_SIZE(omap54xx_io_desc));
+	omap_barriers_init();
 }
 #endif
 /*
diff --git a/arch/arm/mach-omap2/omap-secure.h b/arch/arm/mach-omap2/omap-secure.h
index af2851fbcdf0..dec2b05d184b 100644
--- a/arch/arm/mach-omap2/omap-secure.h
+++ b/arch/arm/mach-omap2/omap-secure.h
@@ -70,6 +70,13 @@ extern u32 rx51_secure_dispatcher(u32 idx, u32 process, u32 flag, u32 nargs,
 extern u32 rx51_secure_update_aux_cr(u32 set_bits, u32 clear_bits);
 extern u32 rx51_secure_rng_call(u32 ptr, u32 count, u32 flag);
 
+#ifdef CONFIG_OMAP4_ERRATA_I688
+extern int omap_barrier_reserve_memblock(void);
+#else
+static inline void omap_barrier_reserve_memblock(void)
+{ }
+#endif
+
 #ifdef CONFIG_SOC_HAS_REALTIME_COUNTER
 void set_cntfreq(void);
 #else
diff --git a/arch/arm/mach-omap2/omap4-common.c b/arch/arm/mach-omap2/omap4-common.c
index 16350eefa66c..7bb116a6f86f 100644
--- a/arch/arm/mach-omap2/omap4-common.c
+++ b/arch/arm/mach-omap2/omap4-common.c
@@ -51,6 +51,75 @@ static void __iomem *twd_base;
 
 #define IRQ_LOCALTIMER		29
 
+#ifdef CONFIG_OMAP4_ERRATA_I688
+/* Used to implement memory barrier on DRAM path */
+#define OMAP4_DRAM_BARRIER_VA			0xfe600000
+
+void __iomem *dram_sync, *sram_sync;
+
+static phys_addr_t paddr;
+static u32 size;
+
+void omap_bus_sync(void)
+{
+	if (dram_sync && sram_sync) {
+		writel_relaxed(readl_relaxed(dram_sync), dram_sync);
+		writel_relaxed(readl_relaxed(sram_sync), sram_sync);
+		isb();
+	}
+}
+EXPORT_SYMBOL(omap_bus_sync);
+
+static int __init omap4_sram_init(void)
+{
+	struct device_node *np;
+	struct gen_pool *sram_pool;
+
+	np = of_find_compatible_node(NULL, NULL, "ti,omap4-mpu");
+	if (!np)
+		pr_warn("%s:Unable to allocate sram needed to handle errata I688\n",
+			__func__);
+	sram_pool = of_get_named_gen_pool(np, "sram", 0);
+	if (!sram_pool)
+		pr_warn("%s:Unable to get sram pool needed to handle errata I688\n",
+			__func__);
+	else
+		sram_sync = (void *)gen_pool_alloc(sram_pool, PAGE_SIZE);
+
+	return 0;
+}
+omap_arch_initcall(omap4_sram_init);
+
+/* Steal one page physical memory for barrier implementation */
+int __init omap_barrier_reserve_memblock(void)
+{
+
+	size = ALIGN(PAGE_SIZE, SZ_1M);
+	paddr = arm_memblock_steal(size, SZ_1M);
+
+	return 0;
+}
+
+void __init omap_barriers_init(void)
+{
+	struct map_desc dram_io_desc[1];
+
+	dram_io_desc[0].virtual = OMAP4_DRAM_BARRIER_VA;
+	dram_io_desc[0].pfn = __phys_to_pfn(paddr);
+	dram_io_desc[0].length = size;
+	dram_io_desc[0].type = MT_MEMORY_RW_SO;
+	iotable_init(dram_io_desc, ARRAY_SIZE(dram_io_desc));
+	dram_sync = (void __iomem *) dram_io_desc[0].virtual;
+
+	pr_info("OMAP4: Map 0x%08llx to 0x%08lx for dram barrier\n",
+		(long long) paddr, dram_io_desc[0].virtual);
+
+}
+#else
+void __init omap_barriers_init(void)
+{}
+#endif
+
 void gic_dist_disable(void)
 {
 	if (gic_dist_base_addr)
diff --git a/arch/arm/mach-omap2/sleep44xx.S b/arch/arm/mach-omap2/sleep44xx.S
index ad1bb9431e94..b84a0122d823 100644
--- a/arch/arm/mach-omap2/sleep44xx.S
+++ b/arch/arm/mach-omap2/sleep44xx.S
@@ -333,9 +333,11 @@ ENDPROC(omap4_cpu_resume)
 
 #endif	/* defined(CONFIG_SMP) && defined(CONFIG_PM) */
 
+#ifndef CONFIG_OMAP4_ERRATA_I688
 ENTRY(omap_bus_sync)
 	ret	lr
 ENDPROC(omap_bus_sync)
+#endif
 
 ENTRY(omap_do_wfi)
 	stmfd	sp!, {lr}
-- 
2.1.0

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

* [PATCH 3/4] Revert "ARM: OMAP4: remove dead kconfig option OMAP4_ERRATA_I688"
@ 2015-07-15 17:47   ` Russell King
  0 siblings, 0 replies; 22+ messages in thread
From: Russell King @ 2015-07-15 17:47 UTC (permalink / raw)
  To: linux-arm-kernel

This reverts commit 606da4826b89b044b51e3a84958b802204cfe4c7.

We actually need this code for proper behaviour of OMAP4, and it needs
fixing a different way other than just removing the code.  Disabling
code which is necessary in the hopes of persuing multiplatform kernels
is a stupid approach.

Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
---
 arch/arm/mach-omap2/Kconfig        | 21 ++++++++++++
 arch/arm/mach-omap2/common.c       |  1 +
 arch/arm/mach-omap2/common.h       |  3 ++
 arch/arm/mach-omap2/io.c           |  2 ++
 arch/arm/mach-omap2/omap-secure.h  |  7 ++++
 arch/arm/mach-omap2/omap4-common.c | 69 ++++++++++++++++++++++++++++++++++++++
 arch/arm/mach-omap2/sleep44xx.S    |  2 ++
 7 files changed, 105 insertions(+)

diff --git a/arch/arm/mach-omap2/Kconfig b/arch/arm/mach-omap2/Kconfig
index ecc04ff13e95..2128441430ad 100644
--- a/arch/arm/mach-omap2/Kconfig
+++ b/arch/arm/mach-omap2/Kconfig
@@ -240,6 +240,27 @@ config OMAP3_SDRC_AC_TIMING
 	  wish to say no.  Selecting yes without understanding what is
 	  going on could result in system crashes;
 
+config OMAP4_ERRATA_I688
+	bool "OMAP4 errata: Async Bridge Corruption"
+	depends on (ARCH_OMAP4 || SOC_OMAP5) && !ARCH_MULTIPLATFORM
+	select ARCH_HAS_BARRIERS
+	help
+	  If a data is stalled inside asynchronous bridge because of back
+	  pressure, it may be accepted multiple times, creating pointer
+	  misalignment that will corrupt next transfers on that data path
+	  until next reset of the system (No recovery procedure once the
+	  issue is hit, the path remains consistently broken). Async bridge
+	  can be found on path between MPU to EMIF and MPU to L3 interconnect.
+	  This situation can happen only when the idle is initiated by a
+	  Master Request Disconnection (which is trigged by software when
+	  executing WFI on CPU).
+	  The work-around for this errata needs all the initiators connected
+	  through async bridge must ensure that data path is properly drained
+	  before issuing WFI. This condition will be met if one Strongly ordered
+	  access is performed to the target right before executing the WFI.
+	  In MPU case, L3 T2ASYNC FIFO and DDR T2ASYNC FIFO needs to be drained.
+	  IO barrier ensure that there is no synchronisation loss on initiators
+	  operating on both interconnect port simultaneously.
 endmenu
 
 endif
diff --git a/arch/arm/mach-omap2/common.c b/arch/arm/mach-omap2/common.c
index eae6a0e87c90..484cdadfb187 100644
--- a/arch/arm/mach-omap2/common.c
+++ b/arch/arm/mach-omap2/common.c
@@ -30,4 +30,5 @@ int __weak omap_secure_ram_reserve_memblock(void)
 void __init omap_reserve(void)
 {
 	omap_secure_ram_reserve_memblock();
+	omap_barrier_reserve_memblock();
 }
diff --git a/arch/arm/mach-omap2/common.h b/arch/arm/mach-omap2/common.h
index cf3cf22ecd42..46e24581d624 100644
--- a/arch/arm/mach-omap2/common.h
+++ b/arch/arm/mach-omap2/common.h
@@ -200,6 +200,9 @@ void __init omap4_map_io(void);
 void __init omap5_map_io(void);
 void __init ti81xx_map_io(void);
 
+/* omap_barriers_init() is OMAP4 only */
+void omap_barriers_init(void);
+
 /**
  * omap_test_timeout - busy-loop, testing a condition
  * @cond: condition to test until it evaluates to true
diff --git a/arch/arm/mach-omap2/io.c b/arch/arm/mach-omap2/io.c
index 820dde8b5b04..7743e3672f98 100644
--- a/arch/arm/mach-omap2/io.c
+++ b/arch/arm/mach-omap2/io.c
@@ -306,6 +306,7 @@ void __init am33xx_map_io(void)
 void __init omap4_map_io(void)
 {
 	iotable_init(omap44xx_io_desc, ARRAY_SIZE(omap44xx_io_desc));
+	omap_barriers_init();
 }
 #endif
 
@@ -313,6 +314,7 @@ void __init omap4_map_io(void)
 void __init omap5_map_io(void)
 {
 	iotable_init(omap54xx_io_desc, ARRAY_SIZE(omap54xx_io_desc));
+	omap_barriers_init();
 }
 #endif
 /*
diff --git a/arch/arm/mach-omap2/omap-secure.h b/arch/arm/mach-omap2/omap-secure.h
index af2851fbcdf0..dec2b05d184b 100644
--- a/arch/arm/mach-omap2/omap-secure.h
+++ b/arch/arm/mach-omap2/omap-secure.h
@@ -70,6 +70,13 @@ extern u32 rx51_secure_dispatcher(u32 idx, u32 process, u32 flag, u32 nargs,
 extern u32 rx51_secure_update_aux_cr(u32 set_bits, u32 clear_bits);
 extern u32 rx51_secure_rng_call(u32 ptr, u32 count, u32 flag);
 
+#ifdef CONFIG_OMAP4_ERRATA_I688
+extern int omap_barrier_reserve_memblock(void);
+#else
+static inline void omap_barrier_reserve_memblock(void)
+{ }
+#endif
+
 #ifdef CONFIG_SOC_HAS_REALTIME_COUNTER
 void set_cntfreq(void);
 #else
diff --git a/arch/arm/mach-omap2/omap4-common.c b/arch/arm/mach-omap2/omap4-common.c
index 16350eefa66c..7bb116a6f86f 100644
--- a/arch/arm/mach-omap2/omap4-common.c
+++ b/arch/arm/mach-omap2/omap4-common.c
@@ -51,6 +51,75 @@ static void __iomem *twd_base;
 
 #define IRQ_LOCALTIMER		29
 
+#ifdef CONFIG_OMAP4_ERRATA_I688
+/* Used to implement memory barrier on DRAM path */
+#define OMAP4_DRAM_BARRIER_VA			0xfe600000
+
+void __iomem *dram_sync, *sram_sync;
+
+static phys_addr_t paddr;
+static u32 size;
+
+void omap_bus_sync(void)
+{
+	if (dram_sync && sram_sync) {
+		writel_relaxed(readl_relaxed(dram_sync), dram_sync);
+		writel_relaxed(readl_relaxed(sram_sync), sram_sync);
+		isb();
+	}
+}
+EXPORT_SYMBOL(omap_bus_sync);
+
+static int __init omap4_sram_init(void)
+{
+	struct device_node *np;
+	struct gen_pool *sram_pool;
+
+	np = of_find_compatible_node(NULL, NULL, "ti,omap4-mpu");
+	if (!np)
+		pr_warn("%s:Unable to allocate sram needed to handle errata I688\n",
+			__func__);
+	sram_pool = of_get_named_gen_pool(np, "sram", 0);
+	if (!sram_pool)
+		pr_warn("%s:Unable to get sram pool needed to handle errata I688\n",
+			__func__);
+	else
+		sram_sync = (void *)gen_pool_alloc(sram_pool, PAGE_SIZE);
+
+	return 0;
+}
+omap_arch_initcall(omap4_sram_init);
+
+/* Steal one page physical memory for barrier implementation */
+int __init omap_barrier_reserve_memblock(void)
+{
+
+	size = ALIGN(PAGE_SIZE, SZ_1M);
+	paddr = arm_memblock_steal(size, SZ_1M);
+
+	return 0;
+}
+
+void __init omap_barriers_init(void)
+{
+	struct map_desc dram_io_desc[1];
+
+	dram_io_desc[0].virtual = OMAP4_DRAM_BARRIER_VA;
+	dram_io_desc[0].pfn = __phys_to_pfn(paddr);
+	dram_io_desc[0].length = size;
+	dram_io_desc[0].type = MT_MEMORY_RW_SO;
+	iotable_init(dram_io_desc, ARRAY_SIZE(dram_io_desc));
+	dram_sync = (void __iomem *) dram_io_desc[0].virtual;
+
+	pr_info("OMAP4: Map 0x%08llx to 0x%08lx for dram barrier\n",
+		(long long) paddr, dram_io_desc[0].virtual);
+
+}
+#else
+void __init omap_barriers_init(void)
+{}
+#endif
+
 void gic_dist_disable(void)
 {
 	if (gic_dist_base_addr)
diff --git a/arch/arm/mach-omap2/sleep44xx.S b/arch/arm/mach-omap2/sleep44xx.S
index ad1bb9431e94..b84a0122d823 100644
--- a/arch/arm/mach-omap2/sleep44xx.S
+++ b/arch/arm/mach-omap2/sleep44xx.S
@@ -333,9 +333,11 @@ ENDPROC(omap4_cpu_resume)
 
 #endif	/* defined(CONFIG_SMP) && defined(CONFIG_PM) */
 
+#ifndef CONFIG_OMAP4_ERRATA_I688
 ENTRY(omap_bus_sync)
 	ret	lr
 ENDPROC(omap_bus_sync)
+#endif
 
 ENTRY(omap_do_wfi)
 	stmfd	sp!, {lr}
-- 
2.1.0

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

* [PATCH 4/4] ARM: omap2: restore OMAP4 barrier behaviour
  2015-07-15 17:46 ` Russell King - ARM Linux
@ 2015-07-15 17:47   ` Russell King
  -1 siblings, 0 replies; 22+ messages in thread
From: Russell King @ 2015-07-15 17:47 UTC (permalink / raw)
  To: linux-arm-kernel, linux-omap; +Cc: Tony Lindgren, Will Deacon

Restore the OMAP4 barrier behaviour using the new implementation which
allows multiplatform systems to hook into the mb() and wmb() ARM
implementations to perform any necessary additional barrier maintanence.

Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
---
 arch/arm/mach-omap2/Kconfig                 | 28 +++------
 arch/arm/mach-omap2/common.h                | 12 +++-
 arch/arm/mach-omap2/include/mach/barriers.h | 33 -----------
 arch/arm/mach-omap2/omap-secure.h           |  7 ---
 arch/arm/mach-omap2/omap4-common.c          | 90 +++++++++++++++++++++++------
 arch/arm/mach-omap2/sleep44xx.S             | 10 +---
 6 files changed, 90 insertions(+), 90 deletions(-)
 delete mode 100644 arch/arm/mach-omap2/include/mach/barriers.h

diff --git a/arch/arm/mach-omap2/Kconfig b/arch/arm/mach-omap2/Kconfig
index 2128441430ad..8427997e09c4 100644
--- a/arch/arm/mach-omap2/Kconfig
+++ b/arch/arm/mach-omap2/Kconfig
@@ -29,6 +29,7 @@ config ARCH_OMAP4
 	select HAVE_ARM_SCU if SMP
 	select HAVE_ARM_TWD if SMP
 	select OMAP_INTERCONNECT
+	select OMAP_INTERCONNECT_BARRIER
 	select PL310_ERRATA_588369 if CACHE_L2X0
 	select PL310_ERRATA_727915 if CACHE_L2X0
 	select PM_OPP if PM
@@ -46,6 +47,7 @@ config SOC_OMAP5
 	select HAVE_ARM_TWD if SMP
 	select HAVE_ARM_ARCH_TIMER
 	select ARM_ERRATA_798181 if SMP
+	select OMAP_INTERCONNECT_BARRIER
 
 config SOC_AM33XX
 	bool "TI AM33XX"
@@ -70,6 +72,7 @@ config SOC_DRA7XX
 	select HAVE_ARM_ARCH_TIMER
 	select IRQ_CROSSBAR
 	select ARM_ERRATA_798181 if SMP
+	select OMAP_INTERCONNECT_BARRIER
 
 config ARCH_OMAP2PLUS
 	bool
@@ -91,6 +94,10 @@ config ARCH_OMAP2PLUS
 	help
 	  Systems based on OMAP2, OMAP3, OMAP4 or OMAP5
 
+config OMAP_INTERCONNECT_BARRIER
+	bool
+	select ARM_HEAVY_MB
+	
 
 if ARCH_OMAP2PLUS
 
@@ -240,27 +247,6 @@ config OMAP3_SDRC_AC_TIMING
 	  wish to say no.  Selecting yes without understanding what is
 	  going on could result in system crashes;
 
-config OMAP4_ERRATA_I688
-	bool "OMAP4 errata: Async Bridge Corruption"
-	depends on (ARCH_OMAP4 || SOC_OMAP5) && !ARCH_MULTIPLATFORM
-	select ARCH_HAS_BARRIERS
-	help
-	  If a data is stalled inside asynchronous bridge because of back
-	  pressure, it may be accepted multiple times, creating pointer
-	  misalignment that will corrupt next transfers on that data path
-	  until next reset of the system (No recovery procedure once the
-	  issue is hit, the path remains consistently broken). Async bridge
-	  can be found on path between MPU to EMIF and MPU to L3 interconnect.
-	  This situation can happen only when the idle is initiated by a
-	  Master Request Disconnection (which is trigged by software when
-	  executing WFI on CPU).
-	  The work-around for this errata needs all the initiators connected
-	  through async bridge must ensure that data path is properly drained
-	  before issuing WFI. This condition will be met if one Strongly ordered
-	  access is performed to the target right before executing the WFI.
-	  In MPU case, L3 T2ASYNC FIFO and DDR T2ASYNC FIFO needs to be drained.
-	  IO barrier ensure that there is no synchronisation loss on initiators
-	  operating on both interconnect port simultaneously.
 endmenu
 
 endif
diff --git a/arch/arm/mach-omap2/common.h b/arch/arm/mach-omap2/common.h
index 46e24581d624..82f88b4ec15f 100644
--- a/arch/arm/mach-omap2/common.h
+++ b/arch/arm/mach-omap2/common.h
@@ -189,6 +189,15 @@ static inline void omap44xx_restart(enum reboot_mode mode, const char *cmd)
 }
 #endif
 
+#ifdef CONFIG_OMAP_INTERCONNECT_BARRIER
+void omap_barrier_reserve_memblock(void);
+void omap_barriers_init(void);
+#else
+static inline void omap_barrier_reserve_memblock(void)
+{
+}
+#endif
+
 /* This gets called from mach-omap2/io.c, do not call this */
 void __init omap2_set_globals_tap(u32 class, void __iomem *tap);
 
@@ -200,9 +209,6 @@ void __init omap4_map_io(void);
 void __init omap5_map_io(void);
 void __init ti81xx_map_io(void);
 
-/* omap_barriers_init() is OMAP4 only */
-void omap_barriers_init(void);
-
 /**
  * omap_test_timeout - busy-loop, testing a condition
  * @cond: condition to test until it evaluates to true
diff --git a/arch/arm/mach-omap2/include/mach/barriers.h b/arch/arm/mach-omap2/include/mach/barriers.h
deleted file mode 100644
index 1c582a8592b9..000000000000
--- a/arch/arm/mach-omap2/include/mach/barriers.h
+++ /dev/null
@@ -1,33 +0,0 @@
-/*
- * OMAP memory barrier header.
- *
- * Copyright (C) 2011 Texas Instruments, Inc.
- *  Santosh Shilimkar <santosh.shilimkar@ti.com>
- *  Richard Woodruff <r-woodruff2@ti.com>
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License version 2 as
- * published by the Free Software Foundation.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
- */
-
-#ifndef __MACH_BARRIERS_H
-#define __MACH_BARRIERS_H
-
-#include <asm/outercache.h>
-
-extern void omap_bus_sync(void);
-
-#define rmb()		dsb()
-#define wmb()		do { dsb(); outer_sync(); omap_bus_sync(); } while (0)
-#define mb()		wmb()
-
-#endif	/* __MACH_BARRIERS_H */
diff --git a/arch/arm/mach-omap2/omap-secure.h b/arch/arm/mach-omap2/omap-secure.h
index dec2b05d184b..af2851fbcdf0 100644
--- a/arch/arm/mach-omap2/omap-secure.h
+++ b/arch/arm/mach-omap2/omap-secure.h
@@ -70,13 +70,6 @@ extern u32 rx51_secure_dispatcher(u32 idx, u32 process, u32 flag, u32 nargs,
 extern u32 rx51_secure_update_aux_cr(u32 set_bits, u32 clear_bits);
 extern u32 rx51_secure_rng_call(u32 ptr, u32 count, u32 flag);
 
-#ifdef CONFIG_OMAP4_ERRATA_I688
-extern int omap_barrier_reserve_memblock(void);
-#else
-static inline void omap_barrier_reserve_memblock(void)
-{ }
-#endif
-
 #ifdef CONFIG_SOC_HAS_REALTIME_COUNTER
 void set_cntfreq(void);
 #else
diff --git a/arch/arm/mach-omap2/omap4-common.c b/arch/arm/mach-omap2/omap4-common.c
index 7bb116a6f86f..9c7aac616938 100644
--- a/arch/arm/mach-omap2/omap4-common.c
+++ b/arch/arm/mach-omap2/omap4-common.c
@@ -51,16 +51,73 @@ static void __iomem *twd_base;
 
 #define IRQ_LOCALTIMER		29
 
-#ifdef CONFIG_OMAP4_ERRATA_I688
+#ifdef CONFIG_OMAP_INTERCONNECT_BARRIER
+
 /* Used to implement memory barrier on DRAM path */
 #define OMAP4_DRAM_BARRIER_VA			0xfe600000
 
-void __iomem *dram_sync, *sram_sync;
+static void __iomem *dram_sync, *sram_sync;
+static phys_addr_t dram_sync_paddr;
+static u32 dram_sync_size;
+
+/*
+ * The OMAP4 bus structure contains asynchrnous bridges which can buffer
+ * data writes from the MPU. These asynchronous bridges can be found on
+ * paths between the MPU to EMIF, and the MPU to L3 interconnects.
+ *
+ * We need to be careful about re-ordering which can happen as a result
+ * of different accesses being performed via different paths, and
+ * therefore different asynchronous bridges.
+ */
 
-static phys_addr_t paddr;
-static u32 size;
+/*
+ * OMAP4 interconnect barrier which is called for each mb() and wmb().
+ * This is to ensure that normal paths to DRAM (normal memory, cacheable
+ * accesses) are properly synchronised with writes to DMA coherent memory
+ * (normal memory, uncacheable) and device writes.
+ *
+ * The mb() and wmb() barriers only operate only on the MPU->MA->EMIF
+ * path, as we need to ensure that data is visible to other system
+ * masters prior to writes to those system masters being seen.
+ *
+ * Note: the SRAM path is not synchronised via mb() and wmb().
+ */
+static void omap4_mb(void)
+{
+	if (dram_sync)
+		writel_relaxed(0, dram_sync);
+}
 
-void omap_bus_sync(void)
+/*
+ * OMAP4 Errata i688 - asynchronous bridge corruption when entering WFI.
+ *
+ * If a data is stalled inside asynchronous bridge because of back
+ * pressure, it may be accepted multiple times, creating pointer
+ * misalignment that will corrupt next transfers on that data path until
+ * next reset of the system. No recovery procedure once the issue is hit,
+ * the path remains consistently broken.
+ *
+ * Async bridges can be found on paths between MPU to EMIF and MPU to L3
+ * interconnects.
+ *
+ * This situation can happen only when the idle is initiated by a Master
+ * Request Disconnection (which is trigged by software when executing WFI
+ * on the CPU).
+ *
+ * The work-around for this errata needs all the initiators connected
+ * through an async bridge to ensure that data path is properly drained
+ * before issuing WFI. This condition will be met if one Strongly ordered
+ * access is performed to the target right before executing the WFI.
+ *
+ * In MPU case, L3 T2ASYNC FIFO and DDR T2ASYNC FIFO needs to be drained.
+ * IO barrier ensure that there is no synchronisation loss on initiators
+ * operating on both interconnect port simultaneously.
+ *
+ * This is a stronger version of the OMAP4 memory barrier below, and
+ * operates on both the MPU->MA->EMIF path but also the MPU->OCP path
+ * as well, and is necessary prior to executing a WFI.
+ */
+void omap_interconnect_sync(void)
 {
 	if (dram_sync && sram_sync) {
 		writel_relaxed(readl_relaxed(dram_sync), dram_sync);
@@ -68,7 +125,6 @@ void omap_bus_sync(void)
 		isb();
 	}
 }
-EXPORT_SYMBOL(omap_bus_sync);
 
 static int __init omap4_sram_init(void)
 {
@@ -91,13 +147,10 @@ static int __init omap4_sram_init(void)
 omap_arch_initcall(omap4_sram_init);
 
 /* Steal one page physical memory for barrier implementation */
-int __init omap_barrier_reserve_memblock(void)
+void __init omap_barrier_reserve_memblock(void)
 {
-
-	size = ALIGN(PAGE_SIZE, SZ_1M);
-	paddr = arm_memblock_steal(size, SZ_1M);
-
-	return 0;
+	dram_sync_size = ALIGN(PAGE_SIZE, SZ_1M);
+	dram_sync_paddr = arm_memblock_steal(dram_sync_size, SZ_1M);
 }
 
 void __init omap_barriers_init(void)
@@ -105,19 +158,18 @@ void __init omap_barriers_init(void)
 	struct map_desc dram_io_desc[1];
 
 	dram_io_desc[0].virtual = OMAP4_DRAM_BARRIER_VA;
-	dram_io_desc[0].pfn = __phys_to_pfn(paddr);
-	dram_io_desc[0].length = size;
+	dram_io_desc[0].pfn = __phys_to_pfn(dram_sync_paddr);
+	dram_io_desc[0].length = dram_sync_size;
 	dram_io_desc[0].type = MT_MEMORY_RW_SO;
 	iotable_init(dram_io_desc, ARRAY_SIZE(dram_io_desc));
 	dram_sync = (void __iomem *) dram_io_desc[0].virtual;
 
-	pr_info("OMAP4: Map 0x%08llx to 0x%08lx for dram barrier\n",
-		(long long) paddr, dram_io_desc[0].virtual);
+	pr_info("OMAP4: Map %pa to %p for dram barrier\n",
+		&dram_sync_paddr, dram_sync);
 
+	soc_mb = omap4_mb;
 }
-#else
-void __init omap_barriers_init(void)
-{}
+
 #endif
 
 void gic_dist_disable(void)
diff --git a/arch/arm/mach-omap2/sleep44xx.S b/arch/arm/mach-omap2/sleep44xx.S
index b84a0122d823..9b09d85d811a 100644
--- a/arch/arm/mach-omap2/sleep44xx.S
+++ b/arch/arm/mach-omap2/sleep44xx.S
@@ -333,16 +333,12 @@ ENDPROC(omap4_cpu_resume)
 
 #endif	/* defined(CONFIG_SMP) && defined(CONFIG_PM) */
 
-#ifndef CONFIG_OMAP4_ERRATA_I688
-ENTRY(omap_bus_sync)
-	ret	lr
-ENDPROC(omap_bus_sync)
-#endif
-
 ENTRY(omap_do_wfi)
 	stmfd	sp!, {lr}
+#ifdef CONFIG_OMAP_INTERCONNECT_BARRIER
 	/* Drain interconnect write buffers. */
-	bl omap_bus_sync
+	bl	omap_interconnect_sync
+#endif
 
 	/*
 	 * Execute an ISB instruction to ensure that all of the
-- 
2.1.0

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

* [PATCH 4/4] ARM: omap2: restore OMAP4 barrier behaviour
@ 2015-07-15 17:47   ` Russell King
  0 siblings, 0 replies; 22+ messages in thread
From: Russell King @ 2015-07-15 17:47 UTC (permalink / raw)
  To: linux-arm-kernel

Restore the OMAP4 barrier behaviour using the new implementation which
allows multiplatform systems to hook into the mb() and wmb() ARM
implementations to perform any necessary additional barrier maintanence.

Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
---
 arch/arm/mach-omap2/Kconfig                 | 28 +++------
 arch/arm/mach-omap2/common.h                | 12 +++-
 arch/arm/mach-omap2/include/mach/barriers.h | 33 -----------
 arch/arm/mach-omap2/omap-secure.h           |  7 ---
 arch/arm/mach-omap2/omap4-common.c          | 90 +++++++++++++++++++++++------
 arch/arm/mach-omap2/sleep44xx.S             | 10 +---
 6 files changed, 90 insertions(+), 90 deletions(-)
 delete mode 100644 arch/arm/mach-omap2/include/mach/barriers.h

diff --git a/arch/arm/mach-omap2/Kconfig b/arch/arm/mach-omap2/Kconfig
index 2128441430ad..8427997e09c4 100644
--- a/arch/arm/mach-omap2/Kconfig
+++ b/arch/arm/mach-omap2/Kconfig
@@ -29,6 +29,7 @@ config ARCH_OMAP4
 	select HAVE_ARM_SCU if SMP
 	select HAVE_ARM_TWD if SMP
 	select OMAP_INTERCONNECT
+	select OMAP_INTERCONNECT_BARRIER
 	select PL310_ERRATA_588369 if CACHE_L2X0
 	select PL310_ERRATA_727915 if CACHE_L2X0
 	select PM_OPP if PM
@@ -46,6 +47,7 @@ config SOC_OMAP5
 	select HAVE_ARM_TWD if SMP
 	select HAVE_ARM_ARCH_TIMER
 	select ARM_ERRATA_798181 if SMP
+	select OMAP_INTERCONNECT_BARRIER
 
 config SOC_AM33XX
 	bool "TI AM33XX"
@@ -70,6 +72,7 @@ config SOC_DRA7XX
 	select HAVE_ARM_ARCH_TIMER
 	select IRQ_CROSSBAR
 	select ARM_ERRATA_798181 if SMP
+	select OMAP_INTERCONNECT_BARRIER
 
 config ARCH_OMAP2PLUS
 	bool
@@ -91,6 +94,10 @@ config ARCH_OMAP2PLUS
 	help
 	  Systems based on OMAP2, OMAP3, OMAP4 or OMAP5
 
+config OMAP_INTERCONNECT_BARRIER
+	bool
+	select ARM_HEAVY_MB
+	
 
 if ARCH_OMAP2PLUS
 
@@ -240,27 +247,6 @@ config OMAP3_SDRC_AC_TIMING
 	  wish to say no.  Selecting yes without understanding what is
 	  going on could result in system crashes;
 
-config OMAP4_ERRATA_I688
-	bool "OMAP4 errata: Async Bridge Corruption"
-	depends on (ARCH_OMAP4 || SOC_OMAP5) && !ARCH_MULTIPLATFORM
-	select ARCH_HAS_BARRIERS
-	help
-	  If a data is stalled inside asynchronous bridge because of back
-	  pressure, it may be accepted multiple times, creating pointer
-	  misalignment that will corrupt next transfers on that data path
-	  until next reset of the system (No recovery procedure once the
-	  issue is hit, the path remains consistently broken). Async bridge
-	  can be found on path between MPU to EMIF and MPU to L3 interconnect.
-	  This situation can happen only when the idle is initiated by a
-	  Master Request Disconnection (which is trigged by software when
-	  executing WFI on CPU).
-	  The work-around for this errata needs all the initiators connected
-	  through async bridge must ensure that data path is properly drained
-	  before issuing WFI. This condition will be met if one Strongly ordered
-	  access is performed to the target right before executing the WFI.
-	  In MPU case, L3 T2ASYNC FIFO and DDR T2ASYNC FIFO needs to be drained.
-	  IO barrier ensure that there is no synchronisation loss on initiators
-	  operating on both interconnect port simultaneously.
 endmenu
 
 endif
diff --git a/arch/arm/mach-omap2/common.h b/arch/arm/mach-omap2/common.h
index 46e24581d624..82f88b4ec15f 100644
--- a/arch/arm/mach-omap2/common.h
+++ b/arch/arm/mach-omap2/common.h
@@ -189,6 +189,15 @@ static inline void omap44xx_restart(enum reboot_mode mode, const char *cmd)
 }
 #endif
 
+#ifdef CONFIG_OMAP_INTERCONNECT_BARRIER
+void omap_barrier_reserve_memblock(void);
+void omap_barriers_init(void);
+#else
+static inline void omap_barrier_reserve_memblock(void)
+{
+}
+#endif
+
 /* This gets called from mach-omap2/io.c, do not call this */
 void __init omap2_set_globals_tap(u32 class, void __iomem *tap);
 
@@ -200,9 +209,6 @@ void __init omap4_map_io(void);
 void __init omap5_map_io(void);
 void __init ti81xx_map_io(void);
 
-/* omap_barriers_init() is OMAP4 only */
-void omap_barriers_init(void);
-
 /**
  * omap_test_timeout - busy-loop, testing a condition
  * @cond: condition to test until it evaluates to true
diff --git a/arch/arm/mach-omap2/include/mach/barriers.h b/arch/arm/mach-omap2/include/mach/barriers.h
deleted file mode 100644
index 1c582a8592b9..000000000000
--- a/arch/arm/mach-omap2/include/mach/barriers.h
+++ /dev/null
@@ -1,33 +0,0 @@
-/*
- * OMAP memory barrier header.
- *
- * Copyright (C) 2011 Texas Instruments, Inc.
- *  Santosh Shilimkar <santosh.shilimkar@ti.com>
- *  Richard Woodruff <r-woodruff2@ti.com>
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License version 2 as
- * published by the Free Software Foundation.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
- */
-
-#ifndef __MACH_BARRIERS_H
-#define __MACH_BARRIERS_H
-
-#include <asm/outercache.h>
-
-extern void omap_bus_sync(void);
-
-#define rmb()		dsb()
-#define wmb()		do { dsb(); outer_sync(); omap_bus_sync(); } while (0)
-#define mb()		wmb()
-
-#endif	/* __MACH_BARRIERS_H */
diff --git a/arch/arm/mach-omap2/omap-secure.h b/arch/arm/mach-omap2/omap-secure.h
index dec2b05d184b..af2851fbcdf0 100644
--- a/arch/arm/mach-omap2/omap-secure.h
+++ b/arch/arm/mach-omap2/omap-secure.h
@@ -70,13 +70,6 @@ extern u32 rx51_secure_dispatcher(u32 idx, u32 process, u32 flag, u32 nargs,
 extern u32 rx51_secure_update_aux_cr(u32 set_bits, u32 clear_bits);
 extern u32 rx51_secure_rng_call(u32 ptr, u32 count, u32 flag);
 
-#ifdef CONFIG_OMAP4_ERRATA_I688
-extern int omap_barrier_reserve_memblock(void);
-#else
-static inline void omap_barrier_reserve_memblock(void)
-{ }
-#endif
-
 #ifdef CONFIG_SOC_HAS_REALTIME_COUNTER
 void set_cntfreq(void);
 #else
diff --git a/arch/arm/mach-omap2/omap4-common.c b/arch/arm/mach-omap2/omap4-common.c
index 7bb116a6f86f..9c7aac616938 100644
--- a/arch/arm/mach-omap2/omap4-common.c
+++ b/arch/arm/mach-omap2/omap4-common.c
@@ -51,16 +51,73 @@ static void __iomem *twd_base;
 
 #define IRQ_LOCALTIMER		29
 
-#ifdef CONFIG_OMAP4_ERRATA_I688
+#ifdef CONFIG_OMAP_INTERCONNECT_BARRIER
+
 /* Used to implement memory barrier on DRAM path */
 #define OMAP4_DRAM_BARRIER_VA			0xfe600000
 
-void __iomem *dram_sync, *sram_sync;
+static void __iomem *dram_sync, *sram_sync;
+static phys_addr_t dram_sync_paddr;
+static u32 dram_sync_size;
+
+/*
+ * The OMAP4 bus structure contains asynchrnous bridges which can buffer
+ * data writes from the MPU. These asynchronous bridges can be found on
+ * paths between the MPU to EMIF, and the MPU to L3 interconnects.
+ *
+ * We need to be careful about re-ordering which can happen as a result
+ * of different accesses being performed via different paths, and
+ * therefore different asynchronous bridges.
+ */
 
-static phys_addr_t paddr;
-static u32 size;
+/*
+ * OMAP4 interconnect barrier which is called for each mb() and wmb().
+ * This is to ensure that normal paths to DRAM (normal memory, cacheable
+ * accesses) are properly synchronised with writes to DMA coherent memory
+ * (normal memory, uncacheable) and device writes.
+ *
+ * The mb() and wmb() barriers only operate only on the MPU->MA->EMIF
+ * path, as we need to ensure that data is visible to other system
+ * masters prior to writes to those system masters being seen.
+ *
+ * Note: the SRAM path is not synchronised via mb() and wmb().
+ */
+static void omap4_mb(void)
+{
+	if (dram_sync)
+		writel_relaxed(0, dram_sync);
+}
 
-void omap_bus_sync(void)
+/*
+ * OMAP4 Errata i688 - asynchronous bridge corruption when entering WFI.
+ *
+ * If a data is stalled inside asynchronous bridge because of back
+ * pressure, it may be accepted multiple times, creating pointer
+ * misalignment that will corrupt next transfers on that data path until
+ * next reset of the system. No recovery procedure once the issue is hit,
+ * the path remains consistently broken.
+ *
+ * Async bridges can be found on paths between MPU to EMIF and MPU to L3
+ * interconnects.
+ *
+ * This situation can happen only when the idle is initiated by a Master
+ * Request Disconnection (which is trigged by software when executing WFI
+ * on the CPU).
+ *
+ * The work-around for this errata needs all the initiators connected
+ * through an async bridge to ensure that data path is properly drained
+ * before issuing WFI. This condition will be met if one Strongly ordered
+ * access is performed to the target right before executing the WFI.
+ *
+ * In MPU case, L3 T2ASYNC FIFO and DDR T2ASYNC FIFO needs to be drained.
+ * IO barrier ensure that there is no synchronisation loss on initiators
+ * operating on both interconnect port simultaneously.
+ *
+ * This is a stronger version of the OMAP4 memory barrier below, and
+ * operates on both the MPU->MA->EMIF path but also the MPU->OCP path
+ * as well, and is necessary prior to executing a WFI.
+ */
+void omap_interconnect_sync(void)
 {
 	if (dram_sync && sram_sync) {
 		writel_relaxed(readl_relaxed(dram_sync), dram_sync);
@@ -68,7 +125,6 @@ void omap_bus_sync(void)
 		isb();
 	}
 }
-EXPORT_SYMBOL(omap_bus_sync);
 
 static int __init omap4_sram_init(void)
 {
@@ -91,13 +147,10 @@ static int __init omap4_sram_init(void)
 omap_arch_initcall(omap4_sram_init);
 
 /* Steal one page physical memory for barrier implementation */
-int __init omap_barrier_reserve_memblock(void)
+void __init omap_barrier_reserve_memblock(void)
 {
-
-	size = ALIGN(PAGE_SIZE, SZ_1M);
-	paddr = arm_memblock_steal(size, SZ_1M);
-
-	return 0;
+	dram_sync_size = ALIGN(PAGE_SIZE, SZ_1M);
+	dram_sync_paddr = arm_memblock_steal(dram_sync_size, SZ_1M);
 }
 
 void __init omap_barriers_init(void)
@@ -105,19 +158,18 @@ void __init omap_barriers_init(void)
 	struct map_desc dram_io_desc[1];
 
 	dram_io_desc[0].virtual = OMAP4_DRAM_BARRIER_VA;
-	dram_io_desc[0].pfn = __phys_to_pfn(paddr);
-	dram_io_desc[0].length = size;
+	dram_io_desc[0].pfn = __phys_to_pfn(dram_sync_paddr);
+	dram_io_desc[0].length = dram_sync_size;
 	dram_io_desc[0].type = MT_MEMORY_RW_SO;
 	iotable_init(dram_io_desc, ARRAY_SIZE(dram_io_desc));
 	dram_sync = (void __iomem *) dram_io_desc[0].virtual;
 
-	pr_info("OMAP4: Map 0x%08llx to 0x%08lx for dram barrier\n",
-		(long long) paddr, dram_io_desc[0].virtual);
+	pr_info("OMAP4: Map %pa to %p for dram barrier\n",
+		&dram_sync_paddr, dram_sync);
 
+	soc_mb = omap4_mb;
 }
-#else
-void __init omap_barriers_init(void)
-{}
+
 #endif
 
 void gic_dist_disable(void)
diff --git a/arch/arm/mach-omap2/sleep44xx.S b/arch/arm/mach-omap2/sleep44xx.S
index b84a0122d823..9b09d85d811a 100644
--- a/arch/arm/mach-omap2/sleep44xx.S
+++ b/arch/arm/mach-omap2/sleep44xx.S
@@ -333,16 +333,12 @@ ENDPROC(omap4_cpu_resume)
 
 #endif	/* defined(CONFIG_SMP) && defined(CONFIG_PM) */
 
-#ifndef CONFIG_OMAP4_ERRATA_I688
-ENTRY(omap_bus_sync)
-	ret	lr
-ENDPROC(omap_bus_sync)
-#endif
-
 ENTRY(omap_do_wfi)
 	stmfd	sp!, {lr}
+#ifdef CONFIG_OMAP_INTERCONNECT_BARRIER
 	/* Drain interconnect write buffers. */
-	bl omap_bus_sync
+	bl	omap_interconnect_sync
+#endif
 
 	/*
 	 * Execute an ISB instruction to ensure that all of the
-- 
2.1.0

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

* Re: [PATCH 4/4] ARM: omap2: restore OMAP4 barrier behaviour
  2015-07-15 17:47   ` Russell King
@ 2015-07-16  6:48     ` Tony Lindgren
  -1 siblings, 0 replies; 22+ messages in thread
From: Tony Lindgren @ 2015-07-16  6:48 UTC (permalink / raw)
  To: Russell King; +Cc: linux-omap, Will Deacon, linux-arm-kernel

Hi,

* Russell King <rmk+kernel@arm.linux.org.uk> [150715 10:50]:
> Restore the OMAP4 barrier behaviour using the new implementation which
> allows multiplatform systems to hook into the mb() and wmb() ARM
> implementations to perform any necessary additional barrier maintanence.

I'm getthing this with omap2plus_defconfig with the last patch
applied:

arch/arm/mach-omap2/omap4-common.c: In function ‘omap4_sram_init’:
arch/arm/mach-omap2/omap4-common.c:138:14: error: implicit declaration of function ‘of_get_named_gen_pool’ [-Werror=implicit-function-declaration]
  sram_pool = of_get_named_gen_pool(np, "sram", 0);
              ^
arch/arm/mach-omap2/omap4-common.c:138:12: warning: assignment makes pointer from integer without a cast [-Wint-conversion]
  sram_pool = of_get_named_gen_pool(np, "sram", 0);
            ^
Regards,

Tony

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

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

* [PATCH 4/4] ARM: omap2: restore OMAP4 barrier behaviour
@ 2015-07-16  6:48     ` Tony Lindgren
  0 siblings, 0 replies; 22+ messages in thread
From: Tony Lindgren @ 2015-07-16  6:48 UTC (permalink / raw)
  To: linux-arm-kernel

Hi,

* Russell King <rmk+kernel@arm.linux.org.uk> [150715 10:50]:
> Restore the OMAP4 barrier behaviour using the new implementation which
> allows multiplatform systems to hook into the mb() and wmb() ARM
> implementations to perform any necessary additional barrier maintanence.

I'm getthing this with omap2plus_defconfig with the last patch
applied:

arch/arm/mach-omap2/omap4-common.c: In function ?omap4_sram_init?:
arch/arm/mach-omap2/omap4-common.c:138:14: error: implicit declaration of function ?of_get_named_gen_pool? [-Werror=implicit-function-declaration]
  sram_pool = of_get_named_gen_pool(np, "sram", 0);
              ^
arch/arm/mach-omap2/omap4-common.c:138:12: warning: assignment makes pointer from integer without a cast [-Wint-conversion]
  sram_pool = of_get_named_gen_pool(np, "sram", 0);
            ^
Regards,

Tony

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

* Re: [PATCH 4/4] ARM: omap2: restore OMAP4 barrier behaviour
  2015-07-16  6:48     ` Tony Lindgren
@ 2015-07-16 13:54       ` Russell King - ARM Linux
  -1 siblings, 0 replies; 22+ messages in thread
From: Russell King - ARM Linux @ 2015-07-16 13:54 UTC (permalink / raw)
  To: Tony Lindgren; +Cc: linux-omap, Will Deacon, linux-arm-kernel

On Wed, Jul 15, 2015 at 11:48:54PM -0700, Tony Lindgren wrote:
> Hi,
> 
> * Russell King <rmk+kernel@arm.linux.org.uk> [150715 10:50]:
> > Restore the OMAP4 barrier behaviour using the new implementation which
> > allows multiplatform systems to hook into the mb() and wmb() ARM
> > implementations to perform any necessary additional barrier maintanence.
> 
> I'm getthing this with omap2plus_defconfig with the last patch
> applied:
> 
> arch/arm/mach-omap2/omap4-common.c: In function ‘omap4_sram_init’:
> arch/arm/mach-omap2/omap4-common.c:138:14: error: implicit declaration of function ‘of_get_named_gen_pool’ [-Werror=implicit-function-declaration]
>   sram_pool = of_get_named_gen_pool(np, "sram", 0);
>               ^
> arch/arm/mach-omap2/omap4-common.c:138:12: warning: assignment makes pointer from integer without a cast [-Wint-conversion]
>   sram_pool = of_get_named_gen_pool(np, "sram", 0);
>             ^

I'd forgotten to merge in the merge window fixes for this... which have now
been lost.  This needs to become of_gen_pool_get() in 4.2-rc1 and later.

-- 
FTTC broadband for 0.8mile line: currently at 10.5Mbps down 400kbps up
according to speedtest.net.

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

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

* [PATCH 4/4] ARM: omap2: restore OMAP4 barrier behaviour
@ 2015-07-16 13:54       ` Russell King - ARM Linux
  0 siblings, 0 replies; 22+ messages in thread
From: Russell King - ARM Linux @ 2015-07-16 13:54 UTC (permalink / raw)
  To: linux-arm-kernel

On Wed, Jul 15, 2015 at 11:48:54PM -0700, Tony Lindgren wrote:
> Hi,
> 
> * Russell King <rmk+kernel@arm.linux.org.uk> [150715 10:50]:
> > Restore the OMAP4 barrier behaviour using the new implementation which
> > allows multiplatform systems to hook into the mb() and wmb() ARM
> > implementations to perform any necessary additional barrier maintanence.
> 
> I'm getthing this with omap2plus_defconfig with the last patch
> applied:
> 
> arch/arm/mach-omap2/omap4-common.c: In function ?omap4_sram_init?:
> arch/arm/mach-omap2/omap4-common.c:138:14: error: implicit declaration of function ?of_get_named_gen_pool? [-Werror=implicit-function-declaration]
>   sram_pool = of_get_named_gen_pool(np, "sram", 0);
>               ^
> arch/arm/mach-omap2/omap4-common.c:138:12: warning: assignment makes pointer from integer without a cast [-Wint-conversion]
>   sram_pool = of_get_named_gen_pool(np, "sram", 0);
>             ^

I'd forgotten to merge in the merge window fixes for this... which have now
been lost.  This needs to become of_gen_pool_get() in 4.2-rc1 and later.

-- 
FTTC broadband for 0.8mile line: currently at 10.5Mbps down 400kbps up
according to speedtest.net.

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

* Re: [PATCH 4/4] ARM: omap2: restore OMAP4 barrier behaviour
  2015-07-16 13:54       ` Russell King - ARM Linux
@ 2015-07-17  5:48         ` Tony Lindgren
  -1 siblings, 0 replies; 22+ messages in thread
From: Tony Lindgren @ 2015-07-17  5:48 UTC (permalink / raw)
  To: Russell King - ARM Linux; +Cc: linux-omap, Will Deacon, linux-arm-kernel

* Russell King - ARM Linux <linux@arm.linux.org.uk> [150716 06:56]:
> On Wed, Jul 15, 2015 at 11:48:54PM -0700, Tony Lindgren wrote:
> > Hi,
> > 
> > * Russell King <rmk+kernel@arm.linux.org.uk> [150715 10:50]:
> > > Restore the OMAP4 barrier behaviour using the new implementation which
> > > allows multiplatform systems to hook into the mb() and wmb() ARM
> > > implementations to perform any necessary additional barrier maintanence.
> > 
> > I'm getthing this with omap2plus_defconfig with the last patch
> > applied:
> > 
> > arch/arm/mach-omap2/omap4-common.c: In function ‘omap4_sram_init’:
> > arch/arm/mach-omap2/omap4-common.c:138:14: error: implicit declaration of function ‘of_get_named_gen_pool’ [-Werror=implicit-function-declaration]
> >   sram_pool = of_get_named_gen_pool(np, "sram", 0);
> >               ^
> > arch/arm/mach-omap2/omap4-common.c:138:12: warning: assignment makes pointer from integer without a cast [-Wint-conversion]
> >   sram_pool = of_get_named_gen_pool(np, "sram", 0);
> >             ^
> 
> I'd forgotten to merge in the merge window fixes for this... which have now
> been lost.  This needs to become of_gen_pool_get() in 4.2-rc1 and later.

OK with that change looks good to me, so please feel free to
add for the whole series:

Acked-by: Tony Lindgren <tony@atomide.com>

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

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

* [PATCH 4/4] ARM: omap2: restore OMAP4 barrier behaviour
@ 2015-07-17  5:48         ` Tony Lindgren
  0 siblings, 0 replies; 22+ messages in thread
From: Tony Lindgren @ 2015-07-17  5:48 UTC (permalink / raw)
  To: linux-arm-kernel

* Russell King - ARM Linux <linux@arm.linux.org.uk> [150716 06:56]:
> On Wed, Jul 15, 2015 at 11:48:54PM -0700, Tony Lindgren wrote:
> > Hi,
> > 
> > * Russell King <rmk+kernel@arm.linux.org.uk> [150715 10:50]:
> > > Restore the OMAP4 barrier behaviour using the new implementation which
> > > allows multiplatform systems to hook into the mb() and wmb() ARM
> > > implementations to perform any necessary additional barrier maintanence.
> > 
> > I'm getthing this with omap2plus_defconfig with the last patch
> > applied:
> > 
> > arch/arm/mach-omap2/omap4-common.c: In function ?omap4_sram_init?:
> > arch/arm/mach-omap2/omap4-common.c:138:14: error: implicit declaration of function ?of_get_named_gen_pool? [-Werror=implicit-function-declaration]
> >   sram_pool = of_get_named_gen_pool(np, "sram", 0);
> >               ^
> > arch/arm/mach-omap2/omap4-common.c:138:12: warning: assignment makes pointer from integer without a cast [-Wint-conversion]
> >   sram_pool = of_get_named_gen_pool(np, "sram", 0);
> >             ^
> 
> I'd forgotten to merge in the merge window fixes for this... which have now
> been lost.  This needs to become of_gen_pool_get() in 4.2-rc1 and later.

OK with that change looks good to me, so please feel free to
add for the whole series:

Acked-by: Tony Lindgren <tony@atomide.com>

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

* RE: [PATCH 3/4] Revert "ARM: OMAP4: remove dead kconfig option OMAP4_ERRATA_I688"
  2015-07-15 17:47   ` Russell King
@ 2015-07-22 20:13     ` Woodruff, Richard
  -1 siblings, 0 replies; 22+ messages in thread
From: Woodruff, Richard @ 2015-07-22 20:13 UTC (permalink / raw)
  To: Russell King, linux-arm-kernel, linux-omap; +Cc: Tony Lindgren, Will Deacon

> From: linux-arm-kernel [mailto:linux-arm-kernel-
> bounces@lists.infradead.org] On Behalf Of Russell King
> Sent: Wednesday, July 15, 2015 12:47 PM

> This reverts commit 606da4826b89b044b51e3a84958b802204cfe4c7.
> 
> We actually need this code for proper behaviour of OMAP4, and it needs
> fixing a different way other than just removing the code.  Disabling code
> which is necessary in the hopes of persuing multiplatform kernels is a stupid
> approach.
> 
> Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>

The series looks good.  It improves code generation and fixes race issues which have been see production devices running Linux.

Acked-by: Richard Woodruff <r-woodruff2@ti.com>

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

* [PATCH 3/4] Revert "ARM: OMAP4: remove dead kconfig option OMAP4_ERRATA_I688"
@ 2015-07-22 20:13     ` Woodruff, Richard
  0 siblings, 0 replies; 22+ messages in thread
From: Woodruff, Richard @ 2015-07-22 20:13 UTC (permalink / raw)
  To: linux-arm-kernel

> From: linux-arm-kernel [mailto:linux-arm-kernel-
> bounces at lists.infradead.org] On Behalf Of Russell King
> Sent: Wednesday, July 15, 2015 12:47 PM

> This reverts commit 606da4826b89b044b51e3a84958b802204cfe4c7.
> 
> We actually need this code for proper behaviour of OMAP4, and it needs
> fixing a different way other than just removing the code.  Disabling code
> which is necessary in the hopes of persuing multiplatform kernels is a stupid
> approach.
> 
> Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>

The series looks good.  It improves code generation and fixes race issues which have been see production devices running Linux.

Acked-by: Richard Woodruff <r-woodruff2@ti.com>

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

* Re: [PATCH 4/4] ARM: omap2: restore OMAP4 barrier behaviour
  2015-07-15 17:47   ` Russell King
@ 2015-07-27 21:23     ` Dan Murphy
  -1 siblings, 0 replies; 22+ messages in thread
From: Dan Murphy @ 2015-07-27 21:23 UTC (permalink / raw)
  To: Russell King, linux-arm-kernel, linux-omap; +Cc: Tony Lindgren, Will Deacon

Russell

On 07/15/2015 12:47 PM, Russell King wrote:
> Restore the OMAP4 barrier behaviour using the new implementation which
> allows multiplatform systems to hook into the mb() and wmb() ARM
> implementations to perform any necessary additional barrier maintanence.
>
> Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
> ---
>  arch/arm/mach-omap2/Kconfig                 | 28 +++------
>  arch/arm/mach-omap2/common.h                | 12 +++-
>  arch/arm/mach-omap2/include/mach/barriers.h | 33 -----------
>  arch/arm/mach-omap2/omap-secure.h           |  7 ---
>  arch/arm/mach-omap2/omap4-common.c          | 90 +++++++++++++++++++++++------
>  arch/arm/mach-omap2/sleep44xx.S             | 10 +---
>  6 files changed, 90 insertions(+), 90 deletions(-)
>  delete mode 100644 arch/arm/mach-omap2/include/mach/barriers.h
>
> diff --git a/arch/arm/mach-omap2/Kconfig b/arch/arm/mach-omap2/Kconfig
> index 2128441430ad..8427997e09c4 100644
> --- a/arch/arm/mach-omap2/Kconfig
> +++ b/arch/arm/mach-omap2/Kconfig
> @@ -29,6 +29,7 @@ config ARCH_OMAP4
>  	select HAVE_ARM_SCU if SMP
>  	select HAVE_ARM_TWD if SMP
>  	select OMAP_INTERCONNECT
> +	select OMAP_INTERCONNECT_BARRIER
>  	select PL310_ERRATA_588369 if CACHE_L2X0
>  	select PL310_ERRATA_727915 if CACHE_L2X0
>  	select PM_OPP if PM
> @@ -46,6 +47,7 @@ config SOC_OMAP5
>  	select HAVE_ARM_TWD if SMP
>  	select HAVE_ARM_ARCH_TIMER
>  	select ARM_ERRATA_798181 if SMP
> +	select OMAP_INTERCONNECT_BARRIER
>  
>  config SOC_AM33XX
>  	bool "TI AM33XX"
> @@ -70,6 +72,7 @@ config SOC_DRA7XX
>  	select HAVE_ARM_ARCH_TIMER
>  	select IRQ_CROSSBAR
>  	select ARM_ERRATA_798181 if SMP
> +	select OMAP_INTERCONNECT_BARRIER
>  
>  config ARCH_OMAP2PLUS
>  	bool
> @@ -91,6 +94,10 @@ config ARCH_OMAP2PLUS
>  	help
>  	  Systems based on OMAP2, OMAP3, OMAP4 or OMAP5
>  
> +config OMAP_INTERCONNECT_BARRIER
> +	bool
> +	select ARM_HEAVY_MB
> +	
>  
>  if ARCH_OMAP2PLUS
>  
> @@ -240,27 +247,6 @@ config OMAP3_SDRC_AC_TIMING
>  	  wish to say no.  Selecting yes without understanding what is
>  	  going on could result in system crashes;
>  
> -config OMAP4_ERRATA_I688
> -	bool "OMAP4 errata: Async Bridge Corruption"
> -	depends on (ARCH_OMAP4 || SOC_OMAP5) && !ARCH_MULTIPLATFORM
> -	select ARCH_HAS_BARRIERS
> -	help
> -	  If a data is stalled inside asynchronous bridge because of back
> -	  pressure, it may be accepted multiple times, creating pointer
> -	  misalignment that will corrupt next transfers on that data path
> -	  until next reset of the system (No recovery procedure once the
> -	  issue is hit, the path remains consistently broken). Async bridge
> -	  can be found on path between MPU to EMIF and MPU to L3 interconnect.
> -	  This situation can happen only when the idle is initiated by a
> -	  Master Request Disconnection (which is trigged by software when
> -	  executing WFI on CPU).
> -	  The work-around for this errata needs all the initiators connected
> -	  through async bridge must ensure that data path is properly drained
> -	  before issuing WFI. This condition will be met if one Strongly ordered
> -	  access is performed to the target right before executing the WFI.
> -	  In MPU case, L3 T2ASYNC FIFO and DDR T2ASYNC FIFO needs to be drained.
> -	  IO barrier ensure that there is no synchronisation loss on initiators
> -	  operating on both interconnect port simultaneously.
>  endmenu
>  
>  endif
> diff --git a/arch/arm/mach-omap2/common.h b/arch/arm/mach-omap2/common.h
> index 46e24581d624..82f88b4ec15f 100644
> --- a/arch/arm/mach-omap2/common.h
> +++ b/arch/arm/mach-omap2/common.h
> @@ -189,6 +189,15 @@ static inline void omap44xx_restart(enum reboot_mode mode, const char *cmd)
>  }
>  #endif
>  
> +#ifdef CONFIG_OMAP_INTERCONNECT_BARRIER
> +void omap_barrier_reserve_memblock(void);
> +void omap_barriers_init(void);
> +#else
> +static inline void omap_barrier_reserve_memblock(void)
> +{
> +}
> +#endif
> +
>  /* This gets called from mach-omap2/io.c, do not call this */
>  void __init omap2_set_globals_tap(u32 class, void __iomem *tap);
>  
> @@ -200,9 +209,6 @@ void __init omap4_map_io(void);
>  void __init omap5_map_io(void);
>  void __init ti81xx_map_io(void);
>  
> -/* omap_barriers_init() is OMAP4 only */
> -void omap_barriers_init(void);
> -
>  /**
>   * omap_test_timeout - busy-loop, testing a condition
>   * @cond: condition to test until it evaluates to true
> diff --git a/arch/arm/mach-omap2/include/mach/barriers.h b/arch/arm/mach-omap2/include/mach/barriers.h
> deleted file mode 100644
> index 1c582a8592b9..000000000000
> --- a/arch/arm/mach-omap2/include/mach/barriers.h
> +++ /dev/null
> @@ -1,33 +0,0 @@
> -/*
> - * OMAP memory barrier header.
> - *
> - * Copyright (C) 2011 Texas Instruments, Inc.
> - *  Santosh Shilimkar <santosh.shilimkar@ti.com>
> - *  Richard Woodruff <r-woodruff2@ti.com>
> - *
> - * This program is free software; you can redistribute it and/or modify
> - * it under the terms of the GNU General Public License version 2 as
> - * published by the Free Software Foundation.
> - *
> - * This program is distributed in the hope that it will be useful,
> - * but WITHOUT ANY WARRANTY; without even the implied warranty of
> - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
> - * GNU General Public License for more details.
> - *
> - * You should have received a copy of the GNU General Public License
> - * along with this program; if not, write to the Free Software
> - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
> - */
> -
> -#ifndef __MACH_BARRIERS_H
> -#define __MACH_BARRIERS_H
> -
> -#include <asm/outercache.h>
> -
> -extern void omap_bus_sync(void);
> -
> -#define rmb()		dsb()
> -#define wmb()		do { dsb(); outer_sync(); omap_bus_sync(); } while (0)
> -#define mb()		wmb()
> -
> -#endif	/* __MACH_BARRIERS_H */
> diff --git a/arch/arm/mach-omap2/omap-secure.h b/arch/arm/mach-omap2/omap-secure.h
> index dec2b05d184b..af2851fbcdf0 100644
> --- a/arch/arm/mach-omap2/omap-secure.h
> +++ b/arch/arm/mach-omap2/omap-secure.h
> @@ -70,13 +70,6 @@ extern u32 rx51_secure_dispatcher(u32 idx, u32 process, u32 flag, u32 nargs,
>  extern u32 rx51_secure_update_aux_cr(u32 set_bits, u32 clear_bits);
>  extern u32 rx51_secure_rng_call(u32 ptr, u32 count, u32 flag);
>  
> -#ifdef CONFIG_OMAP4_ERRATA_I688
> -extern int omap_barrier_reserve_memblock(void);
> -#else
> -static inline void omap_barrier_reserve_memblock(void)
> -{ }
> -#endif
> -
>  #ifdef CONFIG_SOC_HAS_REALTIME_COUNTER
>  void set_cntfreq(void);
>  #else
> diff --git a/arch/arm/mach-omap2/omap4-common.c b/arch/arm/mach-omap2/omap4-common.c
> index 7bb116a6f86f..9c7aac616938 100644
> --- a/arch/arm/mach-omap2/omap4-common.c
> +++ b/arch/arm/mach-omap2/omap4-common.c
> @@ -51,16 +51,73 @@ static void __iomem *twd_base;
>  
>  #define IRQ_LOCALTIMER		29
>  
> -#ifdef CONFIG_OMAP4_ERRATA_I688
> +#ifdef CONFIG_OMAP_INTERCONNECT_BARRIER
> +
>  /* Used to implement memory barrier on DRAM path */
>  #define OMAP4_DRAM_BARRIER_VA			0xfe600000
>  
> -void __iomem *dram_sync, *sram_sync;
> +static void __iomem *dram_sync, *sram_sync;
> +static phys_addr_t dram_sync_paddr;
> +static u32 dram_sync_size;
> +
> +/*
> + * The OMAP4 bus structure contains asynchrnous bridges which can buffer
> + * data writes from the MPU. These asynchronous bridges can be found on
> + * paths between the MPU to EMIF, and the MPU to L3 interconnects.
> + *
> + * We need to be careful about re-ordering which can happen as a result
> + * of different accesses being performed via different paths, and
> + * therefore different asynchronous bridges.
> + */
>  
> -static phys_addr_t paddr;
> -static u32 size;
> +/*
> + * OMAP4 interconnect barrier which is called for each mb() and wmb().
> + * This is to ensure that normal paths to DRAM (normal memory, cacheable
> + * accesses) are properly synchronised with writes to DMA coherent memory
> + * (normal memory, uncacheable) and device writes.
> + *
> + * The mb() and wmb() barriers only operate only on the MPU->MA->EMIF
> + * path, as we need to ensure that data is visible to other system
> + * masters prior to writes to those system masters being seen.
> + *
> + * Note: the SRAM path is not synchronised via mb() and wmb().
> + */
> +static void omap4_mb(void)

Sorry for the late response but this throws a warning when CONFIG_ARCH_OMAP4
is not configured.

arch/arm/mach-omap2/omap4-common.c:85:13: warning: 'omap4_mb' defined but not used [-Wunused-function]

If this was already taken I can just throw a patch up against what ever tree it is on.

<snip>

-- 
------------------
Dan Murphy

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

* [PATCH 4/4] ARM: omap2: restore OMAP4 barrier behaviour
@ 2015-07-27 21:23     ` Dan Murphy
  0 siblings, 0 replies; 22+ messages in thread
From: Dan Murphy @ 2015-07-27 21:23 UTC (permalink / raw)
  To: linux-arm-kernel

Russell

On 07/15/2015 12:47 PM, Russell King wrote:
> Restore the OMAP4 barrier behaviour using the new implementation which
> allows multiplatform systems to hook into the mb() and wmb() ARM
> implementations to perform any necessary additional barrier maintanence.
>
> Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
> ---
>  arch/arm/mach-omap2/Kconfig                 | 28 +++------
>  arch/arm/mach-omap2/common.h                | 12 +++-
>  arch/arm/mach-omap2/include/mach/barriers.h | 33 -----------
>  arch/arm/mach-omap2/omap-secure.h           |  7 ---
>  arch/arm/mach-omap2/omap4-common.c          | 90 +++++++++++++++++++++++------
>  arch/arm/mach-omap2/sleep44xx.S             | 10 +---
>  6 files changed, 90 insertions(+), 90 deletions(-)
>  delete mode 100644 arch/arm/mach-omap2/include/mach/barriers.h
>
> diff --git a/arch/arm/mach-omap2/Kconfig b/arch/arm/mach-omap2/Kconfig
> index 2128441430ad..8427997e09c4 100644
> --- a/arch/arm/mach-omap2/Kconfig
> +++ b/arch/arm/mach-omap2/Kconfig
> @@ -29,6 +29,7 @@ config ARCH_OMAP4
>  	select HAVE_ARM_SCU if SMP
>  	select HAVE_ARM_TWD if SMP
>  	select OMAP_INTERCONNECT
> +	select OMAP_INTERCONNECT_BARRIER
>  	select PL310_ERRATA_588369 if CACHE_L2X0
>  	select PL310_ERRATA_727915 if CACHE_L2X0
>  	select PM_OPP if PM
> @@ -46,6 +47,7 @@ config SOC_OMAP5
>  	select HAVE_ARM_TWD if SMP
>  	select HAVE_ARM_ARCH_TIMER
>  	select ARM_ERRATA_798181 if SMP
> +	select OMAP_INTERCONNECT_BARRIER
>  
>  config SOC_AM33XX
>  	bool "TI AM33XX"
> @@ -70,6 +72,7 @@ config SOC_DRA7XX
>  	select HAVE_ARM_ARCH_TIMER
>  	select IRQ_CROSSBAR
>  	select ARM_ERRATA_798181 if SMP
> +	select OMAP_INTERCONNECT_BARRIER
>  
>  config ARCH_OMAP2PLUS
>  	bool
> @@ -91,6 +94,10 @@ config ARCH_OMAP2PLUS
>  	help
>  	  Systems based on OMAP2, OMAP3, OMAP4 or OMAP5
>  
> +config OMAP_INTERCONNECT_BARRIER
> +	bool
> +	select ARM_HEAVY_MB
> +	
>  
>  if ARCH_OMAP2PLUS
>  
> @@ -240,27 +247,6 @@ config OMAP3_SDRC_AC_TIMING
>  	  wish to say no.  Selecting yes without understanding what is
>  	  going on could result in system crashes;
>  
> -config OMAP4_ERRATA_I688
> -	bool "OMAP4 errata: Async Bridge Corruption"
> -	depends on (ARCH_OMAP4 || SOC_OMAP5) && !ARCH_MULTIPLATFORM
> -	select ARCH_HAS_BARRIERS
> -	help
> -	  If a data is stalled inside asynchronous bridge because of back
> -	  pressure, it may be accepted multiple times, creating pointer
> -	  misalignment that will corrupt next transfers on that data path
> -	  until next reset of the system (No recovery procedure once the
> -	  issue is hit, the path remains consistently broken). Async bridge
> -	  can be found on path between MPU to EMIF and MPU to L3 interconnect.
> -	  This situation can happen only when the idle is initiated by a
> -	  Master Request Disconnection (which is trigged by software when
> -	  executing WFI on CPU).
> -	  The work-around for this errata needs all the initiators connected
> -	  through async bridge must ensure that data path is properly drained
> -	  before issuing WFI. This condition will be met if one Strongly ordered
> -	  access is performed to the target right before executing the WFI.
> -	  In MPU case, L3 T2ASYNC FIFO and DDR T2ASYNC FIFO needs to be drained.
> -	  IO barrier ensure that there is no synchronisation loss on initiators
> -	  operating on both interconnect port simultaneously.
>  endmenu
>  
>  endif
> diff --git a/arch/arm/mach-omap2/common.h b/arch/arm/mach-omap2/common.h
> index 46e24581d624..82f88b4ec15f 100644
> --- a/arch/arm/mach-omap2/common.h
> +++ b/arch/arm/mach-omap2/common.h
> @@ -189,6 +189,15 @@ static inline void omap44xx_restart(enum reboot_mode mode, const char *cmd)
>  }
>  #endif
>  
> +#ifdef CONFIG_OMAP_INTERCONNECT_BARRIER
> +void omap_barrier_reserve_memblock(void);
> +void omap_barriers_init(void);
> +#else
> +static inline void omap_barrier_reserve_memblock(void)
> +{
> +}
> +#endif
> +
>  /* This gets called from mach-omap2/io.c, do not call this */
>  void __init omap2_set_globals_tap(u32 class, void __iomem *tap);
>  
> @@ -200,9 +209,6 @@ void __init omap4_map_io(void);
>  void __init omap5_map_io(void);
>  void __init ti81xx_map_io(void);
>  
> -/* omap_barriers_init() is OMAP4 only */
> -void omap_barriers_init(void);
> -
>  /**
>   * omap_test_timeout - busy-loop, testing a condition
>   * @cond: condition to test until it evaluates to true
> diff --git a/arch/arm/mach-omap2/include/mach/barriers.h b/arch/arm/mach-omap2/include/mach/barriers.h
> deleted file mode 100644
> index 1c582a8592b9..000000000000
> --- a/arch/arm/mach-omap2/include/mach/barriers.h
> +++ /dev/null
> @@ -1,33 +0,0 @@
> -/*
> - * OMAP memory barrier header.
> - *
> - * Copyright (C) 2011 Texas Instruments, Inc.
> - *  Santosh Shilimkar <santosh.shilimkar@ti.com>
> - *  Richard Woodruff <r-woodruff2@ti.com>
> - *
> - * This program is free software; you can redistribute it and/or modify
> - * it under the terms of the GNU General Public License version 2 as
> - * published by the Free Software Foundation.
> - *
> - * This program is distributed in the hope that it will be useful,
> - * but WITHOUT ANY WARRANTY; without even the implied warranty of
> - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
> - * GNU General Public License for more details.
> - *
> - * You should have received a copy of the GNU General Public License
> - * along with this program; if not, write to the Free Software
> - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
> - */
> -
> -#ifndef __MACH_BARRIERS_H
> -#define __MACH_BARRIERS_H
> -
> -#include <asm/outercache.h>
> -
> -extern void omap_bus_sync(void);
> -
> -#define rmb()		dsb()
> -#define wmb()		do { dsb(); outer_sync(); omap_bus_sync(); } while (0)
> -#define mb()		wmb()
> -
> -#endif	/* __MACH_BARRIERS_H */
> diff --git a/arch/arm/mach-omap2/omap-secure.h b/arch/arm/mach-omap2/omap-secure.h
> index dec2b05d184b..af2851fbcdf0 100644
> --- a/arch/arm/mach-omap2/omap-secure.h
> +++ b/arch/arm/mach-omap2/omap-secure.h
> @@ -70,13 +70,6 @@ extern u32 rx51_secure_dispatcher(u32 idx, u32 process, u32 flag, u32 nargs,
>  extern u32 rx51_secure_update_aux_cr(u32 set_bits, u32 clear_bits);
>  extern u32 rx51_secure_rng_call(u32 ptr, u32 count, u32 flag);
>  
> -#ifdef CONFIG_OMAP4_ERRATA_I688
> -extern int omap_barrier_reserve_memblock(void);
> -#else
> -static inline void omap_barrier_reserve_memblock(void)
> -{ }
> -#endif
> -
>  #ifdef CONFIG_SOC_HAS_REALTIME_COUNTER
>  void set_cntfreq(void);
>  #else
> diff --git a/arch/arm/mach-omap2/omap4-common.c b/arch/arm/mach-omap2/omap4-common.c
> index 7bb116a6f86f..9c7aac616938 100644
> --- a/arch/arm/mach-omap2/omap4-common.c
> +++ b/arch/arm/mach-omap2/omap4-common.c
> @@ -51,16 +51,73 @@ static void __iomem *twd_base;
>  
>  #define IRQ_LOCALTIMER		29
>  
> -#ifdef CONFIG_OMAP4_ERRATA_I688
> +#ifdef CONFIG_OMAP_INTERCONNECT_BARRIER
> +
>  /* Used to implement memory barrier on DRAM path */
>  #define OMAP4_DRAM_BARRIER_VA			0xfe600000
>  
> -void __iomem *dram_sync, *sram_sync;
> +static void __iomem *dram_sync, *sram_sync;
> +static phys_addr_t dram_sync_paddr;
> +static u32 dram_sync_size;
> +
> +/*
> + * The OMAP4 bus structure contains asynchrnous bridges which can buffer
> + * data writes from the MPU. These asynchronous bridges can be found on
> + * paths between the MPU to EMIF, and the MPU to L3 interconnects.
> + *
> + * We need to be careful about re-ordering which can happen as a result
> + * of different accesses being performed via different paths, and
> + * therefore different asynchronous bridges.
> + */
>  
> -static phys_addr_t paddr;
> -static u32 size;
> +/*
> + * OMAP4 interconnect barrier which is called for each mb() and wmb().
> + * This is to ensure that normal paths to DRAM (normal memory, cacheable
> + * accesses) are properly synchronised with writes to DMA coherent memory
> + * (normal memory, uncacheable) and device writes.
> + *
> + * The mb() and wmb() barriers only operate only on the MPU->MA->EMIF
> + * path, as we need to ensure that data is visible to other system
> + * masters prior to writes to those system masters being seen.
> + *
> + * Note: the SRAM path is not synchronised via mb() and wmb().
> + */
> +static void omap4_mb(void)

Sorry for the late response but this throws a warning when CONFIG_ARCH_OMAP4
is not configured.

arch/arm/mach-omap2/omap4-common.c:85:13: warning: 'omap4_mb' defined but not used [-Wunused-function]

If this was already taken I can just throw a patch up against what ever tree it is on.

<snip>

-- 
------------------
Dan Murphy

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

* Re: [PATCH 4/4] ARM: omap2: restore OMAP4 barrier behaviour
  2015-07-27 21:23     ` Dan Murphy
@ 2015-07-28 12:55       ` Russell King - ARM Linux
  -1 siblings, 0 replies; 22+ messages in thread
From: Russell King - ARM Linux @ 2015-07-28 12:55 UTC (permalink / raw)
  To: Dan Murphy; +Cc: Tony Lindgren, linux-omap, Will Deacon, linux-arm-kernel

On Mon, Jul 27, 2015 at 04:23:45PM -0500, Dan Murphy wrote:
> Russell
> 
> On 07/15/2015 12:47 PM, Russell King wrote:
> > +#ifdef CONFIG_OMAP_INTERCONNECT_BARRIER
> > +
> >  /* Used to implement memory barrier on DRAM path */
> >  #define OMAP4_DRAM_BARRIER_VA			0xfe600000
> >  
> > -void __iomem *dram_sync, *sram_sync;
> > +static void __iomem *dram_sync, *sram_sync;
> > +static phys_addr_t dram_sync_paddr;
> > +static u32 dram_sync_size;
> > +
> > +/*
> > + * The OMAP4 bus structure contains asynchrnous bridges which can buffer
> > + * data writes from the MPU. These asynchronous bridges can be found on
> > + * paths between the MPU to EMIF, and the MPU to L3 interconnects.
> > + *
> > + * We need to be careful about re-ordering which can happen as a result
> > + * of different accesses being performed via different paths, and
> > + * therefore different asynchronous bridges.
> > + */
> >  
> > -static phys_addr_t paddr;
> > -static u32 size;
> > +/*
> > + * OMAP4 interconnect barrier which is called for each mb() and wmb().
> > + * This is to ensure that normal paths to DRAM (normal memory, cacheable
> > + * accesses) are properly synchronised with writes to DMA coherent memory
> > + * (normal memory, uncacheable) and device writes.
> > + *
> > + * The mb() and wmb() barriers only operate only on the MPU->MA->EMIF
> > + * path, as we need to ensure that data is visible to other system
> > + * masters prior to writes to those system masters being seen.
> > + *
> > + * Note: the SRAM path is not synchronised via mb() and wmb().
> > + */
> > +static void omap4_mb(void)
> 
> Sorry for the late response but this throws a warning when CONFIG_ARCH_OMAP4
> is not configured.
> 
> arch/arm/mach-omap2/omap4-common.c:85:13: warning: 'omap4_mb' defined but not used [-Wunused-function]

Sorry, I'm going to have to disagree with you and your compiler on this.
This is how the code is structured:

#ifdef CONFIG_OMAP_INTERCONNECT_BARRIER
...
static void omap4_mb(void)
{
        if (dram_sync)
                writel_relaxed(0, dram_sync);
}
...
void __init omap_barriers_init(void)
{
...
        soc_mb = omap4_mb;
}

#endif

So, the definition of omap4_mb(), and the use of the same are both
under the same ifdef.  You can't build omap4_mb() without also building
omap_barriers_init() as well.

So, there's no way that omap4_mb() would be "defined but not used".

I think you have some changes in your kernel which, maybe, place an
ifdef around omap_barriers_init() which _would_ cause the warning you're
seeing if they aren't set.

Also, please trim context before the relevant part to which you're
replying. I almost gave up paging down to see whether there was actually
anything worth replying to.  If there's nothing in the first 50 lines of
the message, it's a waste of space.

-- 
FTTC broadband for 0.8mile line: currently at 10.5Mbps down 400kbps up
according to speedtest.net.

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

* [PATCH 4/4] ARM: omap2: restore OMAP4 barrier behaviour
@ 2015-07-28 12:55       ` Russell King - ARM Linux
  0 siblings, 0 replies; 22+ messages in thread
From: Russell King - ARM Linux @ 2015-07-28 12:55 UTC (permalink / raw)
  To: linux-arm-kernel

On Mon, Jul 27, 2015 at 04:23:45PM -0500, Dan Murphy wrote:
> Russell
> 
> On 07/15/2015 12:47 PM, Russell King wrote:
> > +#ifdef CONFIG_OMAP_INTERCONNECT_BARRIER
> > +
> >  /* Used to implement memory barrier on DRAM path */
> >  #define OMAP4_DRAM_BARRIER_VA			0xfe600000
> >  
> > -void __iomem *dram_sync, *sram_sync;
> > +static void __iomem *dram_sync, *sram_sync;
> > +static phys_addr_t dram_sync_paddr;
> > +static u32 dram_sync_size;
> > +
> > +/*
> > + * The OMAP4 bus structure contains asynchrnous bridges which can buffer
> > + * data writes from the MPU. These asynchronous bridges can be found on
> > + * paths between the MPU to EMIF, and the MPU to L3 interconnects.
> > + *
> > + * We need to be careful about re-ordering which can happen as a result
> > + * of different accesses being performed via different paths, and
> > + * therefore different asynchronous bridges.
> > + */
> >  
> > -static phys_addr_t paddr;
> > -static u32 size;
> > +/*
> > + * OMAP4 interconnect barrier which is called for each mb() and wmb().
> > + * This is to ensure that normal paths to DRAM (normal memory, cacheable
> > + * accesses) are properly synchronised with writes to DMA coherent memory
> > + * (normal memory, uncacheable) and device writes.
> > + *
> > + * The mb() and wmb() barriers only operate only on the MPU->MA->EMIF
> > + * path, as we need to ensure that data is visible to other system
> > + * masters prior to writes to those system masters being seen.
> > + *
> > + * Note: the SRAM path is not synchronised via mb() and wmb().
> > + */
> > +static void omap4_mb(void)
> 
> Sorry for the late response but this throws a warning when CONFIG_ARCH_OMAP4
> is not configured.
> 
> arch/arm/mach-omap2/omap4-common.c:85:13: warning: 'omap4_mb' defined but not used [-Wunused-function]

Sorry, I'm going to have to disagree with you and your compiler on this.
This is how the code is structured:

#ifdef CONFIG_OMAP_INTERCONNECT_BARRIER
...
static void omap4_mb(void)
{
        if (dram_sync)
                writel_relaxed(0, dram_sync);
}
...
void __init omap_barriers_init(void)
{
...
        soc_mb = omap4_mb;
}

#endif

So, the definition of omap4_mb(), and the use of the same are both
under the same ifdef.  You can't build omap4_mb() without also building
omap_barriers_init() as well.

So, there's no way that omap4_mb() would be "defined but not used".

I think you have some changes in your kernel which, maybe, place an
ifdef around omap_barriers_init() which _would_ cause the warning you're
seeing if they aren't set.

Also, please trim context before the relevant part to which you're
replying. I almost gave up paging down to see whether there was actually
anything worth replying to.  If there's nothing in the first 50 lines of
the message, it's a waste of space.

-- 
FTTC broadband for 0.8mile line: currently at 10.5Mbps down 400kbps up
according to speedtest.net.

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

end of thread, other threads:[~2015-07-28 12:55 UTC | newest]

Thread overview: 22+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2015-07-15 17:46 [PATCH 0/4] Fix OMAP4 barrier support Russell King - ARM Linux
2015-07-15 17:46 ` Russell King - ARM Linux
2015-07-15 17:47 ` [PATCH 1/4] ARM: move heavy barrier support out of line Russell King
2015-07-15 17:47   ` Russell King
2015-07-15 17:47 ` [PATCH 2/4] ARM: add soc memory barrier extension Russell King
2015-07-15 17:47   ` Russell King
2015-07-15 17:47 ` [PATCH 3/4] Revert "ARM: OMAP4: remove dead kconfig option OMAP4_ERRATA_I688" Russell King
2015-07-15 17:47   ` Russell King
2015-07-22 20:13   ` Woodruff, Richard
2015-07-22 20:13     ` Woodruff, Richard
2015-07-15 17:47 ` [PATCH 4/4] ARM: omap2: restore OMAP4 barrier behaviour Russell King
2015-07-15 17:47   ` Russell King
2015-07-16  6:48   ` Tony Lindgren
2015-07-16  6:48     ` Tony Lindgren
2015-07-16 13:54     ` Russell King - ARM Linux
2015-07-16 13:54       ` Russell King - ARM Linux
2015-07-17  5:48       ` Tony Lindgren
2015-07-17  5:48         ` Tony Lindgren
2015-07-27 21:23   ` Dan Murphy
2015-07-27 21:23     ` Dan Murphy
2015-07-28 12:55     ` Russell King - ARM Linux
2015-07-28 12:55       ` Russell King - ARM Linux

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.