From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from phobos.denx.de (phobos.denx.de [85.214.62.61]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id C02B4C54E94 for ; Wed, 25 Jan 2023 17:19:10 +0000 (UTC) Received: from h2850616.stratoserver.net (localhost [IPv6:::1]) by phobos.denx.de (Postfix) with ESMTP id 38C53856B9; Wed, 25 Jan 2023 18:18:53 +0100 (CET) Authentication-Results: phobos.denx.de; dmarc=none (p=none dis=none) header.from=linux.ibm.com Authentication-Results: phobos.denx.de; spf=pass smtp.mailfrom=u-boot-bounces@lists.denx.de Authentication-Results: phobos.denx.de; dkim=pass (2048-bit key; unprotected) header.d=ibm.com header.i=@ibm.com header.b="UR7BTrPc"; dkim-atps=neutral Received: by phobos.denx.de (Postfix, from userid 109) id 0D422856CE; Wed, 25 Jan 2023 18:18:34 +0100 (CET) Received: from mx0a-001b2d01.pphosted.com (mx0a-001b2d01.pphosted.com [148.163.156.1]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by phobos.denx.de (Postfix) with ESMTPS id 361BF8551E for ; Wed, 25 Jan 2023 18:18:23 +0100 (CET) Authentication-Results: phobos.denx.de; dmarc=none (p=none dis=none) header.from=linux.ibm.com Authentication-Results: phobos.denx.de; spf=pass smtp.mailfrom=eajames@linux.ibm.com Received: from pps.filterd (m0098404.ppops.net [127.0.0.1]) by mx0a-001b2d01.pphosted.com (8.17.1.19/8.17.1.19) with ESMTP id 30PHEqfX009941; Wed, 25 Jan 2023 17:18:19 GMT DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=ibm.com; h=from : to : cc : subject : date : message-id : in-reply-to : references : mime-version : content-transfer-encoding; s=pp1; bh=rmhQaPkqbjjDEl5MWGksH/erVqjs+VqIRxLsuSe6clk=; b=UR7BTrPcEkD3qtagqbxBgqajNI8dkbE8yJ9BEvJuEmQcduLOr2j9iy8qfuiyJjMbIpwX T5tmu0zv2d84iVqusxK8i6VKae60xvBiFw5X4Q9/WFkGajpFx3bbQepkT+V0ohO4DKTb HE2ij3qvULuChKUpc2Gx2uEf0pyaJrLl0ISeO8pl3CYoy+/sgNkw1wUwiTjVZhQ75EKU 7QpUnVwbOJPsYFZrzaIILO4nxX+YU5RFahP+f0ANVpKwOtDjYFfSHTRKE1qJ8yvm2KBw M2UTQN1TX6JgEjLl8lBIINRQH0nignhQeKqJ1BAHOjLh/g9/rKiw6ffsCfC3HzPOxu0b bw== Received: from pps.reinject (localhost [127.0.0.1]) by mx0a-001b2d01.pphosted.com (PPS) with ESMTPS id 3na839baqt-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT); Wed, 25 Jan 2023 17:18:19 +0000 Received: from m0098404.ppops.net (m0098404.ppops.net [127.0.0.1]) by pps.reinject (8.17.1.5/8.17.1.5) with ESMTP id 30PHF7LY012780; Wed, 25 Jan 2023 17:18:18 GMT Received: from ppma02wdc.us.ibm.com (aa.5b.37a9.ip4.static.sl-reverse.com [169.55.91.170]) by mx0a-001b2d01.pphosted.com (PPS) with ESMTPS id 3na839baq3-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT); Wed, 25 Jan 2023 17:18:18 +0000 Received: from pps.filterd (ppma02wdc.us.ibm.com [127.0.0.1]) by ppma02wdc.us.ibm.com (8.17.1.19/8.17.1.19) with ESMTP id 30PGHtaI012727; Wed, 25 Jan 2023 17:18:17 GMT Received: from smtprelay06.wdc07v.mail.ibm.com ([9.208.129.118]) by ppma02wdc.us.ibm.com (PPS) with ESMTPS id 3n87p7s2gb-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT); Wed, 25 Jan 2023 17:18:17 +0000 Received: from smtpav03.wdc07v.mail.ibm.com (smtpav03.wdc07v.mail.ibm.com [10.39.53.230]) by smtprelay06.wdc07v.mail.ibm.com (8.14.9/8.14.9/NCO v10.0) with ESMTP id 30PHIGMH4784786 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-GCM-SHA384 bits=256 verify=OK); Wed, 25 Jan 2023 17:18:16 GMT Received: from smtpav03.wdc07v.mail.ibm.com (unknown [127.0.0.1]) by IMSVA (Postfix) with ESMTP id E9B445805A; Wed, 25 Jan 2023 17:18:15 +0000 (GMT) Received: from smtpav03.wdc07v.mail.ibm.com (unknown [127.0.0.1]) by IMSVA (Postfix) with ESMTP id F02295805F; Wed, 25 Jan 2023 17:18:14 +0000 (GMT) Received: from slate16.aus.stglabs.ibm.com (unknown [9.77.150.21]) by smtpav03.wdc07v.mail.ibm.com (Postfix) with ESMTP; Wed, 25 Jan 2023 17:18:14 +0000 (GMT) From: Eddie James To: u-boot@lists.denx.de Cc: sjg@chromium.org, ilias.apalodimas@linaro.org, xypron.glpk@gmx.de, eajames@linux.ibm.com Subject: [PATCH v4 3/6] bootm: Support boot measurement Date: Wed, 25 Jan 2023 11:18:07 -0600 Message-Id: <20230125171810.3724530-4-eajames@linux.ibm.com> X-Mailer: git-send-email 2.31.1 In-Reply-To: <20230125171810.3724530-1-eajames@linux.ibm.com> References: <20230125171810.3724530-1-eajames@linux.ibm.com> MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-TM-AS-GCONF: 00 X-Proofpoint-GUID: n0Yxee6Wfbz2M90vLQ3GQp-xK04X3Qd3 X-Proofpoint-ORIG-GUID: -KsQxYYBhaCjD_KNUcGmHKpnbZBPCzgb X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.219,Aquarius:18.0.930,Hydra:6.0.562,FMLib:17.11.122.1 definitions=2023-01-25_11,2023-01-25_01,2022-06-22_01 X-Proofpoint-Spam-Details: rule=outbound_notspam policy=outbound score=0 impostorscore=0 phishscore=0 spamscore=0 mlxlogscore=999 adultscore=0 lowpriorityscore=0 bulkscore=0 clxscore=1015 malwarescore=0 mlxscore=0 priorityscore=1501 suspectscore=0 classifier=spam adjust=0 reason=mlx scancount=1 engine=8.12.0-2212070000 definitions=main-2301250152 X-BeenThere: u-boot@lists.denx.de X-Mailman-Version: 2.1.39 Precedence: list List-Id: U-Boot discussion List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: u-boot-bounces@lists.denx.de Sender: "U-Boot" X-Virus-Scanned: clamav-milter 0.103.6 at phobos.denx.de X-Virus-Status: Clean Add a configuration option to measure the boot through the bootm function. Add the measurement state to the booti and bootz paths as well. Signed-off-by: Eddie James --- boot/Kconfig | 23 ++++++++++++++++ boot/bootm.c | 70 +++++++++++++++++++++++++++++++++++++++++++++++++ cmd/booti.c | 1 + cmd/bootm.c | 2 ++ cmd/bootz.c | 1 + include/bootm.h | 2 ++ include/image.h | 1 + 7 files changed, 100 insertions(+) diff --git a/boot/Kconfig b/boot/Kconfig index fdcfbae7b2..831b9e954c 100644 --- a/boot/Kconfig +++ b/boot/Kconfig @@ -601,6 +601,29 @@ config LEGACY_IMAGE_FORMAT loaded. If a board needs the legacy image format support in this case, enable it here. +config MEASURED_BOOT + bool "Measure boot images and configuration to TPM and event log" + depends on HASH && TPM_V2 + help + This option enables measurement of the boot process. Measurement + involves creating cryptographic hashes of the binary images that + are booting and storing them in the TPM. In addition, a log of + these hashes is stored in memory for the OS to verify the booted + images and configuration. Enable this if the OS has configured + some memory area for the event log and you intend to use some + attestation tools on your system. + +if MEASURED_BOOT + config MEASURE_DEVICETREE + bool "Measure the devicetree image" + default y if MEASURED_BOOT + help + On some platforms, the devicetree is not static as it may contain + random MAC addresses or other such data that changes each boot. + Therefore, it should not be measured into the TPM. In that case, + disable the measurement here. +endif # MEASURED_BOOT + config SUPPORT_RAW_INITRD bool "Enable raw initrd images" help diff --git a/boot/bootm.c b/boot/bootm.c index 15fce8ad95..c8423f2c60 100644 --- a/boot/bootm.c +++ b/boot/bootm.c @@ -22,6 +22,7 @@ #include #include #include +#include #if defined(CONFIG_CMD_USB) #include #endif @@ -659,6 +660,72 @@ int bootm_process_cmdline_env(int flags) return 0; } +int bootm_measure(struct bootm_headers *images) +{ + int ret = 0; + + /* Skip measurement if EFI is going to do it */ + if (images->os.os == IH_OS_EFI && + IS_ENABLED(CONFIG_EFI_TCG2_PROTOCOL) && + IS_ENABLED(CONFIG_BOOTM_EFI)) + return ret; + + if (IS_ENABLED(CONFIG_MEASURED_BOOT)) { + struct tcg2_event_log elog; + struct udevice *dev; + void *initrd_buf; + void *image_buf; + const char *s; + u32 rd_len; + + ret = tcg2_measurement_init(&dev, &elog); + if (ret) + return ret; + + image_buf = map_sysmem(images->os.image_start, + images->os.image_len); + ret = tcg2_measure_data(dev, &elog, 8, images->os.image_len, + image_buf, EV_COMPACT_HASH, + strlen("linux") + 1, (u8 *)"linux"); + if (ret) + goto unmap_image; + + rd_len = images->rd_end - images->rd_start; + initrd_buf = map_sysmem(images->rd_start, rd_len); + ret = tcg2_measure_data(dev, &elog, 8, rd_len, initrd_buf, + EV_COMPACT_HASH, strlen("initrd") + 1, + (u8 *)"initrd"); + if (ret) + goto unmap_initrd; + + if (IS_ENABLED(CONFIG_MEASURE_DEVICETREE)) { + ret = tcg2_measure_data(dev, &elog, 9, images->ft_len, + (u8 *)images->ft_addr, + EV_TABLE_OF_DEVICES, + strlen("dts") + 1, + (u8 *)"dts"); + if (ret) + goto unmap_initrd; + } + + s = env_get("bootargs"); + if (!s) + s = ""; + ret = tcg2_measure_data(dev, &elog, 1, strlen(s) + 1, (u8 *)s, + EV_PLATFORM_CONFIG_FLAGS, + strlen(s) + 1, (u8 *)s); + +unmap_initrd: + unmap_sysmem(initrd_buf); + +unmap_image: + unmap_sysmem(image_buf); + tcg2_measurement_term(dev, &elog, ret != 0); + } + + return ret; +} + /** * Execute selected states of the bootm command. * @@ -710,6 +777,9 @@ int do_bootm_states(struct cmd_tbl *cmdtp, int flag, int argc, if (!ret && (states & BOOTM_STATE_FINDOTHER)) ret = bootm_find_other(cmdtp, flag, argc, argv); + if (IS_ENABLED(CONFIG_MEASURED_BOOT) && !ret && (states & BOOTM_STATE_MEASURE)) + bootm_measure(images); + /* Load the OS */ if (!ret && (states & BOOTM_STATE_LOADOS)) { iflag = bootm_disable_interrupts(); diff --git a/cmd/booti.c b/cmd/booti.c index 6ac39193db..659bb10549 100644 --- a/cmd/booti.c +++ b/cmd/booti.c @@ -127,6 +127,7 @@ int do_booti(struct cmd_tbl *cmdtp, int flag, int argc, char *const argv[]) #ifdef CONFIG_SYS_BOOT_RAMDISK_HIGH BOOTM_STATE_RAMDISK | #endif + BOOTM_STATE_MEASURE | BOOTM_STATE_OS_PREP | BOOTM_STATE_OS_FAKE_GO | BOOTM_STATE_OS_GO, &images, 1); diff --git a/cmd/bootm.c b/cmd/bootm.c index 37c2af96e0..0c4a713e02 100644 --- a/cmd/bootm.c +++ b/cmd/bootm.c @@ -161,6 +161,8 @@ int do_bootm(struct cmd_tbl *cmdtp, int flag, int argc, char *const argv[]) BOOTM_STATE_OS_GO; if (IS_ENABLED(CONFIG_SYS_BOOT_RAMDISK_HIGH)) states |= BOOTM_STATE_RAMDISK; + if (IS_ENABLED(CONFIG_MEASURED_BOOT)) + states |= BOOTM_STATE_MEASURE; if (IS_ENABLED(CONFIG_PPC) || IS_ENABLED(CONFIG_MIPS)) states |= BOOTM_STATE_OS_CMDLINE; ret = do_bootm_states(cmdtp, flag, argc, argv, states, &images, 1); diff --git a/cmd/bootz.c b/cmd/bootz.c index f1423573d2..87922bfc3c 100644 --- a/cmd/bootz.c +++ b/cmd/bootz.c @@ -81,6 +81,7 @@ int do_bootz(struct cmd_tbl *cmdtp, int flag, int argc, char *const argv[]) #ifdef CONFIG_SYS_BOOT_RAMDISK_HIGH BOOTM_STATE_RAMDISK | #endif + BOOTM_STATE_MEASURE | BOOTM_STATE_OS_PREP | BOOTM_STATE_OS_FAKE_GO | BOOTM_STATE_OS_GO, &images, 1); diff --git a/include/bootm.h b/include/bootm.h index 044a4797ed..06d8b1acd8 100644 --- a/include/bootm.h +++ b/include/bootm.h @@ -55,6 +55,8 @@ ulong bootm_disable_interrupts(void); int bootm_find_images(int flag, int argc, char *const argv[], ulong start, ulong size); +int bootm_measure(struct bootm_headers *images); + int do_bootm_states(struct cmd_tbl *cmdtp, int flag, int argc, char *const argv[], int states, struct bootm_headers *images, int boot_progress); diff --git a/include/image.h b/include/image.h index 7717a4c13d..f7414b5338 100644 --- a/include/image.h +++ b/include/image.h @@ -407,6 +407,7 @@ struct bootm_headers { #define BOOTM_STATE_OS_FAKE_GO 0x00000200 /* 'Almost' run the OS */ #define BOOTM_STATE_OS_GO 0x00000400 #define BOOTM_STATE_PRE_LOAD 0x00000800 +#define BOOTM_STATE_MEASURE 0x00001000 int state; #if defined(CONFIG_LMB) && !defined(USE_HOSTCC) -- 2.31.1