Tools: Count partition numbers and output config

For implementation runtime model configurations. If there is no
IPC partition, the runtime model can be set as SFN. And the
runtime model is IPC by default.

Generate file 'config_impl.h' to indicate the current runtime
model. This file can be referenced by components like SPM,
partitions and interfaces.

Change-Id: I584ada22446a0da67d15e95d8a64a8700f82c75a
Signed-off-by: Ken Liu <Ken.Liu@arm.com>
diff --git a/interface/include/config_impl.h.template b/interface/include/config_impl.h.template
new file mode 100644
index 0000000..e021242
--- /dev/null
+++ b/interface/include/config_impl.h.template
@@ -0,0 +1,28 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+{{utilities.donotedit_warning}}
+
+#ifndef __CONFIG_IMPL_H__
+#define __CONFIG_IMPL_H__
+
+{% if ipc_partition_num > 0 and sfn_partition_num == 0 %}
+#define BACKEND_IPC                 1
+{% elif sfn_partition_num > 0 and ipc_partition_num == 0 %}
+#define BACKEND_SFN                 1
+
+#if TFM_LVL > 1
+#error "High isolation level SFN model is not supported."
+#endif
+
+{% elif sfn_partition_num > 0 and ipc_partition_num > 0 %}
+#error "IPC and SFN co-work not supported yet."
+{% else %}
+#error "Invalid partition number inputted, check configurations."
+{% endif %}
+
+#endif /* __CONFIG_IMPL_H__ */
diff --git a/tools/tfm_generated_file_list.yaml b/tools/tfm_generated_file_list.yaml
index 95eae40..0c866c7 100644
--- a/tools/tfm_generated_file_list.yaml
+++ b/tools/tfm_generated_file_list.yaml
@@ -50,6 +50,12 @@
         "short_name": "pid.h",
         "template": "interface/include/psa_manifest/pid.h.template",
         "output": "interface/include/psa_manifest/pid.h"
+    },
+    {
+        "name": "SPM config header",
+        "short_name": "config_impl.h",
+        "template": "interface/include/config_impl.h.template",
+        "output": "interface/include/config_impl.h"
     }
   ]
 }
diff --git a/tools/tfm_parse_manifest_list.py b/tools/tfm_parse_manifest_list.py
index 9b7a36a..82acdb1 100644
--- a/tools/tfm_parse_manifest_list.py
+++ b/tools/tfm_parse_manifest_list.py
@@ -109,6 +109,8 @@
 
     partition_list = []
     manifest_list = []
+    ipc_partition_num = 0
+    sfn_partition_num = 0
 
     for f in manifest_list_files:
         with open(f) as manifest_list_yaml_file:
@@ -168,6 +170,14 @@
         manifest = manifest_validation(yaml.safe_load(file))
         file.close()
 
+        # Count the number of IPC partitions
+        if manifest["psa_framework_version"] == 1.1 and manifest["model"] == 'IPC':
+            ipc_partition_num += 1
+        elif manifest["psa_framework_version"] == 1.1 and manifest["model"] == 'SFN':
+            sfn_partition_num += 1
+        elif "services" in manifest.keys():
+            ipc_partition_num += 1
+
         manifest_dir, manifest_name = os.path.split(manifest_path)
         manifest_out_basename = manifest_name.replace('.yaml', '').replace('.json', '')
 
@@ -217,7 +227,7 @@
 
         raise Exception("Duplicated SID found, check above for details")
 
-    return partition_list
+    return partition_list, ipc_partition_num, sfn_partition_num
 
 def gen_per_partition_files(context):
     """
@@ -481,7 +491,7 @@
     """
     os.chdir(os.path.join(sys.path[0], ".."))
 
-    partition_list = process_partition_manifests(manifest_list, extra_manifests_list)
+    partition_list, ipc_partition_num, sfn_partition_num = process_partition_manifests(manifest_list, extra_manifests_list)
 
     utilities = {}
     utilities['donotedit_warning'] = donotedit_warning
@@ -491,6 +501,9 @@
     context['utilities'] = utilities
     context['stateless_services'] = process_stateless_services(partition_list, 32)
 
+    context['ipc_partition_num'] = ipc_partition_num
+    context['sfn_partition_num'] = sfn_partition_num
+
     gen_per_partition_files(context)
     gen_summary_files(context, gen_file_list)