Merge changes from topic "kc/stmm"

* changes:
  refactor: move StMM to cactus tertiary
  feat(hob): add boot-time prints for cactus-stmm HOB list
  refactor(cactus): map boot information regions
  feat(hob): add HOB definitions to TFTF
  feat(spm): add STMM cactus partition
diff --git a/include/lib/hob/efi_types.h b/include/lib/hob/efi_types.h
new file mode 100644
index 0000000..2d1158d
--- /dev/null
+++ b/include/lib/hob/efi_types.h
@@ -0,0 +1,86 @@
+/*
+ * Copyright (c) 2024, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef EFI_TYPES_H
+#define EFI_TYPES_H
+
+#include <lib/libc/uuid.h>
+#include <stdint.h>
+
+typedef uint64_t efi_physical_address_t;
+
+/*****************************************************************************
+ *                            EFI_BOOT_MODE                                  *
+ *****************************************************************************/
+
+typedef uint32_t efi_boot_mode_t;
+/**
+ * EFI boot mode.
+ */
+#define EFI_BOOT_WITH_FULL_CONFIGURATION                   U(0x00)
+#define EFI_BOOT_WITH_MINIMAL_CONFIGURATION                U(0x01)
+#define EFI_BOOT_ASSUMING_NO_CONFIGURATION_CHANGES         U(0x02)
+#define EFI_BOOT_WITH_FULL_CONFIGURATION_PLUS_DIAGNOSTICS  U(0x03)
+#define EFI_BOOT_WITH_DEFAULT_SETTINGS                     U(0x04)
+#define EFI_BOOT_ON_S4_RESUME                              U(0x05)
+#define EFI_BOOT_ON_S5_RESUME                              U(0x06)
+#define EFI_BOOT_WITH_MFG_MODE_SETTINGS                    U(0x07)
+#define EFI_BOOT_ON_S2_RESUME                              U(0x10)
+#define EFI_BOOT_ON_S3_RESUME                              U(0x11)
+#define EFI_BOOT_ON_FLASH_UPDATE                           U(0x12)
+#define EFI_BOOT_IN_RECOVERY_MODE                          U(0x20)
+
+/*****************************************************************************
+ *                            EFI_RESOURCE_TYPE                              *
+ *****************************************************************************/
+
+typedef uint32_t efi_resource_type_t;
+
+/**
+ * Value of EFI_RESOURCE_TYPE used in EFI_HOB_RESOURCE_DESCRIPTOR.
+ */
+#define EFI_RESOURCE_SYSTEM_MEMORY          U(0x00000000)
+#define EFI_RESOURCE_MEMORY_MAPPED_IO       U(0x00000001)
+#define EFI_RESOURCE_IO                     U(0x00000002)
+#define EFI_RESOURCE_FIRMWARE_DEVICE        U(0x00000003)
+#define EFI_RESOURCE_MEMORY_MAPPED_IO_PORT  U(0x00000004)
+#define EFI_RESOURCE_MEMORY_RESERVED        U(0x00000005)
+#define EFI_RESOURCE_IO_RESERVED            U(0x00000006)
+
+/*****************************************************************************
+ *                       EFI_RESOURCE_ATTRIBUTE_TYPE                         *
+ *****************************************************************************/
+
+typedef uint32_t efi_resource_attribute_type_t;
+
+#define EFI_RESOURCE_ATTRIBUTE_PRESENT                  U(0x00000001)
+#define EFI_RESOURCE_ATTRIBUTE_INITIALIZED              U(0x00000002)
+#define EFI_RESOURCE_ATTRIBUTE_TESTED                   U(0x00000004)
+#define EFI_RESOURCE_ATTRIBUTE_READ_PROTECTED           U(0x00000080)
+#define EFI_RESOURCE_ATTRIBUTE_WRITE_PROTECTED          U(0x00000100)
+#define EFI_RESOURCE_ATTRIBUTE_EXECUTION_PROTECTED      U(0x00000200)
+#define EFI_RESOURCE_ATTRIBUTE_PERSISTENT               U(0x00800000)
+#define EFI_RESOURCE_ATTRIBUTE_SINGLE_BIT_ECC           U(0x00000008)
+#define EFI_RESOURCE_ATTRIBUTE_MULTIPLE_BIT_ECC         U(0x00000010)
+#define EFI_RESOURCE_ATTRIBUTE_ECC_RESERVED_1           U(0x00000020)
+#define EFI_RESOURCE_ATTRIBUTE_ECC_RESERVED_2           U(0x00000040)
+#define EFI_RESOURCE_ATTRIBUTE_UNCACHEABLE              U(0x00000400)
+#define EFI_RESOURCE_ATTRIBUTE_WRITE_COMBINEABLE        U(0x00000800)
+#define EFI_RESOURCE_ATTRIBUTE_WRITE_THROUGH_CACHEABLE  U(0x00001000)
+#define EFI_RESOURCE_ATTRIBUTE_WRITE_BACK_CACHEABLE     U(0x00002000)
+#define EFI_RESOURCE_ATTRIBUTE_16_BIT_IO                U(0x00004000)
+#define EFI_RESOURCE_ATTRIBUTE_32_BIT_IO                U(0x00008000)
+#define EFI_RESOURCE_ATTRIBUTE_64_BIT_IO                U(0x00010000)
+#define EFI_RESOURCE_ATTRIBUTE_UNCACHED_EXPORTED        U(0x00020000)
+#define EFI_RESOURCE_ATTRIBUTE_READ_PROTECTABLE         U(0x00100000)
+#define EFI_RESOURCE_ATTRIBUTE_WRITE_PROTECTABLE        U(0x00200000)
+#define EFI_RESOURCE_ATTRIBUTE_EXECUTION_PROTECTABLE    U(0x00400000)
+#define EFI_RESOURCE_ATTRIBUTE_PERSISTABLE              U(0x01000000)
+#define EFI_RESOURCE_ATTRIBUTE_READ_ONLY_PROTECTED      U(0x00040000)
+#define EFI_RESOURCE_ATTRIBUTE_READ_ONLY_PROTECTABLE    U(0x00080000)
+#define EFI_RESOURCE_ATTRIBUTE_MORE_RELIABLE            U(0x02000000)
+
+#endif  /* EFI_TYPES_H */
diff --git a/include/lib/hob/hob.h b/include/lib/hob/hob.h
new file mode 100644
index 0000000..4e96cbb
--- /dev/null
+++ b/include/lib/hob/hob.h
@@ -0,0 +1,101 @@
+/*
+ * Copyright (c) 2024, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef HOB_H
+#define HOB_H
+
+#include <lib/libc/uuid.h>
+#include <stdbool.h>
+#include <stdint.h>
+
+#include <lib/hob/efi_types.h>
+#include <lib/utils_def.h>
+
+/*****************************************************************************
+ *                            Hob Generic Header                             *
+ *****************************************************************************/
+
+/**
+ * HobType values of EFI_HOB_GENERIC_HEADER.
+ */
+#define EFI_HOB_TYPE_HANDOFF              U(0x0001)
+#define EFI_HOB_TYPE_MEMORY_ALLOCATION    U(0x0002)
+#define EFI_HOB_TYPE_RESOURCE_DESCRIPTOR  U(0x0003)
+#define EFI_HOB_TYPE_GUID_EXTENSION       U(0x0004)
+#define EFI_HOB_TYPE_FV                   U(0x0005)
+#define EFI_HOB_TYPE_CPU                  U(0x0006)
+#define EFI_HOB_TYPE_MEMORY_POOL          U(0x0007)
+#define EFI_HOB_TYPE_FV2                  U(0x0009)
+#define EFI_HOB_TYPE_LOAD_PEIM_UNUSED     U(0x000A)
+#define EFI_HOB_TYPE_UEFI_CAPSULE         U(0x000B)
+#define EFI_HOB_TYPE_FV3                  U(0x000C)
+#define EFI_HOB_TYPE_UNUSED               U(0xFFFE)
+#define EFI_HOB_TYPE_END_OF_HOB_LIST      U(0xFFFF)
+
+struct efi_hob_generic_header {
+	uint16_t hob_type;
+	uint16_t hob_length;
+	uint32_t reserved;
+};
+
+/*****************************************************************************
+ *                               PHIT Hob.                                   *
+ *****************************************************************************/
+
+#define EFI_HOB_HANDOFF_TABLE_VERSION     U(0x000a)
+
+struct efi_hob_handoff_info_table {
+	struct efi_hob_generic_header header;
+	uint32_t version;
+	efi_boot_mode_t  boot_mode;
+	efi_physical_address_t efi_memory_top;
+	efi_physical_address_t efi_memory_bottom;
+	efi_physical_address_t efi_free_memory_top;
+	efi_physical_address_t efi_free_memory_bottom;
+	efi_physical_address_t efi_end_of_hob_list;
+};
+
+/*****************************************************************************
+ *                       Resource Descriptor Hob.                            *
+ *****************************************************************************/
+
+struct efi_hob_resource_descriptor {
+	struct efi_hob_generic_header header;
+	struct efi_guid owner;
+	efi_resource_type_t resource_type;
+	efi_resource_attribute_type_t resource_attribute;
+	efi_physical_address_t physical_start;
+	uint64_t resource_length;
+};
+
+/*****************************************************************************
+ *                           Guid Extension Hob.                             *
+ *****************************************************************************/
+struct efi_hob_guid_type {
+	struct efi_hob_generic_header header;
+	struct efi_guid name;
+	/**
+	 * Guid specific data goes here.
+	 */
+};
+
+/*****************************************************************************
+ *                           Firmware Volume Hob.                            *
+ *****************************************************************************/
+struct efi_hob_firmware_volume {
+	struct efi_hob_generic_header header;
+	efi_physical_address_t base_address;
+	uint64_t length;
+};
+
+/*****************************************************************************
+ *                              Interfaces.                                  *
+ *****************************************************************************/
+
+void dump_hob_list(struct efi_hob_handoff_info_table *hob_list);
+void dump_hob_generic_header(struct efi_hob_generic_header *header);
+
+#endif /* HOB_H */
diff --git a/include/lib/hob/hob_guid.h b/include/lib/hob/hob_guid.h
new file mode 100644
index 0000000..507b2e9
--- /dev/null
+++ b/include/lib/hob/hob_guid.h
@@ -0,0 +1,32 @@
+/*
+ * Copyright (c) 2024, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef HOB_GUID_H
+#define HOB_GUID_H
+
+#include <stdint.h>
+#include <lib/hob/efi_types.h>
+
+/**
+ * Guid used for creating StandaloneMm related information.
+ */
+
+#define MM_PEI_MMRAM_MEMORY_RESERVE_GUID                                        \
+{                                                                               \
+	0x0703f912, 0xbf8d, 0x4e2a, {0xbe, 0x07, 0xab, 0x27, 0x25, 0x25, 0xc5, 0x92 } \
+}
+
+#define MM_NS_BUFFER_GUID                                                       \
+{                                                                               \
+	0xf00497e3, 0xbfa2, 0x41a1, {0x9d, 0x29, 0x54, 0xc2, 0xe9, 0x37, 0x21, 0xc5 } \
+}
+
+struct mm_comm_buffer_desc {
+	efi_physical_address_t physical_start;
+	uint64_t number_of_pages;
+};
+
+#endif /* HOB_GUID_H */
diff --git a/include/lib/hob/mmram.h b/include/lib/hob/mmram.h
new file mode 100644
index 0000000..b269c64
--- /dev/null
+++ b/include/lib/hob/mmram.h
@@ -0,0 +1,45 @@
+/*
+ * Copyright (c) 2024, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
+ */
+
+#ifndef MMRAM_H
+#define MMRAM_H
+
+#include <lib/hob/efi_types.h>
+
+/**
+ * MMRAM states and capabilities
+ * See UEFI Platform Initialization Specification Version 1.8, IV-5.3.5
+ */
+#define EFI_MMRAM_OPEN                U(0x00000001)
+#define EFI_MMRAM_CLOSED              U(0x00000002)
+#define EFI_MMRAM_LOCKED              U(0x00000004)
+#define EFI_CACHEABLE                 U(0x00000008)
+#define EFI_ALLOCATED                 U(0x00000010)
+#define EFI_NEEDS_TESTING             U(0x00000020)
+#define EFI_NEEDS_ECC_INITIALIZATION  U(0x00000040)
+
+#define EFI_SMRAM_OPEN    EFI_MMRAM_OPEN
+#define EFI_SMRAM_CLOSED  EFI_MMRAM_CLOSED
+#define EFI_SMRAM_LOCKED  EFI_MMRAM_LOCKED
+
+struct efi_mmram_descriptor {
+	efi_physical_address_t physical_start;
+	efi_physical_address_t cpu_start;
+	uint64_t physical_size;
+	uint64_t region_state;
+};
+
+/**
+ * MMRAM block descriptor
+ * This definition comes from
+ *     https://github.com/tianocore/edk2/blob/master/StandaloneMmPkg/Include/Guid/MmramMemoryReserve.h
+ */
+struct efi_mmram_hob_descriptor_block {
+	uint32_t number_of_mm_reserved_regions;
+	struct efi_mmram_descriptor descriptor[];
+};
+
+#endif /* MMRAM_H */
diff --git a/include/lib/libc/uuid.h b/include/lib/libc/uuid.h
index 3a1699b..8ba973d 100644
--- a/include/lib/libc/uuid.h
+++ b/include/lib/libc/uuid.h
@@ -51,6 +51,18 @@
 	uint8_t		node[_UUID_NODE_LEN];
 };
 
+struct efi_guid {
+	uint32_t time_low;
+	uint16_t time_mid;
+	uint16_t time_hi_and_version;
+	uint8_t clock_seq_and_node[8];
+};
+
+union uuid_helper_t {
+	struct uuid uuid_struct;
+	struct efi_guid efi_guid;
+};
+
 typedef struct uuid uuid_t;
 
 #endif /* _SYS_UUID_H_ */
diff --git a/lib/hob/hob.c b/lib/hob/hob.c
new file mode 100644
index 0000000..4fa3cf3
--- /dev/null
+++ b/lib/hob/hob.c
@@ -0,0 +1,142 @@
+/*
+ * Copyright (c) 2024, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+#include <stddef.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <debug.h>
+#include <lib/hob/hob.h>
+#include <lib/hob/hob_guid.h>
+#include <lib/hob/mmram.h>
+#include <lib/utils/uuid_utils.h>
+#include <lib/utils_def.h>
+
+#define ALIGN_UP(x, a)		((x + (a - 1)) & ~(a - 1))
+
+void dump_hob_generic_header(struct efi_hob_generic_header *h)
+{
+	assert(h != NULL);
+	INFO("Hob Type: 0x%x\n", h->hob_type);
+	INFO("Hob Length: 0x%x\n", h->hob_length);
+}
+
+void dump_efi_mmram_descriptor(struct efi_mmram_descriptor *m)
+{
+	INFO("        Physical start: 0x%llx\n", m->physical_start);
+	INFO("        CPU start: 0x%llx\n", m->cpu_start);
+	INFO("        Physical size: 0x%llx\n", m->physical_size);
+	INFO("        Region state: 0x%llx\n", m->region_state);
+}
+
+void dump_efi_hob_firmware_volume(struct efi_hob_firmware_volume *fv)
+{
+	dump_hob_generic_header(&fv->header);
+	INFO("    Base_address: 0x%llx\n", fv->base_address);
+	INFO("    Length: 0x%llx\n", fv->length);
+}
+
+static void dump_efi_guid(struct efi_guid guid)
+{
+	INFO("    Time low: 0x%x\n", guid.time_low);
+	INFO("    Time mid: 0x%x\n", guid.time_mid);
+	INFO("    Time hi and version: 0x%x\n", guid.time_hi_and_version);
+	INFO("    Clock_seq_and_node: [0x%x, 0x%x, 0x%x, 0x%x, 0x%x, 0x%x, 0x%x, 0x%x]\n",
+		guid.clock_seq_and_node[0],
+		guid.clock_seq_and_node[1],
+		guid.clock_seq_and_node[2],
+		guid.clock_seq_and_node[3],
+		guid.clock_seq_and_node[4],
+		guid.clock_seq_and_node[5],
+		guid.clock_seq_and_node[6],
+		guid.clock_seq_and_node[7]);
+}
+
+static void dump_guid_hob_data(struct efi_hob_guid_type *guid_hob)
+{
+	union uuid_helper_t uuid_name = {.efi_guid = guid_hob->name};
+	union uuid_helper_t mmram_mem_resv_guid = {
+		.efi_guid = (struct efi_guid)MM_PEI_MMRAM_MEMORY_RESERVE_GUID};
+	union uuid_helper_t ns_buffer_guid = {
+		.efi_guid = (struct efi_guid)MM_NS_BUFFER_GUID};
+	uintptr_t guid_data = (uintptr_t)(&guid_hob->name + 1);
+
+	/* Dump GUID HOB data according to GUID type. */
+	if (uuid_equal(&uuid_name.uuid_struct,
+		       &mmram_mem_resv_guid.uuid_struct)) {
+		struct efi_mmram_hob_descriptor_block *mmram_desc_block =
+			(struct efi_mmram_hob_descriptor_block *)guid_data;
+		INFO("    MM_PEI_MMRAM_MEMORY_RESERVE_GUID with %u regions\n",
+		     mmram_desc_block->number_of_mm_reserved_regions);
+		for (uint32_t i = 0;
+		     i < mmram_desc_block->number_of_mm_reserved_regions; i++) {
+			INFO("    MMRAM_DESC[%u]:\n", i);
+			dump_efi_mmram_descriptor(
+				&mmram_desc_block->descriptor[i]);
+		}
+	} else if (uuid_equal(&uuid_name.uuid_struct,
+			      &ns_buffer_guid.uuid_struct)) {
+		INFO("    MM_NS_BUFFER_GUID\n");
+		dump_efi_mmram_descriptor(
+			(struct efi_mmram_descriptor *)guid_data);
+	}
+}
+
+static void dump_guid_hob(struct efi_hob_guid_type *guid_hob)
+{
+	dump_hob_generic_header(&guid_hob->header);
+	dump_efi_guid(guid_hob->name);
+	dump_guid_hob_data(guid_hob);
+}
+
+void dump_hob_list(struct efi_hob_handoff_info_table *hob_list)
+{
+	uintptr_t next_hob_addr;
+	struct efi_hob_generic_header *next;
+
+	assert(hob_list != NULL);
+	dump_hob_generic_header(&hob_list->header);
+	INFO("    Version: %u\n", hob_list->version);
+	INFO("    Boot Mode: %u\n", hob_list->boot_mode);
+	INFO("    EFI Memory Top: 0x%llx\n", hob_list->efi_memory_top);
+	INFO("    EFI Memory Bottom: 0x%llx\n", hob_list->efi_memory_bottom);
+	INFO("    EFI Free Memory Top: 0x%llx\n", hob_list->efi_free_memory_top);
+	INFO("    EFI Free Memory Bottom: 0x%llx\n", hob_list->efi_free_memory_bottom);
+	INFO("    EFI End of Hob List: 0x%llx\n", hob_list->efi_end_of_hob_list);
+
+	next_hob_addr = (uintptr_t)(hob_list) + (uintptr_t)hob_list->header.hob_length;
+	assert(next_hob_addr < (uintptr_t)hob_list->efi_end_of_hob_list);
+	next = (struct efi_hob_generic_header *)next_hob_addr;
+
+	while (next != NULL) {
+		assert(next->hob_type != 0x0);
+		switch (next->hob_type) {
+		case EFI_HOB_TYPE_GUID_EXTENSION:
+			dump_guid_hob((struct efi_hob_guid_type *)next);
+			break;
+		case EFI_HOB_TYPE_FV:
+			dump_efi_hob_firmware_volume((struct
+					efi_hob_firmware_volume *)next);
+			break;
+		default:
+			dump_hob_generic_header(next);
+		}
+
+		if (next->hob_type == EFI_HOB_TYPE_END_OF_HOB_LIST) {
+			break;
+		}
+
+		next_hob_addr = (uintptr_t)(next) + (uintptr_t)next->hob_length;
+
+		if (next_hob_addr >= (uintptr_t) hob_list->efi_end_of_hob_list) {
+			next = NULL;
+		} else {
+			assert(next_hob_addr < (uintptr_t)hob_list->efi_end_of_hob_list);
+			next = (struct efi_hob_generic_header *)next_hob_addr;
+		}
+	}
+
+}
diff --git a/lib/hob/hob.mk b/lib/hob/hob.mk
new file mode 100644
index 0000000..332738b
--- /dev/null
+++ b/lib/hob/hob.mk
@@ -0,0 +1,12 @@
+#
+# Copyright (c) 2024, Arm Limited and Contributors. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+HOB_LIST_SOURCES	+=	$(addprefix lib/hob/,	\
+				hob.c)
+
+INCLUDES	+=	-Iinclude/lib/hob
+
+BL31_SOURCES	+=	$(HOB_LIST_SOURCES)
diff --git a/spm/cactus/cactus.mk b/spm/cactus/cactus.mk
index b50975c..7d39221 100644
--- a/spm/cactus/cactus.mk
+++ b/spm/cactus/cactus.mk
@@ -23,6 +23,7 @@
 	-Iinclude/common/${ARCH}			\
 	-Iinclude/lib					\
 	-Iinclude/lib/extensions			\
+	-Iinclude/lib/hob				\
 	-Iinclude/lib/${ARCH}				\
 	-Iinclude/lib/utils				\
 	-Iinclude/lib/xlat_tables			\
@@ -74,6 +75,8 @@
 			drivers/arm/sp805/sp805.c			\
 			lib/${ARCH}/cache_helpers.S			\
 			lib/${ARCH}/misc_helpers.S			\
+			lib/hob/hob.c					\
+			lib/utils/uuid.c					\
 			lib/smc/${ARCH}/asm_smc.S			\
 			lib/smc/${ARCH}/smc.c				\
 			lib/smc/${ARCH}/hvc.c				\
diff --git a/spm/cactus/cactus_main.c b/spm/cactus/cactus_main.c
index c15ee4e..8554709 100644
--- a/spm/cactus/cactus_main.c
+++ b/spm/cactus/cactus_main.c
@@ -12,6 +12,7 @@
 #include <drivers/arm/pl011.h>
 #include <drivers/console.h>
 #include <lib/aarch64/arch_helpers.h>
+#include <lib/hob/hob.h>
 #include <lib/tftf_lib.h>
 #include <lib/xlat_tables/xlat_mmu_helpers.h>
 #include <lib/xlat_tables/xlat_tables_v2.h>
@@ -155,6 +156,15 @@
 		(void *)get_sp_tx_end(vm_id));
 }
 
+static void cactus_print_hob_list(uint64_t hob_content_addr, size_t size)
+{
+	INFO("SP Hob List Contents: 0x%llx, size 0x%lx\n", hob_content_addr, size);
+	struct efi_hob_handoff_info_table *hob_list = (struct
+			efi_hob_handoff_info_table *) hob_content_addr;
+
+	dump_hob_list(hob_list);
+}
+
 static void cactus_print_boot_info(struct ffa_boot_info_header *boot_info_header)
 {
 	struct ffa_boot_info_desc *boot_info_desc;
@@ -191,6 +201,9 @@
 				ffa_boot_info_content_format(&boot_info_desc[i]));
 		VERBOSE("      Size: %u\n", boot_info_desc[i].size);
 		VERBOSE("      Value: %llx\n", boot_info_desc[i].content);
+		if (ffa_boot_info_type_id(&boot_info_desc[i]) == 1) {
+			cactus_print_hob_list(boot_info_desc[i].content, boot_info_desc[i].size);
+		}
 	}
 }
 
@@ -237,6 +250,36 @@
 	return ffa_service_call(&args);
 }
 
+static void cactus_map_boot_info(struct ffa_boot_info_header *boot_info_header,
+		bool do_desc_access)
+{
+	struct ffa_boot_info_desc *boot_info_desc;
+
+	assert(boot_info_header != NULL);
+
+	boot_info_desc = boot_info_header->boot_info;
+	/*
+	 * TODO: Currently just validating that cactus can
+	 * access the boot info descriptors. By default, allocate one page
+	 * for boot info. In case we want to use the boot info contents, we should check the
+	 * blob and remap if the size is bigger than one page.
+	 * Only then access the contents.
+	 */
+	mmap_add_dynamic_region(
+		(unsigned long long)boot_info_header,
+		(uintptr_t)boot_info_header,
+		PAGE_SIZE, MT_RO_DATA);
+
+	if (do_desc_access) {
+		for (uint32_t i = 0; i < boot_info_header->desc_count; i++) {
+			mmap_add_dynamic_region(
+				(unsigned long long)boot_info_desc[i].content,
+				(uintptr_t)boot_info_desc[i].content,
+				PAGE_SIZE, MT_RO_DATA);
+		}
+	}
+}
+
 void __dead2 cactus_main(bool primary_cold_boot,
 			 struct ffa_boot_info_header *boot_info_header)
 {
@@ -268,17 +311,7 @@
 		sp_handler_spin_lock_init();
 
 		if (boot_info_header != NULL) {
-			/*
-			 * TODO: Currently just validating that cactus can
-			 * access the boot info descriptors. In case we want to
-			 * use the boot info contents, we should check the
-			 * blob and remap if the size is bigger than one page.
-			 * Only then access the contents.
-			 */
-			mmap_add_dynamic_region(
-				(unsigned long long)boot_info_header,
-				(uintptr_t)boot_info_header,
-				PAGE_SIZE, MT_RO_DATA);
+			cactus_map_boot_info(boot_info_header, ffa_id == SP_ID(3));
 		}
 	}
 
@@ -304,11 +337,22 @@
 	NOTICE("Booting Secure Partition (ID: %x)\n%s\n%s\n",
 		ffa_id, build_message, version_string);
 
-	if (ffa_id == SP_ID(1)) {
+	/*
+	 * Print FF-A boot info if requested in manifest via FF-A boot info
+	 * protocol.
+	 */
+	if (ffa_id == SP_ID(1) || ffa_id == SP_ID(3)) {
 		cactus_print_boot_info(boot_info_header);
 	}
 
-	if (ffa_id == (SPM_VM_ID_FIRST + 2)) {
+	cactus_print_memory_layout(ffa_id);
+
+	/*
+	 * Cactus-tertiary makes use of FFA_RXTX_MAP API instead of specifying
+	 * `rx_tx-info` in its manifest, as done by the primary and secondary
+	 * cactus partitions.
+	 */
+	if (ffa_id == SP_ID(3)) {
 		VERBOSE("Mapping RXTX Region\n");
 		CONFIGURE_AND_MAP_MAILBOX(mb, PAGE_SIZE, ret);
 		if (ffa_func_id(ret) != FFA_SUCCESS_SMC32) {
@@ -318,12 +362,11 @@
 		}
 	}
 
-	cactus_print_memory_layout(ffa_id);
 
 	ret = register_secondary_entrypoint();
 
 	/* FFA_SECONDARY_EP_REGISTER interface is not supported for UP SP. */
-	if (ffa_id == (SPM_VM_ID_FIRST + 2)) {
+	if (ffa_id == SP_ID(3)) {
 		EXPECT(ffa_func_id(ret), FFA_ERROR);
 		EXPECT(ffa_error_code(ret), FFA_ERROR_NOT_SUPPORTED);
 	} else {
diff --git a/spm/cactus/plat/arm/fvp/fdts/cactus-tertiary.dts b/spm/cactus/plat/arm/fvp/fdts/cactus-tertiary.dts
index d1ffa2f..6c0ea57 100644
--- a/spm/cactus/plat/arm/fvp/fdts/cactus-tertiary.dts
+++ b/spm/cactus/plat/arm/fvp/fdts/cactus-tertiary.dts
@@ -24,7 +24,8 @@
 	exception-level = <2>; /* S-EL1 */
 	execution-state = <0>; /* AARCH64 */
 	load-address = <0x7200000>;
-	entrypoint-offset = <0x00002000>;
+	image-size = <0x300000>;
+	entrypoint-offset = <0x00003000>; /*Image after manifest and HOB list. */
 	xlat-granule = <0>; /* 4KiB */
 	boot-order = <2>;
 	notification-support;
@@ -32,6 +33,15 @@
 	managed-exit; /* Managed exit is supported */
 	managed-exit-virq;
 
+	/* Boot protocol */
+	gp-register-num = <0>;
+
+	/* Boot Info */
+	boot-info {
+		compatible = "arm,ffa-manifest-boot-info";
+		hob_list;
+	};
+
 	memory-regions {
 		compatible = "arm,ffa-manifest-memory-regions";
 
@@ -50,5 +60,37 @@
 			base-address = <0x00008800 0x80001000>;
 			attributes = <0xb>; /* NS / read-write */
 		};
+
+		/* StMM-specific region used for HOB list testing. */
+		rx-tx-buffers {
+			description = "shared-buff";
+			base-address = <0x0 0xfd500000>;
+			pages-count = <0x100>;
+			attributes = <0x3>;
+		};
+
+		/* StMM-specific region used for HOB list testing. */
+		ns_comm_buffer {
+			/*
+			 * Description is needed for StMM to identify
+			 * ns-communication buffer.
+			 */
+			description = "ns-comm";
+			base-address = <0x80000000>;
+			pages-count = <0x1>;
+			attributes = <0xB>;
+		};
+
+		/* StMM-specific region used for HOB list testing. */
+		heap {
+			/*
+			 * Description is needed for StMM to identify
+			 * heap buffer.
+			 */
+			description = "heap";
+			base-address = <0x0 0xff100000>;
+			pages-count = <0x7>;
+			attributes = <0x3>;
+		};
 	};
 };
diff --git a/tftf/framework/framework.mk b/tftf/framework/framework.mk
index 4e27995..d5d3300 100644
--- a/tftf/framework/framework.mk
+++ b/tftf/framework/framework.mk
@@ -19,6 +19,7 @@
 	-Iinclude/lib					\
 	-Iinclude/lib/${ARCH}				\
 	-Iinclude/lib/extensions			\
+	-Iinclude/lib/hob			\
 	-Iinclude/lib/pcie				\
 	-Iinclude/lib/spdm				\
 	-Iinclude/lib/utils				\
@@ -57,6 +58,7 @@
 	lib/extensions/amu/${ARCH}/amu.c				\
 	lib/extensions/amu/${ARCH}/amu_helpers.S			\
 	lib/exceptions/irq.c						\
+	lib/hob/hob.c						\
 	lib/locks/${ARCH}/spinlock.S					\
 	lib/power_management/hotplug/hotplug.c				\
 	lib/power_management/suspend/${ARCH}/asm_tftf_suspend.S		\
diff --git a/tools/generate_json/generate_json.sh b/tools/generate_json/generate_json.sh
index 9d51ba5..463b110 100755
--- a/tools/generate_json/generate_json.sh
+++ b/tools/generate_json/generate_json.sh
@@ -68,7 +68,8 @@
 	"pm": "cactus-tertiary.dts",
 	"physical-load-address": "0x7200000",
 	"owner": "Plat",
-	"package": "tl_pkg"
+	"package": "tl_pkg",
+	"size": "0x300000"
 EOF
 	PARTITION_ALREADY_PRESENT=true
 fi
@@ -99,7 +100,8 @@
 	"pm": "ivy-sel1.dts",
 	"physical-load-address": "0x7600000",
 	"owner": "Plat",
-	"package":"tl_pkg"
+	"package":"tl_pkg",
+	"size": "0x100000"
 }
 EOF