[PATCH 7/8] FIT: Implement opening images with no configuration

Sascha Hauer s.hauer at pengutronix.de
Wed Jan 31 03:11:15 PST 2018


different images can be grouped together to build a FIT configuration.
So far we only supported opening images as parts of configurations.
This patch adds support for opening images that are not part of a
configuration. This mode is used when the configuration parameter of
fit_open_image is NULL.

The main difference is in the way the RSA signature is checked. When
being part of a configuration all involved nodes (including the hash
nodes of the images, but not the image itself) are covered by the
signature, thus during opening an image only the validity of the image
data hash has to be checked. When not being part of a configuration,
the image data itself is signed and must be checked.

Signed-off-by: Sascha Hauer <s.hauer at pengutronix.de>
---
 common/image-fit.c | 82 +++++++++++++++++++++++++++++++++++++++++++++++++-----
 1 file changed, 75 insertions(+), 7 deletions(-)

diff --git a/common/image-fit.c b/common/image-fit.c
index 86516f0ba9..4ebd4b8c42 100644
--- a/common/image-fit.c
+++ b/common/image-fit.c
@@ -444,6 +444,52 @@ err_digest_free:
 	return ret;
 }
 
+static int fit_image_verify_signature(struct fit_handle *handle,
+				      struct device_node *image,
+				      const void *data, int data_len)
+{
+	struct digest *digest;
+	struct device_node *sig_node;
+	enum hash_algo algo = 0;
+	void *hash;
+	int ret;
+
+	if (!IS_ENABLED(CONFIG_FITIMAGE_SIGNATURE))
+		return 0;
+
+	switch (handle->verify) {
+	case BOOTM_VERIFY_NONE:
+		return 0;
+	case BOOTM_VERIFY_AVAILABLE:
+		ret = 0;
+		break;
+	default:
+		ret = -EINVAL;
+	}
+
+	sig_node = of_get_child_by_name(image, "signature at 1");
+	if (!sig_node) {
+		pr_err("Image %s has no signature\n", image->full_name);
+		return ret;
+	}
+
+	digest = fit_alloc_digest(sig_node, &algo);
+	if (IS_ERR(digest))
+		return PTR_ERR(digest);
+
+	digest_update(digest, data, data_len);
+	hash = xzalloc(digest_length(digest));
+	digest_final(digest, hash);
+
+	ret = fit_check_rsa_signature(sig_node, algo, hash);
+
+	free(hash);
+
+	digest_free(digest);
+
+	return ret;
+}
+
 int fit_has_image(struct fit_handle *handle, void *configuration,
 		  const char *name)
 {
@@ -459,6 +505,23 @@ int fit_has_image(struct fit_handle *handle, void *configuration,
 	return 1;
 }
 
+/**
+ * fit_open_image - Open an image in a FIT image
+ * @handle: The FIT image handle
+ * @name: The name of the image to open
+ * @outdata: The returned image
+ * @outsize: Size of the returned image
+ *
+ * Open an image in a FIT image. The returned image is freed during fit_close().
+ * @configuration holds the cookie returned from fit_open_configuration() if
+ * the image is opened as part of a configuration, or NULL if the image is
+ * opened without a configuration. If @configuration is NULL then the RSA
+ * signature of the image is checked if desired, if @configuration is non NULL,
+ * then only the hash is checked (because opening the configuration already
+ * checks the RSA signature of all involved nodes).
+ *
+ * Return: 0 for success, negative error code otherwise
+ */
 int fit_open_image(struct fit_handle *handle, void *configuration,
 		   const char *name, const void **outdata,
 		   unsigned long *outsize)
@@ -470,12 +533,13 @@ int fit_open_image(struct fit_handle *handle, void *configuration,
 	int ret = 0;
 	struct device_node *conf_node = configuration;
 
-	if (!conf_node)
-		return -EINVAL;
-
-	if (of_property_read_string(conf_node, name, &unit)) {
-		pr_err("No image named '%s'\n", name);
-		return -ENOENT;
+	if (conf_node) {
+		if (of_property_read_string(conf_node, name, &unit)) {
+			pr_err("No image named '%s'\n", name);
+			return -ENOENT;
+		}
+	} else {
+		unit = name;
 	}
 
 	image = of_get_child_by_name(handle->images, unit);
@@ -497,7 +561,11 @@ int fit_open_image(struct fit_handle *handle, void *configuration,
 		return -EINVAL;
 	}
 
-	ret = fit_verify_hash(handle, image, data, data_len);
+	if (conf_node)
+		ret = fit_verify_hash(handle, image, data, data_len);
+	else
+		ret = fit_image_verify_signature(handle, image, data, data_len);
+
 	if (ret < 0)
 		return ret;
 
-- 
2.15.1




More information about the barebox mailing list