blob: 9544b4f63b03e929bcc54d401e11d18ace820fa5 [file] [log] [blame]
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +00001/*
2 * Copyright (c) 2022, Arm Limited and Contributors. All rights reserved.
3 *
4 * SPDX-License-Identifier: BSD-3-Clause
5 */
6
Andre Przywara5b005112022-11-14 15:38:58 +00007#include <arch_features.h>
8#include <common/debug.h>
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +00009#include <common/feat_detect.h>
10
Andre Przywaracc4118d2022-11-14 15:42:44 +000011static bool tainted;
12
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +000013/*******************************************************************************
14 * This section lists the wrapper modules for each feature to evaluate the
Andre Przywara5b005112022-11-14 15:38:58 +000015 * feature states (FEAT_STATE_ALWAYS and FEAT_STATE_CHECK) and perform
16 * necessary action as below:
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +000017 *
18 * It verifies whether the FEAT_XXX (eg: FEAT_SB) is supported by the PE or not.
19 * Without this check an exception would occur during context save/restore
20 * routines, if the feature is enabled but not supported by PE.
21 ******************************************************************************/
22
Andre Przywara5b005112022-11-14 15:38:58 +000023#define feat_detect_panic(a, b) ((a) ? (void)0 : feature_panic(b))
24
25/*******************************************************************************
26 * Function : feature_panic
27 * Customised panic function with error logging mechanism to list the feature
28 * not supported by the PE.
29 ******************************************************************************/
30static inline void feature_panic(char *feat_name)
31{
32 ERROR("FEAT_%s not supported by the PE\n", feat_name);
33 panic();
34}
35
Andre Przywaracc4118d2022-11-14 15:42:44 +000036/*******************************************************************************
37 * Function : check_feature
38 * Check for a valid combination of build time flags (ENABLE_FEAT_xxx) and
39 * feature availability on the hardware.
40 * Panics if a feature is forcefully enabled, but not available on the PE.
41 *
42 * We force inlining here to let the compiler optimise away the whole check
43 * if the feature is disabled at build time (FEAT_STATE_DISABLED).
44 ******************************************************************************/
45static inline void __attribute((__always_inline__))
46check_feature(int state, unsigned long field, const char *feat_name)
47{
48 if (state == FEAT_STATE_ALWAYS && field == 0U) {
49 ERROR("FEAT_%s not supported by the PE\n", feat_name);
50 tainted = true;
51 }
52}
53
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +000054/******************************************
55 * Feature : FEAT_SB (Speculation Barrier)
56 *****************************************/
57static void read_feat_sb(void)
58{
Andre Przywara5b005112022-11-14 15:38:58 +000059#if (ENABLE_FEAT_SB == FEAT_STATE_ALWAYS)
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +000060 feat_detect_panic(is_armv8_0_feat_sb_present(), "SB");
61#endif
62}
63
64/******************************************************
65 * Feature : FEAT_CSV2_2 (Cache Speculation Variant 2)
66 *****************************************************/
67static void read_feat_csv2_2(void)
68{
Andre Przywara5b005112022-11-14 15:38:58 +000069#if (ENABLE_FEAT_CSV2_2 == FEAT_STATE_ALWAYS)
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +000070 feat_detect_panic(is_armv8_0_feat_csv2_2_present(), "CSV2_2");
71#endif
72}
73
74/***********************************************
75 * Feature : FEAT_PAN (Privileged Access Never)
76 **********************************************/
77static void read_feat_pan(void)
78{
Andre Przywara5b005112022-11-14 15:38:58 +000079#if (ENABLE_FEAT_PAN == FEAT_STATE_ALWAYS)
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +000080 feat_detect_panic(is_armv8_1_pan_present(), "PAN");
81#endif
82}
83
84/******************************************************
85 * Feature : FEAT_VHE (Virtualization Host Extensions)
86 *****************************************************/
87static void read_feat_vhe(void)
88{
Andre Przywara5b005112022-11-14 15:38:58 +000089#if (ENABLE_FEAT_VHE == FEAT_STATE_ALWAYS)
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +000090 feat_detect_panic(is_armv8_1_vhe_present(), "VHE");
91#endif
92}
93
94/*******************************************************************************
95 * Feature : FEAT_RAS (Reliability, Availability, and Serviceability Extension)
96 ******************************************************************************/
97static void read_feat_ras(void)
98{
Andre Przywara5b005112022-11-14 15:38:58 +000099#if (RAS_EXTENSION == FEAT_STATE_ALWAYS)
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +0000100 feat_detect_panic(is_armv8_2_feat_ras_present(), "RAS");
101#endif
102}
103
104/************************************************
105 * Feature : FEAT_PAUTH (Pointer Authentication)
106 ***********************************************/
107static void read_feat_pauth(void)
108{
Andre Przywara5b005112022-11-14 15:38:58 +0000109#if (ENABLE_PAUTH == FEAT_STATE_ALWAYS) || (CTX_INCLUDE_PAUTH_REGS == FEAT_STATE_ALWAYS)
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +0000110 feat_detect_panic(is_armv8_3_pauth_present(), "PAUTH");
111#endif
112}
113
114/************************************************************
115 * Feature : FEAT_DIT (Data Independent Timing Instructions)
116 ***********************************************************/
117static void read_feat_dit(void)
118{
Andre Przywara5b005112022-11-14 15:38:58 +0000119#if (ENABLE_FEAT_DIT == FEAT_STATE_ALWAYS)
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +0000120 feat_detect_panic(is_armv8_4_feat_dit_present(), "DIT");
121#endif
122}
123
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +0000124/****************************************************************************
125 * Feature : FEAT_MPAM (Memory Partitioning and Monitoring (MPAM) Extension)
126 ***************************************************************************/
127static void read_feat_mpam(void)
128{
Andre Przywara5b005112022-11-14 15:38:58 +0000129#if (ENABLE_MPAM_FOR_LOWER_ELS == FEAT_STATE_ALWAYS)
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +0000130 feat_detect_panic(get_mpam_version() != 0U, "MPAM");
131#endif
132}
133
134/**************************************************************
135 * Feature : FEAT_NV2 (Enhanced Nested Virtualization Support)
136 *************************************************************/
137static void read_feat_nv2(void)
138{
Andre Przywara5b005112022-11-14 15:38:58 +0000139#if (CTX_INCLUDE_NEVE_REGS == FEAT_STATE_ALWAYS)
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +0000140 unsigned int nv = get_armv8_4_feat_nv_support();
141
142 feat_detect_panic((nv == ID_AA64MMFR2_EL1_NV2_SUPPORTED), "NV2");
143#endif
144}
145
146/***********************************
147 * Feature : FEAT_SEL2 (Secure EL2)
148 **********************************/
149static void read_feat_sel2(void)
150{
Andre Przywara5b005112022-11-14 15:38:58 +0000151#if (ENABLE_FEAT_SEL2 == FEAT_STATE_ALWAYS)
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +0000152 feat_detect_panic(is_armv8_4_sel2_present(), "SEL2");
153#endif
154}
155
156/****************************************************
157 * Feature : FEAT_TRF (Self-hosted Trace Extensions)
158 ***************************************************/
159static void read_feat_trf(void)
160{
Andre Przywara5b005112022-11-14 15:38:58 +0000161#if (ENABLE_TRF_FOR_NS == FEAT_STATE_ALWAYS)
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +0000162 feat_detect_panic(is_arm8_4_feat_trf_present(), "TRF");
163#endif
164}
165
166/************************************************
167 * Feature : FEAT_MTE (Memory Tagging Extension)
168 ***********************************************/
169static void read_feat_mte(void)
170{
Andre Przywara5b005112022-11-14 15:38:58 +0000171#if (CTX_INCLUDE_MTE_REGS == FEAT_STATE_ALWAYS)
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +0000172 unsigned int mte = get_armv8_5_mte_support();
173
174 feat_detect_panic((mte != MTE_UNIMPLEMENTED), "MTE");
175#endif
176}
177
178/***********************************************
179 * Feature : FEAT_RNG (Random Number Generator)
180 **********************************************/
181static void read_feat_rng(void)
182{
Andre Przywara5b005112022-11-14 15:38:58 +0000183#if (ENABLE_FEAT_RNG == FEAT_STATE_ALWAYS)
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +0000184 feat_detect_panic(is_armv8_5_rng_present(), "RNG");
185#endif
186}
187
188/****************************************************
189 * Feature : FEAT_BTI (Branch Target Identification)
190 ***************************************************/
191static void read_feat_bti(void)
192{
Andre Przywara5b005112022-11-14 15:38:58 +0000193#if (ENABLE_BTI == FEAT_STATE_ALWAYS)
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +0000194 feat_detect_panic(is_armv8_5_bti_present(), "BTI");
195#endif
196}
197
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +0000198/***********************************************
199 * Feature : FEAT_AMUv1p1 (AMU Extensions v1.1)
200 **********************************************/
201static void read_feat_amuv1p1(void)
202{
Andre Przywara5b005112022-11-14 15:38:58 +0000203#if (ENABLE_FEAT_AMUv1p1 == FEAT_STATE_ALWAYS)
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +0000204 feat_detect_panic(is_armv8_6_feat_amuv1p1_present(), "AMUv1p1");
205#endif
206}
207
208/*******************************************************
209 * Feature : FEAT_ECV (Enhanced Counter Virtualization)
210 ******************************************************/
211static void read_feat_ecv(void)
212{
Andre Przywara5b005112022-11-14 15:38:58 +0000213#if (ENABLE_FEAT_ECV == FEAT_STATE_ALWAYS)
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +0000214 unsigned int ecv = get_armv8_6_ecv_support();
215
216 feat_detect_panic(((ecv == ID_AA64MMFR0_EL1_ECV_SUPPORTED) ||
217 (ecv == ID_AA64MMFR0_EL1_ECV_SELF_SYNCH)), "ECV");
218#endif
219}
220
Jayanth Dodderi Chidanand4b5489c2022-03-28 15:28:55 +0100221/***********************************************************
222 * Feature : FEAT_TWED (Delayed Trapping of WFE Instruction)
223 **********************************************************/
224static void read_feat_twed(void)
225{
Andre Przywara5b005112022-11-14 15:38:58 +0000226#if (ENABLE_FEAT_TWED == FEAT_STATE_ALWAYS)
Jayanth Dodderi Chidanand4b5489c2022-03-28 15:28:55 +0100227 feat_detect_panic(is_armv8_6_twed_present(), "TWED");
228#endif
229}
230
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +0000231/******************************************************************
232 * Feature : FEAT_HCX (Extended Hypervisor Configuration Register)
233 *****************************************************************/
234static void read_feat_hcx(void)
235{
Andre Przywara5b005112022-11-14 15:38:58 +0000236#if (ENABLE_FEAT_HCX == FEAT_STATE_ALWAYS)
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +0000237 feat_detect_panic(is_feat_hcx_present(), "HCX");
238#endif
239}
240
241/**************************************************
242 * Feature : FEAT_RME (Realm Management Extension)
243 *************************************************/
244static void read_feat_rme(void)
245{
Andre Przywara5b005112022-11-14 15:38:58 +0000246#if (ENABLE_RME == FEAT_STATE_ALWAYS)
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +0000247 feat_detect_panic((get_armv9_2_feat_rme_support() !=
248 ID_AA64PFR0_FEAT_RME_NOT_SUPPORTED), "RME");
249#endif
250}
251
Jayanth Dodderi Chidanand69316752022-05-09 12:33:03 +0100252/******************************************************
253 * Feature : FEAT_BRBE (Branch Record Buffer Extension)
254 *****************************************************/
255static void read_feat_brbe(void)
256{
Andre Przywara5b005112022-11-14 15:38:58 +0000257#if (ENABLE_BRBE_FOR_NS == FEAT_STATE_ALWAYS)
Jayanth Dodderi Chidanand69316752022-05-09 12:33:03 +0100258 feat_detect_panic(is_feat_brbe_present(), "BRBE");
259#endif
260}
261
Jayanth Dodderi Chidananda793ccc2022-05-19 14:08:28 +0100262/******************************************************
263 * Feature : FEAT_TRBE (Trace Buffer Extension)
264 *****************************************************/
265static void read_feat_trbe(void)
266{
Andre Przywara5b005112022-11-14 15:38:58 +0000267#if (ENABLE_TRBE_FOR_NS == FEAT_STATE_ALWAYS)
Jayanth Dodderi Chidananda793ccc2022-05-19 14:08:28 +0100268 feat_detect_panic(is_feat_trbe_present(), "TRBE");
269#endif
270}
271
Juan Pablo Conde42305f22022-07-12 16:40:29 -0400272/******************************************************************
273 * Feature : FEAT_RNG_TRAP (Trapping support for RNDR/RNDRRS)
274 *****************************************************************/
275static void read_feat_rng_trap(void)
276{
Andre Przywara5b005112022-11-14 15:38:58 +0000277#if (ENABLE_FEAT_RNG_TRAP == FEAT_STATE_ALWAYS)
Juan Pablo Conde42305f22022-07-12 16:40:29 -0400278 feat_detect_panic(is_feat_rng_trap_present(), "RNG_TRAP");
279#endif
280}
281
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +0000282/***********************************************************************************
283 * TF-A supports many Arm architectural features starting from arch version
284 * (8.0 till 8.7+). These features are mostly enabled through build flags. This
285 * mechanism helps in validating these build flags in the early boot phase
286 * either in BL1 or BL31 depending on the platform and assists in identifying
287 * and notifying the features which are enabled but not supported by the PE.
288 *
289 * It reads all the enabled features ID-registers and ensures the features
290 * are supported by the PE.
291 * In case if they aren't it stops booting at an early phase and logs the error
292 * messages, notifying the platforms about the features that are not supported.
293 *
294 * Further the procedure is implemented with a tri-state approach for each feature:
295 * ENABLE_FEAT_xxx = 0 : The feature is disabled statically at compile time
296 * ENABLE_FEAT_xxx = 1 : The feature is enabled and must be present in hardware.
297 * There will be panic if feature is not present at cold boot.
298 * ENABLE_FEAT_xxx = 2 : The feature is enabled but dynamically enabled at runtime
299 * depending on hardware capability.
300 *
Andre Przywara5b005112022-11-14 15:38:58 +0000301 * For better readability, state values are defined with macros, namely:
302 * { FEAT_STATE_DISABLED, FEAT_STATE_ALWAYS, FEAT_STATE_CHECK }, taking values
303 * { 0, 1, 2 }, respectively, as their naming.
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +0000304 **********************************************************************************/
305void detect_arch_features(void)
306{
Andre Przywaracc4118d2022-11-14 15:42:44 +0000307 tainted = false;
308
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +0000309 /* v8.0 features */
310 read_feat_sb();
311 read_feat_csv2_2();
312
313 /* v8.1 features */
314 read_feat_pan();
315 read_feat_vhe();
316
317 /* v8.2 features */
318 read_feat_ras();
319
320 /* v8.3 features */
321 read_feat_pauth();
322
323 /* v8.4 features */
324 read_feat_dit();
Andre Przywara2c550e32022-11-10 14:41:07 +0000325 check_feature(ENABLE_FEAT_AMUv1, read_feat_amu_id_field(), "AMUv1");
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +0000326 read_feat_mpam();
327 read_feat_nv2();
328 read_feat_sel2();
329 read_feat_trf();
330
331 /* v8.5 features */
332 read_feat_mte();
333 read_feat_rng();
334 read_feat_bti();
Juan Pablo Conde42305f22022-07-12 16:40:29 -0400335 read_feat_rng_trap();
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +0000336
337 /* v8.6 features */
338 read_feat_amuv1p1();
Andre Przywarae8920f62022-11-10 14:28:01 +0000339 check_feature(ENABLE_FEAT_FGT, read_feat_fgt_id_field(), "FGT");
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +0000340 read_feat_ecv();
Jayanth Dodderi Chidanand4b5489c2022-03-28 15:28:55 +0100341 read_feat_twed();
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +0000342
343 /* v8.7 features */
344 read_feat_hcx();
345
Jayanth Dodderi Chidanand69316752022-05-09 12:33:03 +0100346 /* v9.0 features */
347 read_feat_brbe();
Jayanth Dodderi Chidananda793ccc2022-05-19 14:08:28 +0100348 read_feat_trbe();
Jayanth Dodderi Chidanand69316752022-05-09 12:33:03 +0100349
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +0000350 /* v9.2 features */
351 read_feat_rme();
Andre Przywaracc4118d2022-11-14 15:42:44 +0000352
353 if (tainted) {
354 panic();
355 }
Jayanth Dodderi Chidanand9461a892022-01-17 18:57:17 +0000356}