Skip to contentSkip to conversation

Verified boot implementation based on FIT

PATCH In review Simon Glass 5 participants 24 messages Jun 13, 2013 – Jun 27, 2013 1 message not in the archive Kbuild

lore
Share & tools
lore
#0 lore raw

v3 cover Verified boot implementation based on FIT

This series implemented a verified boot system based around FIT images as discussed on the U-Boot mailing list, including on this thread:

http://permalink.gmane.org/gmane.comp.boot-loaders.u-boot/147830

RSA is used to implement the encryption. Images are signed by mkimage using private keys created by the user. Public keys are written into U-Boot control FDT (CONFIG_OF_CONTROL) for access by bootm etc. at run-time. The control FDT must be stored in a secure place where it cannot be changed after manufacture. Some notes are provided in the documentaion on how this can be achieved. The implementation is fairly efficient and fits nicely into U-Boot. FIT plus RSA adds around 18KB to SPL size which is manageable on modern SoCs.

When images are loaded, they are verified with the public keys.

It is important to have a test framework for this series. For this, sandbox is used, and a script is provided which signs images and gets sandbox to load them using a script, to check that all is well.

Rollback prevention has been added in a separate TPM patch. This ensures that an attacker cannot boot your system with an old image that has been compromised. Support for this is not built into bootm, but instead must be scripted in U-Boot. It is possible that a standard scheme for this could be devised by adding version number tags to the signing procedure. However scripts do provide more flexibility. See the 'tpm' command for more information.

Two patches affect libfdt and have material which is not yet upstream in that project:

image: Add support for signing of FIT configurations
libfdt: Add fdt_find_regions()

If these are not desired, then the rest of the series can stand alone, just without the configuration-signing feature.

This series requires the 'trace' series since it sits on top of the bootm refactor there.

This series is available at:

http://git.denx.de/u-boot-x86.git

in the branch 'vboot'.

Changes in v3:
- Fix 'compile' typo
- Rebase to master
- Use new fdt_first/next_subnode()

Changes in v2:
- Add sanity checks on key sizes in RSA (improves security)
- Adjust how signing enable works in image.h
- Adjust mkimage help to separate out signing options
- Avoid using malloc in RSA routines (for smaller SPL code size)
- Build signing support unconditionally in mkimage
- Fix FDT error handling in fit_image_write_sig()
- Fix checkpatch checks about parenthesis alignment
- Fix checkpatch warnings about split strings
- Fix spelling of multiply in rsa-verify.c
- Only build RSA support into mkimage if CONFIG_RSA is defined
- Rebase on previous patches
- Require CONFIG_FIT_SIGNATURE in image.h for mkimage to support signing
- Support RSA library version without ERR_remove_thread_state()
- Tweak tools/Makefile to make image signing optional
- Update README to fix typos
- Update README to fix typos and clarify some points
- Use U-Boot's -c option instead of hard-coding a boot script
- Use stack instead of calloc() within U-Boot's signature verification code
- gd->fdt_blob is now available on all archs (generic board landed)

Simon Glass (12):
image: Add signing infrastructure
image: Support signing of images
image: Add RSA support for image signing
mkimage: Add -k option to specify key directory
mkimage: Add -K to write public keys to an FDT blob
mkimage: Add -F option to modify an existing .fit file
mkimage: Add -c option to specify a comment for key signing
mkimage: Add -r option to specify keys that must be verified
libfdt: Add fdt_find_regions()
image: Add support for signing of FIT configurations
sandbox: config: Enable FIT signatures with RSA Add verified boot information and test

 Makefile                         |   1 +
 README                           |  15 ++
 common/Makefile                  |   1 +
 common/image-fit.c               |  83 ++++--
 common/image-sig.c               | 422 +++++++++++++++++++++++++++++++
 config.mk                        |   1 +
 doc/mkimage.1                    |  73 +++++-
 doc/uImage.FIT/sign-configs.its  |  45 ++++
 doc/uImage.FIT/sign-images.its   |  42 ++++
 doc/uImage.FIT/signature.txt     | 382 ++++++++++++++++++++++++++++
 doc/uImage.FIT/verified-boot.txt | 104 ++++++++
 include/configs/sandbox.h        |   2 +
 include/image.h                  | 165 +++++++++++-
 include/libfdt.h                 |  64 +++++
 include/rsa.h                    | 108 ++++++++
 lib/libfdt/fdt_wip.c             | 129 ++++++++++
 lib/rsa/Makefile                 |  48 ++++
 lib/rsa/rsa-sign.c               | 460 ++++++++++++++++++++++++++++++++++
 lib/rsa/rsa-verify.c             | 385 ++++++++++++++++++++++++++++
 test/vboot/.gitignore            |   3 +
 test/vboot/sandbox-kernel.dts    |   7 +
 test/vboot/sandbox-u-boot.dts    |   7 +
 test/vboot/sign-configs.its      |  45 ++++
 test/vboot/sign-images.its       |  42 ++++
 test/vboot/vboot_test.sh         | 126 ++++++++++
 tools/Makefile                   |  19 +-
 tools/fit_image.c                |  44 +++-
 tools/image-host.c               | 527 ++++++++++++++++++++++++++++++++++++++-
 tools/mkimage.c                  |  36 ++-
 tools/mkimage.h                  |   4 +
 30 files changed, 3333 insertions(+), 57 deletions(-)
 create mode 100644 common/image-sig.c
 create mode 100644 doc/uImage.FIT/sign-configs.its
 create mode 100644 doc/uImage.FIT/sign-images.its
 create mode 100644 doc/uImage.FIT/signature.txt
 create mode 100644 doc/uImage.FIT/verified-boot.txt
 create mode 100644 include/rsa.h
 create mode 100644 lib/rsa/Makefile
 create mode 100644 lib/rsa/rsa-sign.c
 create mode 100644 lib/rsa/rsa-verify.c
 create mode 100644 test/vboot/.gitignore
 create mode 100644 test/vboot/sandbox-kernel.dts
 create mode 100644 test/vboot/sandbox-u-boot.dts
 create mode 100644 test/vboot/sign-configs.its
 create mode 100644 test/vboot/sign-images.its
 create mode 100755 test/vboot/vboot_test.sh
Signature · 1 line
1.8.3
#1 lore raw

PATCH v3 1/12 image: Add signing infrastructure

Add a structure to describe an algorithm which can sign and (later) verify images.

---
Changes in v3: None
Changes in v2:
- Adjust how signing enable works in image.h
- Rebase on previous patches
- Tweak tools/Makefile to make image signing optional
- Update README to fix typos and clarify some points
- gd->fdt_blob is now available on all archs (generic board landed)

 README                       |   5 +
 common/Makefile              |   1 +
 common/image-sig.c           |  42 +++++++++
 doc/uImage.FIT/signature.txt | 216 +++++++++++++++++++++++++++++++++++++++++++
 include/image.h              |  90 +++++++++++++++++-
 tools/Makefile               |   6 ++
 6 files changed, 358 insertions(+), 2 deletions(-)
 create mode 100644 common/image-sig.c
 create mode 100644 doc/uImage.FIT/signature.txt
README +5 -0
index 33bda8c..3e586c3 100644
@@ -2781,6 +2781,11 @@ FIT uImage format:
 		most specific compatibility entry of U-Boot's fdt's root node.
 		The order of entries in the configuration's fdt is ignored.
 
+		CONFIG_FIT_SIGNATURE
+		This option enables signature verification of FIT uImages,
+		using a hash signed and verified using RSA. See
+		doc/uImage.FIT/signature.txt for more details.
+
 - Standalone program support:
 		CONFIG_STANDALONE_LOAD_ADDR
 
common/Makefile +1 -0
index d40fb1f..84ae279 100644
@@ -235,6 +235,7 @@ COBJS-y += dlmalloc.o
 COBJS-y += image.o
 COBJS-$(CONFIG_OF_LIBFDT) += image-fdt.o
 COBJS-$(CONFIG_FIT) += image-fit.o
+COBJS-$(CONFIG_FIT_SIGNATURE) += image-sig.o
 COBJS-y += memsize.o
 COBJS-y += stdio.o
 
common/image-sig.c new file +42 -0

42 lines not on this page · raw message

doc/uImage.FIT/signature.txt new file +216 -0

216 lines not on this page · raw message

include/image.h +88 -2

126 lines not on this page · raw message

tools/Makefile +6 -0
index 569dc77..38fd934 100644
@@ -80,6 +80,7 @@ BIN_FILES-y += proftool(SFX)
 EXT_OBJ_FILES-$(CONFIG_BUILD_ENVCRC) += common/env_embedded.o
 EXT_OBJ_FILES-y += common/image.o
 EXT_OBJ_FILES-$(CONFIG_FIT) += common/image-fit.o
+EXT_OBJ_FILES-y += common/image-sig.o
 EXT_OBJ_FILES-y += lib/crc32.o
 EXT_OBJ_FILES-y += lib/md5.o
 EXT_OBJ_FILES-y += lib/sha1.o
@@ -161,6 +162,10 @@ HOSTSRCS += $(addprefix $(SRCTREE)/lib/libfdt/,$(LIBFDT_OBJ_FILES-y:.o=.c))
 BINS	:= $(addprefix $(obj),$(sort $(BIN_FILES-y)))
 LIBFDT_OBJS	:= $(addprefix $(obj),$(LIBFDT_OBJ_FILES-y))
 
+# We cannot check CONFIG_FIT_SIGNATURE here since it is not set on the host
+FIT_SIG_OBJ_FILES	:= image-sig.o
+FIT_SIG_OBJS		:= $(addprefix $(obj),$(FIT_SIG_OBJ_FILES))
+
 HOSTOBJS := $(addprefix $(obj),$(OBJ_FILES-y))
 NOPEDOBJS := $(addprefix $(obj),$(NOPED_OBJ_FILES-y))
 
@@ -220,6 +225,7 @@ $(obj)mkimage$(SFX):	$(obj)aisimage.o \
 			$(obj)image-fit.o \
 			$(obj)image.o \
 			$(obj)image-host.o \
+			$(FIT_SIG_OBJS) \
 			$(obj)imximage.o \
 			$(obj)kwbimage.o \
 			$(obj)pblimage.o \
Signature · 1 line
1.8.3
#2 lore raw

PATCH v3 2/12 image: Support signing of images

In reply to Simon Glass

Add support for signing images using a new signature node. The process is handled by fdt_add_verification_data() which now takes parameters to provide the keys and related information.

---
Changes in v3:
- Use new fdt_first/next_subnode()

Changes in v2:
- Adjust how signing enable works in image.h
- Fix FDT error handling in fit_image_write_sig()
- Fix checkpatch checks about parenthesis alignment
- Fix checkpatch warnings about split strings
- Require CONFIG_FIT_SIGNATURE in image.h for mkimage to support signing

 common/image-fit.c             |  83 +++++++++++++-----
 common/image-sig.c             | 144 +++++++++++++++++++++++++++++++
 doc/uImage.FIT/sign-images.its |  42 ++++++++++
 include/image.h                |  59 ++++++++++++-
 tools/fit_image.c              |   2 +-
 tools/image-host.c             | 186 ++++++++++++++++++++++++++++++++++++++---
 6 files changed, 478 insertions(+), 38 deletions(-)
 create mode 100644 doc/uImage.FIT/sign-images.its
common/image-fit.c +60 -23
index 7bf82d3..06426ad 100644
@@ -234,42 +234,45 @@ void fit_print_contents(const void *fit)
  * @fit: pointer to the FIT format image header
  * @noffset: offset of the hash node
  * @p: pointer to prefix string
+ * @type: Type of information to print ("hash" or "sign")
  *
  * fit_image_print_data() lists properies for the processed hash node
  *
+ * This function avoid using puts() since it prints a newline on the host
+ * but does not in U-Boot.
+ *
  * returns:
  *     no returned results
  */
-static void fit_image_print_data(const void *fit, int noffset, const char *p)
+static void fit_image_print_data(const void *fit, int noffset, const char *p,
+				 const char *type)
 {
-	char *algo;
+	const char *keyname;
 	uint8_t *value;
 	int value_len;
-	int i, ret;
-
-	/*
-	 * Check subnode name, must be equal to "hash".
-	 * Multiple hash nodes require unique unit node
-	 * names, e.g. hash at 1, hash at 2, etc.
-	 */
-	if (strncmp(fit_get_name(fit, noffset, NULL),
-		    FIT_HASH_NODENAME,
-		    strlen(FIT_HASH_NODENAME)) != 0)
-		return;
+	char *algo;
+	int required;
+	int ret, i;
 
-	debug("%s  Hash node:    '%s'\n", p,
+	debug("%s  %s node:    '%s'\n", p, type,
 	      fit_get_name(fit, noffset, NULL));
-
-	printf("%s  Hash algo:    ", p);
+	printf("%s  %s algo:    ", p, type);
 	if (fit_image_hash_get_algo(fit, noffset, &algo)) {
 		printf("invalid/unsupported\n");
 		return;
 	}
-	printf("%s\n", algo);
+	printf("%s", algo);
+	keyname = fdt_getprop(fit, noffset, "key-name-hint", NULL);
+	required = fdt_getprop(fit, noffset, "required", NULL) != NULL;
+	if (keyname)
+		printf(":%s", keyname);
+	if (required)
+		printf(" (required)");
+	printf("\n");
 
 	ret = fit_image_hash_get_value(fit, noffset, &value,
 					&value_len);
-	printf("%s  Hash value:   ", p);
+	printf("%s  %s value:   ", p, type);
 	if (ret) {
 		printf("unavailable\n");
 	} else {
@@ -278,7 +281,18 @@ static void fit_image_print_data(const void *fit, int noffset, const char *p)
 		printf("\n");
 	}
 
-	debug("%s  Hash len:     %d\n", p, value_len);
+	debug("%s  %s len:     %d\n", p, type, value_len);
+
+	/* Signatures have a time stamp */
+	if (IMAGE_ENABLE_TIMESTAMP && keyname) {
+		time_t timestamp;
+
+		printf("%s  Timestamp:    ", p);
+		if (fit_get_timestamp(fit, noffset, &timestamp))
+			printf("unavailable\n");
+		else
+			genimg_print_time(timestamp);
+	}
 }
 
 /**
@@ -303,8 +317,12 @@ static void fit_image_print_verification_data(const void *fit, int noffset,
 	 * names, e.g. hash at 1, hash at 2, signature at 1, signature at 2, etc.
 	 */
 	name = fit_get_name(fit, noffset, NULL);
-	if (!strncmp(name, FIT_HASH_NODENAME, strlen(FIT_HASH_NODENAME)))
-		fit_image_print_data(fit, noffset, p);
+	if (!strncmp(name, FIT_HASH_NODENAME, strlen(FIT_HASH_NODENAME))) {
+		fit_image_print_data(fit, noffset, p, "Hash");
+	} else if (!strncmp(name, FIT_SIG_NODENAME,
+				strlen(FIT_SIG_NODENAME))) {
+		fit_image_print_data(fit, noffset, p, "Sign");
+	}
 }
 
 /**
@@ -944,13 +962,23 @@ int fit_image_verify(const void *fit, int image_noffset)
 {
 	const void	*data;
 	size_t		size;
-	int		noffset;
+	int		noffset = 0;
 	char		*err_msg = "";
+	int verify_all = 1;
+	int ret;
 
 	/* Get image data and data length */
 	if (fit_image_get_data(fit, image_noffset, &data, &size)) {
 		err_msg = "Can't get image data/size";
-		return 0;
+		goto error;
+	}
+
+	/* Verify all required signatures */
+	if (IMAGE_ENABLE_VERIFY &&
+	    fit_image_verify_required_sigs(fit, image_noffset, data, size,
+					   gd_fdt_blob(), &verify_all)) {
+		err_msg = "Unable to verify required signature";
+		goto error;
 	}
 
 	/* Process all hash subnodes of the component image node */
@@ -970,6 +998,15 @@ int fit_image_verify(const void *fit, int image_noffset)
 						 &err_msg))
 				goto error;
 			puts("+ ");
+		} else if (IMAGE_ENABLE_VERIFY && verify_all &&
+				!strncmp(name, FIT_SIG_NODENAME,
+					strlen(FIT_SIG_NODENAME))) {
+			ret = fit_image_check_sig(fit, noffset, data,
+							size, -1, &err_msg);
+			if (ret)
+				puts("- ");
+			else
+				puts("+ ");
 		}
 	}
 
common/image-sig.c +144 -0

153 lines not on this page · raw message

doc/uImage.FIT/sign-images.its new file +42 -0

42 lines not on this page · raw message

include/image.h +55 -4

73 lines not on this page · raw message

tools/fit_image.c +1 -1
index cc123dd..ef6ef44 100644
@@ -137,7 +137,7 @@ static int fit_handle_file (struct mkimage_params *params)
 		goto err_mmap;
 
 	/* set hashes for images in the blob */
-	if (fit_add_verification_data(ptr)) {
+	if (fit_add_verification_data(NULL, NULL, ptr, NULL, 0)) {
 		fprintf (stderr, "%s Can't add hashes to FIT blob",
 				params->cmdname);
 		goto err_add_hashes;
tools/image-host.c +176 -10

228 lines not on this page · raw message

Signature · 1 line
1.8.3
#3 lore raw

PATCH v3 3/12 image: Add RSA support for image signing

In reply to Simon Glass

RSA provides a public key encryption facility which is ideal for image signing and verification.

Images are signed using a private key by mkimage. Then at run-time, the images are verified using a private key.

This implementation uses openssl for the host part (mkimage). To avoid bringing large libraries into the U-Boot binary, the RSA public key is encoded using a simple numeric representation in the device tree.

---
Changes in v3: None
Changes in v2:
- Add sanity checks on key sizes in RSA (improves security)
- Avoid using malloc in RSA routines (for smaller SPL code size)
- Build signing support unconditionally in mkimage
- Fix checkpatch checks about parenthesis alignment
- Fix spelling of multiply in rsa-verify.c
- Only build RSA support into mkimage if CONFIG_RSA is defined
- Support RSA library version without ERR_remove_thread_state()

 Makefile             |   1 +
 README               |  10 ++
 common/image-sig.c   |   7 +
 config.mk            |   1 +
 include/rsa.h        | 108 ++++++++++++
 lib/rsa/Makefile     |  48 ++++++
 lib/rsa/rsa-sign.c   | 460 +++++++++++++++++++++++++++++++++++++++++++++++++++
 lib/rsa/rsa-verify.c | 385 ++++++++++++++++++++++++++++++++++++++++++
 tools/Makefile       |  13 +-
 9 files changed, 1031 insertions(+), 2 deletions(-)
 create mode 100644 include/rsa.h
 create mode 100644 lib/rsa/Makefile
 create mode 100644 lib/rsa/rsa-sign.c
 create mode 100644 lib/rsa/rsa-verify.c
Makefile +1 -0
index eb751f4..90f2bb9 100644
@@ -247,6 +247,7 @@ OBJS := $(addprefix $(obj),$(OBJS))
 HAVE_VENDOR_COMMON_LIB = $(if $(wildcard board/$(VENDOR)/common/Makefile),y,n)
 
 LIBS-y += lib/libgeneric.o
+LIBS-y += lib/rsa/librsa.o
 LIBS-y += lib/lzma/liblzma.o
 LIBS-y += lib/lzo/liblzo.o
 LIBS-y += lib/zlib/libz.o
README +10 -0
index 3e586c3..f91e431 100644
@@ -2557,6 +2557,16 @@ CBFS (Coreboot Filesystem) support
 		Note: There is also a sha1sum command, which should perhaps
 		be deprecated in favour of 'hash sha1'.
 
+- Signing support:
+		CONFIG_RSA
+
+		This enables the RSA algorithm used for FIT image verification
+		in U-Boot. See doc/uImage/signature for more information.
+
+		The signing part is build into mkimage regardless of this
+		option.
+
+
 - Show boot progress:
 		CONFIG_SHOW_BOOT_PROGRESS
 
common/image-sig.c +7 -0
index 9b222da..9928bfc 100644
@@ -27,8 +27,15 @@ DECLARE_GLOBAL_DATA_PTR;
 #endif /* !USE_HOSTCC*/
 #include <errno.h>
 #include <image.h>
+#include <rsa.h>
 
 struct image_sig_algo image_sig_algos[] = {
+	{
+		"sha1,rsa2048",
+		rsa_sign,
+		rsa_add_verify_data,
+		rsa_verify,
+	}
 };
 
 struct image_sig_algo *image_get_sig_algo(const char *name)
config.mk +1 -0
index 9003268..a5e26e3 100644
@@ -96,6 +96,7 @@ HOSTCFLAGS	+= $(call os_x_before, 10, 4, "-traditional-cpp")
 HOSTLDFLAGS	+= $(call os_x_before, 10, 5, "-multiply_defined suppress")
 else
 HOSTCC		= gcc
+HOSTLIBS	+= -lssl -lcrypto
 endif
 
 ifeq ($(HOSTOS),cygwin)
include/rsa.h new file +108 -0

108 lines not on this page · raw message

lib/rsa/Makefile new file +48 -0

48 lines not on this page · raw message

lib/rsa/rsa-sign.c new file +460 -0

460 lines not on this page · raw message

lib/rsa/rsa-verify.c new file +385 -0

385 lines not on this page · raw message

tools/Makefile +11 -2
index 38fd934..b589cae 100644
@@ -125,6 +125,9 @@ LIBFDT_OBJ_FILES-y += fdt_rw.o
 LIBFDT_OBJ_FILES-y += fdt_strerror.o
 LIBFDT_OBJ_FILES-y += fdt_wip.o
 
+# RSA objects
+RSA_OBJ_FILES-y += rsa-sign.o
+
 # Generated LCD/video logo
 LOGO_H = $(OBJTREE)/include/bmp_logo.h
 LOGO_DATA_H = $(OBJTREE)/include/bmp_logo_data.h
@@ -159,8 +162,10 @@ endif
 HOSTSRCS += $(addprefix $(SRCTREE)/,$(EXT_OBJ_FILES-y:.o=.c))
 HOSTSRCS += $(addprefix $(SRCTREE)/tools/,$(OBJ_FILES-y:.o=.c))
 HOSTSRCS += $(addprefix $(SRCTREE)/lib/libfdt/,$(LIBFDT_OBJ_FILES-y:.o=.c))
+HOSTSRCS += $(addprefix $(SRCTREE)/lib/rsa/,$(RSA_OBJ_FILES-y:.o=.c))
 BINS	:= $(addprefix $(obj),$(sort $(BIN_FILES-y)))
 LIBFDT_OBJS	:= $(addprefix $(obj),$(LIBFDT_OBJ_FILES-y))
+RSA_OBJS	:= $(addprefix $(obj),$(RSA_OBJ_FILES-y))
 
 # We cannot check CONFIG_FIT_SIGNATURE here since it is not set on the host
 FIT_SIG_OBJ_FILES	:= image-sig.o
@@ -235,8 +240,9 @@ $(obj)mkimage$(SFX):	$(obj)aisimage.o \
 			$(obj)omapimage.o \
 			$(obj)sha1.o \
 			$(obj)ublimage.o \
-			$(LIBFDT_OBJS)
-	$(HOSTCC) $(HOSTCFLAGS) $(HOSTLDFLAGS) -o $@ $^
+			$(LIBFDT_OBJS) \
+			$(RSA_OBJS)
+	$(HOSTCC) $(HOSTCFLAGS) $(HOSTLDFLAGS) -o $@ $^ $(HOSTLIBS)
 	$(HOSTSTRIP) $@
 
 $(obj)mk$(BOARD)spl$(SFX):	$(obj)mkexynosspl.o
@@ -272,6 +278,9 @@ $(obj)%.o: $(SRCTREE)/lib/%.c
 $(obj)%.o: $(SRCTREE)/lib/libfdt/%.c
 	$(HOSTCC) -g $(HOSTCFLAGS_NOPED) -c -o $@ $<
 
+$(obj)%.o: $(SRCTREE)/lib/rsa/%.c
+	$(HOSTCC) -g $(HOSTCFLAGS_NOPED) -c -o $@ $<
+
 subdirs:
 ifeq ($(TOOLSUBDIRS),)
 	@:
Signature · 1 line
1.8.3
#4 lore raw

PATCH v3 3/12 image: Add RSA support for image signing

Hello, Simon.

When compiling the master branch,
I got an error while a tools/mkimage build.

u-boot/lib/rsa/rsa-sign.c:26:25: fatal error: openssl/rsa.h: No such file or directory

I think this erorr is caused by commit 19c402a.

I searched and installed the necessary package and I could resolve this error.

$ apt-file search openssl/rsa.h
libssl-dev: /usr/include/openssl/rsa.h
$ sudo apt-get install libssl-dev

Let me ask a question.

Going forward do we always need the openssl development package for creating mkimage tool?
Or is it possible to disable RSA feature by some CONFIG option?

Best Regards
Masahiro Yamada

#5 lore raw

PATCH v3 3/12 image: Add RSA support for image signing

Hi Masahiro,

Quoted 22 lines · Masahiro Yamada

Hello, Simon.

When compiling the master branch,
I got an error while a tools/mkimage build.

u-boot/lib/rsa/rsa-sign.c:26:25: fatal error: openssl/rsa.h: No such file or directory

I think this erorr is caused by commit 19c402a.

I searched and installed the necessary package and I could resolve this error.

$ apt-file search openssl/rsa.h
libssl-dev: /usr/include/openssl/rsa.h
$ sudo apt-get install libssl-dev
Quoted 6 lines

Let me ask a question.

Going forward do we always need the openssl development package for creating mkimage tool?
Or is it possible to disable RSA feature by some CONFIG option?

This is to support verified boot using FIT. Yes it would be possible to make it an option. I had it that way for a while, but then I worried that it would create two versions of mkimage, one of which is incapable of signing images. That means that mkimage would need to be built for a board with verified boot enabled in order to get full functionality.

Perhaps another way would be to check for the header and (if not present), silently build without signing support?

Regards,
Simon

Quoted 6 lines

Best Regards
Masahiro Yamada

#6 lore raw

PATCH v3 3/12 image: Add RSA support for image signing

-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1

Quoted 41 lines · Simon Glass

Hi Masahiro,

On Wed, Jun 26, 2013 at 9:08 PM, Masahiro Yamada <yamada.m at jp.panasonic.com <mailto:[email protected]>> wrote:

Hello, Simon.

When compiling the master branch, I got an error while a tools/mkimage build.

u-boot/lib/rsa/rsa-sign.c:26:25: fatal error: openssl/rsa.h: No such file or directory

I think this erorr is caused by commit 19c402a.

I searched and installed the necessary package and I could resolve this error.

$ apt-file search openssl/rsa.h libssl-dev: 
/usr/include/openssl/rsa.h $ sudo apt-get install libssl-dev

Let me ask a question.

Going forward do we always need the openssl development package for creating mkimage tool? Or is it possible to disable RSA feature by some CONFIG option?

This is to support verified boot using FIT. Yes it would be possible to make it an option. I had it that way for a while, but then I worried that it would create two versions of mkimage, one of which is incapable of signing images. That means that mkimage would need to be built for a board with verified boot enabled in order to get full functionality.

Quoted 2 lines

Perhaps another way would be to check for the header and (if not present), silently build without signing support?

Hurk, dang it.. Yes, I think we need to build and go with an error message on attempted use. Skimming the code, we can't rely on CONFIG_FIT_SIGNATURE being inherited from the config, on the host side, yes?

- --
Tom
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.4.11 (GNU/Linux)
Comment: Using GnuPG with Thunderbird - http://www.enigmail.net/

iQIcBAEBAgAGBQJRzDUoAAoJENk4IS6UOR1WOF8P/in1joGCy0NcOJ3g3PKRRi5Y eUgwTbOaQ3x82dJ3820YEkxSpaJIxiw+l0cvbWVH9TR6wO/7EiVjNLmFwauhuVBU BAf9ghleHjd3T6utxEzDk0z9O2E9f8aliSQ1d31oK1NrM/IvhW06udv6V0shFRCN i3uD4bkWPgv+qChZ+94ma4rc3SDz393lG2dwn0L9TZ/Kv3qOaoEr1qTDSS2fRXqg 2Yd1vFD3mT9ZEMQwfteoThuXWZfyWFYfh9wsUjwjHonJNauwKkZgWFHnZpYCv6tJ TQEOH7pVpO7RAMFw/7f/tXdk/U2Qnmq/GH0Gy/p9E7UYb4IqXNGrXBOjhEGizH+c gA4bAxjooHoVayUf/m3m6g5WUd1uv6cKhcS5WppmaduPdPncB8wPKxksT/ti1NKi 4yDdFLsudPvO+0R94MT+5dgV4Album8aoICmSgzxRy+3x9lGGxEGHeCleDtwnLTR dQEnmUEweKvwL1MNJZ6TBtqekbf/hKVbgn4EqEi0fb4CLKCVFOGT3YSu8oWDaZEQ q0C08/hn6lNgbGqTQL83I0lahp2HiPjHZMvUVVcE0lzOIowkTLLxvsZLfLhlCdXv LxG26Pi0rG/CU8BnYQ/W00X4HPi20UDOt9nLyINq63ctKLWKMMA3B7IkcpBGbT2U dA8uceK04MStQdxiB3kh
=wI1Q
-----END PGP SIGNATURE-----

#7 lore raw

PATCH v3 3/12 image: Add RSA support for image signing

Hi Tom,

Quoted 45 lines · Tom Rini

-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1

Quoted 41 lines · Simon Glass

Hi Masahiro,

On Wed, Jun 26, 2013 at 9:08 PM, Masahiro Yamada <yamada.m at jp.panasonic.com <mailto:[email protected]>> wrote:

Hello, Simon.

When compiling the master branch, I got an error while a tools/mkimage build.

u-boot/lib/rsa/rsa-sign.c:26:25: fatal error: openssl/rsa.h: No such file or directory

I think this erorr is caused by commit 19c402a.

I searched and installed the necessary package and I could resolve this error.

$ apt-file search openssl/rsa.h libssl-dev:
/usr/include/openssl/rsa.h $ sudo apt-get install libssl-dev

Let me ask a question.

Going forward do we always need the openssl development package for creating mkimage tool? Or is it possible to disable RSA feature by some CONFIG option?

This is to support verified boot using FIT. Yes it would be possible to make it an option. I had it that way for a while, but then I worried that it would create two versions of mkimage, one of which is incapable of signing images. That means that mkimage would need to be built for a board with verified boot enabled in order to get full functionality.

Quoted 8 lines
Quoted 2 lines

Perhaps another way would be to check for the header and (if not present), silently build without signing support?

Hurk, dang it.. Yes, I think we need to build and go with an error message on attempted use. Skimming the code, we can't rely on CONFIG_FIT_SIGNATURE being inherited from the config, on the host side, yes?

Yes I can make this check CONFIG_FIT_SIGNATURE - as mentioned I had it that way originally but worred about creating different versions of mkimage.

There is actually code there for this which we can use:

#ifdef CONFIG_FIT_SIGNATURE
fprintf(stderr, "Signing / verified boot options: [-k keydir] [-K dtb] [ -c <comment>] [-r]\n"

"          -k => set directory containing private keys\n"
"          -K => write public keys to this .dtb file\n"
"          -c => add comment in signature node\n"
"          -F => re-sign existing FIT image\n"
"          -r => mark keys used as 'required' in dtb\n");

#else
fprintf(stderr, "Signing / verified boot not supported (CONFIG_FIT_SIGNATURE undefined)\n");
#endif

Let me know if this is the preferred option and I will prepare a patch.

Regards,
Simon

#8 lore raw

PATCH v3 3/12 image: Add RSA support for image signing

Quoted 71 lines · Simon Glass

Hi Tom,

Quoted 45 lines · Tom Rini

-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1

Quoted 41 lines · Simon Glass

Hi Masahiro,

On Wed, Jun 26, 2013 at 9:08 PM, Masahiro Yamada <yamada.m at jp.panasonic.com <mailto:[email protected]>> wrote:

Hello, Simon.

When compiling the master branch, I got an error while a tools/mkimage build.

u-boot/lib/rsa/rsa-sign.c:26:25: fatal error: openssl/rsa.h: No such file or directory

I think this erorr is caused by commit 19c402a.

I searched and installed the necessary package and I could resolve this error.

$ apt-file search openssl/rsa.h libssl-dev:
/usr/include/openssl/rsa.h $ sudo apt-get install libssl-dev

Let me ask a question.

Going forward do we always need the openssl development package for creating mkimage tool? Or is it possible to disable RSA feature by some CONFIG option?

This is to support verified boot using FIT. Yes it would be possible to make it an option. I had it that way for a while, but then I worried that it would create two versions of mkimage, one of which is incapable of signing images. That means that mkimage would need to be built for a board with verified boot enabled in order to get full functionality.

Quoted 8 lines
Quoted 2 lines

Perhaps another way would be to check for the header and (if not present), silently build without signing support?

Hurk, dang it.. Yes, I think we need to build and go with an error message on attempted use. Skimming the code, we can't rely on CONFIG_FIT_SIGNATURE being inherited from the config, on the host side, yes?

Yes I can make this check CONFIG_FIT_SIGNATURE - as mentioned I had it that way originally but worred about creating different versions of mkimage.

There is actually code there for this which we can use:

#ifdef CONFIG_FIT_SIGNATURE
fprintf(stderr, "Signing / verified boot options: [-k keydir] [-K dtb] [ -c <comment>] [-r]\n"

"          -k => set directory containing private keys\n"
"          -K => write public keys to this .dtb file\n"
"          -c => add comment in signature node\n"
"          -F => re-sign existing FIT image\n"
"          -r => mark keys used as 'required' in dtb\n");
Quoted 6 lines

#else
fprintf(stderr, "Signing / verified boot not supported (CONFIG_FIT_SIGNATURE undefined)\n");
#endif

Let me know if this is the preferred option and I will prepare a patch.

The Makefile fragments I saw implied we couldn't use this approach on the host. But if we can, lets.

Signature · 8 lines
Tom
-------------- next part --------------
A non-text attachment was scrubbed...
Name: not available
Type: application/pgp-signature
Size: 836 bytes
Desc: Digital signature
URL: <http://lists.denx.de/pipermail/u-boot/attachments/20130627/b1dfbf7f/attachment.pgp>
#9 lore raw

PATCH v3 3/12 image: Add RSA support for image signing

Hi Tom,

Quoted 79 lines · Tom Rini
Quoted 52 lines · Simon Glass

Hi Tom,

Quoted 48 lines · Tom Rini

-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1

Quoted 43 lines · Simon Glass

Hi Masahiro,

On Wed, Jun 26, 2013 at 9:08 PM, Masahiro Yamada <yamada.m at jp.panasonic.com <mailto:[email protected]>> wrote:

Hello, Simon.

When compiling the master branch, I got an error while a tools/mkimage build.

u-boot/lib/rsa/rsa-sign.c:26:25: fatal error: openssl/rsa.h: No such file or directory

I think this erorr is caused by commit 19c402a.

I searched and installed the necessary package and I could resolve this error.

$ apt-file search openssl/rsa.h libssl-dev:
/usr/include/openssl/rsa.h $ sudo apt-get install libssl-dev

Let me ask a question.

Going forward do we always need the openssl development package for creating mkimage tool? Or is it possible to disable RSA feature by some CONFIG option?

This is to support verified boot using FIT. Yes it would be possible to make it an option. I had it that way for a while, but then I worried that it would create two versions of mkimage, one of which is incapable of signing images. That means that mkimage would need to be built for a board with verified boot enabled in order to get full functionality.

Perhaps another way would be to check for the header and (if not present), silently build without signing support?

Quoted 7 lines
Quoted 5 lines

Hurk, dang it.. Yes, I think we need to build and go with an error message on attempted use. Skimming the code, we can't rely on CONFIG_FIT_SIGNATURE being inherited from the config, on the host side, yes?

Yes I can make this check CONFIG_FIT_SIGNATURE - as mentioned I had it

that

Quoted 6 lines

way originally but worred about creating different versions of mkimage.

There is actually code there for this which we can use:

#ifdef CONFIG_FIT_SIGNATURE
fprintf(stderr, "Signing / verified boot options: [-k keydir] [-K dtb] [

-c

Quoted 11 lines

<comment>] [-r]\n"

"          -k => set directory containing private keys\n"
"          -K => write public keys to this .dtb file\n"
"          -c => add comment in signature node\n"
"          -F => re-sign existing FIT image\n"
"          -r => mark keys used as 'required' in dtb\n");

#else
fprintf(stderr, "Signing / verified boot not supported (CONFIG_FIT_SIGNATURE undefined)\n");
#endif

Quoted 5 lines
Quoted 1 line

Let me know if this is the preferred option and I will prepare a patch.

The Makefile fragments I saw implied we couldn't use this approach on the host. But if we can, lets.

That still seems to work OK. Will send a patch.

Regards,
Simon

#10 lore raw

PATCH v3 4/12 mkimage: Add -k option to specify key directory

In reply to Simon Glass

Keys required for signing images will be in a specific directory. Add a -k option to specify that directory.

Also update the mkimage man page with this information and a clearer list of available commands.

---
Changes in v3: None
Changes in v2:
- Adjust mkimage help to separate out signing options
- Fix checkpatch warnings about split strings

 doc/mkimage.1     | 25 ++++++++++++++++++++++---
 tools/fit_image.c |  2 +-
 tools/mkimage.c   | 15 ++++++++++++++-
 tools/mkimage.h   |  1 +
 4 files changed, 38 insertions(+), 5 deletions(-)
doc/mkimage.1 +22 -3
index 39652c8..6740fb1 100644
@@ -4,7 +4,14 @@
 mkimage \- Generate image for U-Boot
 .SH SYNOPSIS
 .B mkimage
-.RB [\fIoptions\fP]
+.RB "\-l [" "uimage file name" "]"
+
+.B mkimage
+.RB [\fIoptions\fP] " \-f [" "image tree source file" "]" " [" "uimage file name" "]"
+
+.B mkimage
+.RB [\fIoptions\fP] " (legacy mode)"
+
 .SH "DESCRIPTION"
 The
 .B mkimage
@@ -26,7 +33,8 @@ etc.
 The new
 .I FIT (Flattened Image Tree) format
 allows for more flexibility in handling images of various types and also
-enhances integrity protection of images with stronger checksums.
+enhances integrity protection of images with stronger checksums. It also
+supports verified boot.
 
 .SH "OPTIONS"
 
@@ -67,6 +75,10 @@ Set load address with a hex number.
 Set entry point with a hex number.
 
 .TP
+.BI "\-l"
+List the contents of an image.
+
+.TP
 .BI "\-n [" "image name" "]"
 Set image name to 'image name'.
 
@@ -91,6 +103,12 @@ create the image.
 Image tree source file that describes the structure and contents of the
 FIT image.
 
+.TP
+.BI "\-k [" "key_directory" "]"
+Specifies the directory containing keys to use for signing. This directory
+should contain a private key file <name>.key for use with signing and a
+certificate <name>.crt (containing the public key) for use with verification.
+
 .SH EXAMPLES
 
 List image information:
@@ -115,4 +133,5 @@ http://www.denx.de/wiki/U-Boot/WebHome
 .PP
 .SH AUTHOR
 This manual page was written by Nobuhiro Iwamatsu <[email protected]>
-and Wolfgang Denk <[email protected]>
+and Wolfgang Denk <[email protected]>. It was updated for image signing by
+Simon Glass <[email protected]>.
tools/fit_image.c +1 -1
index ef6ef44..339e0f8 100644
@@ -137,7 +137,7 @@ static int fit_handle_file (struct mkimage_params *params)
 		goto err_mmap;
 
 	/* set hashes for images in the blob */
-	if (fit_add_verification_data(NULL, NULL, ptr, NULL, 0)) {
+	if (fit_add_verification_data(params->keydir, NULL, ptr, NULL, 0)) {
 		fprintf (stderr, "%s Can't add hashes to FIT blob",
 				params->cmdname);
 		goto err_add_hashes;
tools/mkimage.c +14 -1
index e43b09f..def7df2 100644
@@ -248,6 +248,11 @@ main (int argc, char **argv)
 				params.datafile = *++argv;
 				params.fflag = 1;
 				goto NXTARG;
+			case 'k':
+				if (--argc <= 0)
+					usage();
+				params.keydir = *++argv;
+				goto NXTARG;
 			case 'n':
 				if (--argc <= 0)
 					usage ();
@@ -623,8 +628,16 @@ usage ()
 			 "          -d ==> use image data from 'datafile'\n"
 			 "          -x ==> set XIP (execute in place)\n",
 		params.cmdname);
-	fprintf (stderr, "       %s [-D dtc_options] -f fit-image.its fit-image\n",
+	fprintf(stderr, "       %s [-D dtc_options] -f fit-image.its fit-image\n",
 		params.cmdname);
+	fprintf(stderr, "          -D => set options for device tree compiler\n"
+			"          -f => input filename for FIT source\n");
+#ifdef CONFIG_FIT_SIGNATURE
+	fprintf(stderr, "Signing / verified boot options: [-k keydir]\n"
+			"          -k => set directory containing private keys\n");
+#else
+	fprintf(stderr, "Signing / verified boot not supported (CONFIG_FIT_SIGNATURE undefined)\n");
+#endif
 	fprintf (stderr, "       %s -V ==> print version information and exit\n",
 		params.cmdname);
 
tools/mkimage.h +1 -0
index 03c6c8f..059e124 100644
@@ -87,6 +87,7 @@ struct mkimage_params {
 	char *datafile;
 	char *imagefile;
 	char *cmdname;
+	const char *keydir;	/* Directory holding private keys */
 };
 
 /*
Signature · 1 line
1.8.3
#11 lore raw

PATCH v3 5/12 mkimage: Add -K to write public keys to an FDT blob

In reply to Simon Glass

FIT image verification requires public keys. Add a convenient option to mkimage to write the public keys to an FDT blob when it uses then for signing an image. This allows us to use:

mkimage -f test.its -K dest.dtb -k keys test.fit

and have the signatures written to test.fit and the corresponding public keys written to dest.dtb. Then dest.dtb can be used as the control FDT for U-Boot (CONFIG_OF_CONTROL), thus providing U-Boot with access to the public keys it needs.

---
Changes in v3: None
Changes in v2:
- Adjust mkimage help to separate out signing options
- Rebase on previous patches

 doc/mkimage.1     | 16 ++++++++++++++++
 tools/fit_image.c | 21 +++++++++++++++++++--
 tools/mkimage.c   | 10 ++++++++--
 tools/mkimage.h   |  1 +
 4 files changed, 44 insertions(+), 4 deletions(-)
doc/mkimage.1 +16 -0
index 6740fb1..8185ff5 100644
@@ -109,6 +109,14 @@ Specifies the directory containing keys to use for signing. This directory
 should contain a private key file <name>.key for use with signing and a
 certificate <name>.crt (containing the public key) for use with verification.
 
+.TP
+.BI "\-K [" "key_destination" "]"
+Specifies a compiled device tree binary file (typically .dtb) to write
+public key information into. When a private key is used to sign an image,
+the corresponding public key is written into this file for for run-time
+verification. Typically the file here is the device tree binary used by
+CONFIG_OF_CONTROL in U-Boot.
+
 .SH EXAMPLES
 
 List image information:
@@ -127,6 +135,14 @@ Create FIT image with compressed PowerPC Linux kernel:
 .nf
 .B mkimage -f kernel.its kernel.itb
 .fi
+.P
+Create FIT image with compressed kernel and sign it with keys in the
+/public/signing-keys directory. Add corresponding public keys into u-boot.dtb,
+skipping those for which keys cannot be found. Also add a comment.
+.nf
+.B mkimage -f kernel.its -k /public/signing-keys -K u-boot.dtb \\\\
+-c "Kernel 3.8 image for production devices" kernel.itb
+.fi
 
 .SH HOMEPAGE
 http://www.denx.de/wiki/U-Boot/WebHome
tools/fit_image.c +19 -2
index 339e0f8..b17fa2d 100644
@@ -105,9 +105,11 @@ static int fit_handle_file (struct mkimage_params *params)
 {
 	char tmpfile[MKIMAGE_MAX_TMPFILE_LEN];
 	char cmd[MKIMAGE_MAX_DTC_CMDLINE_LEN];
-	int tfd;
+	int tfd, destfd = 0;
+	void *dest_blob = NULL;
 	struct stat sbuf;
 	void *ptr;
+	off_t destfd_size = 0;
 
 	/* Flattened Image Tree (FIT) format  handling */
 	debug ("FIT format handling\n");
@@ -132,12 +134,20 @@ static int fit_handle_file (struct mkimage_params *params)
 		goto err_system;
 	}
 
+	if (params->keydest) {
+		destfd = mmap_fdt(params, params->keydest, &dest_blob, &sbuf);
+		if (destfd < 0)
+			goto err_keydest;
+		destfd_size = sbuf.st_size;
+	}
+
 	tfd = mmap_fdt(params, tmpfile, &ptr, &sbuf);
 	if (tfd < 0)
 		goto err_mmap;
 
 	/* set hashes for images in the blob */
-	if (fit_add_verification_data(params->keydir, NULL, ptr, NULL, 0)) {
+	if (fit_add_verification_data(params->keydir, dest_blob, ptr,
+				      NULL, 0)) {
 		fprintf (stderr, "%s Can't add hashes to FIT blob",
 				params->cmdname);
 		goto err_add_hashes;
@@ -153,6 +163,10 @@ static int fit_handle_file (struct mkimage_params *params)
 
 	munmap ((void *)ptr, sbuf.st_size);
 	close (tfd);
+	if (dest_blob) {
+		munmap(dest_blob, destfd_size);
+		close(destfd);
+	}
 
 	if (rename (tmpfile, params->imagefile) == -1) {
 		fprintf (stderr, "%s: Can't rename %s to %s: %s\n",
@@ -168,6 +182,9 @@ err_add_timestamp:
 err_add_hashes:
 	munmap(ptr, sbuf.st_size);
 err_mmap:
+	if (dest_blob)
+		munmap(dest_blob, destfd_size);
+err_keydest:
 err_system:
 	unlink(tmpfile);
 	return -1;
tools/mkimage.c +8 -2
index def7df2..3760392 100644
@@ -253,6 +253,11 @@ main (int argc, char **argv)
 					usage();
 				params.keydir = *++argv;
 				goto NXTARG;
+			case 'K':
+				if (--argc <= 0)
+					usage();
+				params.keydest = *++argv;
+				goto NXTARG;
 			case 'n':
 				if (--argc <= 0)
 					usage ();
@@ -633,8 +638,9 @@ usage ()
 	fprintf(stderr, "          -D => set options for device tree compiler\n"
 			"          -f => input filename for FIT source\n");
 #ifdef CONFIG_FIT_SIGNATURE
-	fprintf(stderr, "Signing / verified boot options: [-k keydir]\n"
-			"          -k => set directory containing private keys\n");
+	fprintf(stderr, "Signing / verified boot options: [-k keydir] [-K dtb]\n"
+			"          -k => set directory containing private keys\n"
+			"          -K => write public keys to this .dtb file\n");
 #else
 	fprintf(stderr, "Signing / verified boot not supported (CONFIG_FIT_SIGNATURE undefined)\n");
 #endif
tools/mkimage.h +1 -0
index 059e124..63b9b4f 100644
@@ -88,6 +88,7 @@ struct mkimage_params {
 	char *imagefile;
 	char *cmdname;
 	const char *keydir;	/* Directory holding private keys */
+	const char *keydest;	/* Destination .dtb for public key */
 };
 
 /*
Signature · 1 line
1.8.3
#12 lore raw

PATCH v3 6/12 mkimage: Add -F option to modify an existing .fit file

In reply to Simon Glass

When signing images it is sometimes necessary to sign with different keys at different times, or make the signer entirely separate from the FIT creation to avoid needing the private keys to be publicly available in the system.

Add a -F option so that key signing can be a separate step, and possibly done multiple times as different keys are avaiable.

---
Changes in v3: None
Changes in v2:
- Adjust mkimage help to separate out signing options
- Fix checkpatch checks about parenthesis alignment
- Rebase on previous patches

 doc/mkimage.1     | 20 ++++++++++++++++++++
 tools/fit_image.c | 18 ++++++++++++------
 tools/mkimage.c   |  9 ++++++---
 3 files changed, 38 insertions(+), 9 deletions(-)
doc/mkimage.1 +20 -0
index 8185ff5..f9c733a 100644
@@ -10,6 +10,9 @@ mkimage \- Generate image for U-Boot
 .RB [\fIoptions\fP] " \-f [" "image tree source file" "]" " [" "uimage file name" "]"
 
 .B mkimage
+.RB [\fIoptions\fP] " \-F [" "uimage file name" "]"
+
+.B mkimage
 .RB [\fIoptions\fP] " (legacy mode)"
 
 .SH "DESCRIPTION"
@@ -104,6 +107,13 @@ Image tree source file that describes the structure and contents of the
 FIT image.
 
 .TP
+.BI "\-F"
+Indicates that an existing FIT image should be modified. No dtc
+compilation is performed and the -f flag should not be given.
+This can be used to sign images with additional keys after initial image
+creation.
+
+.TP
 .BI "\-k [" "key_directory" "]"
 Specifies the directory containing keys to use for signing. This directory
 should contain a private key file <name>.key for use with signing and a
@@ -144,6 +154,16 @@ skipping those for which keys cannot be found. Also add a comment.
 -c "Kernel 3.8 image for production devices" kernel.itb
 .fi
 
+.P
+Update an existing FIT image, signing it with additional keys.
+Add corresponding public keys into u-boot.dtb. This will resign all images
+with keys that are available in the new directory. Images that request signing
+with unavailable keys are skipped.
+.nf
+.B mkimage -F -k /secret/signing-keys -K u-boot.dtb \\\\
+-c "Kernel 3.8 image for production devices" kernel.itb
+.fi
+
 .SH HOMEPAGE
 http://www.denx.de/wiki/U-Boot/WebHome
 .PP
tools/fit_image.c +12 -6
index b17fa2d..645e93c 100644
@@ -124,10 +124,16 @@ static int fit_handle_file (struct mkimage_params *params)
 	}
 	sprintf (tmpfile, "%s%s", params->imagefile, MKIMAGE_TMPFILE_SUFFIX);
 
-	/* dtc -I dts -O dtb -p 500 datafile > tmpfile */
-	sprintf (cmd, "%s %s %s > %s",
-		MKIMAGE_DTC, params->dtc, params->datafile, tmpfile);
-	debug ("Trying to execute \"%s\"\n", cmd);
+	/* We either compile the source file, or use the existing FIT image */
+	if (params->datafile) {
+		/* dtc -I dts -O dtb -p 500 datafile > tmpfile */
+		snprintf(cmd, sizeof(cmd), "%s %s %s > %s",
+			 MKIMAGE_DTC, params->dtc, params->datafile, tmpfile);
+		debug("Trying to execute \"%s\"\n", cmd);
+	} else {
+		snprintf(cmd, sizeof(cmd), "cp %s %s",
+			 params->imagefile, tmpfile);
+	}
 	if (system (cmd) == -1) {
 		fprintf (stderr, "%s: system(%s) failed: %s\n",
 				params->cmdname, cmd, strerror(errno));
@@ -153,8 +159,8 @@ static int fit_handle_file (struct mkimage_params *params)
 		goto err_add_hashes;
 	}
 
-	/* add a timestamp at offset 0 i.e., root  */
-	if (fit_set_timestamp (ptr, 0, sbuf.st_mtime)) {
+	/* for first image creation, add a timestamp at offset 0 i.e., root  */
+	if (params->datafile && fit_set_timestamp(ptr, 0, sbuf.st_mtime)) {
 		fprintf (stderr, "%s: Can't add image timestamp\n",
 				params->cmdname);
 		goto err_add_timestamp;
tools/mkimage.c +6 -3
index 3760392..e2b82d0 100644
@@ -240,12 +240,14 @@ main (int argc, char **argv)
 			case 'f':
 				if (--argc <= 0)
 					usage ();
+				params.datafile = *++argv;
+				/* no break */
+			case 'F':
 				/*
 				 * The flattened image tree (FIT) format
 				 * requires a flattened device tree image type
 				 */
 				params.type = IH_TYPE_FLATDT;
-				params.datafile = *++argv;
 				params.fflag = 1;
 				goto NXTARG;
 			case 'k':
@@ -633,14 +635,15 @@ usage ()
 			 "          -d ==> use image data from 'datafile'\n"
 			 "          -x ==> set XIP (execute in place)\n",
 		params.cmdname);
-	fprintf(stderr, "       %s [-D dtc_options] -f fit-image.its fit-image\n",
+	fprintf(stderr, "       %s [-D dtc_options] [-f fit-image.its|-F] fit-image\n",
 		params.cmdname);
 	fprintf(stderr, "          -D => set options for device tree compiler\n"
 			"          -f => input filename for FIT source\n");
 #ifdef CONFIG_FIT_SIGNATURE
 	fprintf(stderr, "Signing / verified boot options: [-k keydir] [-K dtb]\n"
 			"          -k => set directory containing private keys\n"
-			"          -K => write public keys to this .dtb file\n");
+			"          -K => write public keys to this .dtb file\n"
+			"          -F => re-sign existing FIT image\n");
 #else
 	fprintf(stderr, "Signing / verified boot not supported (CONFIG_FIT_SIGNATURE undefined)\n");
 #endif
Signature · 1 line
1.8.3
#13 lore raw

PATCH v3 7/12 mkimage: Add -c option to specify a comment for key signing

In reply to Simon Glass

When signing an image, it is useful to add some details about which tool or person is authorising the signing. Add a comment field which can take care of miscellaneous requirements.

---
Changes in v3: None
Changes in v2:
- Adjust mkimage help to separate out signing options
- Rebase on previous patches

 doc/mkimage.1     | 6 ++++++
 tools/fit_image.c | 4 ++--
 tools/mkimage.c   | 8 +++++++-
 tools/mkimage.h   | 1 +
 4 files changed, 16 insertions(+), 3 deletions(-)
doc/mkimage.1 +6 -0
index f9c733a..b67a351 100644
@@ -97,6 +97,12 @@ Set XIP (execute in place) flag.
 .B Create FIT image:
 
 .TP
+.BI "\-c [" "comment" "]"
+Specifies a comment to be added when signing. This is typically a useful
+message which describes how the image was signed or some other useful
+information.
+
+.TP
 .BI "\-D [" "dtc options" "]"
 Provide special options to the device tree compiler that is used to
 create the image.
tools/fit_image.c +2 -2
index 645e93c..d48f571 100644
@@ -153,9 +153,9 @@ static int fit_handle_file (struct mkimage_params *params)
 
 	/* set hashes for images in the blob */
 	if (fit_add_verification_data(params->keydir, dest_blob, ptr,
-				      NULL, 0)) {
+				      params->comment, 0)) {
 		fprintf (stderr, "%s Can't add hashes to FIT blob",
-				params->cmdname);
+			 params->cmdname);
 		goto err_add_hashes;
 	}
 
tools/mkimage.c +7 -1
index e2b82d0..b3b45a4 100644
@@ -183,6 +183,11 @@ main (int argc, char **argv)
 					genimg_get_arch_id (*++argv)) < 0)
 					usage ();
 				goto NXTARG;
+			case 'c':
+				if (--argc <= 0)
+					usage();
+				params.comment = *++argv;
+				goto NXTARG;
 			case 'C':
 				if ((--argc <= 0) ||
 					(params.comp =
@@ -640,9 +645,10 @@ usage ()
 	fprintf(stderr, "          -D => set options for device tree compiler\n"
 			"          -f => input filename for FIT source\n");
 #ifdef CONFIG_FIT_SIGNATURE
-	fprintf(stderr, "Signing / verified boot options: [-k keydir] [-K dtb]\n"
+	fprintf(stderr, "Signing / verified boot options: [-k keydir] [-K dtb] [ -c <comment>]\n"
 			"          -k => set directory containing private keys\n"
 			"          -K => write public keys to this .dtb file\n"
+			"          -c => add comment in signature node\n"
 			"          -F => re-sign existing FIT image\n");
 #else
 	fprintf(stderr, "Signing / verified boot not supported (CONFIG_FIT_SIGNATURE undefined)\n");
tools/mkimage.h +1 -0
index 63b9b4f..ab8baf8 100644
@@ -89,6 +89,7 @@ struct mkimage_params {
 	char *cmdname;
 	const char *keydir;	/* Directory holding private keys */
 	const char *keydest;	/* Destination .dtb for public key */
+	const char *comment;	/* Comment to add to signature node */
 };
 
 /*
Signature · 1 line
1.8.3
#14 lore raw

PATCH v3 8/12 mkimage: Add -r option to specify keys that must be verified

In reply to Simon Glass

Normally, multiple public keys can be provided and U-Boot is not required to use all of them for verification. This is because some images may not be signed, or may be optionally signed.

But we still need a mechanism to determine when a key must be used. This feature cannot be implemented in the FIT itself, since anyone could change it to mark a key as optional. The requirement for key verification must go in with the public keys, in a place that is protected from modification.

Add a -r option which tells mkimage to mark all keys that it uses for signing as 'required'.

If some keys are optional and some are required, run mkimage several times (perhaps with different key directories if some keys are very secret) using the -F flag to update an existing FIT.

---
Changes in v3: None
Changes in v2:
- Adjust mkimage help to separate out signing options
- Rebase on previous patches

 doc/mkimage.1     | 6 ++++++
 tools/fit_image.c | 9 +++++----
 tools/mkimage.c   | 8 ++++++--
 tools/mkimage.h   | 1 +
 4 files changed, 18 insertions(+), 6 deletions(-)
doc/mkimage.1 +6 -0
index b67a351..14374da 100644
@@ -133,6 +133,12 @@ the corresponding public key is written into this file for for run-time
 verification. Typically the file here is the device tree binary used by
 CONFIG_OF_CONTROL in U-Boot.
 
+.TP
+.BI "\-r
+Specifies that keys used to sign the FIT are required. This means that they
+must be verified for the image to boot. Without this option, the verification
+will be optional (useful for testing but not for release).
+
 .SH EXAMPLES
 
 List image information:
tools/fit_image.c +5 -4
index d48f571..281c2bd 100644
@@ -152,10 +152,11 @@ static int fit_handle_file (struct mkimage_params *params)
 		goto err_mmap;
 
 	/* set hashes for images in the blob */
-	if (fit_add_verification_data(params->keydir, dest_blob, ptr,
-				      params->comment, 0)) {
-		fprintf (stderr, "%s Can't add hashes to FIT blob",
-			 params->cmdname);
+	if (fit_add_verification_data(params->keydir,
+				      dest_blob, ptr, params->comment,
+				      params->require_keys)) {
+		fprintf(stderr, "%s Can't add hashes to FIT blob\n",
+			params->cmdname);
 		goto err_add_hashes;
 	}
 
tools/mkimage.c +6 -2
index b3b45a4..d312844 100644
@@ -270,6 +270,9 @@ main (int argc, char **argv)
 					usage ();
 				params.imagename = *++argv;
 				goto NXTARG;
+			case 'r':
+				params.require_keys = 1;
+				break;
 			case 'R':
 				if (--argc <= 0)
 					usage();
@@ -645,11 +648,12 @@ usage ()
 	fprintf(stderr, "          -D => set options for device tree compiler\n"
 			"          -f => input filename for FIT source\n");
 #ifdef CONFIG_FIT_SIGNATURE
-	fprintf(stderr, "Signing / verified boot options: [-k keydir] [-K dtb] [ -c <comment>]\n"
+	fprintf(stderr, "Signing / verified boot options: [-k keydir] [-K dtb] [ -c <comment>] [-r]\n"
 			"          -k => set directory containing private keys\n"
 			"          -K => write public keys to this .dtb file\n"
 			"          -c => add comment in signature node\n"
-			"          -F => re-sign existing FIT image\n");
+			"          -F => re-sign existing FIT image\n"
+			"          -r => mark keys used as 'required' in dtb\n");
 #else
 	fprintf(stderr, "Signing / verified boot not supported (CONFIG_FIT_SIGNATURE undefined)\n");
 #endif
tools/mkimage.h +1 -0
index ab8baf8..1d9984e 100644
@@ -90,6 +90,7 @@ struct mkimage_params {
 	const char *keydir;	/* Directory holding private keys */
 	const char *keydest;	/* Destination .dtb for public key */
 	const char *comment;	/* Comment to add to signature node */
+	int require_keys;	/* 1 to mark signing keys as 'required' */
 };
 
 /*
Signature · 1 line
1.8.3

A message that is not in the archive (sent off-list or not yet received): 1371161411-2834-1-git-send-email-sjg-F7+t8E8rja9g9hUCZPvPmw@public.gmane.org

#16 lore raw

PATCH v3 9/12 libfdt: Add fdt_find_regions()

Add a function to find regions in device tree given a list of nodes to include and properties to exclude.

See the header file for full documentation.

---
Changes in v3: None
Changes in v2:
- Fix checkpatch checks about parenthesis alignment

 include/libfdt.h     |  64 +++++++++++++++++++++++++
 lib/libfdt/fdt_wip.c | 129 +++++++++++++++++++++++++++++++++++++++++++++++++++
 2 files changed, 193 insertions(+)
include/libfdt.h +64 -0
index c5ec2ac..765d84f 100644
@@ -1511,4 +1511,68 @@ int fdt_del_node(void *fdt, int nodeoffset);
 
 const char *fdt_strerror(int errval);
 
+struct fdt_region {
+	int offset;
+	int size;
+};
+
+/**
+ * fdt_find_regions() - find regions in device tree
+ *
+ * Given a list of nodes to include and properties to exclude, find
+ * the regions of the device tree which describe those included parts.
+ *
+ * The intent is to get a list of regions which will be invariant provided
+ * those parts are invariant. For example, if you request a list of regions
+ * for all nodes but exclude the property "data", then you will get the
+ * same region contents regardless of any change to "data" properties.
+ *
+ * This function can be used to produce a byte-stream to send to a hashing
+ * function to verify that critical parts of the FDT have not changed.
+ *
+ * Nodes which are given in 'inc' are included in the region list, as
+ * are the names of the immediate subnodes nodes (but not the properties
+ * or subnodes of those subnodes).
+ *
+ * For eaxample "/" means to include the root node, all root properties
+ * and the FDT_BEGIN_NODE and FDT_END_NODE of all subnodes of /. The latter
+ * ensures that we capture the names of the subnodes. In a hashing situation
+ * it prevents the root node from changing at all Any change to non-excluded
+ * properties, names of subnodes or number of subnodes would be detected.
+ *
+ * When used with FITs this provides the ability to hash and sign parts of
+ * the FIT based on different configurations in the FIT. Then it is
+ * impossible to change anything about that configuration (include images
+ * attached to the configuration), but it may be possible to add new
+ * configurations, new images or new signatures within the existing
+ * framework.
+ *
+ * Adding new properties to a device tree may result in the string table
+ * being extended (if the new property names are different from those
+ * already added). This function can optionally include a region for
+ * the string table so that this can be part of the hash too.
+ *
+ * The device tree header is not included in the list.
+ *
+ * @fdt:	Device tree to check
+ * @inc:	List of node paths to included
+ * @inc_count:	Number of node paths in list
+ * @exc_prop:	List of properties names to exclude
+ * @exc_prop_count:	Number of properties in exclude list
+ * @region:	Returns list of regions
+ * @max_region:	Maximum length of region list
+ * @path:	Pointer to a temporary string for the function to use for
+ *		building path names
+ * @path_len:	Length of path, must be large enough to hold the longest
+ *		path in the tree
+ * @add_string_tab:	1 to add a region for the string table
+ * @return number of regions in list. If this is >max_regions then the
+ * region array was exhausted. You should increase max_regions and try
+ * the call again.
+ */
+int fdt_find_regions(const void *fdt, char * const inc[], int inc_count,
+		     char * const exc_prop[], int exc_prop_count,
+		     struct fdt_region region[], int max_regions,
+		     char *path, int path_len, int add_string_tab);
+
 #endif /* _LIBFDT_H */
lib/libfdt/fdt_wip.c +129 -0

132 lines not on this page · raw message

Signature · 1 line
1.8.3
#17 lore raw
In reply to a message not in the archive
Quoted 124 lines · Simon Glass

This series implemented a verified boot system based around FIT images as discussed on the U-Boot mailing list, including on this thread:

http://permalink.gmane.org/gmane.comp.boot-loaders.u-boot/147830

RSA is used to implement the encryption. Images are signed by mkimage using private keys created by the user. Public keys are written into U-Boot control FDT (CONFIG_OF_CONTROL) for access by bootm etc. at run-time. The control FDT must be stored in a secure place where it cannot be changed after manufacture. Some notes are provided in the documentaion on how this can be achieved. The implementation is fairly efficient and fits nicely into U-Boot. FIT plus RSA adds around 18KB to SPL size which is manageable on modern SoCs.

When images are loaded, they are verified with the public keys.

It is important to have a test framework for this series. For this, sandbox is used, and a script is provided which signs images and gets sandbox to load them using a script, to check that all is well.

Rollback prevention has been added in a separate TPM patch. This ensures that an attacker cannot boot your system with an old image that has been compromised. Support for this is not built into bootm, but instead must be scripted in U-Boot. It is possible that a standard scheme for this could be devised by adding version number tags to the signing procedure. However scripts do provide more flexibility. See the 'tpm' command for more information.

Two patches affect libfdt and have material which is not yet upstream in that project:

image: Add support for signing of FIT configurations
libfdt: Add fdt_find_regions()

If these are not desired, then the rest of the series can stand alone, just without the configuration-signing feature.

This series requires the 'trace' series since it sits on top of the bootm refactor there.

This series is available at:

http://git.denx.de/u-boot-x86.git

in the branch 'vboot'.

Changes in v3:
- Fix 'compile' typo
- Rebase to master
- Use new fdt_first/next_subnode()

Changes in v2:
- Add sanity checks on key sizes in RSA (improves security)
- Adjust how signing enable works in image.h
- Adjust mkimage help to separate out signing options
- Avoid using malloc in RSA routines (for smaller SPL code size)
- Build signing support unconditionally in mkimage
- Fix FDT error handling in fit_image_write_sig()
- Fix checkpatch checks about parenthesis alignment
- Fix checkpatch warnings about split strings
- Fix spelling of multiply in rsa-verify.c
- Only build RSA support into mkimage if CONFIG_RSA is defined
- Rebase on previous patches
- Require CONFIG_FIT_SIGNATURE in image.h for mkimage to support signing
- Support RSA library version without ERR_remove_thread_state()
- Tweak tools/Makefile to make image signing optional
- Update README to fix typos
- Update README to fix typos and clarify some points
- Use U-Boot's -c option instead of hard-coding a boot script
- Use stack instead of calloc() within U-Boot's signature verification code
- gd->fdt_blob is now available on all archs (generic board landed)

Simon Glass (12):
image: Add signing infrastructure
image: Support signing of images
image: Add RSA support for image signing
mkimage: Add -k option to specify key directory
mkimage: Add -K to write public keys to an FDT blob
mkimage: Add -F option to modify an existing .fit file
mkimage: Add -c option to specify a comment for key signing
mkimage: Add -r option to specify keys that must be verified
libfdt: Add fdt_find_regions()
image: Add support for signing of FIT configurations
sandbox: config: Enable FIT signatures with RSA Add verified boot information and test

 Makefile                         |   1 +
 README                           |  15 ++
 common/Makefile                  |   1 +
 common/image-fit.c               |  83 ++++--
 common/image-sig.c               | 422 +++++++++++++++++++++++++++++++
 config.mk                        |   1 +
 doc/mkimage.1                    |  73 +++++-
 doc/uImage.FIT/sign-configs.its  |  45 ++++
 doc/uImage.FIT/sign-images.its   |  42 ++++
 doc/uImage.FIT/signature.txt     | 382 ++++++++++++++++++++++++++++
 doc/uImage.FIT/verified-boot.txt | 104 ++++++++
 include/configs/sandbox.h        |   2 +
 include/image.h                  | 165 +++++++++++-
 include/libfdt.h                 |  64 +++++
 include/rsa.h                    | 108 ++++++++
 lib/libfdt/fdt_wip.c             | 129 ++++++++++
 lib/rsa/Makefile                 |  48 ++++
 lib/rsa/rsa-sign.c               | 460 ++++++++++++++++++++++++++++++++++
 lib/rsa/rsa-verify.c             | 385 ++++++++++++++++++++++++++++
 test/vboot/.gitignore            |   3 +
 test/vboot/sandbox-kernel.dts    |   7 +
 test/vboot/sandbox-u-boot.dts    |   7 +
 test/vboot/sign-configs.its      |  45 ++++
 test/vboot/sign-images.its       |  42 ++++
 test/vboot/vboot_test.sh         | 126 ++++++++++
 tools/Makefile                   |  19 +-
 tools/fit_image.c                |  44 +++-
 tools/image-host.c               | 527 ++++++++++++++++++++++++++++++++++++++-
 tools/mkimage.c                  |  36 ++-
 tools/mkimage.h                  |   4 +
 30 files changed, 3333 insertions(+), 57 deletions(-)
 create mode 100644 common/image-sig.c
 create mode 100644 doc/uImage.FIT/sign-configs.its
 create mode 100644 doc/uImage.FIT/sign-images.its
 create mode 100644 doc/uImage.FIT/signature.txt
 create mode 100644 doc/uImage.FIT/verified-boot.txt
 create mode 100644 include/rsa.h
 create mode 100644 lib/rsa/Makefile
Quoted 8 lines
 create mode 100644 lib/rsa/rsa-sign.c
 create mode 100644 lib/rsa/rsa-verify.c
 create mode 100644 test/vboot/.gitignore
 create mode 100644 test/vboot/sandbox-kernel.dts
 create mode 100644 test/vboot/sandbox-u-boot.dts
 create mode 100644 test/vboot/sign-configs.its
 create mode 100644 test/vboot/sign-images.its
 create mode 100755 test/vboot/vboot_test.sh

Applied to u-boot/master, thanks!

Signature · 1 line
Tom

_______________________________________________
devicetree-discuss mailing list devicetree-discuss-uLR06cmDAlY/[email protected]
https://lists.ozlabs.org/listinfo/devicetree-discuss

#18 lore raw

PATCH v3 10/12 image: Add support for signing of FIT configurations

In reply to Simon Glass

While signing images is useful, it does not provide complete protection against several types of attack. For example, it it possible to create a FIT with the same signed images, but with the configuration changed such that a different one is selected (mix and match attack). It is also possible to substitute a signed image from an older FIT version into a newer FIT (roll-back attack).

Add support for signing of FIT configurations using the libfdt's region support.

Please see doc/uImage.FIT/signature.txt for more information.

---
Changes in v3:
- Use new fdt_first/next_subnode()

Changes in v2:
- Fix checkpatch checks about parenthesis alignment
- Fix checkpatch warnings about split strings
- Require CONFIG_FIT_SIGNATURE in image.h for mkimage to support signing
- Update README to fix typos and clarify some points
- Use stack instead of calloc() within U-Boot's signature verification code

 common/image-sig.c              | 231 ++++++++++++++++++++++++++-
 doc/uImage.FIT/sign-configs.its |  45 ++++++
 doc/uImage.FIT/signature.txt    | 168 +++++++++++++++++++-
 include/image.h                 |  16 ++
 tools/image-host.c              | 341 +++++++++++++++++++++++++++++++++++++++-
 5 files changed, 798 insertions(+), 3 deletions(-)
 create mode 100644 doc/uImage.FIT/sign-configs.its
common/image-sig.c +230 -1
index 9928bfc..5d907cf 100644
@@ -25,10 +25,11 @@
 #include <malloc.h>
 DECLARE_GLOBAL_DATA_PTR;
 #endif /* !USE_HOSTCC*/
-#include <errno.h>
 #include <image.h>
 #include <rsa.h>
 
+#define IMAGE_MAX_HASHED_NODES		100
+
 struct image_sig_algo image_sig_algos[] = {
 	{
 		"sha1,rsa2048",
@@ -50,6 +51,50 @@ struct image_sig_algo *image_get_sig_algo(const char *name)
 	return NULL;
 }
 
+/**
+ * fit_region_make_list() - Make a list of image regions
+ *
+ * Given a list of fdt_regions, create a list of image_regions. This is a
+ * simple conversion routine since the FDT and image code use different
+ * structures.
+ *
+ * @fit: FIT image
+ * @fdt_regions: Pointer to FDT regions
+ * @count: Number of FDT regions
+ * @region: Pointer to image regions, which must hold @count records. If
+ * region is NULL, then (except for an SPL build) the array will be
+ * allocated.
+ * @return: Pointer to image regions
+ */
+struct image_region *fit_region_make_list(const void *fit,
+		struct fdt_region *fdt_regions, int count,
+		struct image_region *region)
+{
+	int i;
+
+	debug("Hash regions:\n");
+	debug("%10s %10s\n", "Offset", "Size");
+
+	/*
+	 * Use malloc() except in SPL (to save code size). In SPL the caller
+	 * must allocate the array.
+	 */
+#ifndef CONFIG_SPL_BUILD
+	if (!region)
+		region = calloc(sizeof(*region), count);
+#endif
+	if (!region)
+		return NULL;
+	for (i = 0; i < count; i++) {
+		debug("%10x %10x\n", fdt_regions[i].offset,
+		      fdt_regions[i].size);
+		region[i].data = fit + fdt_regions[i].offset;
+		region[i].size = fdt_regions[i].size;
+	}
+
+	return region;
+}
+
 static int fit_image_setup_verify(struct image_sign_info *info,
 		const void *fit, int noffset, int required_keynode,
 		char **err_msgp)
@@ -191,3 +236,187 @@ int fit_image_verify_required_sigs(const void *fit, int image_noffset,
 
 	return 0;
 }
+
+int fit_config_check_sig(const void *fit, int noffset, int required_keynode,
+			 char **err_msgp)
+{
+	char * const exc_prop[] = {"data"};
+	const char *prop, *end, *name;
+	struct image_sign_info info;
+	const uint32_t *strings;
+	uint8_t *fit_value;
+	int fit_value_len;
+	int max_regions;
+	int i, prop_len;
+	char path[200];
+	int count;
+
+	debug("%s: fdt=%p, conf='%s', sig='%s'\n", __func__, gd_fdt_blob(),
+	      fit_get_name(fit, noffset, NULL),
+	      fit_get_name(gd_fdt_blob(), required_keynode, NULL));
+	*err_msgp = NULL;
+	if (fit_image_setup_verify(&info, fit, noffset, required_keynode,
+				   err_msgp))
+		return -1;
+
+	if (fit_image_hash_get_value(fit, noffset, &fit_value,
+				     &fit_value_len)) {
+		*err_msgp = "Can't get hash value property";
+		return -1;
+	}
+
+	/* Count the number of strings in the property */
+	prop = fdt_getprop(fit, noffset, "hashed-nodes", &prop_len);
+	end = prop ? prop + prop_len : prop;
+	for (name = prop, count = 0; name < end; name++)
+		if (!*name)
+			count++;
+	if (!count) {
+		*err_msgp = "Can't get hashed-nodes property";
+		return -1;
+	}
+
+	/* Add a sanity check here since we are using the stack */
+	if (count > IMAGE_MAX_HASHED_NODES) {
+		*err_msgp = "Number of hashed nodes exceeds maximum";
+		return -1;
+	}
+
+	/* Create a list of node names from those strings */
+	char *node_inc[count];
+
+	debug("Hash nodes (%d):\n", count);
+	for (name = prop, i = 0; name < end; name += strlen(name) + 1, i++) {
+		debug("   '%s'\n", name);
+		node_inc[i] = (char *)name;
+	}
+
+	/*
+	 * Each node can generate one region for each sub-node. Allow for
+	 * 7 sub-nodes (hash at 1, signature@1, etc.) and some extra.
+	 */
+	max_regions = 20 + count * 7;
+	struct fdt_region fdt_regions[max_regions];
+
+	/* Get a list of regions to hash */
+	count = fdt_find_regions(fit, node_inc, count,
+			exc_prop, ARRAY_SIZE(exc_prop),
+			fdt_regions, max_regions - 1,
+			path, sizeof(path), 0);
+	if (count < 0) {
+		*err_msgp = "Failed to hash configuration";
+		return -1;
+	}
+	if (count == 0) {
+		*err_msgp = "No data to hash";
+		return -1;
+	}
+	if (count >= max_regions - 1) {
+		*err_msgp = "Too many hash regions";
+		return -1;
+	}
+
+	/* Add the strings */
+	strings = fdt_getprop(fit, noffset, "hashed-strings", NULL);
+	if (strings) {
+		fdt_regions[count].offset = fdt_off_dt_strings(fit) +
+				fdt32_to_cpu(strings[0]);
+		fdt_regions[count].size = fdt32_to_cpu(strings[1]);
+		count++;
+	}
+
+	/* Allocate the region list on the stack */
+	struct image_region region[count];
+
+	fit_region_make_list(fit, fdt_regions, count, region);
+	if (info.algo->verify(&info, region, count, fit_value,
+			      fit_value_len)) {
+		*err_msgp = "Verification failed";
+		return -1;
+	}
+
+	return 0;
+}
+
+static int fit_config_verify_sig(const void *fit, int conf_noffset,
+		const void *sig_blob, int sig_offset)
+{
+	int noffset;
+	char *err_msg = "";
+	int verified = 0;
+	int ret;
+
+	/* Process all hash subnodes of the component conf node */
+	for (noffset = fdt_first_subnode(fit, conf_noffset);
+	     noffset >= 0;
+	     noffset = fdt_next_subnode(fit, noffset)) {
+		const char *name = fit_get_name(fit, noffset, NULL);
+
+		if (!strncmp(name, FIT_SIG_NODENAME,
+			     strlen(FIT_SIG_NODENAME))) {
+			ret = fit_config_check_sig(fit, noffset, sig_offset,
+						   &err_msg);
+			if (ret) {
+				puts("- ");
+			} else {
+				puts("+ ");
+				verified = 1;
+				break;
+			}
+		}
+	}
+
+	if (noffset == -FDT_ERR_TRUNCATED || noffset == -FDT_ERR_BADSTRUCTURE) {
+		err_msg = "Corrupted or truncated tree";
+		goto error;
+	}
+
+	return verified ? 0 : -EPERM;
+
+error:
+	printf(" error!\n%s for '%s' hash node in '%s' config node\n",
+	       err_msg, fit_get_name(fit, noffset, NULL),
+	       fit_get_name(fit, conf_noffset, NULL));
+	return -1;
+}
+
+int fit_config_verify_required_sigs(const void *fit, int conf_noffset,
+		const void *sig_blob)
+{
+	int noffset;
+	int sig_node;
+
+	/* Work out what we need to verify */
+	sig_node = fdt_subnode_offset(sig_blob, 0, FIT_SIG_NODENAME);
+	if (sig_node < 0) {
+		debug("%s: No signature node found: %s\n", __func__,
+		      fdt_strerror(sig_node));
+		return 0;
+	}
+
+	for (noffset = fdt_first_subnode(sig_blob, sig_node);
+	     noffset >= 0;
+	     noffset = fdt_next_subnode(sig_blob, noffset)) {
+		const char *required;
+		int ret;
+
+		required = fdt_getprop(sig_blob, noffset, "required", NULL);
+		if (!required || strcmp(required, "conf"))
+			continue;
+		ret = fit_config_verify_sig(fit, conf_noffset, sig_blob,
+					    noffset);
+		if (ret) {
+			printf("Failed to verify required signature '%s'\n",
+			       fit_get_name(sig_blob, noffset, NULL));
+			return ret;
+		}
+	}
+
+	return 0;
+}
+
+int fit_config_verify(const void *fit, int conf_noffset)
+{
+	return !fit_config_verify_required_sigs(fit, conf_noffset,
+						gd_fdt_blob());
+}
doc/uImage.FIT/sign-configs.its new file +45 -0

45 lines not on this page · raw message

doc/uImage.FIT/signature.txt +167 -1

181 lines not on this page · raw message

include/image.h +16 -0
index da7b9a0..2614918 100644
@@ -964,6 +964,22 @@ int fit_image_verify_required_sigs(const void *fit, int image_noffset,
 int fit_image_check_sig(const void *fit, int noffset, const void *data,
 		size_t size, int required_keynode, char **err_msgp);
 
+/**
+ * fit_region_make_list() - Make a list of regions to hash
+ *
+ * Given a list of FIT regions (offset, size) provided by libfdt, create
+ * a list of regions (void *, size) for use by the signature creationg
+ * and verification code.
+ *
+ * @fit:		FIT image to process
+ * @fdt_regions:	Regions as returned by libfdt
+ * @count:		Number of regions returned by libfdt
+ * @region:		Place to put list of regions (NULL to allocate it)
+ * @return pointer to list of regions, or NULL if out of memory
+ */
+struct image_region *fit_region_make_list(const void *fit,
+		struct fdt_region *fdt_regions, int count,
+		struct image_region *region);
 
 static inline int fit_image_check_target_arch(const void *fdt, int node)
 {
tools/image-host.c +340 -1

355 lines not on this page · raw message

Signature · 1 line
1.8.3
#19 lore raw

PATCH v3 11/12 sandbox: config: Enable FIT signatures with RSA

In reply to Simon Glass

We want to sign and verify images using sandbox, so enable these options.

---
Changes in v3: None
Changes in v2: None

 include/configs/sandbox.h | 2 ++
 1 file changed, 2 insertions(+)
include/configs/sandbox.h +2 -0
index d704329..98dd083 100644
@@ -43,6 +43,8 @@
 #define CONFIG_OF_LIBFDT
 #define CONFIG_LMB
 #define CONFIG_FIT
+#define CONFIG_FIT_SIGNATURE
+#define CONFIG_RSA
 #define CONFIG_CMD_FDT
 
 #define CONFIG_FS_FAT
Signature · 1 line
1.8.3
#20 lore raw

PATCH v3 12/12 Add verified boot information and test

In reply to Simon Glass

Add a description of how to implement verified boot using signed FIT images, and a simple test which verifies operation on sandbox.

The test signs a FIT image and verifies it, then signs a FIT configuration and verifies it. Then it corrupts the signature to check that this is detected.

---
Changes in v3:
- Fix 'compile' typo
- Rebase to master

Changes in v2:
- Update README to fix typos
- Use U-Boot's -c option instead of hard-coding a boot script

 doc/uImage.FIT/verified-boot.txt | 104 ++++++++++++++++++++++++++++++++
 test/vboot/.gitignore            |   3 +
 test/vboot/sandbox-kernel.dts    |   7 +++
 test/vboot/sandbox-u-boot.dts    |   7 +++
 test/vboot/sign-configs.its      |  45 ++++++++++++++
 test/vboot/sign-images.its       |  42 +++++++++++++
 test/vboot/vboot_test.sh         | 126 +++++++++++++++++++++++++++++++++++++++
 7 files changed, 334 insertions(+)
 create mode 100644 doc/uImage.FIT/verified-boot.txt
 create mode 100644 test/vboot/.gitignore
 create mode 100644 test/vboot/sandbox-kernel.dts
 create mode 100644 test/vboot/sandbox-u-boot.dts
 create mode 100644 test/vboot/sign-configs.its
 create mode 100644 test/vboot/sign-images.its
 create mode 100755 test/vboot/vboot_test.sh
doc/uImage.FIT/verified-boot.txt new file +104 -0
new file mode 100644
index 0000000..3c83fbc
@@ -0,0 +1,104 @@
+U-Boot Verified Boot
+====================
+
+Introduction
+------------
+Verified boot here means the verification of all software loaded into a
+machine during the boot process to ensure that it is authorised and correct
+for that machine.
+
+Verified boot extends from the moment of system reset to as far as you wish
+into the boot process. An example might be loading U-Boot from read-only
+memory, then loading a signed kernel, then using the kernel's dm-verity
+driver to mount a signed root filesystem.
+
+A key point is that it is possible to field-upgrade the software on machines
+which use verified boot. Since the machine will only run software that has
+been correctly signed, it is safe to read software from an updatable medium.
+It is also possible to add a secondary signed firmware image, in read-write
+memory, so that firmware can easily be upgraded in a secure manner.
+
+
+Signing
+-------
+Verified boot uses cryptographic algorithms to 'sign' software images.
+Images are signed using a private key known only to the signer, but can
+be verified using a public key. As its name suggests the public key can be
+made available without risk to the verification process. The private and
+public keys are mathematically related. For more information on how this
+works look up "public key cryptography" and "RSA" (a particular algorithm).
+
+The signing and verification process looks something like this:
+
+
+      Signing                                      Verification
+      =======                                      ============
+
+ +--------------+                   *
+ | RSA key pair |                   *             +---------------+
+ | .key  .crt   |                   *             | Public key in |
+ +--------------+       +------> public key ----->| trusted place |
+       |                |           *             +---------------+
+       |                |           *                    |
+       v                |           *                    v
+   +---------+          |           *              +--------------+
+   |         |----------+           *              |              |
+   | signer  |                      *              |    U-Boot    |
+   |         |----------+           *              |  signature   |--> yes/no
+   +---------+          |           *              | verification |
+      ^                 |           *              |              |
+      |                 |           *              +--------------+
+      |                 |           *                    ^
+ +----------+           |           *                    |
+ | Software |           +----> signed image -------------+
+ |  image   |                       *
+ +----------+                       *
+
+
+The signature algorithm relies only on the public key to do its work. Using
+this key it checks the signature that it finds in the image. If it verifies
+then we know that the image is OK.
+
+The public key from the signer allows us to verify and therefore trust
+software from updatable memory.
+
+It is critical that the public key be secure and cannot be tampered with.
+It can be stored in read-only memory, or perhaps protected by other on-chip
+crypto provided by some modern SOCs. If the public key can ben changed, then
+the verification is worthless.
+
+
+Chaining Images
+---------------
+The above method works for a signer providing images to a run-time U-Boot.
+It is also possible to extend this scheme to a second level, like this:
+
+1. Master private key is used by the signer to sign a first-stage image.
+2. Master public key is placed in read-only memory.
+2. Secondary private key is created and used to sign second-stage images.
+3. Secondary public key is placed in first stage images
+4. We use the master public key to verify the first-stage image. We then
+use the secondary public key in the first-stage image to verify the second-
+state image.
+5. This chaining process can go on indefinitely. It is recommended to use a
+different key at each stage, so that a compromise in one place will not
+affect the whole change.
+
+
+Flattened Image Tree (FIT)
+--------------------------
+The FIT format is alreay widely used in U-Boot. It is a flattened device
+tree (FDT) in a particular format, with images contained within. FITs
+include hashes to verify images, so it is relatively straightforward to
+add signatures as well.
+
+The public key can be stored in U-Boot's CONFIG_OF_CONTROL device tree in
+a standard place. Then when a FIT it loaded it can be verified using that
+public key. Multiple keys and multiple signatures are supported.
+
+See signature.txt for more information.
+
+
+Simon Glass
+sjg at chromium.org
+1-1-13
test/vboot/.gitignore new file +3 -0
new file mode 100644
index 0000000..4631242
@@ -0,0 +1,3 @@
+/*.dtb
+/test.fit
+/dev-keys
test/vboot/sandbox-kernel.dts new file +7 -0
new file mode 100644
index 0000000..a1e853c
@@ -0,0 +1,7 @@
+/dts-v1/;
+
+/ {
+	model = "Sandbox Verified Boot Test";
+	compatible = "sandbox";
+
+};
test/vboot/sandbox-u-boot.dts new file +7 -0
new file mode 100644
index 0000000..a1e853c
@@ -0,0 +1,7 @@
+/dts-v1/;
+
+/ {
+	model = "Sandbox Verified Boot Test";
+	compatible = "sandbox";
+
+};
test/vboot/sign-configs.its new file +45 -0

45 lines not on this page · raw message

test/vboot/sign-images.its new file +42 -0

42 lines not on this page · raw message

test/vboot/vboot_test.sh new file +126 -0

126 lines not on this page · raw message

Signature · 1 line
1.8.3
#21 lore raw

PATCH v3 12/12 Add verified boot information and test

Hi Tom,

Quoted 10 lines · Simon Glass

Add a description of how to implement verified boot using signed FIT images,
and a simple test which verifies operation on sandbox.

The test signs a FIT image and verifies it, then signs a FIT configuration and verifies it. Then it corrupts the signature to check that this is detected.

If it helps, here are the results of my build for this series (and the trace one). No new failures but you can see quite a few problems with Xscale.

./tools/buildman/buildman -b us-vboot9c -s
Summary of 35 commits for 1124 boards (32 threads, 1 job per thread) 01: pci: introduce CONFIG_PCI_INDIRECT_BRIDGE option
blackfin: + bf561-acvilon cm-bf561 blackstamp br4 bct-brettl2 cm-bf527
dnp5370 bf506f-ezkit ip04 bf527-sdp bf609-ezkit bf537-stamp bf527-ezkit-v2 cm-bf537e tcm-bf518 cm-bf537u bf527-ezkit bf537-pnav cm-bf533 pr1 bf533-ezkit ibf-dsp561 bf537-srv1 cm-bf548 bf537-minotaur bf538f-ezkit bf548-ezkit bf525-ucr2 blackvme tcm-bf537 bf533-stamp bf518f-ezbrd bf527-ad7160-eval bf526-ezbrd bf561-ezkit

      m68k: +   M54455EVB_a66 M5329AFEE M5249EVB idmr M5208EVBE M5475FFE

M54451EVB astro_mcf5373l M54418TWR_serial_rmii M54455EVB_intel M5282EVB M54455EVB_i66 M5475GFE M5253DEMO M54455EVB_stm33 M5485BFE M5485DFE M5329BFEE M52277EVB M5475EFE M5475CFE M5485AFE M53017EVB M5475AFE M5485HFE M5235EVB M5253EVBE M54418TWR_nand_mii M54418TWR_nand_rmii_lowfreq TASREG cobra5272 M5475BFE M5475DFE M5275EVB M52277EVB_stmicro eb_cpu5282 eb_cpu5282_internal M54451EVB_stmicro M5271EVB M5485GFE M5485EFE M5485FFE M54418TWR M5235EVB_Flash32 M5373EVB M54418TWR_nand_rmii M54418TWR_serial_mii M5485CFE M54455EVB M5272C3

   powerpc: +   MVBLM7 MVSMR lcd4_lwmon5
        sh: +   rsk7269 rsk7264 sh7757lcr sh7752evb rsk7203
microblaze: +   microblaze-generic
  openrisc: +   openrisc-generic
       arm: +   palmtc zipitz2 VCMA9 lubbock zynq_dcc vpac270_nor_128
colibri_pxa270 kzm9g zynq xaeniax polaris pxa255_idp vpac270_ond_256
vpac270_nor_256 smdk2410 h2200 balloon3 palmld trizepsiv
     nds32: +   adp-ag101p adp-ag102 adp-ag101

02: pci: Convert extern inline functions to static inline 03: x86: Correct missing local variable in bootm
04: Fix missing return in do_mem_loop()
05: Show stdout on error in fit-test
06: bootstage: Correct printf types
07: Add function to print a number with grouped digits 08: Add trace library
09: Add a trace command
10: Support tracing in config.mk when enabled
11: Add trace support to generic board
12: Add proftool to decode profile data
13: sandbox: Support trace feature
14: Add a simple test for sandbox trace
15: Clarify bootm OS arguments
16: Refactor the bootm command to reduce code duplication 17: Add a 'fake' go command to the bootm command
18: arm: Implement the 'fake' go command
19: exynos: Avoid function instrumentation for microsecond timer 20: exynos: config: Add tracing options
21: x86: Support tracing function
22: x86: config: Add tracing options
23: wip
24: image: Add signing infrastructure
25: image: Support signing of images
26: image: Add RSA support for image signing
27: mkimage: Add -k option to specify key directory 28: mkimage: Add -K to write public keys to an FDT blob 29: mkimage: Add -F option to modify an existing .fit file 30: mkimage: Add -c option to specify a comment for key signing 31: mkimage: Add -r option to specify keys that must be verified 32: libfdt: Add fdt_find_regions()
33: image: Add support for signing of FIT configurations 34: sandbox: config: Enable FIT signatures with RSA 35: Add verified boot information and test

Regards,
Simon

#22 lore raw

PATCH v3 12/12 Add verified boot information and test

Quoted 12 lines · Simon Glass

Hi Tom,

Quoted 8 lines · Simon Glass

Add a description of how to implement verified boot using signed FIT images,
and a simple test which verifies operation on sandbox.

The test signs a FIT image and verifies it, then signs a FIT configuration and verifies it. Then it corrupts the signature to check that this is detected.

Quoted 6 lines
Quoted 2 lines

If it helps, here are the results of my build for this series (and the trace one). No new failures but you can see quite a few problems with Xscale.

I _think_ Xscale is toolchain choice related. My question is, for arches which use --gc-sections, what is the size change from before to after, when not opting in on this?

Signature · 8 lines
Tom
-------------- next part --------------
A non-text attachment was scrubbed...
Name: not available
Type: application/pgp-signature
Size: 836 bytes
Desc: Digital signature
URL: <http://lists.denx.de/pipermail/u-boot/attachments/20130620/72b50def/attachment.pgp>
#23 lore raw

PATCH v3 12/12 Add verified boot information and test

Hi Tom,

Quoted 17 lines · Tom Rini
Quoted 9 lines · Simon Glass

Hi Tom,

Quoted 5 lines · Simon Glass

Add a description of how to implement verified boot using signed FIT images,
and a simple test which verifies operation on sandbox.

The test signs a FIT image and verifies it, then signs a FIT

configuration

Quoted 6 lines
Quoted 5 lines

and verifies it. Then it corrupts the signature to check that this is detected.

Quoted 8 lines
Quoted 3 lines

If it helps, here are the results of my build for this series (and the trace one). No new failures but you can see quite a few problems with Xscale.

I _think_ Xscale is toolchain choice related. My question is, for arches which use --gc-sections, what is the size change from before to after, when not opting in on this?

Yes I think you are right. Unfortunately I don't have that build now, but I will redo it and check.

Regards,
Simon

Quoted 4 lines

--
Tom

#24 lore raw

PATCH v3 12/12 Add verified boot information and test

In reply to Tom Rini

Hi Tom,

Quoted 17 lines · Tom Rini
Quoted 9 lines · Simon Glass

Hi Tom,

Quoted 5 lines · Simon Glass

Add a description of how to implement verified boot using signed FIT images,
and a simple test which verifies operation on sandbox.

The test signs a FIT image and verifies it, then signs a FIT

configuration

Quoted 6 lines
Quoted 5 lines

and verifies it. Then it corrupts the signature to check that this is detected.

Quoted 8 lines
Quoted 3 lines

If it helps, here are the results of my build for this series (and the trace one). No new failures but you can see quite a few problems with Xscale.

I _think_ Xscale is toolchain choice related. My question is, for arches which use --gc-sections, what is the size change from before to after, when not opting in on this?

Including both trace and verified boot series, the size drops a little for ARM and powerpc:

$ ./tools/buildman/buildman -b us-vboot9d  -sS arm powerpc --step 0
Summary of 2 commits for 955 boards (32 threads, 1 job per thread)
01: Merge branch 'master' of git://www.denx.de/git/u-boot-mmc
       arm: +   palmtc zipitz2 VCMA9 lubbock vpac270_nor_128 colibri_pxa270
kzm9g zynq_dcc zynq xaeniax polaris pxa255_idp vpac270_ond_256
vpac270_nor_256 smdk2410 balloon3 palmld trizepsiv h2200
   powerpc: +   MVBLM7 MVSMR lcd4_lwmon5
36: wip
       arm: (for 290/314 boards)  all -142.6  bss +4.5  data +27.1  rodata
-20.4  spl/u-boot-spl:all +1.9  spl/u-boot-spl:bss +0.0
 spl/u-boot-spl:rodata +1.9  text -153.8
   powerpc: (for 639/641 boards)  all -190.2  bss +0.0  data +25.6  rodata
-12.2  spl/u-boot-spl:all +0.2  spl/u-boot-spl:rodata +0.2  text -203.6

(the wip commit is just a patman change). You can see the text size drops by 100-200 bytes. This is all due to the bootm refactor which removed duplicated code.

If you are interested you can see this in the detail view. Commit 16 removes quite a bit of code. Commit 25 adds up to 80 bytes of text.

$ ./tools/buildman/buildman -b us-vboot9d  -sS arm powerpc
Summary of 36 commits for 955 boards (32 threads, 1 job per thread)
01: Merge branch 'master' of git://www.denx.de/git/u-boot-mmc
       arm: +   palmtc zipitz2 VCMA9 lubbock vpac270_nor_128 colibri_pxa270
kzm9g zynq_dcc zynq xaeniax polaris pxa255_idp vpac270_ond_256
vpac270_nor_256 smdk2410 balloon3 palmld trizepsiv h2200
   powerpc: +   MVBLM7 MVSMR lcd4_lwmon5
02: pci: Convert extern inline functions to static inline
03: x86: Correct missing local variable in bootm
04: Fix missing return in do_mem_loop()
05: Show stdout on error in fit-test
06: bootstage: Correct printf types
07: Add function to print a number with grouped digits
       arm: (for 290/314 boards)  all +6.0  bss -1.2  data +0.0  rodata
+7.2  spl/u-boot-spl:all +1.8  spl/u-boot-spl:bss -0.1
 spl/u-boot-spl:rodata +1.9
   powerpc: (for 639/641 boards)  all +7.8  bss -0.0  rodata +4.8
 spl/u-boot-spl:all +0.1  spl/u-boot-spl:rodata +0.1  text +3.0
08: Add trace library
       arm: (for 290/314 boards)  all +0.1  bss -0.0  data +0.1
 spl/u-boot-spl:all +0.1  spl/u-boot-spl:bss +0.1
   powerpc: (for 639/641 boards)  all +0.0  bss +0.0
09: Add a trace command
10: Support tracing in config.mk when enabled
11: Add trace support to generic board
       arm: (for 290/314 boards)  all +2.7  bss -0.4  data +0.6  text +2.5
12: Add proftool to decode profile data
13: sandbox: Support trace feature
14: Add a simple test for sandbox trace
15: Clarify bootm OS arguments
       arm: (for 290/314 boards)  all +13.0  bss +1.1  text +12.0
   powerpc: (for 639/641 boards)  all +15.4  text +15.4
16: Refactor the bootm command to reduce code duplication
       arm: (for 290/314 boards)  all -352.1  bss +2.1  rodata -69.0  text
-285.2
   powerpc: (for 639/641 boards)  all -345.4  rodata -44.2  text -301.2
17: Add a 'fake' go command to the bootm command
       arm: (for 290/314 boards)  all +55.1  bss +0.1  data +26.2  rodata
+5.0  text +23.8
   powerpc: (for 639/641 boards)  all +42.5  data +25.6  rodata +3.2  text
+13.7
18: arm: Implement the 'fake' go command
       arm: (for 290/314 boards)  all +89.4  bss +4.5  rodata +25.0  text
+59.9
19: exynos: Avoid function instrumentation for microsecond timer
20: exynos: config: Add tracing options
       arm: (for 290/314 boards)  all +25.0  bss -0.1  data +0.2  rodata
+6.9  text +18.0
   powerpc: (for 639/641 boards)  all -0.0  text -0.0
21: x86: Support tracing function
   powerpc: (for 639/641 boards)  all +0.0  text +0.0
22: x86: config: Add tracing options
       arm: (for 290/314 boards)  all -0.9  bss -0.7  rodata -0.1
   powerpc: (for 639/641 boards)  all -0.4  rodata -0.4
23: wip
       arm: (for 290/314 boards)  all +0.9  bss +0.7  rodata +0.1
   powerpc: (for 639/641 boards)  all +0.4  rodata +0.4
24: image: Add signing infrastructure
       arm: (for 290/314 boards)  all -0.3  bss -0.4  data +0.1
25: image: Support signing of images
       arm: (for 290/314 boards)  all +18.9  bss -0.6  data -0.0  rodata
+4.5  text +15.1
   powerpc: (for 639/641 boards)  all +89.4  rodata +23.9
 spl/u-boot-spl:all +0.1  spl/u-boot-spl:rodata +0.1  text +65.5
26: image: Add RSA support for image signing
   powerpc: (for 639/641 boards)  all +0.0  rodata +0.0
27: mkimage: Add -k option to specify key directory
   powerpc: (for 639/641 boards)  all +0.0  text +0.0
28: mkimage: Add -K to write public keys to an FDT blob
29: mkimage: Add -F option to modify an existing .fit file
   powerpc: (for 639/641 boards)  all -0.0  rodata -0.0  text -0.0
30: mkimage: Add -c option to specify a comment for key signing
   powerpc: (for 639/641 boards)  all -0.0  rodata -0.0  text +0.0
31: mkimage: Add -r option to specify keys that must be verified
   powerpc: (for 639/641 boards)  all +0.0  rodata +0.0
32: libfdt: Add fdt_find_regions()
       arm: (for 290/314 boards)  all -0.4  bss -0.4  data +0.0
33: image: Add support for signing of FIT configurations
       arm: (for 290/314 boards)  all +0.0  bss +0.1  data -0.0
34: sandbox: config: Enable FIT signatures with RSA
35: Add verified boot information and test
36: wip

Regards,
Simon