Merge "test(realm): add test for validating RTT calls"
diff --git a/Makefile b/Makefile
index e7efa2e..19f2a38 100644
--- a/Makefile
+++ b/Makefile
@@ -6,7 +6,7 @@
 
 # TFTF Version
 VERSION_MAJOR		:= 2
-VERSION_MINOR		:= 11
+VERSION_MINOR		:= 12
 
 MAKE_HELPERS_DIRECTORY := make_helpers/
 include ${MAKE_HELPERS_DIRECTORY}build_macros.mk
diff --git a/docs/change-log.rst b/docs/change-log.rst
index 89d9c10..0f22ded 100644
--- a/docs/change-log.rst
+++ b/docs/change-log.rst
@@ -7,6 +7,139 @@
 Tests are not guaranteed to be compatible. This also means that a version
 upgrade on the TF-A-Tests side might not necessarily introduce any new feature.
 
+Version 2.12
+------------
+
+New features
+^^^^^^^^^^^^
+
+-  More tests are made available in this release to help validate the
+   functionalities in the following areas:
+
+   - FF-A
+   - Realm Management Extension
+   - EL3 Runtime
+   - New Platform ports
+
+TFTF
+^^^^
+
+- SPM/FF-A Testing:
+
+    - Added tests to attest SPMC handles GPF in memory sharing ABIs:
+
+        - FFA_MEM_RETRIEVE_REQ
+        - FFA_MEM_FRAG_RX/TX
+        - FFA_MEM_RELINQUISH
+
+    - Added tests using the SMC64 ABI version for the FF-A memory management
+      interfaces.
+    - Tests to attest the SPMC is doing the necessary context management
+      of SME registers.
+    - Check that SRI delay flag use from normal world results in an error.
+    - FF-A Setup and discovery interfaces:
+
+        - FFA_VERSION called restricted to be used until first FF-A call,
+          from a given endpoint is handled.
+        - FFA_FEATURES tests changed to cater for feature return based on
+          EL of the FF-A endpoint, and the security state it relates to.
+        - FFA_PARTITION_INFO_GET changed to report support of indirect
+          messaging.
+
+  - New tests
+
+    - Added AMU counter restriction (RAZ) test.
+    - Added test to validate EL1 and EL2 registers during context switch.
+    - Added PCIe DOE library and tests.
+    - Added tests for newly supported features FEAT_FGT2, LS64_ACCDATA,
+      FEAT_Debugv8p9.
+    - Added test for 64-byte load/store instructions introduced by LS64.
+    - Added asymmetric feature testing for FEAT_SPE, FEAT_TRBE, and FEAT_TCR2.
+    - Added a new test suite supported by EL3 SPMC.
+    - Added SDEI tests for attempting to bind too many events.
+    - Added test suite to exercise SIMD context management with Cactus SP
+      (supported by EL3 SPMC).
+
+- Platforms
+
+    - Corstone-1000:
+
+        - Updated test skip list.
+
+    - FVP:
+
+        - Added PCIe support.
+
+    - Neoverse-RD:
+
+        - Defined naming convention for CSS macros.
+        - Introduced flash and ROS macros.
+        - Introduced timer and watchdog macros.
+        - Refactored header files for first gen platforms.
+        - refactored header files for second gen platforms.
+        - Removed deprecated header files.
+
+    - Versal-2:
+
+        - Added support for AMD Versal Gen 2 platform.
+        - Added AMD Versal Gen 2 documentation.
+
+- Miscellaneous:
+
+    - Added skeleton for asymmetric feature testing capability.
+    - Added asymmetric tests to skip when features are not present on a core.
+    - Added test to ensure arch timer in NWd is honored across world switch.
+    - Added test to confirm errata 2938996/2726228 workaround by checking
+      trbe_el1 access.
+    - Fixed GICD_ITARGETSR assertion to relax check on unicore systems.
+    - Fixed expect to print file and line number on failure for easier debugging.
+    - Fixed TRBE extension test to skip on Cortex-A520 and Cortex-X4 due to errata.
+    - Refactored to register undef_injection_handler only during register accesses
+      for better control over exceptions.
+    - Fixed firmware handoff register convention value to match updated spec.
+    - Updated toolchain requirements.
+
+Realm Management Extension
+^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+    - Set number of num_bps and num_wps.
+    - Updated rsi_ipa_state_get() function.
+    - Increased maximum number of RECs.
+    - Use random start REC.
+    - Added specific tests for FEAT_LPA2 on RMI tests.
+    - Added support for FEAT_LPA2 to the Realm Extension tests.
+    - Added test for rtt_fold unassigned.
+    - Added test for rtt_fold assigned.
+    - Unified SIMD test cases.
+    - Fixed pauth exception test.
+    - Fix(realm): cater for removal of SH from rtte.
+    - Fixed RMI and RSI definitions to match RMM Specification 1.0-rel0-rc1.
+    - Fixed RMI commands arguments descriptions.
+    - Fixed calculation of Realm's REC index.
+    - Fixed host_realm_init_ipa_state()'s retry path.
+    - Fixed realm initialisation code.
+    - Separated pool creation from Realm creation helpers.
+    - Fixed tests passing with TRP but not with RMM.
+
+Cactus (Secure-EL1 FF-A test partition)
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+    - Added support for Cactus SP to boot on EL3 SPMC.
+    - Added fix to skip computing linear core id.
+    - Fixed cactus_mm verbosity on some tests.
+
+Issues resolved since last release
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+    - Added "build" directory dependency to ensure correct ordering
+      on slow systems.
+    - Fixed race condition in tests_list generation by using grouped target.
+    - Fixed virtual timer enablement by moving it to command handler.
+    - Fixed test case test_smccc_callee_preserved.
+    - Updated definitions for sysregs on older toolchains.
+    - Fixed undef_injection_handler to clarify it catches both undef injections
+  and EL2 register traps.
+
 Version 2.11
 ------------
 
diff --git a/include/common/test_helpers.h b/include/common/test_helpers.h
index 28b1d4e..6b41e51 100644
--- a/include/common/test_helpers.h
+++ b/include/common/test_helpers.h
@@ -364,6 +364,13 @@
 		}							\
 	} while (false)
 
+#define SKIP_TEST_IF_DOUBLE_FAULT2_NOT_SUPPORTED()				\
+	do {									\
+		if (is_feat_double_fault2_present() == false) {			\
+			return TEST_RESULT_SKIPPED;				\
+		}								\
+	} while (false)
+
 /* Helper macro to verify if system suspend API is supported */
 #define is_psci_sys_susp_supported()	\
 		(tftf_get_psci_feature_info(SMC_PSCI_SYSTEM_SUSPEND)		\
diff --git a/include/lib/aarch64/arch.h b/include/lib/aarch64/arch.h
index 50cb5f9..dd2d967 100644
--- a/include/lib/aarch64/arch.h
+++ b/include/lib/aarch64/arch.h
@@ -452,12 +452,19 @@
 #define ID_AA64MMFR3_EL1_S1PIE_WIDTH		U(4)
 #define ID_AA64MMFR3_EL1_S1PIE_SUPPORTED	ULL(0x1)
 
+#define ID_AA64MMFR3_EL1_SCTLRX_SHIFT		U(4)
+#define ID_AA64MMFR3_EL1_SCTLRX_WIDTH		ULL(0x4)
+
 #define ID_AA64MMFR3_EL1_TCRX_SHIFT		U(0)
 #define ID_AA64MMFR3_EL1_TCRX_MASK		ULL(0xf)
 #define ID_AA64MMFR3_EL1_TCRX_WIDTH		U(4)
 #define ID_AA64MMFR3_EL1_TCR2_SUPPORTED		ULL(0x1)
 
 /* ID_AA64PFR1_EL1 definitions */
+#define ID_AA64PFR1_EL1_DF2_SHIFT		U(56)
+#define ID_AA64PFR1_EL1_DF2_WIDTH		U(4)
+#define ID_AA64PFR1_EL1_DF2_MASK		(0xf << ID_AA64PFR1_EL1_DF2_SHIFT)
+
 #define ID_AA64PFR1_EL1_GCS_SHIFT		U(44)
 #define ID_AA64PFR1_EL1_GCS_MASK		ULL(0xf)
 #define ID_AA64PFR1_EL1_GCS_WIDTH		U(4)
@@ -484,6 +491,7 @@
 #define ID_AA64PFR1_MPAM_FRAC_SHIFT		U(16)
 #define ID_AA64PFR1_MPAM_FRAC_MASK		ULL(0xf)
 
+#define ID_AA64PFR1_RAS_FRAC_MASK		ULL(0xf)
 #define ID_AA64PFR1_RAS_FRAC_SHIFT		U(12)
 #define ID_AA64PFR1_RAS_FRAC_MASK		ULL(0xf)
 #define ID_AA64PFR1_RAS_FRAC_WIDTH		U(4)
@@ -504,6 +512,9 @@
 #define ID_AA64PFR1_EL1_BT_MASK			ULL(0xf)
 #define BTI_IMPLEMENTED				ULL(1)	/* The BTI mechanism is implemented */
 
+#define ID_AA64PFR1_DF2_SHIFT			U(56)
+#define ID_AA64PFR1_DF2_WIDTH			ULL(0x4)
+
 /* ID_PFR1_EL1 definitions */
 #define ID_PFR1_VIRTEXT_SHIFT	U(12)
 #define ID_PFR1_VIRTEXT_MASK	U(0xf)
@@ -553,6 +564,15 @@
 #define SCTLR_DSSBS_BIT		(ULL(1) << 44)
 #define SCTLR_RESET_VAL		SCTLR_EL3_RES1
 
+/* SCTLR2_EL1 register definitions */
+#define SCTLR2_EL1		S3_0_C1_C0_3
+
+#define SCTLR2_NMEA_BIT		(UL(1) << 2)
+#define SCTLR2_EnADERR_BIT	(UL(1) << 3)
+#define SCTLR2_EnANERR_BIT	(UL(1) << 4)
+#define SCTLR2_EASE_BIT		(UL(1) << 5)
+#define SCTLR2_EnIDCP128_BIT	(UL(1) << 6)
+
 /* CPACR_El1 definitions */
 #define CPACR_EL1_FPEN(x)	((x) << 20)
 #define CPACR_EL1_FP_TRAP_EL0	U(0x1)
diff --git a/include/lib/aarch64/arch_features.h b/include/lib/aarch64/arch_features.h
index c7d824a..96d899a 100644
--- a/include/lib/aarch64/arch_features.h
+++ b/include/lib/aarch64/arch_features.h
@@ -525,4 +525,11 @@
 	return EXTRACT(ID_AA64PFR1_EL1_MTE, read_id_aa64pfr1_el1())
 		>= MTE_IMPLEMENTED_ELX;
 }
+
+static inline bool is_feat_double_fault2_present(void)
+{
+	return (EXTRACT(ID_AA64PFR1_EL1_DF2,
+		read_id_aa64pfr1_el1()) == 1UL);
+}
+
 #endif /* ARCH_FEATURES_H */
diff --git a/include/lib/aarch64/arch_helpers.h b/include/lib/aarch64/arch_helpers.h
index c906181..a765548 100644
--- a/include/lib/aarch64/arch_helpers.h
+++ b/include/lib/aarch64/arch_helpers.h
@@ -322,6 +322,8 @@
 DEFINE_SYSREG_RW_FUNCS(sctlr_el2)
 DEFINE_SYSREG_RW_FUNCS(sctlr_el3)
 
+DEFINE_RENAME_SYSREG_RW_FUNCS(sctlr2_el1, SCTLR2_EL1)
+
 DEFINE_SYSREG_RW_FUNCS(actlr_el1)
 DEFINE_SYSREG_RW_FUNCS(actlr_el2)
 DEFINE_SYSREG_RW_FUNCS(actlr_el3)
diff --git a/include/lib/aarch64/serror.h b/include/lib/aarch64/serror.h
index ac25f87..e6aa64f 100644
--- a/include/lib/aarch64/serror.h
+++ b/include/lib/aarch64/serror.h
@@ -7,8 +7,8 @@
 #ifndef __SERROR_H__
 #define  __SERROR_H__
 
-typedef bool (*exception_handler_t)(void);
-void register_custom_serror_handler(exception_handler_t handler);
+typedef bool (*serr_exception_handler_t)(bool *incr_elr_elx);
+void register_custom_serror_handler(serr_exception_handler_t handler);
 void unregister_custom_serror_handler(void);
 
 #endif /* __SERROR_H__ */
diff --git a/include/lib/tftf_lib.h b/include/lib/tftf_lib.h
index 36e2e0f..c65b061 100644
--- a/include/lib/tftf_lib.h
+++ b/include/lib/tftf_lib.h
@@ -140,48 +140,109 @@
 void waitms(uint64_t ms);
 void waitus(uint64_t us);
 
+/* Define fields in common for smc_args and smc_args_ext */
+#define FID_COMMON_ARGS()						\
+	/*								\
+	 * Function identifier. Identifies which function is being	\
+	 * invoked.							\
+	 */								\
+	uint32_t	fid;						\
+									\
+	u_register_t	arg1;						\
+	u_register_t	arg2;						\
+	u_register_t	arg3;						\
+	u_register_t	arg4;						\
+	u_register_t	arg5;						\
+	u_register_t	arg6;						\
+	u_register_t	arg7;
+
+/* Define fields in common for smc_ret_values and smc_ret_values_ext */
+#define COMMON_RETVALS()						\
+	u_register_t	ret0;						\
+	u_register_t	ret1;						\
+	u_register_t	ret2;						\
+	u_register_t	ret3;						\
+	u_register_t	ret4;						\
+	u_register_t	ret5;						\
+	u_register_t	ret6;						\
+	u_register_t	ret7;
+
+
 /*
- * SMC calls take a function identifier and up to 7 arguments.
+ * SMC calls take a function identifier and up to 7 arguments if using x8
+ * as an address pointing to a structure where return values are stored.
  * Additionally, few SMC calls that originate from EL2 leverage the seventh
  * argument explicitly. Given that TFTF runs in EL2, we need to be able to
  * specify it.
  */
 typedef struct {
-	/* Function identifier. Identifies which function is being invoked. */
-	uint32_t	fid;
-
-	u_register_t	arg1;
-	u_register_t	arg2;
-	u_register_t	arg3;
-	u_register_t	arg4;
-	u_register_t	arg5;
-	u_register_t	arg6;
-	u_register_t	arg7;
+	FID_COMMON_ARGS()
 } smc_args;
 
-/* SMC calls can return up to 8 register values */
+/*
+ * If x8 is not used as an address pointing to a structure where the return
+ * values are stored, SMC calls take up to 17 arguments.
+ */
 typedef struct {
-	u_register_t	ret0;
-	u_register_t	ret1;
-	u_register_t	ret2;
-	u_register_t	ret3;
-	u_register_t	ret4;
-	u_register_t	ret5;
-	u_register_t	ret6;
-	u_register_t	ret7;
+	FID_COMMON_ARGS()
+	u_register_t	arg8;
+	u_register_t	arg9;
+	u_register_t	arg10;
+	u_register_t	arg11;
+	u_register_t	arg12;
+	u_register_t	arg13;
+	u_register_t	arg14;
+	u_register_t	arg15;
+	u_register_t	arg16;
+	u_register_t	arg17;
+} smc_args_ext;
+
+/*
+ * SMC calls can return up to 8 register values if x8 is used as an address
+ * pointing to a structure where the return values are stored.
+ */
+typedef struct {
+	COMMON_RETVALS()
 } smc_ret_values;
 
 /*
- * Trigger an SMC call.
+ * If x8 is not used as an address pointing to a structure where the return
+ * values are stored, SMC calls return up to 18 register values.
+ */
+typedef struct {
+	COMMON_RETVALS()
+	u_register_t	ret8;
+	u_register_t	ret9;
+	u_register_t	ret10;
+	u_register_t	ret11;
+	u_register_t	ret12;
+	u_register_t	ret13;
+	u_register_t	ret14;
+	u_register_t	ret15;
+	u_register_t	ret16;
+	u_register_t	ret17;
+} smc_ret_values_ext;
+
+/*
+ * Trigger an SMC call. Return values are stored in structure pointed by address
+ * stored in x8.
  */
 smc_ret_values tftf_smc(const smc_args *args);
 
+/*
+ * Trigger an SMC call. Return values are stored in structure pointed by 'ret'
+ */
+void tftf_smc_no_retval_x8(const smc_args_ext *args, smc_ret_values_ext *ret);
+
 /* Assembler routine to trigger a SMC call. */
 smc_ret_values asm_tftf_smc64(uint32_t fid, u_register_t arg1, u_register_t arg2,
 			      u_register_t arg3, u_register_t arg4,
 			      u_register_t arg5, u_register_t arg6,
 			      u_register_t arg7);
 
+/* Assembler routine to trigger a SMC call without smc_ret_values in x8. */
+u_register_t asm_tftf_smc64_no_retval_x8(const smc_args_ext *args,
+					  smc_ret_values_ext *ret);
 /*
  * Update the SVE hint for the current CPU. Any SMC call made through tftf_smc
  * will update the SVE hint bit in the SMC Function ID.
diff --git a/include/runtime_services/host_realm_managment/host_shared_data.h b/include/runtime_services/host_realm_managment/host_shared_data.h
index 7cfffe6..7005c0d 100644
--- a/include/runtime_services/host_realm_managment/host_shared_data.h
+++ b/include/runtime_services/host_realm_managment/host_shared_data.h
@@ -70,7 +70,10 @@
 	REALM_PAUTH_FAULT,
 	REALM_DIT_CHECK_CMD,
 	REALM_SME_ID_REGISTERS,
-	REALM_SME_UNDEF_ABORT
+	REALM_SME_UNDEF_ABORT,
+	REALM_FEAT_DOUBLEFAULT2_TEST,
+	REALM_ATTESTATION,
+	REALM_ATTESTATION_FAULT
 };
 
 /*
diff --git a/include/runtime_services/host_realm_managment/realm_def.h b/include/runtime_services/host_realm_managment/realm_def.h
index 5258b87..226034f 100644
--- a/include/runtime_services/host_realm_managment/realm_def.h
+++ b/include/runtime_services/host_realm_managment/realm_def.h
@@ -101,4 +101,6 @@
 		(((idx) & ~MASK(RMI_MPIDR_AFF0)) << 	\
 		(RMI_MPIDR_AFF1_SHIFT - RMI_MPIDR_AFF0_WIDTH)));
 
+#define REALM_TOKEN_BUF_SIZE		GRANULE_SIZE
+
 #endif /* REALM_DEF_H */
diff --git a/lib/exceptions/aarch64/serror.c b/lib/exceptions/aarch64/serror.c
index 9c35712..a57514b 100644
--- a/lib/exceptions/aarch64/serror.c
+++ b/lib/exceptions/aarch64/serror.c
@@ -9,9 +9,9 @@
 #include <debug.h>
 #include <serror.h>
 
-static exception_handler_t custom_serror_handler;
+static serr_exception_handler_t custom_serror_handler;
 
-void register_custom_serror_handler(exception_handler_t handler)
+void register_custom_serror_handler(serr_exception_handler_t handler)
 {
 	custom_serror_handler = handler;
 }
@@ -23,9 +23,24 @@
 
 bool tftf_serror_handler(void)
 {
+	uint64_t elr_elx = IS_IN_EL2() ? read_elr_el2() : read_elr_el1();
+	bool resume = false;
+	bool incr_elr_elx = false;
+
 	if (custom_serror_handler == NULL) {
 		return false;
 	}
 
-	return custom_serror_handler();
+	resume = custom_serror_handler(&incr_elr_elx);
+
+	if (resume && incr_elr_elx) {
+		/* Move ELR to next instruction to allow tftf to continue */
+		if (IS_IN_EL2()) {
+			write_elr_el2(elr_elx + 4U);
+		} else {
+			write_elr_el1(elr_elx + 4U);
+		}
+	}
+
+	return resume;
 }
diff --git a/lib/smc/aarch64/asm_smc.S b/lib/smc/aarch64/asm_smc.S
index b11baa8..d4cede9 100644
--- a/lib/smc/aarch64/asm_smc.S
+++ b/lib/smc/aarch64/asm_smc.S
@@ -38,6 +38,59 @@
 
 	.endm
 
+	.macro smccc_conduit_nox8 _conduit
+
+	/*
+	 * Store address pointing at the smc_ret_values structure in the stack
+	 */
+	str	x1, [sp, #-16]!
+
+	/*
+	 * Store arguments in x0..x17. Start from highest registers so address
+	 * pointed by x0 is preserved until it is no longer needed.
+	 */
+	ldp	x16, x17, [x0, #128]
+	ldp	x14, x15, [x0, #112]
+	ldp	x12, x13, [x0, #96]
+	ldp	x10, x11, [x0, #80]
+	ldp	x8, x9, [x0, #64]
+	ldp	x6, x7, [x0, #48]
+	ldp	x4, x5, [x0, #32]
+	ldp	x2, x3, [x0, #16]
+	ldp	x0, x1, [x0, #0]
+
+	/* "Conduit" arguments are already stored in x0..x17 */
+	\_conduit	#0
+
+	/*
+	 * Store value received in x0 as x0 will be used to compute addresses
+	 * to store the results.
+	 */
+	str	x0, [sp, #-16]!
+
+	/* Load address of smc_ret_values structure into x0 */
+	ldr	x0, [sp, #16]
+
+	/* Store values x1..x17 in the smc_ret_values structure */
+	stp	x16, x17, [x0, #128]
+	stp	x14, x15, [x0, #112]
+	stp	x12, x13, [x0, #96]
+	stp	x10, x11, [x0, #80]
+	stp	x8, x9, [x0, #64]
+	stp	x6, x7, [x0, #48]
+	stp	x4, x5, [x0, #32]
+	stp	x2, x3, [x0, #16]
+	str	x1, [x0, #8]
+
+	/*
+	 * Load previously stored value of x0 into x1 and store it in the
+	 * smc_ret_values structure. Return sp to its original position.
+	 */
+	ldr	x1, [sp], #32
+	str	x1, [x0, #0]
+
+	.endm
+
 /* ---------------------------------------------------------------------------
  * smc_ret_values asm_tftf_smc64(uint32_t fid,
  *				 u_register_t arg1,
@@ -56,6 +109,17 @@
 	ret
 endfunc asm_tftf_smc64
 
+	.globl asm_tftf_smc64_no_retval_x8
+
+/* ---------------------------------------------------------------------------
+ * void asm_tftf_smc64_no_retval_x8(smc_args *args, smc_ret_values *ret);
+ * ---------------------------------------------------------------------------
+ */
+func asm_tftf_smc64_no_retval_x8
+	smccc_conduit_nox8 smc
+	ret
+endfunc asm_tftf_smc64_no_retval_x8
+
 /* ---------------------------------------------------------------------------
  * hvc_ret_values asm_tftf_hvcc64(uint32_t fid,
  *				 u_register_t arg1,
diff --git a/lib/smc/aarch64/smc.c b/lib/smc/aarch64/smc.c
index 9912e72..b0fea4b 100644
--- a/lib/smc/aarch64/smc.c
+++ b/lib/smc/aarch64/smc.c
@@ -102,3 +102,19 @@
 			      args->arg6,
 			      args->arg7);
 }
+
+void tftf_smc_no_retval_x8(const smc_args_ext *args, smc_ret_values_ext *ret)
+{
+	uint32_t fid = args->fid;
+	/* Copy args into new structure so the fid field can be modified */
+	smc_args_ext args_copy = *args;
+
+	if (tftf_smc_get_sve_hint()) {
+		fid |= MASK(FUNCID_SVE_HINT);
+	} else {
+		fid &= ~MASK(FUNCID_SVE_HINT);
+	}
+	args_copy.fid = fid;
+
+	asm_tftf_smc64_no_retval_x8(&args_copy, ret);
+}
diff --git a/plat/amd/versal2/include/platform_def.h b/plat/amd/versal2/include/platform_def.h
index 645a5eb..61392a7 100644
--- a/plat/amd/versal2/include/platform_def.h
+++ b/plat/amd/versal2/include/platform_def.h
@@ -122,5 +122,6 @@
 #define IRQ_TWDOG_INTID				U(0x51)
 
 #define TTC_TIMER_IRQ				U(75)
+#define TTC_CLK_SEL_OFFSET			U(0x360)
 
 #endif /* PLATFORM_DEF_H */
diff --git a/plat/xilinx/common/timer/timers.c b/plat/xilinx/common/timer/timers.c
index a6e1afa..f53cd84 100644
--- a/plat/xilinx/common/timer/timers.c
+++ b/plat/xilinx/common/timer/timers.c
@@ -27,7 +27,6 @@
 
 #define TTC_CNT_CNTRL_DISABLE_MASK	BIT(0)
 
-#define TTC_CLK_SEL_OFFSET		U(0x360)
 #define TTC_CLK_SEL_MASK		GENMASK(1, 0)
 
 #define TTC_CLK_SEL_PS_REF		BIT(0)
diff --git a/plat/xilinx/versal/tests_to_skip.txt b/plat/xilinx/versal/tests_to_skip.txt
index 87b9e41..997bc61 100644
--- a/plat/xilinx/versal/tests_to_skip.txt
+++ b/plat/xilinx/versal/tests_to_skip.txt
@@ -30,6 +30,10 @@
 PSCI System Suspend Validation/system suspend from all cores
 PSCI System Suspend Validation/Validate suspend to RAM functionality
 
+#Query runtime services
+Query runtime services/Query Vendor-Specific Service
+Query runtime services/Probe PMF Version
+
 #TESTS: el3-power-state
 EL3 power state parser validation/Create all power states and validate EL3 power state parsing
 EL3 power state parser validation/Create invalid local power state at all levels and validate EL3 power state parsing
diff --git a/plat/xilinx/versal_net/tests_to_skip.txt b/plat/xilinx/versal_net/tests_to_skip.txt
index 80e7cb2..f9668ee 100644
--- a/plat/xilinx/versal_net/tests_to_skip.txt
+++ b/plat/xilinx/versal_net/tests_to_skip.txt
@@ -58,6 +58,10 @@
 PSCI System Suspend Validation/system suspend from all cores
 PSCI System Suspend Validation/Validate suspend to RAM functionality
 
+#Query runtime services
+Query runtime services/Query Vendor-Specific Service
+Query runtime services/Probe PMF Version
+
 #TESTS: el3-power-state
 EL3 power state parser validation
 
diff --git a/plat/xilinx/zynqmp/tests_to_skip.txt b/plat/xilinx/zynqmp/tests_to_skip.txt
index 271fdc8..f72de18 100644
--- a/plat/xilinx/zynqmp/tests_to_skip.txt
+++ b/plat/xilinx/zynqmp/tests_to_skip.txt
@@ -49,6 +49,10 @@
 PSCI STAT/Stats test cases for CPU OFF
 PSCI STAT/Stats test cases after system suspend
 
+#Query runtime services
+Query runtime services/Query Vendor-Specific Service
+Query runtime services/Probe PMF Version
+
 #TESTS: el3-power-state
 EL3 power state parser validation
 
diff --git a/realm/aarch64/realm_exceptions.S b/realm/aarch64/realm_exceptions.S
index 210dd3e..c1d1c0c 100644
--- a/realm/aarch64/realm_exceptions.S
+++ b/realm/aarch64/realm_exceptions.S
@@ -43,8 +43,9 @@
 	b	interrupt_vector_entry
 end_vector_entry fiq_spx
 
-unhandled_exception serr_spx
-
+vector_entry serr_spx
+	b	serr_exception_vector_entry
+end_vector_entry serr_spx
 	/*
 	 * Lower EL using AArch64 : 0x400 - 0x600.
 	 */
@@ -116,6 +117,22 @@
 	eret
 endfunc sync_exception_vector_entry
 
+func serr_exception_vector_entry
+	sub	sp, sp, #0x100
+	save_gp_regs
+	mov	x19, sp
+	bl	tftf_serror_handler
+	cbnz	x0, 0f
+	mov	x0, x19
+	/* Save original stack pointer value on the stack */
+	add	x1, x0, #0x100
+	str	x1, [x0, #0xf8]
+	b	realm_print_exception
+0:	restore_gp_regs
+	add	sp, sp, #0x100
+	eret
+endfunc serr_exception_vector_entry
+
 func interrupt_vector_entry
 	sub	sp, sp, #0x100
 	save_gp_regs
diff --git a/realm/include/realm_helpers.h b/realm/include/realm_helpers.h
new file mode 100644
index 0000000..11c4423
--- /dev/null
+++ b/realm/include/realm_helpers.h
@@ -0,0 +1,15 @@
+/*
+ * Copyright (c) 2024, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef REALM_HELPERS_H
+#define REALM_HELPERS_H
+
+/* Generate 64-bit random number */
+unsigned long long realm_rand64(void);
+
+#endif /* REALM_HELPERS_H */
+
diff --git a/realm/include/realm_rsi.h b/realm/include/realm_rsi.h
index 92a078b..72ee80e 100644
--- a/realm/include/realm_rsi.h
+++ b/realm/include/realm_rsi.h
@@ -127,6 +127,21 @@
  */
 #define RSI_IPA_STATE_GET	SMC_RSI_FID(8U)
 
+/*
+ * ret0 == Status / error
+ * ret1 == Token maximum length
+ */
+#define RSI_ATTEST_TOKEN_INIT	SMC_RSI_FID(4U)
+
+/*
+ * arg0 == Base of buffer to write the token to
+ * arg1 == Offset within the buffer
+ * arg2 == Size of the buffer
+ * ret0 == Status / error
+ * ret1 == Size of received token hunk
+ */
+#define RSI_ATTEST_TOKEN_CONTINUE	SMC_RSI_FID(5U)
+
 typedef enum {
 	RSI_EMPTY = 0U,
 	RSI_RAM,
@@ -162,6 +177,23 @@
 /* This function will call the Host to request IPA of the NS shared buffer */
 u_register_t rsi_get_ns_buffer(void);
 
+/* This function will initialize the attestation context */
+u_register_t rsi_attest_token_init(u_register_t challenge_0,
+				   u_register_t challenge_1,
+				   u_register_t challenge_2,
+				   u_register_t challenge_3,
+				   u_register_t challenge_4,
+				   u_register_t challenge_5,
+				   u_register_t challenge_6,
+				   u_register_t challenge_7,
+				   u_register_t *out_token_upper_bound);
+
+/* This function will retrieve the (or part of) attestation token */
+u_register_t rsi_attest_token_continue(u_register_t buffer_addr,
+					u_register_t offset,
+					u_register_t buffer_size,
+					u_register_t *bytes_copied);
+
 /* This function call Host and request to exit Realm with proper exit code */
 void rsi_exit_to_host(enum host_call_cmd exit_code);
 
diff --git a/realm/include/realm_tests.h b/realm/include/realm_tests.h
index b58949b..2c1d3a1 100644
--- a/realm/include/realm_tests.h
+++ b/realm/include/realm_tests.h
@@ -27,6 +27,9 @@
 bool test_realm_multiple_rec_multiple_cpu_cmd(void);
 bool test_realm_sme_read_id_registers(void);
 bool test_realm_sme_undef_abort(void);
+bool test_realm_sctlr2_ease(void);
+bool test_realm_attestation(void);
+bool test_realm_attestation_fault(void);
 
 #endif /* REALM_TESTS_H */
 
diff --git a/realm/realm.mk b/realm/realm.mk
index 305c007..3e66adc 100644
--- a/realm/realm.mk
+++ b/realm/realm.mk
@@ -26,8 +26,10 @@
 	$(addprefix realm/,						\
 	aarch64/realm_entrypoint.S					\
 	aarch64/realm_exceptions.S					\
+	realm_attestation.c						\
 	realm_exception_report.c					\
 	realm_debug.c							\
+	realm_helpers.c							\
 	realm_interrupt.c						\
 	realm_multiple_rec.c						\
 	realm_pauth.c							\
@@ -43,6 +45,7 @@
 	lib/${ARCH}/misc_helpers.S					\
 	lib/smc/${ARCH}/asm_smc.S					\
 	lib/smc/${ARCH}/smc.c						\
+	lib/exceptions/${ARCH}/serror.c					\
 	lib/exceptions/${ARCH}/sync.c					\
 	lib/locks/${ARCH}/spinlock.S					\
 	lib/delay/delay.c						\
diff --git a/realm/realm_attestation.c b/realm/realm_attestation.c
new file mode 100644
index 0000000..e42484e
--- /dev/null
+++ b/realm/realm_attestation.c
@@ -0,0 +1,98 @@
+/*
+ * Copyright (c) 2024, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <assert.h>
+#include <stdio.h>
+
+#include <realm_rsi.h>
+
+#include <arch_features.h>
+#include <debug.h>
+#include <realm_def.h>
+#include <sync.h>
+#include <realm_helpers.h>
+
+#define CHALLENGE_SIZE	8
+
+static unsigned char attest_token_buffer[REALM_TOKEN_BUF_SIZE]
+	__aligned(GRANULE_SIZE);
+static uint64_t attest_token_offset;
+
+bool test_realm_attestation(void)
+{
+	u_register_t rsi_ret;
+	u_register_t bytes_copied;
+	u_register_t token_upper_bound;
+	u_register_t challenge[CHALLENGE_SIZE];
+
+	for (unsigned int i = 0U; i < CHALLENGE_SIZE; i++) {
+		challenge[i] = realm_rand64();
+	}
+
+	rsi_ret = rsi_attest_token_init(challenge[0],
+					challenge[1],
+					challenge[2],
+					challenge[3],
+					challenge[4],
+					challenge[5],
+					challenge[6],
+					challenge[7],
+					&token_upper_bound);
+
+	if (rsi_ret != RSI_SUCCESS) {
+		realm_printf("RSI_ATTEST_TOKEN_INIT"
+			     " returned with code %lu\n", rsi_ret);
+		return false;
+	}
+
+	if (token_upper_bound > REALM_TOKEN_BUF_SIZE) {
+		realm_printf("Attestation token buffer is not large enough"
+				" to hold the token.\n");
+		return false;
+	}
+
+	do {
+		rsi_ret = rsi_attest_token_continue(
+					(u_register_t)attest_token_buffer,
+					attest_token_offset,
+					REALM_TOKEN_BUF_SIZE,
+					&bytes_copied);
+
+		if ((rsi_ret != RSI_SUCCESS) && (rsi_ret != RSI_INCOMPLETE)) {
+			realm_printf("RSI_ATTEST_TOKEN_CONTINUE"
+				     " returned with code %lu\n", rsi_ret);
+			return false;
+		}
+
+		attest_token_offset += bytes_copied;
+
+	} while (rsi_ret != RSI_SUCCESS);
+
+	return true;
+}
+
+bool test_realm_attestation_fault(void)
+{
+	u_register_t rsi_ret;
+	u_register_t bytes_copied;
+
+	/*
+	 * This RSI call will fail as RSI_ATTEST_TOKEN_INIT has to be invoked
+	 * before calling RSI_ATTEST_TOKEN_CONTINUE.
+	 */
+	rsi_ret = rsi_attest_token_continue(
+				(u_register_t)attest_token_buffer,
+				attest_token_offset,
+				REALM_TOKEN_BUF_SIZE,
+				&bytes_copied);
+
+	if ((rsi_ret == RSI_SUCCESS) || (rsi_ret == RSI_INCOMPLETE)) {
+		return false;
+	}
+
+	return true;
+}
diff --git a/realm/realm_helpers.c b/realm/realm_helpers.c
new file mode 100644
index 0000000..6a3c57d
--- /dev/null
+++ b/realm/realm_helpers.c
@@ -0,0 +1,14 @@
+/*
+ * Copyright (c) 2024, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdlib.h>
+
+/* Generate 64-bit random number */
+unsigned long long realm_rand64(void)
+{
+	return ((unsigned long long)rand() << 32) | rand();
+}
+
diff --git a/realm/realm_payload_main.c b/realm/realm_payload_main.c
index 47f9b9f..3339b9a 100644
--- a/realm/realm_payload_main.c
+++ b/realm/realm_payload_main.c
@@ -16,11 +16,13 @@
 #include "realm_def.h"
 #include <realm_rsi.h>
 #include <realm_tests.h>
+#include <serror.h>
 #include <sync.h>
 #include <tftf_lib.h>
 
 static fpu_state_t rl_fpu_state_write;
 static fpu_state_t rl_fpu_state_read;
+
 /*
  * This function reads sleep time in ms from shared buffer and spins PE
  * in a loop for that time period.
@@ -176,7 +178,7 @@
 	/* Causes data abort */
 	realm_printf("Generate Data Abort\n");
 	*((volatile uint64_t *)base);
-	/* Should not return */
+
 	return false;
 }
 
@@ -200,6 +202,53 @@
 	return false;
 }
 
+static bool realm_serror_handler_doublefault(bool *incr_elr_elx)
+{
+	*incr_elr_elx = false;
+
+	if ((read_sctlr2_el1() & SCTLR2_EASE_BIT) != 0UL) {
+		/* The serror exception should have been routed here */
+		*incr_elr_elx = true;
+
+		return true;
+	}
+
+	rsi_exit_to_host(HOST_CALL_EXIT_FAILED_CMD);
+
+	/* Should have never get here */
+	return false;
+}
+
+static bool realm_sync_handler_doublefault(void)
+{
+	if ((read_sctlr2_el1() & SCTLR2_EASE_BIT) == 0UL) {
+		/* The sync exception should have been routed here */
+		return true;
+	}
+
+	rsi_exit_to_host(HOST_CALL_EXIT_FAILED_CMD);
+
+	/* Should have never get here */
+	return false;
+}
+
+static void test_realm_feat_doublefault2(void)
+{
+	u_register_t ease_bit = realm_shared_data_get_my_host_val(HOST_ARG2_INDEX);
+
+	unregister_custom_sync_exception_handler();
+	register_custom_sync_exception_handler(realm_sync_handler_doublefault);
+	register_custom_serror_handler(realm_serror_handler_doublefault);
+
+	if (ease_bit != 0UL) {
+		write_sctlr2_el1(read_sctlr2_el1() | SCTLR2_EASE_BIT);
+	} else {
+		write_sctlr2_el1(read_sctlr2_el1() & ~SCTLR2_EASE_BIT);
+	}
+
+	(void)test_realm_data_access_cmd();
+}
+
 /*
  * This is the entry function for Realm payload, it first requests the shared buffer
  * IPA address from Host using HOST_CALL/RSI, it reads the command to be executed,
@@ -213,7 +262,12 @@
 	bool test_succeed = false;
 
 	register_custom_sync_exception_handler(realm_exception_handler);
+
+	/* No serror handler registered by default */
+	unregister_custom_serror_handler();
+
 	realm_set_shared_structure((host_shared_data_t *)rsi_get_ns_buffer());
+
 	if (realm_get_my_shared_structure() != NULL) {
 		uint8_t cmd = realm_shared_data_get_my_realm_cmd();
 
@@ -232,6 +286,10 @@
 		case REALM_MULTIPLE_REC_MULTIPLE_CPU_CMD:
 			test_succeed = test_realm_multiple_rec_multiple_cpu_cmd();
 			break;
+		case REALM_FEAT_DOUBLEFAULT2_TEST:
+			test_realm_feat_doublefault2();
+			test_succeed = true;
+			break;
 		case REALM_INSTR_FETCH_CMD:
 			test_succeed = test_realm_instr_fetch_cmd();
 			break;
@@ -310,6 +368,12 @@
 		case REALM_SME_UNDEF_ABORT:
 			test_succeed = test_realm_sme_undef_abort();
 			break;
+		case REALM_ATTESTATION:
+			test_succeed = test_realm_attestation();
+			break;
+		case REALM_ATTESTATION_FAULT:
+			test_succeed = test_realm_attestation_fault();
+			break;
 		default:
 			realm_printf("%s() invalid cmd %u\n", __func__, cmd);
 			break;
diff --git a/realm/realm_rsi.c b/realm/realm_rsi.c
index b2a49d4..db2394c 100644
--- a/realm/realm_rsi.c
+++ b/realm/realm_rsi.c
@@ -87,3 +87,57 @@
 	}
 	return res.ret0;
 }
+
+/* This function will initialize the attestation context */
+u_register_t rsi_attest_token_init(u_register_t challenge_0,
+				   u_register_t challenge_1,
+				   u_register_t challenge_2,
+				   u_register_t challenge_3,
+				   u_register_t challenge_4,
+				   u_register_t challenge_5,
+				   u_register_t challenge_6,
+				   u_register_t challenge_7,
+				   u_register_t *out_token_upper_bound)
+{
+	smc_ret_values_ext res = {};
+
+	tftf_smc_no_retval_x8(&(smc_args_ext) {
+		RSI_ATTEST_TOKEN_INIT,
+		challenge_0,
+		challenge_1,
+		challenge_2,
+		challenge_3,
+		challenge_4,
+		challenge_5,
+		challenge_6,
+		challenge_7
+	},
+	&res);
+
+	if (res.ret0 == RSI_SUCCESS) {
+		*out_token_upper_bound = res.ret1;
+	}
+
+	return res.ret0;
+}
+
+/* This function will retrieve the (or part of) attestation token */
+u_register_t rsi_attest_token_continue(u_register_t buffer_addr,
+					u_register_t offset,
+					u_register_t buffer_size,
+					u_register_t *bytes_copied)
+{
+	smc_ret_values res = {};
+
+	res = tftf_smc(&(smc_args) {
+		RSI_ATTEST_TOKEN_CONTINUE,
+		buffer_addr,
+		offset,
+		buffer_size
+	});
+
+	if ((res.ret0 == RSI_SUCCESS) || (res.ret0 == RSI_INCOMPLETE)) {
+		*bytes_copied = res.ret1;
+	}
+	return res.ret0;
+}
diff --git a/spm/cactus/cactus_main.c b/spm/cactus/cactus_main.c
index 40f7618..b608d7b 100644
--- a/spm/cactus/cactus_main.c
+++ b/spm/cactus/cactus_main.c
@@ -288,12 +288,6 @@
 	enable_irq();
 	enable_fiq();
 
-	/* Disable the arch timer at boot. */
-	write_cntp_ctl_el0(0);
-
-	/* Enable the arch timer virtual interrupt. */
-	spm_interrupt_enable(TIMER_VIRTUAL_INTID, true, 0);
-
 	if (primary_cold_boot == false) {
 		goto msg_loop;
 	}
diff --git a/spm/cactus/cactus_tests/cactus_test_timer.c b/spm/cactus/cactus_tests/cactus_test_timer.c
index 6c8af0c..246afe2 100644
--- a/spm/cactus/cactus_tests/cactus_test_timer.c
+++ b/spm/cactus/cactus_tests/cactus_test_timer.c
@@ -7,6 +7,7 @@
 #include "cactus_message_loop.h"
 #include "cactus_test_cmds.h"
 #include "debug.h"
+#include <spm_helpers.h>
 
 uint32_t ms_to_ticks(uint64_t ms)
 {
@@ -19,7 +20,12 @@
 	uint64_t wait_time = cactus_get_timer_wait_time(*args);
 	uint32_t ticks = ms_to_ticks(deadline_ms);
 
+	/* Disable the arch timer. */
 	write_cntp_ctl_el0(0);
+
+	/* Enable the arch timer virtual interrupt. */
+	spm_interrupt_enable(TIMER_VIRTUAL_INTID, true, 0);
+
 	write_cntp_tval_el0(ticks);
 	write_cntp_ctl_el0(1);
 
diff --git a/tftf/tests/misc_tests/test_ras_kfh.c b/tftf/tests/misc_tests/test_ras_kfh.c
index b38d6c4..f92e048 100644
--- a/tftf/tests/misc_tests/test_ras_kfh.c
+++ b/tftf/tests/misc_tests/test_ras_kfh.c
@@ -13,9 +13,10 @@
 static volatile uint64_t serror_triggered;
 extern void inject_unrecoverable_ras_error(void);
 
-static bool serror_handler(void)
+static bool serror_handler(bool *incr_elr_elx)
 {
 	serror_triggered = 1;
+	*incr_elr_elx = false;
 	return true;
 }
 
diff --git a/tftf/tests/misc_tests/test_ras_kfh_reflect.c b/tftf/tests/misc_tests/test_ras_kfh_reflect.c
index d24fc47..eb93d72 100644
--- a/tftf/tests/misc_tests/test_ras_kfh_reflect.c
+++ b/tftf/tests/misc_tests/test_ras_kfh_reflect.c
@@ -33,9 +33,10 @@
  * One test each to verify reflection in sync and async exception.
  *
  */
-static bool serror_handler(void)
+static bool serror_handler(bool *incr_elr_elx)
 {
 	serror_triggered = 1;
+	*incr_elr_elx = false;
 	tftf_testcase_printf("SError event received.\n");
 	return true;
 }
diff --git a/tftf/tests/runtime_services/realm_payload/host_realm_payload_tests.c b/tftf/tests/runtime_services/realm_payload/host_realm_payload_tests.c
index e22a9f1..ce5409c 100644
--- a/tftf/tests/runtime_services/realm_payload/host_realm_payload_tests.c
+++ b/tftf/tests/runtime_services/realm_payload/host_realm_payload_tests.c
@@ -2525,3 +2525,151 @@
 	}
 	return res;
 }
+
+/*
+ * Test aims to test that TF-RMM takes SCTLR2_EL1.EASE bit into account
+ * when injecting a SEA (Feat_DoubleFault2).
+ */
+test_result_t host_test_feat_doublefault2(void)
+{
+	bool ret;
+	u_register_t rec_flag;
+	u_register_t base;
+	struct realm realm;
+	struct rtt_entry rtt;
+	u_register_t feature_flag = 0UL;
+	long sl = RTT_MIN_LEVEL;
+
+	SKIP_TEST_IF_RME_NOT_SUPPORTED_OR_RMM_IS_TRP();
+	SKIP_TEST_IF_DOUBLE_FAULT2_NOT_SUPPORTED();
+
+	if (is_feat_52b_on_4k_2_supported() == true) {
+		feature_flag = RMI_FEATURE_REGISTER_0_LPA2;
+		sl = RTT_MIN_LEVEL_LPA2;
+	}
+
+	rec_flag = RMI_RUNNABLE;
+
+	if (!host_create_activate_realm_payload(&realm,
+					(u_register_t)REALM_IMAGE_BASE,
+				feature_flag, sl, &rec_flag, 1U)) {
+		return TEST_RESULT_FAIL;
+	}
+
+	/*
+	 * Allocate a page so we pass its address as first argument of
+	 * the test command. The test will attempt an instruction fetch
+	 * from that address, which will fail as the address will not
+	 * be mapped into the Realm.
+	 */
+	base = (u_register_t)page_alloc(PAGE_SIZE);
+
+	(void)host_rmi_rtt_readentry(realm.rd, base, 3L, &rtt);
+	if (rtt.state != RMI_UNASSIGNED ||
+			(rtt.ripas != RMI_EMPTY)) {
+		ERROR("wrong initial state\n");
+		host_destroy_realm(&realm);
+		return TEST_RESULT_FAIL;
+	}
+
+	host_shared_data_set_host_val(&realm, 0U, HOST_ARG1_INDEX, base);
+
+	for (unsigned int i = 0U; i < 2U; i++) {
+		host_shared_data_set_host_val(&realm, 0U, HOST_ARG2_INDEX,
+					      (unsigned long)i);
+
+		/* Rec0 expect IA due to SEA unassigned empty page */
+		ret = host_enter_realm_execute(&realm, REALM_FEAT_DOUBLEFAULT2_TEST,
+							RMI_EXIT_HOST_CALL, 0U);
+
+		if (!ret) {
+			host_destroy_realm(&realm);
+			return TEST_RESULT_FAIL;
+		}
+	}
+
+	host_destroy_realm(&realm);
+	return TEST_RESULT_SUCCESS;
+}
+
+/*
+ * @Test_Aim@ Create realm with a single REC
+ * Test attestation process for REC
+ */
+test_result_t host_realm_test_attestation(void)
+{
+	bool ret1, ret2;
+	u_register_t rec_flag[] = {RMI_RUNNABLE};
+	struct realm realm;
+	u_register_t feature_flag = 0UL;
+	long sl = RTT_MIN_LEVEL;
+
+	SKIP_TEST_IF_RME_NOT_SUPPORTED_OR_RMM_IS_TRP();
+
+	if (is_feat_52b_on_4k_2_supported() == true) {
+		feature_flag = RMI_FEATURE_REGISTER_0_LPA2;
+		sl = RTT_MIN_LEVEL_LPA2;
+	}
+
+	if (!host_create_activate_realm_payload(&realm, (u_register_t)REALM_IMAGE_BASE,
+				feature_flag, sl, rec_flag, 1U)) {
+		return TEST_RESULT_FAIL;
+	}
+
+	ret1 = host_enter_realm_execute(&realm, REALM_ATTESTATION,
+				RMI_EXIT_HOST_CALL, 0U);
+	if (!ret1) {
+		ERROR("Realm attestation test failed\n");
+	}
+
+	ret2 = host_destroy_realm(&realm);
+
+	if (!ret1 || !ret2) {
+		ERROR("%s(): enter=%d destroy=%d\n",
+				__func__, ret1, ret2);
+		return TEST_RESULT_FAIL;
+	}
+
+	return TEST_RESULT_SUCCESS;
+}
+
+/*
+ * @Test_Aim@ Create realm with a single REC
+ * Test attestation fault for REC
+ */
+test_result_t host_realm_test_attestation_fault(void)
+{
+	bool ret1, ret2;
+	u_register_t rec_flag[] = {RMI_RUNNABLE};
+	struct realm realm;
+	u_register_t feature_flag = 0UL;
+	long sl = RTT_MIN_LEVEL;
+
+	SKIP_TEST_IF_RME_NOT_SUPPORTED_OR_RMM_IS_TRP();
+
+	if (is_feat_52b_on_4k_2_supported() == true) {
+		feature_flag = RMI_FEATURE_REGISTER_0_LPA2;
+		sl = RTT_MIN_LEVEL_LPA2;
+	}
+
+	if (!host_create_activate_realm_payload(&realm, (u_register_t)REALM_IMAGE_BASE,
+				feature_flag, sl, rec_flag, 1U)) {
+		return TEST_RESULT_FAIL;
+	}
+
+	ret1 = host_enter_realm_execute(&realm, REALM_ATTESTATION_FAULT,
+				RMI_EXIT_HOST_CALL, 0U);
+	if (!ret1) {
+		ERROR("Realm attestation fault test failed\n");
+	}
+
+	ret2 = host_destroy_realm(&realm);
+
+	if (!ret1 || !ret2) {
+		ERROR("%s(): enter=%d destroy=%d\n",
+				__func__, ret1, ret2);
+		return TEST_RESULT_FAIL;
+	}
+
+	return TEST_RESULT_SUCCESS;
+}
diff --git a/tftf/tests/tests-realm-payload.xml b/tftf/tests/tests-realm-payload.xml
index 02a14de..36fc52b 100644
--- a/tftf/tests/tests-realm-payload.xml
+++ b/tftf/tests/tests-realm-payload.xml
@@ -76,6 +76,8 @@
 	  function="host_realm_set_ripas" />
 	  <testcase name="Realm reject set_ripas"
 	  function="host_realm_reject_set_ripas" />
+	  <testcase name="Realm FEAT_DoubleFault2"
+	  function="host_test_feat_doublefault2" />
 	  <!-- Test case related to SVE support and SIMD state -->
 	  <testcase name="Check RMI reports proper SVE VL"
 	  function="host_check_rmi_reports_proper_sve_vl" />
@@ -126,5 +128,9 @@
 	  function="host_test_data_bound_non_lpa2_realm_on_lpa2plat" />
 	  <testcase name="Test Realm creation with LPA2 enabled but FEAT_LPA2 absent on platform"
 	  function="host_test_lpa2_realm_on_non_lpa2plat" />
+	  <!-- Test cases related to Attestation -->
+	  <testcase name="Test realm attestation" function="host_realm_test_attestation" />
+	  <testcase name="Test realm attestation fault"
+	  function="host_realm_test_attestation_fault" />
   </testsuite>
 </testsuites>