fix(cpus): workaround for Cortex-A715 erratum 2344187

Cortex-A715 erratum 2344187 is a Cat B erratum that applies to r0p0,
r1p0 and is fixed in r1p1. The workaround is to set GCR_EL1.RRND to
0b1, and apply an implementation specific patch sequence.

SDEN: https://developer.arm.com/documentation/SDEN2148827/latest

Change-Id: I78ea39a91254765c964bff89f771af33b23f29c1
Signed-off-by: Harrison Mutai <harrison.mutai@arm.com>
diff --git a/docs/design/cpu-specific-build-macros.rst b/docs/design/cpu-specific-build-macros.rst
index 6f5f01f..07caee7 100644
--- a/docs/design/cpu-specific-build-macros.rst
+++ b/docs/design/cpu-specific-build-macros.rst
@@ -885,6 +885,10 @@
    Cortex-A715 CPU. This needs to be enabled for revisions r0p0 and r1p0.
    It is fixed in r1p1.
 
+- ``ERRATA_A715_2344187``: This applies errata 2344187 workaround to
+   Cortex-A715 CPU. This needs to be enabled for revisions r0p0 and r1p0. It is
+   fixed in r1p1.
+
 -  ``ERRATA_A715_2420947``: This applies errata 2420947 workaround to
    Cortex-A715 CPU. This needs to be enabled only for revision r1p0.
    It is fixed in r1p1.
diff --git a/include/arch/aarch64/arch.h b/include/arch/aarch64/arch.h
index 8a4c071..ee86b7e 100644
--- a/include/arch/aarch64/arch.h
+++ b/include/arch/aarch64/arch.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2023, Arm Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2024, Arm Limited and Contributors. All rights reserved.
  * Copyright (c) 2020-2022, NVIDIA Corporation. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
@@ -1401,6 +1401,8 @@
 #define RGSR_EL1		S3_0_C1_C0_5
 #define GCR_EL1			S3_0_C1_C0_6
 
+#define GCR_EL1_RRND_BIT	(UL(1) << 16)
+
 /*******************************************************************************
  * Armv8.5 - Random Number Generator Registers
  ******************************************************************************/
diff --git a/include/lib/cpus/aarch64/cortex_a715.h b/include/lib/cpus/aarch64/cortex_a715.h
index 366894d..525187c 100644
--- a/include/lib/cpus/aarch64/cortex_a715.h
+++ b/include/lib/cpus/aarch64/cortex_a715.h
@@ -22,6 +22,11 @@
  ******************************************************************************/
 #define CORTEX_A715_CPUECTLR_EL1				S3_0_C15_C1_4
 
+#define CORTEX_A715_CPUPSELR_EL3				S3_6_C15_C8_0
+#define CORTEX_A715_CPUPCR_EL3					S3_6_C15_C8_1
+#define CORTEX_A715_CPUPOR_EL3					S3_6_C15_C8_2
+#define CORTEX_A715_CPUPMR_EL3					S3_6_C15_C8_3
+
 /*******************************************************************************
  * CPU Power Control register specific definitions
  ******************************************************************************/
diff --git a/lib/cpus/aarch64/cortex_a715.S b/lib/cpus/aarch64/cortex_a715.S
index 65f3c04..9e4d78e 100644
--- a/lib/cpus/aarch64/cortex_a715.S
+++ b/lib/cpus/aarch64/cortex_a715.S
@@ -32,6 +32,34 @@
 
 check_erratum_ls cortex_a715, ERRATUM(2331818), CPU_REV(1, 0)
 
+workaround_reset_start cortex_a715, ERRATUM(2344187), ERRATA_A715_2344187
+	/* GCR_EL1 is only present with FEAT_MTE2. */
+	mrs x1, ID_AA64PFR1_EL1
+	ubfx x0, x1, ID_AA64PFR1_EL1_MTE_SHIFT, #4
+	cmp x0, #MTE_IMPLEMENTED_ELX
+	bne #1f
+	sysreg_bit_set GCR_EL1, GCR_EL1_RRND_BIT
+
+1:
+	/* Mitigation upon ERETAA and ERETAB. */
+	mov x0, #2
+	msr CORTEX_A715_CPUPSELR_EL3, x0
+	isb
+	ldr x0, =0xd69f0bff
+	msr CORTEX_A715_CPUPOR_EL3, x0
+	ldr x0, =0xfffffbff
+	msr CORTEX_A715_CPUPMR_EL3, x0
+	mov x1, #0
+	orr x1, x1, #(1<<0)
+	orr x1, x1, #(3<<4)
+	orr x1, x1, #(0xf<<6)
+	orr x1, x1, #(1<<13)
+	orr x1, x1, #(1<<53)
+	msr CORTEX_A715_CPUPCR_EL3, x1
+workaround_reset_end cortex_a715, ERRATUM(2344187)
+
+check_erratum_ls cortex_a715, ERRATUM(2344187), CPU_REV(1, 0)
+
 workaround_reset_start cortex_a715, ERRATUM(2420947), ERRATA_A715_2420947
         sysreg_bit_set CORTEX_A715_CPUACTLR2_EL1, BIT(33)
 workaround_reset_end cortex_a715, ERRATUM(2420947)
diff --git a/lib/cpus/cpu-ops.mk b/lib/cpus/cpu-ops.mk
index 1c0b092..03c8196 100644
--- a/lib/cpus/cpu-ops.mk
+++ b/lib/cpus/cpu-ops.mk
@@ -915,6 +915,10 @@
 # to revisions r0p0 and r1p0. It is fixed in r1p1.
 CPU_FLAG_LIST += ERRATA_A715_2331818
 
+# Flag to apply erratum 2344187 workaround during reset. This erratum applies
+# to revisions r0p0, and r1p0. It is fixed in r1p1.
+CPU_FLAG_LIST += ERRATA_A715_2344187
+
 # Flag to apply erratum 2420947 workaround during reset. This erratum applies
 # only to revision r1p0. It is fixed in r1p1.
 CPU_FLAG_LIST += ERRATA_A715_2420947