I am working on a system based on i.MX8M Mini, Yocto kirkstone, U-Boot v2021.04. It is derived from the imx8mm machine.
I have a complete working system, but I want to enable secure boot for U-Boot etc.
I've been following the instructions in the document doc/imx/habv4/guides/mx8m_secure_boot.txt in the U-Boot v2021.04 source code, but I want to automate the process in Yocto, rather than doing it manually.
In case anyone is interested, I'm sharing what I have done in an imx-boot_%.bbappend file.
As in my other recent question i.MX8M Mini secure boot HAB errors, I was getting HAB errors. Now I think I have resolved the remaining issues, and my U-Boot build is being successfully verified, with my edits to this post.
Note though that I've commented a "hack" that is specific to the imx8mm that I'm using—as noted in the code. This is to work around issues with the way the print_fit_hab.sh calculates the block values, versus the way the build pads the various binary files.
I've tested this with meta-freescale branch kirkstone commit 2e785f257ad98581b684f0e32f6d4bb96faefb10, which in the imx-boot recipe uses imx-mkimage branch lf-5.15.5_1.0.0 commit 22346a32a88aa752d4bad8f2ed1eb641e18849dc.
imx-boot_%.bbappend
FILESEXTRAPATHS:prepend := "${THISDIR}/files:"
SRC_URI:append = "file://crts file://keys file://csf_fit.txt.template file://csf_spl.txt.template"
# libpcre-native for pcregrep-native
# imx-mkimage for print_fit_hab.sh script -- not needed in DEPENDS because imx-boot includes it directly.
# imx-cst-native for code signing
DEPENDS:append = " libpcre-native imx-cst-native"
do_compile:append () {
# Extract ATF_LOAD_ADDR from output of mkimage in temp/log.do_compile
# (Testing has verified the symlink temp/log.do_compile points to the current log file even while do_compile is in-progress)
ATF_LOAD_ADDR=$(cat "${T}/log.do_compile" | pcregrep -o1 'ATF_LOAD_ADDR=(\w*)')
bbnote "ATF_LOAD_ADDR: ${ATF_LOAD_ADDR}"
TEE_LOAD_ADDR=$(cat "${T}/log.do_compile" | pcregrep -o1 'TEE_LOAD_ADDR=(\w*)')
bbnote "TEE_LOAD_ADDR: ${TEE_LOAD_ADDR}"
# Extract SPL CSF offset from output of mkimage in temp/log.do_compile
SPL_CSF_OFFSET=$(cat "${T}/log.do_compile" | pcregrep -o1 '^[[:blank:]]*csf_off[[:blank:]]*(\w*)')
bbnote "SPL_CSF_OFFSET: ${SPL_CSF_OFFSET}"
# Extract FIT CSF offset from output of mkimage in temp/log.do_compile
FIT_CSF_OFFSET=$(cat "${T}/log.do_compile" | pcregrep -o1 '^[[:blank:]]*sld_csf_off[[:blank:]]*(\w*)')
bbnote "FIT_CSF_OFFSET: ${FIT_CSF_OFFSET}"
# Extract spl hab block values from output of mkimage in temp/log.do_compile
SPL_HAB_BLOCK=$(cat "${T}/log.do_compile" | pcregrep -o1 '^[[:blank:]]*spl hab block:[[:blank:]]*(.*)$')
bbnote "spl hab block: ${SPL_HAB_BLOCK}"
# Extract sld hab block values from output of mkimage in temp/log.do_compile
SLD_HAB_BLOCK=$(cat "${T}/log.do_compile" | pcregrep -o1 '^[[:blank:]]*sld hab block:[[:blank:]]*(.*)$')
bbnote "sld hab block: ${SLD_HAB_BLOCK}"
# Extract more fit address values using print_fit_hab.sh script
bbnote print_fit_hab.sh
# Hack for padding of DTB like the iMX8M soc.mak does it (unfortunately soc.mak deletes the padded DTB when it's done).
# TODO: Clean up this hack.
cp ${BOOT_STAGING}/${UBOOT_DTB_NAME} ${BOOT_STAGING}/${UBOOT_DTB_NAME}.pad
scripts/pad_image.sh ${BOOT_STAGING}/u-boot-nodtb.bin ${BOOT_STAGING}/${UBOOT_DTB_NAME}.pad
if ${DEPLOY_OPTEE}; then
export BL32=${BOOT_STAGING}/tee.bin
fi
FIT_HAB=$(VERSION=v1 \
BL31=${BOOT_STAGING}/bl31.bin \
BL33=${BOOT_STAGING}/u-boot-nodtb.bin \
ATF_LOAD_ADDR=${ATF_LOAD_ADDR} \
TEE_LOAD_ADDR=${TEE_LOAD_ADDR} \
${S}/iMX8M/print_fit_hab.sh \
0x60000 ${BOOT_STAGING}/${UBOOT_DTB_NAME}.pad)
echo "${FIT_HAB}"
for target in ${IMXBOOT_TARGETS}; do
# Use code-signing tool to sign the flash.bin
# First, SPL
cp ${WORKDIR}/csf_spl.txt.template csf_spl.txt
echo " Blocks = ${SPL_HAB_BLOCK} \"${BOOT_CONFIG_MACHINE}-${target}\"" >> csf_spl.txt
cst -i csf_spl.txt -o csf_spl.bin
# Second, FIT
cp ${WORKDIR}/csf_fit.txt.template csf_fit.txt
echo " Blocks = \\" >> csf_fit.txt
LINE_OUT="${SLD_HAB_BLOCK} \"${BOOT_CONFIG_MACHINE}-${target}\""
while read -r LINE_IN; do
if [ -n "${LINE_OUT}" ]; then
echo " ${LINE_OUT}, \\" >> csf_fit.txt
fi
LINE_OUT=
if [ -n "${LINE_IN}" ]; then
LINE_OUT="${LINE_IN} \"${BOOT_CONFIG_MACHINE}-${target}\""
fi
done <<EOF
${FIT_HAB}
EOF
echo " ${LINE_OUT}" >> csf_fit.txt
cst -i csf_fit.txt -o csf_fit.bin
# Insert the signature blocks into the flash.bin
# First make a copy of the flash.bin
cp ${BOOT_CONFIG_MACHINE}-${target} ${BOOT_CONFIG_MACHINE}-${target}-signed
# Insert csf_spl.bin in signed flash.bin at SPL_CSF_OFFSET offset
SPL_CSF_OFFSET_DEC=$(printf "%d" ${SPL_CSF_OFFSET})
dd if=csf_spl.bin of=${BOOT_CONFIG_MACHINE}-${target}-signed seek=${SPL_CSF_OFFSET_DEC} bs=1 conv=notrunc
# Insert csf_fit.bin in signed flash.bin at FIT_CSF_OFFSET offset
FIT_CSF_OFFSET_DEC=$(printf "%d" ${FIT_CSF_OFFSET})
dd if=csf_fit.bin of=${BOOT_CONFIG_MACHINE}-${target}-signed seek=${FIT_CSF_OFFSET_DEC} bs=1 conv=notrunc
done
}
do_deploy:append () {
for target in ${IMXBOOT_TARGETS}; do
install -m 0644 ${S}/${BOOT_CONFIG_MACHINE}-${target}-signed ${DEPLOYDIR}
done
}
As far as I know, there is no ready-made solution for building secure boot in Yocto. Apologies for that.
You can have a try to apply for Prosupport from the link: Professional Engineering Services | NXP Semiconductors
Best regards
Harvey
Best regards
Harvey