ccmp1: add support to sign different DDR3 configurations for U-Boot DTB

This commit implements the support to sign the different memory configurations for
the CCMP1 platforms, when trustfence is enabled, using FIT images.

https://onedigi.atlassian.net/browse/DEL-8752

Signed-off-by: Arturo Buzarra <arturo.buzarra@digi.com>
This commit is contained in:
Arturo Buzarra 2023-12-07 11:03:53 +01:00
parent e7d90794f8
commit 7c76b0c351
6 changed files with 374 additions and 19 deletions

View File

@ -251,15 +251,17 @@ do_deploy:append:ccmp1() {
install -m 0777 ${B}/${config}/u-boot-nodtb.bin ${DEPLOYDIR}/${BOOT_TOOLS}/u-boot-nodtb.bin
# Append signature to u-boot DT
if [ "x${UBOOT_SIGN_ENABLE}" = "x1" ] ; then
if [ "x${UBOOT_SIGN_ENABLE}" = "x1" ] && [ -n "${UBOOT_DEVICETREE}" ] ; then
for devicetree in ${UBOOT_DEVICETREE}; do
# get name of u-boot devicetree without signature
ubootdevicetree=`ls -1 ${DEPLOYDIR}/${BOOT_TOOLS}/*.dtb | head -n 1`
ubootdevicetree="${DEPLOYDIR}/${BOOT_TOOLS}/${FIP_UBOOT_DTB}-${devicetree}.dtb"
namewithoutsignature=`echo $ubootdevicetree | sed "s/\.dtb/-without-signature.dtb/g"`
namewithsignature=`echo $ubootdevicetree | sed "s/\.dtb/-with-signature.dtb/g"`
mv $ubootdevicetree $namewithoutsignature
# get name of U-Boot device tree from DEPLOY_DIR
nameonkernel="${DEPLOY_DIR_IMAGE}/u-boot-${MACHINE}*.dtb"
nameonkernel="${DEPLOY_DIR_IMAGE}/${FIP_UBOOT_DTB}-${devicetree}-with-signature.dtb"
cp $nameonkernel $namewithsignature
cp $nameonkernel $ubootdevicetree
done
fi
}

View File

@ -1,4 +1,4 @@
# Copyright (C) 2022,2023 Digi International
# Copyright (C) 2022-2024 Digi International
require u-boot-dey.inc
LIC_FILES_CHKSUM = "file://Licenses/README;md5=5a7450c57ffe5ae63fd732446b988025"
@ -17,22 +17,32 @@ UBOOT_FIT_CFG_FRAGMENTS = " \
SRC_URI += " \
${@oe.utils.conditional('TRUSTFENCE_SIGN', '1', '${UBOOT_FIT_CFG_FRAGMENTS}', '', d)} \
"
install_helper_files() {
# Install UBOOT_ENV_BINARY to datadir, so that kernel can use it
# to include it into the FIT image.
install_helper_bootscr() {
if [ -f "${D}/boot/${UBOOT_ENV_BINARY}" ]; then
# Install UBOOT_ENV_BINARY into datadir to share it with the kernel
install -Dm 0644 ${D}/boot/${UBOOT_ENV_BINARY} ${D}${datadir}/${UBOOT_ENV_IMAGE}
ln -sf ${UBOOT_ENV_IMAGE} ${D}${datadir}/${UBOOT_ENV_BINARY}
else
bbwarn "${D}/boot/${UBOOT_ENV_BINARY} not found"
fi
# Install dtbs from UBOOT_DEVICETREE to datadir, so that kernel
# can use it for signing, and kernel will deploy after signs it.
if [ -n "${UBOOT_DEVICETREE}" ]; then
for devicetree in ${UBOOT_DEVICETREE}; do
install -Dm 0644 ${B}/${config}/arch/arm/dts/${devicetree}.dtb ${D}${datadir}/${devicetree}.dtb
done
else
bbwarn "${UBOOT_DEVICETREE} not found"
fi
}
do_install:append() {
# Copy boot script, so kernel can include it when creating the FIT image
if [ "${TRUSTFENCE_FIT_IMG}" = "1" ] && [ -n "${UBOOT_ENV_BINARY}" ]; then
install_helper_bootscr
# Copy additional files, so kernel can use it when creating the FIT image
if [ "${TRUSTFENCE_FIT_IMG}" = "1" ]; then
install_helper_files
fi
}

View File

@ -0,0 +1,233 @@
From: Roman Kopytin <Roman.Kopytin@kaspersky.com>
Date: Wed, 8 Mar 2023 01:13:41 +0000
Subject: [PATCH] tools: add fdt_add_pubkey
Having to use the -K option to mkimage to populate U-Boot's .dtb with the
public key while signing the kernel FIT image is often a little
awkward. In particular, when using a meta-build system such as
bitbake/Yocto, having the tasks of the kernel and U-Boot recipes
intertwined, modifying deployed artifacts and rebuilding U-Boot with
an updated .dtb is quite cumbersome. Also, in some scenarios one may
wish to build U-Boot complete with the public key(s) embedded in the
.dtb without the corresponding private keys being present on the same
build host.
So this adds a simple tool that allows one to disentangle the kernel
and U-Boot builds, by simply copy-pasting just enough of the mkimage
code to allow one to add a public key to a .dtb. When using mkimage,
some of the information is taken from the .its used to build the
kernel (algorithm and key name), so that of course needs to be
supplied on the command line.
Signed-off-by: Roman Kopytin <Roman.Kopytin@kaspersky.com>
Signed-off-by: Ivan Mikhaylov <fr0st61te@gmail.com>
Signed-off-by: Jan Kiszka <jan.kiszka@siemens.com>
Cc: Rasmus Villemoes <rasmus.villemoes@prevas.dk>
---
tools/.gitignore | 1 +
tools/Makefile | 3 +
tools/fdt_add_pubkey.c | 138 +++++++++++++++++++++++++++++++++++++++++
3 files changed, 142 insertions(+)
create mode 100644 tools/fdt_add_pubkey.c
diff --git a/tools/.gitignore b/tools/.gitignore
index a88453f64d..f312b760e4 100644
--- a/tools/.gitignore
+++ b/tools/.gitignore
@@ -4,10 +4,11 @@
/bmp_logo
/common/
/dumpimage
/easylogo/easylogo
/envcrc
+/fdt_add_pubkey
/fdtgrep
/file2include
/fit_check_sign
/fit_info
/gdb/gdbcont
diff --git a/tools/Makefile b/tools/Makefile
index 1763f44cac..ce7a49ff61 100644
--- a/tools/Makefile
+++ b/tools/Makefile
@@ -71,10 +71,11 @@ HOSTCFLAGS_xway-swap-bytes.o := -pedantic
hostprogs-y += mkenvimage
mkenvimage-objs := mkenvimage.o os_support.o lib/crc32.o
hostprogs-y += dumpimage mkimage
hostprogs-$(CONFIG_TOOLS_LIBCRYPTO) += fit_info fit_check_sign
+hostprogs-$(CONFIG_TOOLS_LIBCRYPTO) += fdt_add_pubkey
hostprogs-$(CONFIG_CMD_BOOTEFI_SELFTEST) += file2include
FIT_OBJS-y := fit_common.o fit_image.o image-host.o boot/image-fit.o
FIT_SIG_OBJS-$(CONFIG_TOOLS_LIBCRYPTO) := image-sig-host.o boot/image-fit-sig.o
@@ -152,10 +153,11 @@ dumpimage-mkimage-objs := aisimage.o \
dumpimage-objs := $(dumpimage-mkimage-objs) dumpimage.o
mkimage-objs := $(dumpimage-mkimage-objs) mkimage.o
fit_info-objs := $(dumpimage-mkimage-objs) fit_info.o
fit_check_sign-objs := $(dumpimage-mkimage-objs) fit_check_sign.o
+fdt_add_pubkey-objs := $(dumpimage-mkimage-objs) fdt_add_pubkey.o
file2include-objs := file2include.o
ifneq ($(CONFIG_MX23)$(CONFIG_MX28)$(CONFIG_TOOLS_LIBCRYPTO),)
# Add CONFIG_MXS into host CFLAGS, so we can check whether or not register
# the mxsimage support within tools/mxsimage.c .
@@ -189,10 +191,11 @@ endif
HOSTCFLAGS_fit_image.o += -DMKIMAGE_DTC=\"$(CONFIG_MKIMAGE_DTC_PATH)\"
HOSTLDLIBS_dumpimage := $(HOSTLDLIBS_mkimage)
HOSTLDLIBS_fit_info := $(HOSTLDLIBS_mkimage)
HOSTLDLIBS_fit_check_sign := $(HOSTLDLIBS_mkimage)
+HOSTLDLIBS_fdt_add_pubkey := $(HOSTLDLIBS_mkimage)
hostprogs-$(CONFIG_EXYNOS5250) += mkexynosspl
hostprogs-$(CONFIG_EXYNOS5420) += mkexynosspl
HOSTCFLAGS_mkexynosspl.o := -pedantic
diff --git a/tools/fdt_add_pubkey.c b/tools/fdt_add_pubkey.c
new file mode 100644
index 0000000000..999f5a7e83
--- /dev/null
+++ b/tools/fdt_add_pubkey.c
@@ -0,0 +1,138 @@
+// SPDX-License-Identifier: GPL-2.0+
+#include <image.h>
+#include "fit_common.h"
+
+static const char *cmdname;
+
+static const char *algo_name = "sha1,rsa2048"; /* -a <algo> */
+static const char *keydir = "."; /* -k <keydir> */
+static const char *keyname = "key"; /* -n <keyname> */
+static const char *require_keys; /* -r <conf|image> */
+static const char *keydest; /* argv[n] */
+
+static void print_usage(const char *msg)
+{
+ fprintf(stderr, "Error: %s\n", msg);
+ fprintf(stderr, "Usage: %s [-a <algo>] [-k <keydir>] [-n <keyname>] [-r <conf|image>]"
+ " <fdt blob>\n", cmdname);
+ fprintf(stderr, "Help information: %s [-h]\n", cmdname);
+ exit(EXIT_FAILURE);
+}
+
+static void print_help(void)
+{
+ fprintf(stderr, "Options:\n"
+ "\t-a <algo> Cryptographic algorithm. Optional parameter, default value: sha1,rsa2048\n"
+ "\t-k <keydir> Directory with public key. Optional parameter, default value: .\n"
+ "\t-n <keyname> Public key name. Optional parameter, default value: key\n"
+ "\t-r <conf|image> Required: If present this indicates that the key must be verified for the image / configuration to be considered valid.\n"
+ "\t<fdt blob> FDT blob file for adding of the public key. Required parameter.\n");
+ exit(EXIT_FAILURE);
+}
+
+static void process_args(int argc, char *argv[])
+{
+ int opt;
+
+ while ((opt = getopt(argc, argv, "a:k:n:r:h")) != -1) {
+ switch (opt) {
+ case 'k':
+ keydir = optarg;
+ break;
+ case 'a':
+ algo_name = optarg;
+ break;
+ case 'n':
+ keyname = optarg;
+ break;
+ case 'r':
+ require_keys = optarg;
+ break;
+ case 'h':
+ print_help();
+ default:
+ print_usage("Invalid option");
+ }
+ }
+ /* The last parameter is expected to be the .dtb to add the public key to */
+ if (optind < argc)
+ keydest = argv[optind];
+
+ if (!keydest)
+ print_usage("Missing dtb file to update");
+}
+
+static void reset_info(struct image_sign_info *info)
+{
+ if (!info)
+ fprintf(stderr, "Error: info is NULL in %s\n", __func__);
+
+ memset(info, 0, sizeof(struct image_sign_info));
+
+ info->keydir = keydir;
+ info->keyname = keyname;
+ info->name = algo_name;
+ info->require_keys = require_keys;
+ info->crypto = image_get_crypto_algo(algo_name);
+
+ if (!info->crypto) {
+ fprintf(stderr, "Unsupported signature algorithm '%s'\n",
+ algo_name);
+ exit(EXIT_FAILURE);
+ }
+}
+
+static int add_pubkey(struct image_sign_info *info)
+{
+ int destfd = -1, ret;
+ void *dest_blob = NULL;
+ struct stat dest_sbuf;
+ size_t size_inc = 0;
+
+ if (!info)
+ fprintf(stderr, "Error: info is NULL in %s\n", __func__);
+
+ do {
+ if (destfd >= 0) {
+ munmap(dest_blob, dest_sbuf.st_size);
+ close(destfd);
+
+ fprintf(stderr, ".dtb too small, increasing size by 1024 bytes\n");
+ size_inc = 1024;
+ }
+
+ destfd = mmap_fdt(cmdname, keydest, size_inc, &dest_blob,
+ &dest_sbuf, false, false);
+ if (destfd < 0)
+ exit(EXIT_FAILURE);
+
+ ret = info->crypto->add_verify_data(info, dest_blob);
+ if (ret == -ENOSPC)
+ continue;
+ else if (ret < 0)
+ break;
+ } while (ret == -ENOSPC);
+
+ return ret;
+}
+
+int main(int argc, char *argv[])
+{
+ struct image_sign_info info;
+ int ret;
+
+ cmdname = argv[0];
+
+ process_args(argc, argv);
+ reset_info(&info);
+ ret = add_pubkey(&info);
+
+ if (ret < 0) {
+ fprintf(stderr, "%s: Cannot add public key to FIT blob: %s\n",
+ cmdname, strerror(ret));
+ exit(EXIT_FAILURE);
+ }
+
+ exit(EXIT_SUCCESS);
+}
+

View File

@ -0,0 +1,48 @@
From: Heinrich Schuchardt <heinrich.schuchardt@canonical.com>
Date: Sat, 1 Apr 2023 08:09:34 +0200
Subject: [PATCH] tools: avoid implicit fallthrough in fdt_add_pubkey
When building with -Wimplicit-fallthrough we get a warning
tools/fdt_add_pubkey.c:52:25: warning:
this statement may fall through [-Wimplicit-fallthrough=]
52 | print_help();
|
Explicitly declare which functions don't return.
Fixes: 30238e99619c ("tools: add fdt_add_pubkey")
Signed-off-by: Heinrich Schuchardt <heinrich.schuchardt@canonical.com>
Reviewed-by: Simon Glass <sjg@chromium.org>
---
tools/fdt_add_pubkey.c | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/tools/fdt_add_pubkey.c b/tools/fdt_add_pubkey.c
index 999f5a7e83..5582d7a8ef 100644
--- a/tools/fdt_add_pubkey.c
+++ b/tools/fdt_add_pubkey.c
@@ -8,20 +8,20 @@ static const char *algo_name = "sha1,rsa2048"; /* -a <algo> */
static const char *keydir = "."; /* -k <keydir> */
static const char *keyname = "key"; /* -n <keyname> */
static const char *require_keys; /* -r <conf|image> */
static const char *keydest; /* argv[n] */
-static void print_usage(const char *msg)
+static void __attribute__((__noreturn__)) print_usage(const char *msg)
{
fprintf(stderr, "Error: %s\n", msg);
fprintf(stderr, "Usage: %s [-a <algo>] [-k <keydir>] [-n <keyname>] [-r <conf|image>]"
" <fdt blob>\n", cmdname);
fprintf(stderr, "Help information: %s [-h]\n", cmdname);
exit(EXIT_FAILURE);
}
-static void print_help(void)
+static void __attribute__((__noreturn__)) print_help(void)
{
fprintf(stderr, "Options:\n"
"\t-a <algo> Cryptographic algorithm. Optional parameter, default value: sha1,rsa2048\n"
"\t-k <keydir> Directory with public key. Optional parameter, default value: .\n"
"\t-n <keyname> Public key name. Optional parameter, default value: key\n"

View File

@ -0,0 +1,21 @@
# Copyright (C) 2024 Digi International
FILESEXTRAPATHS:prepend := "${THISDIR}/${BPN}:"
# Backport from v2023.07
SRC_URI:append = " \
file://0001-tools-add-fdt_add_pubkey.patch \
file://0002-tools-avoid-implicit-fallthrough-in-fdt_add_pubkey.patch \
"
do_install:append () {
install -d ${D}${bindir}
# fdt_add_pubkey
if [ -f tools/fdt_add_pubkey ]; then
install -m 0755 tools/fdt_add_pubkey ${D}${bindir}/uboot-fdt_add_pubkey
ln -sf uboot-fdt_add_pubkey ${D}${bindir}/fdt_add_pubkey
fi
}
FILES:${PN}-mkimage += "${bindir}/uboot-fdt_add_pubkey"

View File

@ -1,4 +1,4 @@
# Copyright (C) 2022,2023 Digi International
# Copyright (C) 2022-2024 Digi International
require recipes-kernel/linux/linux-dey.inc
@ -13,4 +13,45 @@ do_assemble_fitimage:prepend:ccmp1() {
install -m 0644 ${RECIPE_SYSROOT}/${datadir}/${UBOOT_ENV_BINARY} ${STAGING_DIR_HOST}/boot/
}
do_assemble_fitimage:append:ccmp1() {
#
# Step 9: Add public keys to the different U-Boot dtb files
#
if [ "${UBOOT_SIGN_ENABLE}" = "1" ] && [ -n "${UBOOT_DEVICETREE}" ]; then
for devicetree in ${UBOOT_DEVICETREE}; do
if [ -f "${STAGING_DATADIR}/${devicetree}.dtb" ]; then
cp -P "${STAGING_DATADIR}/${devicetree}.dtb" ${B}
# Add image public key in U-Boot dtb file
fdt_add_pubkey -a "${FIT_HASH_ALG},${FIT_SIGN_ALG}" \
-k "${UBOOT_SIGN_KEYDIR}" \
-n "${UBOOT_SIGN_IMG_KEYNAME}" \
-r "image" \
"${B}/${devicetree}.dtb"
# Add configuration public key in U-Boot dtb file
fdt_add_pubkey -a "${FIT_HASH_ALG},${FIT_SIGN_ALG}" \
-k "${UBOOT_SIGN_KEYDIR}" \
-n "${UBOOT_SIGN_KEYNAME}" \
-r "conf" \
"${B}/${devicetree}.dtb"
fi
done
fi
}
kernel_do_deploy:append:ccmp1() {
if [ "${UBOOT_SIGN_ENABLE}" = "1" -o "${UBOOT_FITIMAGE_ENABLE}" = "1" ] && \
[ -n "${UBOOT_DTB_BINARY}" ] ; then
# Install device tree files with signature
if [ -n "${UBOOT_DEVICETREE}" ]; then
for devicetree in ${UBOOT_DEVICETREE}; do
if [ -f "${B}/${devicetree}.dtb" ]; then
install -m 0644 ${B}/${devicetree}.dtb "${DEPLOYDIR}/${FIP_UBOOT_DTB}-${devicetree}-with-signature.dtb"
fi
done
fi
fi
}
COMPATIBLE_MACHINE = "(ccimx6|ccimx6ul|ccimx8m|ccimx8x|ccmp1)"