Add fwu_app for test and demonstration

Adds the fwu_app class to facilitate deployment of the update agent
as part of an application e.g. a user-space or UEFI app. It uses
the standard FWU service components but operates on a disk image
file rather than on a flash device. The disk image file needs to
be a UEFI formated image with MBR+GPT with partitions for metadata
and firmware banks. Will be initially used to test operation with
boot images generated from build tools.

Signed-off-by: Julian Hall <julian.hall@arm.com>
Change-Id: Ia4151841115010333a922c217352614062f8f86a
diff --git a/components/service/fwu/app/metadata_v1_reader.cpp b/components/service/fwu/app/metadata_v1_reader.cpp
new file mode 100644
index 0000000..58faa23
--- /dev/null
+++ b/components/service/fwu/app/metadata_v1_reader.cpp
@@ -0,0 +1,85 @@
+/*
+ * Copyright (c) 2023, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+#include <protocols/service/fwu/packed-c/metadata_v1.h>
+#include "metadata_reader.h"
+
+class metadata_v1_reader : public metadata_version_specific_reader {
+
+public:
+
+	metadata_v1_reader();
+	~metadata_v1_reader();
+
+	bool is_supported(
+		const uint8_t *buf,
+		size_t data_len) const;
+
+	void get_version(
+		const uint8_t *buf,
+		size_t data_len,
+		unsigned int &version) const;
+
+	void get_active_index(
+		const uint8_t *buf,
+		size_t data_len,
+		unsigned int &active_index) const;
+};
+
+/* Registers on static construction */
+static metadata_v1_reader the_v1_reader;
+
+
+metadata_v1_reader::metadata_v1_reader() :
+	metadata_version_specific_reader()
+{
+	metadata_reader::instance()->register_reader(this);
+}
+
+metadata_v1_reader::~metadata_v1_reader()
+{
+
+}
+
+bool metadata_v1_reader::is_supported(
+	const uint8_t *buf,
+	size_t data_len) const
+{
+	assert(buf);
+
+	const struct fwu_metadata *metadata = (const struct fwu_metadata *)buf;
+
+	return
+		(data_len >= sizeof(struct fwu_metadata)) &&
+		(metadata->version == 1);
+}
+
+void metadata_v1_reader::get_version(
+	const uint8_t *buf,
+	size_t data_len,
+	unsigned int &version) const
+{
+	assert(buf);
+	assert(data_len >= sizeof(struct fwu_metadata));
+
+	const struct fwu_metadata *metadata = (const struct fwu_metadata *)buf;
+
+	version = metadata->version;
+}
+
+void metadata_v1_reader::get_active_index(
+	const uint8_t *buf,
+	size_t data_len,
+	unsigned int &active_index) const
+{
+	assert(buf);
+	assert(data_len >= sizeof(struct fwu_metadata));
+
+	const struct fwu_metadata *metadata = (const struct fwu_metadata *)buf;
+
+	active_index = metadata->active_index;
+}
\ No newline at end of file