## # Copyright OpenEmbedded Contributors # # SPDX-License-Identifier: MIT # # # Discoverable Disk Image (DDI) # # "DDIs (Discoverable Disk Images) are self-describing file system # images that follow the DPS ( Discoverable Partitions Specification), # wrapped in a GPT partition table, that may contain root (or /usr/) # filesystems for bootable OS images, system extensions, configuration # extensions, portable services, containers and more, and shall be # protected by signed dm-verity all combined into one. They are # designed to be composable and stackable, and provide security by # default." # https://uapi-group.org/specifications/specs/discoverable_disk_image/ # https://uapi-group.org/specifications/specs/discoverable_partitions_specification/ # https://www.freedesktop.org/software/systemd/man/latest/systemd.image-policy.html # To be able to use discoverable-disk-images with a # root-verity-sig or usr-verity-sig configuration: # - systemd needs to include the PACKAGECONFIG 'cryptsetup', and # - the kernel needs the following features enabled: # CONFIG_DM_VERITY_VERIFY_ROOTHASH_SIG=y # CONFIG_DM_VERITY_VERIFY_ROOTHASH_SIG_PLATFORM_KEYRING=y # CONFIG_EROFS_FS=y # CONFIG_EROFS_FS_XATTR=y # CONFIG_EROFS_FS_ZIP=y # CONFIG_EROFS_FS_ZIP_LZMA=y # CONFIG_INTEGRITY_SIGNATURE=y # CONFIG_INTEGRITY_ASYMMETRIC_KEYS=y # CONFIG_INTEGRITY_PLATFORM_KEYRING=y # CONFIG_SYSTEM_BLACKLIST_KEYRING=y # CONFIG_SYSTEM_BLACKLIST_HASH_LIST="" # CONFIG_SIGNATURE=y # To sign DDIs, a key and certificate need to be provided by setting # the variables: # REPART_PRIVATE_KEY # private key so sign the verity-hash # REPART_PRIVATE_KEY_SOURCE # optional, can be "engine:pkcs11" when using a (soft)hsm # REPART_CERTIFICATE # corresponding public certificate, in .pem format # # For signature verification, systemd-sysext expects the matching # certificate to reside in /etc/verity.d as PEM formated .crt file. # # To enforce loading of only signed extension images, an appropriate # image policy has to be passed to systemd-sysext, e.g.: # systemd-sysext --image-policy='root=signed+absent:usr=signed+absent:=unused+absent' merge # 'systemd-dissect' can be used to inspect, manually mount, ... a DDI. inherit image IMAGE_FSTYPES = "ddi" DEPENDS += " \ systemd-repart-native \ erofs-utils-native \ openssl-native \ " # systemd-repart --make-ddi takes one of "sysext", "confext" or "portable", # which it then takes and looks up definitions in the host os; which we need # to divert to the sysroot-native by setting '--definitions=' instead. # The chosen DDI_TYPE influences which parts of the rootfs are copied into # the ddi by systemd-repart: # sysext: /usr (and if it exists: /opt) # confext: /etc # portable: / # For details see systemd/repart/definitions/${REPART_DDI_TYPE}.repart.d/* REPART_DDI_TYPE ?= "sysext" REPART_DDI_EXTENSION ?= "ddi" # systemd-repart creates temporary directoryies under /var/tmp/.#repartXXXXXXX/, # to estimate partition size etc. Since files are copied there from the image/rootfs # folder - which are owned by pseudo-root - this temporary location has to be # added to the directories handled by pseudo; otherwise calls to e.g. # fchown(0,0) inside systemd git/src/shared/copy.c end up failing. PSEUDO_INCLUDE_PATHS .= ",/var/tmp/" oe_image_systemd_repart_make_ddi() { local additional_args="" if [ -n "${REPART_PRIVATE_KEY}" ] then if [ -n "${REPART_PRIVATE_KEY_SOURCE}" ] then additional_args="$additional_args --private-key-source=${REPART_PRIVATE_KEY_SOURCE}" fi additional_args="$additional_args --private-key=${REPART_PRIVATE_KEY}" fi if [ -n "${REPART_CERTIFICATE}" ] then additional_args="$additional_args --certificate=${REPART_CERTIFICATE}" fi # map architectures to systemd's expected values local systemd_arch="${TARGET_ARCH}" case "${systemd_arch}" in aarch64) systemd_arch=arm64 ;; x86_64) systemd_arch=x86-64 ;; esac # prepare system-repart configuration mkdir -p ${B}/definitions.repart.d cp ${STAGING_LIBDIR_NATIVE}/systemd/repart/definitions/${REPART_DDI_TYPE}.repart.d/* ${B}/definitions.repart.d/ # enable erofs compression sed -i "/^Compression/d" ${B}/definitions.repart.d/10-root.conf echo "Compression=lzma\nCompressionLevel=3" >> ${B}/definitions.repart.d/10-root.conf # disable verity signature partition creation, if no key is provided if [ -z "${REPART_PRIVATE_KEY}" ]; then rm ${B}/definitions.repart.d/30-root-verity-sig.conf fi systemd-repart \ --definitions="${B}/definitions.repart.d/" \ --copy-source="${IMAGE_ROOTFS}" \ --empty=create --size=auto --dry-run=no --offline=yes \ --architecture="${systemd_arch}" \ --json=pretty --no-pager $additional_args \ "${IMGDEPLOYDIR}/${IMAGE_NAME}${IMAGE_NAME_SUFFIX}.${REPART_DDI_EXTENSION}" } IMAGE_CMD:ddi = "oe_image_systemd_repart_make_ddi" do_image_ddi[deptask] += "do_unpack"