Re: [RFC PATCH v3 7/8] mkimage: add public key for image pre-load stage

2021-12-03 Thread Philippe REYNES

Hi Simon,

Le 25/11/2021 à 01:13, Simon Glass a écrit :

Hi Philippe,

On Wed, 17 Nov 2021 at 10:52, Philippe Reynes
 wrote:

This commit enhances mkimage to update the node
/image/pre-load/sig with the public key.

Signed-off-by: Philippe Reynes 
---
  include/image.h|  15 ++
  tools/fit_image.c  |   3 ++
  tools/image-host.c | 116 +
  3 files changed, 134 insertions(+)

I'm a bit unsure about the format of the key here. Is it different
from the normal one used by U-Boot?

The format used by pkey is the der format without the first 24 bytes.
For example, to create this key in a shell, I use the following commands :

openssl rsa -in private.pem -pubout -outform der -out public.der
dd if=public.der of=public.raw bs=24 skip=1

As described in the comment line 340 in the file test/lib/asn1.c.


Regards,
Simon

Regards,
Philippe


-- This message and any attachments herein are confidential, intended solely 
for the addressees and are SoftAtHome’s ownership. Any unauthorized use or 
dissemination is prohibited. If you are not the intended addressee of this 
message, please cancel it immediately and inform the sender.


Re: [RFC PATCH v3 7/8] mkimage: add public key for image pre-load stage

2021-11-24 Thread Simon Glass
Hi Philippe,

On Wed, 17 Nov 2021 at 10:52, Philippe Reynes
 wrote:
>
> This commit enhances mkimage to update the node
> /image/pre-load/sig with the public key.
>
> Signed-off-by: Philippe Reynes 
> ---
>  include/image.h|  15 ++
>  tools/fit_image.c  |   3 ++
>  tools/image-host.c | 116 +
>  3 files changed, 134 insertions(+)

I'm a bit unsure about the format of the key here. Is it different
from the normal one used by U-Boot?

Regards,
Simon


[RFC PATCH v3 7/8] mkimage: add public key for image pre-load stage

2021-11-17 Thread Philippe Reynes
This commit enhances mkimage to update the node
/image/pre-load/sig with the public key.

Signed-off-by: Philippe Reynes 
---
 include/image.h|  15 ++
 tools/fit_image.c  |   3 ++
 tools/image-host.c | 116 +
 3 files changed, 134 insertions(+)

diff --git a/include/image.h b/include/image.h
index 42fb01ab07..ac27e7acb2 100644
--- a/include/image.h
+++ b/include/image.h
@@ -1019,6 +1019,21 @@ int fit_image_hash_get_value(const void *fit, int 
noffset, uint8_t **value,
 
 int fit_set_timestamp(void *fit, int noffset, time_t timestamp);
 
+/**
+ * fit_pre_load_data() - add public key to fdt blob
+ *
+ * @keydir:Directory containing keys
+ * @keydest:   FDT blob to write public key
+ * @fit:   Pointer to the FIT format image header
+ *
+ * Adds public key to the node pre load.
+ *
+ * returns:
+ * 0, on success
+ * < 0, on failure
+ */
+int fit_pre_load_data(const char *keydir, void *keydest, void *fit);
+
 int fit_cipher_data(const char *keydir, void *keydest, void *fit,
const char *comment, int require_keys,
const char *engine_id, const char *cmdname);
diff --git a/tools/fit_image.c b/tools/fit_image.c
index f4f372ba62..43ce41efbe 100644
--- a/tools/fit_image.c
+++ b/tools/fit_image.c
@@ -59,6 +59,9 @@ static int fit_add_file_data(struct image_tool_params 
*params, size_t size_inc,
ret = fit_set_timestamp(ptr, 0, time);
}
 
+   if (!ret)
+   ret = fit_pre_load_data(params->keydir, dest_blob, ptr);
+
if (!ret) {
ret = fit_cipher_data(params->keydir, dest_blob, ptr,
  params->comment,
diff --git a/tools/image-host.c b/tools/image-host.c
index a6b0a94420..20e59c14a9 100644
--- a/tools/image-host.c
+++ b/tools/image-host.c
@@ -14,6 +14,11 @@
 #include 
 #include 
 
+#include 
+#include 
+
+#define IMAGE_PRE_LOAD_PATH "/image/pre-load/sig"
+
 /**
  * fit_set_hash_value - set hash value in requested has node
  * @fit: pointer to the FIT format image header
@@ -1020,6 +1025,117 @@ static int fit_config_add_verification_data(const char 
*keydir,
return 0;
 }
 
+/*
+ * 0) open file (open)
+ * 1) read certificate (PEM_read_X509)
+ * 2) get public key (X509_get_pubkey)
+ * 3) provide der format (d2i_RSAPublicKey)
+ */
+static int read_pub_key(const char *keydir, const void *name,
+   unsigned char **pubkey, int *pubkey_len)
+{
+   char path[1024];
+   EVP_PKEY *key = NULL;
+   X509 *cert;
+   FILE *f;
+   int ret;
+
+   memset(path, 0, 1024);
+   snprintf(path, sizeof(path), "%s/%s.crt", keydir, (char *)name);
+
+   /* Open certificate file */
+   f = fopen(path, "r");
+   if (!f) {
+   fprintf(stderr, "Couldn't open RSA certificate: '%s': %s\n",
+   path, strerror(errno));
+   return -EACCES;
+   }
+
+   /* Read the certificate */
+   cert = NULL;
+   if (!PEM_read_X509(f, , NULL, NULL)) {
+   printf("Couldn't read certificate");
+   ret = -EINVAL;
+   goto err_cert;
+   }
+
+   /* Get the public key from the certificate. */
+   key = X509_get_pubkey(cert);
+   if (!key) {
+   printf("Couldn't read public key\n");
+   ret = -EINVAL;
+   goto err_pubkey;
+   }
+
+   /* Get DER form */
+   ret = i2d_PublicKey(key, pubkey);
+   if (ret < 0) {
+   printf("Couldn't get DER form\n");
+   ret = -EINVAL;
+   goto err_pubkey;
+   }
+
+   *pubkey_len = ret;
+   ret = 0;
+
+err_pubkey:
+   X509_free(cert);
+err_cert:
+   fclose(f);
+   return ret;
+}
+
+int fit_pre_load_data(const char *keydir, void *keydest, void *fit)
+{
+   int pre_load_noffset;
+   const void *header_size, *algo_name;
+   const void *key_name;
+   unsigned char *pubkey = NULL;
+   int ret, pubkey_len;
+
+   if (!keydir || !keydest || !fit)
+   return 0;
+
+   /* Search node pre-load sig */
+   pre_load_noffset = fdt_path_offset(keydest, IMAGE_PRE_LOAD_PATH);
+   if (pre_load_noffset < 0) {
+   ret = 0;
+   goto out;
+   }
+
+   header_size  = fdt_getprop(keydest, pre_load_noffset, "header-size", 
NULL);
+   algo_name= fdt_getprop(keydest, pre_load_noffset, "algo-name", 
NULL);
+   key_name = fdt_getprop(keydest, pre_load_noffset, "key-name", NULL);
+
+   /* Check that all mandatory properties are present */
+   if (!header_size || !algo_name || !key_name) {
+   if (!header_size)
+   printf("The property header-size is missing in the node 
%s\n",
+  IMAGE_PRE_LOAD_PATH);
+   if (!algo_name)
+   printf("The property algo-name is missing in the node