xref: /rk3399_ARM-atf/include/lib/cpus/aarch64/dsu_macros.S (revision b62673c645752a78f649282cfa293e8da09e3bef)
1*b62673c6SBoyan Karatotev/*
2*b62673c6SBoyan Karatotev * Copyright (c) 2019-2025, Arm Limited and Contributors. All rights reserved.
3*b62673c6SBoyan Karatotev *
4*b62673c6SBoyan Karatotev * SPDX-License-Identifier: BSD-3-Clause
5*b62673c6SBoyan Karatotev */
6*b62673c6SBoyan Karatotev
7*b62673c6SBoyan Karatotev#ifndef DSU_MACROS_S
8*b62673c6SBoyan Karatotev#define DSU_MACROS_S
9*b62673c6SBoyan Karatotev
10*b62673c6SBoyan Karatotev#include <asm_macros.S>
11*b62673c6SBoyan Karatotev#include <dsu_def.h>
12*b62673c6SBoyan Karatotev#include <lib/cpus/errata.h>
13*b62673c6SBoyan Karatotev
14*b62673c6SBoyan Karatotev.macro check_errata_dsu_798953_impl
15*b62673c6SBoyan Karatotev	mov	x2, #ERRATA_APPLIES
16*b62673c6SBoyan Karatotev	mov	x3, #ERRATA_NOT_APPLIES
17*b62673c6SBoyan Karatotev
18*b62673c6SBoyan Karatotev	/* Check if DSU is equal to r0p0 */
19*b62673c6SBoyan Karatotev	mrs	x1, CLUSTERIDR_EL1
20*b62673c6SBoyan Karatotev
21*b62673c6SBoyan Karatotev	/* DSU variant and revision bitfields in CLUSTERIDR are adjacent */
22*b62673c6SBoyan Karatotev	ubfx	x0, x1, #CLUSTERIDR_REV_SHIFT,\
23*b62673c6SBoyan Karatotev			#(CLUSTERIDR_REV_BITS + CLUSTERIDR_VAR_BITS)
24*b62673c6SBoyan Karatotev	mov	x1, #(0x0 << CLUSTERIDR_REV_SHIFT)
25*b62673c6SBoyan Karatotev	cmp	x0, x1
26*b62673c6SBoyan Karatotev	csel	x0, x2, x3, EQ
27*b62673c6SBoyan Karatotev.endm
28*b62673c6SBoyan Karatotev
29*b62673c6SBoyan Karatotev.macro errata_dsu_798953_wa_impl
30*b62673c6SBoyan Karatotev	/* If erratum applies, disable high-level clock gating */
31*b62673c6SBoyan Karatotev	mrs	x0, CLUSTERACTLR_EL1
32*b62673c6SBoyan Karatotev	orr	x0, x0, #CLUSTERACTLR_EL1_DISABLE_CLOCK_GATING
33*b62673c6SBoyan Karatotev	msr	CLUSTERACTLR_EL1, x0
34*b62673c6SBoyan Karatotev.endm
35*b62673c6SBoyan Karatotev
36*b62673c6SBoyan Karatotev.macro branch_if_scu_not_present _target:req
37*b62673c6SBoyan Karatotev	/* Check if the SCU L3 Unit is present on the DSU */
38*b62673c6SBoyan Karatotev	mrs	x0, CPUCFR_EL1
39*b62673c6SBoyan Karatotev	ubfx	x0, x0, #SCU_SHIFT, #1
40*b62673c6SBoyan Karatotev	eor	x0, x0, #1
41*b62673c6SBoyan Karatotev	/* If SCU is not present, return without applying patch */
42*b62673c6SBoyan Karatotev	cmp	x0, xzr
43*b62673c6SBoyan Karatotev	mov	x0, #ERRATA_NOT_APPLIES
44*b62673c6SBoyan Karatotev	b.eq	\_target
45*b62673c6SBoyan Karatotev.endm
46*b62673c6SBoyan Karatotev
47*b62673c6SBoyan Karatotev.macro check_errata_dsu_936184_impl
48*b62673c6SBoyan Karatotev	mov	x0, #ERRATA_NOT_APPLIES
49*b62673c6SBoyan Karatotev	/* Erratum applies only if DSU has the ACP interface */
50*b62673c6SBoyan Karatotev	mrs	x1, CLUSTERCFR_EL1
51*b62673c6SBoyan Karatotev	ubfx	x1, x1, #CLUSTERCFR_ACP_SHIFT, #1
52*b62673c6SBoyan Karatotev	cbz	x1, 1f
53*b62673c6SBoyan Karatotev
54*b62673c6SBoyan Karatotev	/* If ACP is present, check if DSU is older than r2p0 */
55*b62673c6SBoyan Karatotev	mrs	x1, CLUSTERIDR_EL1
56*b62673c6SBoyan Karatotev
57*b62673c6SBoyan Karatotev	/* DSU variant and revision bitfields in CLUSTERIDR are adjacent */
58*b62673c6SBoyan Karatotev	ubfx	x2, x1, #CLUSTERIDR_REV_SHIFT,\
59*b62673c6SBoyan Karatotev			#(CLUSTERIDR_REV_BITS + CLUSTERIDR_VAR_BITS)
60*b62673c6SBoyan Karatotev	cmp x2, #(0x2 << CLUSTERIDR_VAR_SHIFT)
61*b62673c6SBoyan Karatotev	b.hs	1f
62*b62673c6SBoyan Karatotev	mov	x0, #ERRATA_APPLIES
63*b62673c6SBoyan Karatotev1:
64*b62673c6SBoyan Karatotev.endm
65*b62673c6SBoyan Karatotev
66*b62673c6SBoyan Karatotev.macro errata_dsu_936184_wa_impl
67*b62673c6SBoyan Karatotev	/* If erratum applies, we set a mask to a DSU control register */
68*b62673c6SBoyan Karatotev	mrs	x0, CLUSTERACTLR_EL1
69*b62673c6SBoyan Karatotev	ldr	x1, =DSU_ERRATA_936184_MASK
70*b62673c6SBoyan Karatotev	orr	x0, x0, x1
71*b62673c6SBoyan Karatotev	msr	CLUSTERACTLR_EL1, x0
72*b62673c6SBoyan Karatotev.endm
73*b62673c6SBoyan Karatotev
74*b62673c6SBoyan Karatotev.macro check_errata_dsu_2313941_impl
75*b62673c6SBoyan Karatotev	mov	x2, #ERRATA_APPLIES
76*b62673c6SBoyan Karatotev	mov	x3, #ERRATA_NOT_APPLIES
77*b62673c6SBoyan Karatotev
78*b62673c6SBoyan Karatotev	/* Check if DSU version is less than or equal to r3p1 */
79*b62673c6SBoyan Karatotev	mrs	x1, CLUSTERIDR_EL1
80*b62673c6SBoyan Karatotev
81*b62673c6SBoyan Karatotev	mov	x0, #ERRATA_NOT_APPLIES
82*b62673c6SBoyan Karatotev	/* DSU variant and revision bitfields in CLUSTERIDR are adjacent */
83*b62673c6SBoyan Karatotev	ubfx	x0, x1, #CLUSTERIDR_REV_SHIFT,\
84*b62673c6SBoyan Karatotev			#(CLUSTERIDR_REV_BITS + CLUSTERIDR_VAR_BITS)
85*b62673c6SBoyan Karatotev	mov	x1, #(0x31 << CLUSTERIDR_REV_SHIFT)
86*b62673c6SBoyan Karatotev	cmp	x0, x1
87*b62673c6SBoyan Karatotev	csel	x0, x2, x3, LS
88*b62673c6SBoyan Karatotev1:
89*b62673c6SBoyan Karatotev.endm
90*b62673c6SBoyan Karatotev
91*b62673c6SBoyan Karatotev.macro errata_dsu_2313941_wa_impl
92*b62673c6SBoyan Karatotev	/* If erratum applies, disable high-level clock gating */
93*b62673c6SBoyan Karatotev	mrs	x0, CLUSTERACTLR_EL1
94*b62673c6SBoyan Karatotev	orr	x0, x0, #CLUSTERACTLR_EL1_DISABLE_SCLK_GATING
95*b62673c6SBoyan Karatotev	msr	CLUSTERACTLR_EL1, x0
96*b62673c6SBoyan Karatotev.endm
97*b62673c6SBoyan Karatotev#endif /* DSU_MACROS_S */
98