diff mbox series

arm: mach-k3: Clean non-coherent lines out of L3 cache

Message ID 20200715210236.25580-1-afd@ti.com
State Accepted
Commit 864e2857393dc98504ec5da16e0e41e38a0abe39
Delegated to: Lokesh Vutla
Headers show
Series arm: mach-k3: Clean non-coherent lines out of L3 cache | expand

Commit Message

Andrew Davis July 15, 2020, 9:02 p.m. UTC
When switching on or off the ARM caches some care must be taken to ensure
existing cache line allocations are not left in an inconsistent state.
An example of this is when cache lines are considered non-shared by
and L3 controller even though the lines are shared. To prevent these
and other issues all cache lines should be cleared before enabling
or disabling a coherent master's cache. ARM cores and many L3 controllers
provide a way to efficiently clean out all cache lines to allow for
this, unfortunately there is no such easy way to do this on current K3
MSMC based systems.

We could explicitly clean out every valid external address tracked by
MSMC (all of DRAM), or we could attempt to identify only the set of
addresses accessed by a given boot stage and flush only those
specifically. This patch attempts the latter. We start with cleaning the
SPL load address. More addresses can be added here later as they are
identified.

Note that we perform a flush operation for both the flush and invalidate
operations, this is not a typo. We do this to avoid the situation that
some ARM cores will promote an invalidate to a clean+invalidate, but only
emit the invalidation operation externally, leading to a loss of data.

Signed-off-by: Andrew F. Davis <afd@ti.com>
Tested-by: Faiz Abbas <faiz_abbas@ti.com>
---
 arch/arm/mach-k3/Makefile |  1 +
 arch/arm/mach-k3/cache.S  | 24 ++++++++++++++++++++++++
 2 files changed, 25 insertions(+)
 create mode 100644 arch/arm/mach-k3/cache.S

Comments

Lokesh Vutla Aug. 11, 2020, 10:35 a.m. UTC | #1
On 16/07/20 2:32 am, Andrew F. Davis wrote:
> When switching on or off the ARM caches some care must be taken to ensure
> existing cache line allocations are not left in an inconsistent state.
> An example of this is when cache lines are considered non-shared by
> and L3 controller even though the lines are shared. To prevent these
> and other issues all cache lines should be cleared before enabling
> or disabling a coherent master's cache. ARM cores and many L3 controllers
> provide a way to efficiently clean out all cache lines to allow for
> this, unfortunately there is no such easy way to do this on current K3
> MSMC based systems.
> 
> We could explicitly clean out every valid external address tracked by
> MSMC (all of DRAM), or we could attempt to identify only the set of
> addresses accessed by a given boot stage and flush only those
> specifically. This patch attempts the latter. We start with cleaning the
> SPL load address. More addresses can be added here later as they are
> identified.
> 
> Note that we perform a flush operation for both the flush and invalidate
> operations, this is not a typo. We do this to avoid the situation that
> some ARM cores will promote an invalidate to a clean+invalidate, but only
> emit the invalidation operation externally, leading to a loss of data.
> 
> Signed-off-by: Andrew F. Davis <afd@ti.com>
> Tested-by: Faiz Abbas <faiz_abbas@ti.com>

Applied to u-boot-ti

Thanks and regards,
Lokesh

> ---
>  arch/arm/mach-k3/Makefile |  1 +
>  arch/arm/mach-k3/cache.S  | 24 ++++++++++++++++++++++++
>  2 files changed, 25 insertions(+)
>  create mode 100644 arch/arm/mach-k3/cache.S
> 
> diff --git a/arch/arm/mach-k3/Makefile b/arch/arm/mach-k3/Makefile
> index 028015ed66..7572f56925 100644
> --- a/arch/arm/mach-k3/Makefile
> +++ b/arch/arm/mach-k3/Makefile
> @@ -8,6 +8,7 @@ obj-$(CONFIG_SOC_K3_J721E) += j721e_init.o
>  obj-$(CONFIG_ARM64) += arm64-mmu.o
>  obj-$(CONFIG_CPU_V7R) += r5_mpu.o lowlevel_init.o
>  obj-$(CONFIG_TI_SECURE_DEVICE) += security.o
> +obj-$(CONFIG_ARM64) += cache.o
>  ifeq ($(CONFIG_SPL_BUILD),y)
>  obj-$(CONFIG_K3_LOAD_SYSFW) += sysfw-loader.o
>  endif
> diff --git a/arch/arm/mach-k3/cache.S b/arch/arm/mach-k3/cache.S
> new file mode 100644
> index 0000000000..a5717ea203
> --- /dev/null
> +++ b/arch/arm/mach-k3/cache.S
> @@ -0,0 +1,24 @@
> +/* SPDX-License-Identifier: GPL-2.0 */
> +/*
> + * Copyright (C) 2020 Texas Instruments Incorporated - http://www.ti.com/
> + *	Andrew F. Davis <afd@ti.com>
> + */
> +
> +#include <config.h>
> +#include <linux/linkage.h>
> +
> +#if defined(CONFIG_SPL_BUILD)
> +ENTRY(__asm_invalidate_l3_dcache)
> +	/* Invalidate SPL address range */
> +	mov x0, #CONFIG_SPL_TEXT_BASE
> +	add x1, x0, #CONFIG_SPL_MAX_SIZE
> +	b __asm_flush_dcache_range
> +ENDPROC(__asm_invalidate_l3_dcache)
> +
> +ENTRY(__asm_flush_l3_dcache)
> +	/* Flush SPL address range */
> +	mov x0, #CONFIG_SPL_TEXT_BASE
> +	add x1, x0, #CONFIG_SPL_MAX_SIZE
> +	b __asm_flush_dcache_range
> +ENDPROC(__asm_flush_l3_dcache)
> +#endif
>
diff mbox series

Patch

diff --git a/arch/arm/mach-k3/Makefile b/arch/arm/mach-k3/Makefile
index 028015ed66..7572f56925 100644
--- a/arch/arm/mach-k3/Makefile
+++ b/arch/arm/mach-k3/Makefile
@@ -8,6 +8,7 @@  obj-$(CONFIG_SOC_K3_J721E) += j721e_init.o
 obj-$(CONFIG_ARM64) += arm64-mmu.o
 obj-$(CONFIG_CPU_V7R) += r5_mpu.o lowlevel_init.o
 obj-$(CONFIG_TI_SECURE_DEVICE) += security.o
+obj-$(CONFIG_ARM64) += cache.o
 ifeq ($(CONFIG_SPL_BUILD),y)
 obj-$(CONFIG_K3_LOAD_SYSFW) += sysfw-loader.o
 endif
diff --git a/arch/arm/mach-k3/cache.S b/arch/arm/mach-k3/cache.S
new file mode 100644
index 0000000000..a5717ea203
--- /dev/null
+++ b/arch/arm/mach-k3/cache.S
@@ -0,0 +1,24 @@ 
+/* SPDX-License-Identifier: GPL-2.0 */
+/*
+ * Copyright (C) 2020 Texas Instruments Incorporated - http://www.ti.com/
+ *	Andrew F. Davis <afd@ti.com>
+ */
+
+#include <config.h>
+#include <linux/linkage.h>
+
+#if defined(CONFIG_SPL_BUILD)
+ENTRY(__asm_invalidate_l3_dcache)
+	/* Invalidate SPL address range */
+	mov x0, #CONFIG_SPL_TEXT_BASE
+	add x1, x0, #CONFIG_SPL_MAX_SIZE
+	b __asm_flush_dcache_range
+ENDPROC(__asm_invalidate_l3_dcache)
+
+ENTRY(__asm_flush_l3_dcache)
+	/* Flush SPL address range */
+	mov x0, #CONFIG_SPL_TEXT_BASE
+	add x1, x0, #CONFIG_SPL_MAX_SIZE
+	b __asm_flush_dcache_range
+ENDPROC(__asm_flush_l3_dcache)
+#endif