diff --git a/lib/efi_loader/Makefile b/lib/efi_loader/Makefile
index dec791b310..8888ea193d 100644
--- a/lib/efi_loader/Makefile
+++ b/lib/efi_loader/Makefile
@@ -53,6 +53,7 @@ obj-$(CONFIG_EFI_VARIABLES_PRESEED) += efi_var_seed.o
 endif
 obj-y += efi_watchdog.o
 obj-y += efi_esrt.o
+obj-y += efi_fake_fmp.o
 obj-$(CONFIG_LCD) += efi_gop.o
 obj-$(CONFIG_DM_VIDEO) += efi_gop.o
 obj-$(CONFIG_PARTITIONS) += efi_disk.o
diff --git a/lib/efi_loader/efi_fake_fmp.c b/lib/efi_loader/efi_fake_fmp.c
new file mode 100644
index 0000000000..ab7a8164c9
--- /dev/null
+++ b/lib/efi_loader/efi_fake_fmp.c
@@ -0,0 +1,172 @@
+// SPDX-License-Identifier: GPL-2.0-only
+/*
+ * Fake FMP intended to test ESRT table creation.
+ *
+ *  Copyright (c) 2021 Arm Ltd.
+ */
+
+#include <common.h>
+#include <efi_loader.h>
+#include <net.h>
+
+/*
+ * Note: this GUID is used for code testing purposes.
+ */
+#define EFI_FAKE_IMG_GUID \
+	EFI_GUID(0x00000001, 0x0002, 0x0003, 0x04, 0x05, \
+		 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b)
+
+static const efi_guid_t fake_img_guid = EFI_FAKE_IMG_GUID;
+
+const struct fw_image_info *get_image_info(void);
+
+static
+efi_status_t EFIAPI efi_fake_fmp_get_image_info(
+	struct efi_firmware_management_protocol *this,
+	efi_uintn_t *image_info_size,
+	struct efi_firmware_image_descriptor *image_info,
+	u32 *descriptor_version,
+	u8 *descriptor_count,
+	efi_uintn_t *descriptor_size,
+	u32 *package_version,
+	u16 **package_version_name)
+{
+	efi_status_t ret = EFI_SUCCESS;
+
+	log_debug("EFI FMP: fake fmp get image info\n");
+
+	EFI_ENTRY("%p %p %p %p %p %p %p %p\n", this,
+		  image_info_size, image_info,
+		  descriptor_version, descriptor_count, descriptor_size,
+		  package_version, package_version_name);
+
+	if (!image_info_size)
+		return EFI_EXIT(EFI_INVALID_PARAMETER);
+
+	if (*image_info_size < sizeof(*image_info)) {
+		*image_info_size = sizeof(*image_info);
+		return EFI_EXIT(EFI_BUFFER_TOO_SMALL);
+	}
+
+	*image_info_size = sizeof(*image_info);
+	if (descriptor_version)
+		*descriptor_version = EFI_FIRMWARE_IMAGE_DESCRIPTOR_VERSION;
+	if (descriptor_count)
+		*descriptor_count = 1;
+	if (descriptor_size)
+		*descriptor_size = sizeof(*image_info);
+	if (package_version)
+		*package_version = 0xffffffff; /* not supported */
+	if (package_version_name)
+		*package_version_name = NULL; /* not supported */
+
+	if (!image_info_size)
+		return EFI_EXIT(EFI_INVALID_PARAMETER);
+
+	if (*image_info_size < sizeof(*image_info)) {
+		*image_info_size = sizeof(*image_info);
+		return EFI_EXIT(EFI_BUFFER_TOO_SMALL);
+	}
+
+	if (!image_info)
+		return EFI_EXIT(EFI_INVALID_PARAMETER);
+
+	log_debug("EFI FMP: fake image UUID=%pUl\n", &fake_img_guid);
+
+	image_info[0].image_index = 1;
+	image_info[0].image_type_id = fake_img_guid;
+
+	image_info[0].image_id = 0;
+	image_info[0].image_id_name = NULL;
+	image_info[0].version = 0; /* not supported */
+	image_info[0].version_name = NULL; /* not supported */
+	image_info[0].size = 0;
+
+	image_info[0].hardware_instance = 1;
+
+	return EFI_EXIT(ret);
+}
+
+static
+efi_status_t EFIAPI efi_fake_fmp_get_image(
+	struct efi_firmware_management_protocol *this,
+	u8 image_index,
+	void *image,
+	efi_uintn_t *image_size)
+{
+	return EFI_EXIT(EFI_UNSUPPORTED);
+}
+
+static
+efi_status_t EFIAPI efi_fake_fmp_set_image(
+	struct efi_firmware_management_protocol *this,
+	u8 image_index,
+	const void *image,
+	efi_uintn_t image_size,
+	const void *vendor_code,
+	efi_status_t (*progress)(efi_uintn_t completion),
+	u16 **abort_reason)
+{
+	EFI_ENTRY("%p %d %p %ld %p %p %p\n", this, image_index, image,
+		  image_size, vendor_code, progress, abort_reason);
+
+	return EFI_EXIT(EFI_UNSUPPORTED);
+}
+
+static
+efi_status_t EFIAPI efi_fake_fmp_check_image(
+	struct efi_firmware_management_protocol *this,
+	u8 image_index,
+	const void *image,
+	efi_uintn_t *image_size,
+	u32 *image_updatable)
+{
+	return EFI_EXIT(EFI_UNSUPPORTED);
+}
+
+static
+efi_status_t EFIAPI efi_fake_fmp_get_package_info(
+	struct efi_firmware_management_protocol *this,
+	u32 *package_version,
+	u16 **package_version_name,
+	u32 *package_version_name_maxlen,
+	u64 *attributes_supported,
+	u64 *attributes_setting)
+{
+	return EFI_EXIT(EFI_UNSUPPORTED);
+}
+
+static
+efi_status_t EFIAPI efi_fake_fmp_set_package_info(
+	struct efi_firmware_management_protocol *this,
+	const void *image,
+	efi_uintn_t *image_size,
+	const void *vendor_code,
+	u32 package_version,
+	const u16 *package_version_name)
+{
+	return EFI_EXIT(EFI_UNSUPPORTED);
+}
+
+const struct efi_firmware_management_protocol efi_fake_fmp = {
+	.get_image_info = efi_fake_fmp_get_image_info,
+	.get_image = efi_fake_fmp_get_image,
+	.set_image = efi_fake_fmp_set_image,
+	.check_image = efi_fake_fmp_check_image,
+	.get_package_info = efi_fake_fmp_get_package_info,
+	.set_package_info = efi_fake_fmp_set_package_info,
+};
+
+efi_status_t arch_efi_load_capsule_drivers(void)
+{
+	efi_status_t ret = EFI_SUCCESS;
+
+	EFI_CALL(efi_install_multiple_protocol_interfaces(
+			&efi_root, &efi_guid_firmware_management_protocol,
+			&efi_fake_fmp, NULL));
+
+	if (ret != EFI_SUCCESS)
+		log_err("EFI FMP: failed to install fake FMP %lx\n", ret);
+
+	return ret;
+}
