From patchwork Mon Apr 27 09:48:19 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: AKASHI Takahiro X-Patchwork-Id: 1277486 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=lists.denx.de (client-ip=85.214.62.61; helo=phobos.denx.de; envelope-from=u-boot-bounces@lists.denx.de; receiver=) Authentication-Results: ozlabs.org; dmarc=pass (p=none dis=none) header.from=linaro.org Authentication-Results: ozlabs.org; dkim=pass (2048-bit key; unprotected) header.d=linaro.org header.i=@linaro.org header.a=rsa-sha256 header.s=google header.b=wJVkHx5e; dkim-atps=neutral Received: from phobos.denx.de (phobos.denx.de [85.214.62.61]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (4096 bits) server-digest SHA256) (No client certificate requested) by ozlabs.org (Postfix) with ESMTPS id 499g3D0ClNz9sP7 for ; Mon, 27 Apr 2020 19:49:07 +1000 (AEST) Received: from h2850616.stratoserver.net (localhost [IPv6:::1]) by phobos.denx.de (Postfix) with ESMTP id 540A381DEA; Mon, 27 Apr 2020 11:48:58 +0200 (CEST) Authentication-Results: phobos.denx.de; dmarc=pass (p=none dis=none) header.from=linaro.org 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=linaro.org header.i=@linaro.org header.b="wJVkHx5e"; dkim-atps=neutral Received: by phobos.denx.de (Postfix, from userid 109) id DC6FB81DFF; Mon, 27 Apr 2020 11:48:55 +0200 (CEST) X-Spam-Checker-Version: SpamAssassin 3.4.2 (2018-09-13) on phobos.denx.de X-Spam-Level: X-Spam-Status: No, score=-2.0 required=5.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,SPF_HELO_NONE,URIBL_BLOCKED autolearn=ham autolearn_force=no version=3.4.2 Received: from mail-pj1-x1041.google.com (mail-pj1-x1041.google.com [IPv6:2607:f8b0:4864:20::1041]) (using TLSv1.3 with cipher TLS_AES_128_GCM_SHA256 (128/128 bits)) (No client certificate requested) by phobos.denx.de (Postfix) with ESMTPS id F405C81DC7 for ; Mon, 27 Apr 2020 11:48:51 +0200 (CEST) Authentication-Results: phobos.denx.de; dmarc=pass (p=none dis=none) header.from=linaro.org Authentication-Results: phobos.denx.de; spf=pass smtp.mailfrom=takahiro.akashi@linaro.org Received: by mail-pj1-x1041.google.com with SMTP id fu13so6646748pjb.5 for ; Mon, 27 Apr 2020 02:48:51 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; h=from:to:cc:subject:date:message-id:mime-version :content-transfer-encoding; bh=/d1tIR28hXbSUTSW4KAqK8bPUjyBHWisu41MUpWV1z0=; b=wJVkHx5ePGhlgFLRO8IgYkJYg8GG6QdDPbMrGZwMmGKKZUschAz+gYNSMrK+Ntbhy8 RCRVoAnSTUHTQPPRQ9r8Zvav0cpOal8frbkW1tM1KuQ3AnRWE9IpGd7Y74GJxo38AC95 Z0e/g3BWe0zMo8TM9UcoZo9rICmfgyyn8jKvD1JMdJgF+U/Jt7Io3/X70gB8NQV9spX4 DXl8Ey8zUnIzppTu4KHn53E3AoIRx9YOe/yOJE3NITCYxrGpZVHLpoYtwupNJpAR0Fol lKE6dD2BIndOkh4Vx1OvvnySlzj28JgflNHP268ZnT52oUcY/qhLJOi8Rg3nNTsZMCYa QKAA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:mime-version :content-transfer-encoding; bh=/d1tIR28hXbSUTSW4KAqK8bPUjyBHWisu41MUpWV1z0=; b=PeMpHxRwTPPBGYBcvW+z1zCMCvZS+G5lNFKcvi8jdeHBAziIIFfgJ2jgqspIdoitZW XvJ3yzASDxihKnoqjXSM/EdNphHVgnimb7CHHzj62foL8k/6xT3zgDoGbi+Prit4DBOl d0xleuLHDnTYv6WnI6SKSvqqH1Jj31SsBzNQlnYUENYe6Hx97OJsKA2GuOYNpiryIiBE Jx4kSWjcT2RpLIO9TrTr2PBnIv701u9XJK7G2x0doEe/Yl7DcuWNWuxQWLKe9cjcRgeS Pyo3IpeehmaqR9xtS/UuHtCFrB5SaiD/TVK7v/j0pW++H3SmbPANfn1OaXjRngCUcChz 0Xjg== X-Gm-Message-State: AGi0PuY6ZuRK8UDq8n90qtN2NfVSzq8mIB34aBI40wvbaJYX9shYTlSB gjc6Wr61BxKQ1RRufaUR2I8h1g== X-Google-Smtp-Source: APiQypLLk7UfdSRr9nXM1f99ImDkq3tK6IAIioCKhoXL0y5Mgars2x+O/1fcSOOUnZvbf8V7LXgQmg== X-Received: by 2002:a17:90a:5a:: with SMTP id 26mr22986888pjb.74.1587980929958; Mon, 27 Apr 2020 02:48:49 -0700 (PDT) Received: from localhost.localdomain (p73a21dd7.tkyea130.ap.so-net.ne.jp. [115.162.29.215]) by smtp.gmail.com with ESMTPSA id 3sm12491031pfo.27.2020.04.27.02.48.47 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Mon, 27 Apr 2020 02:48:49 -0700 (PDT) From: AKASHI Takahiro To: xypron.glpk@gmx.de, agraf@csgraf.de Cc: sughosh.ganu@linaro.org, u-boot@lists.denx.de, AKASHI Takahiro Subject: [PATCH 00/10] efi_loader: add capsule update support Date: Mon, 27 Apr 2020 18:48:19 +0900 Message-Id: <20200427094829.1140-1-takahiro.akashi@linaro.org> X-Mailer: git-send-email 2.25.2 MIME-Version: 1.0 X-BeenThere: u-boot@lists.denx.de X-Mailman-Version: 2.1.30rc1 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.102.2 at phobos.denx.de X-Virus-Status: Clean Summary ======= 'UpdateCapsule' is one of runtime services defined in UEFI specification and its aim is to allow a caller (OS) to pass information to the firmware, i.e. U-Boot. This is mostly used to update firmware binary on devices by instructions from OS. While 'UpdateCapsule' is a runtime services function, it is, at least initially, suported only before exiting boot services alike other runtime functions, [Get/]SetVariable. This is because modifying storage which may be shared with OS must be carefully designed and there is no general assumption that we can do it. Therefore, we practically support only "capsule on disk"; any capsule can be handed over to UEFI subsystem as a file on a specific file system. In this patch series, all the related definitions and structures are given as UEFI specification describes, and basic framework for capsule support is provided. Currently supported is * firmware update (Firmware Management Protocol or simply FMP) Most of functionality of firmware update is provided by FMP driver and it will be, by nature, system/platform-specific. So you can and should implement your own FMP driver(s) based on your system requirements. Only a simple FMP driver based on FIT image for a single region is provided here. (So it is "for reference only") ^^^^^^^^^^^^^^^^^^ See more details in the commit, "efi_loader: capsule: add simple firmware management protocol." Patch structure =============== Patch#1-#2: preparatory patches Patch#3-#7: main part of implementation Patch#8-#10: utilities and tests [1] https://git.linaro.org/people/takahiro.akashi/u-boot.git efi/capsule Prerequisite patches ==================== [2] part: detect EFI system partition https://lists.denx.de/pipermail/u-boot/2020-March/403562.html [3] common: update_tftp: remove unnecessary build check https://lists.denx.de/pipermail/u-boot/2020-March/401727.html [4] sandbox: drop CONFIG_SYS_RELOC_GD_ENV_ADDR https://lists.denx.de/pipermail/u-boot/2020-April/408711.html Test ==== * passed all the pytests which are included in this patch series on sandbox build. * passed Travis CI. Please note that, while Travic CI passed, the capsule pytest itself won't be run in the CI because some specific configuration for sandbox build is required. See test_efi_capsule_firmware.py. Issues ====== * Timing of executing capsules-on-disk Currently, processing a capsule is triggered only as part of UEFI subsystem initialization. This means that, for example, firmware update, may not take place at system booting time and will potentially be delayed until a first call of any UEFI functions. => See patch#4 for my proposal TODO's ====== (May not be addressed in future versions of this series.) * capsule authentication * capsule dependency (dependency expression instruction set) * loading drivers in a capsule * handling RESET flag in a capsule and QeuryCapsuleCaps * full semantics of ESRT (EFI System Resource Table) * enabling capsule API at runtime * json capsule * recovery from update failure Changes ======= v1 (April 27, 2020) * rebased to v2020.07-rc * removed already-merged patches (RFC's #1 to #4) * dropped 'variable update' capsule support (RFC's patch#10) * dropped 'variable configuration table' support (RFC's patch#11) (Those two should be discussed separately.) * add preparatory patches (patch#1/#2) * fix several build errors * rename some Kconfig options to be aligned with UEFI specification's terms (patch#3,4,6,7) * enforce UpdateCapsule API to be disabled after ExitBootServices (patch#3) * use config table, runtime_services_supported, instead of variable (patch#3) * make EFI_CAPSULE_ON_DISK buildable even if UpdateCapsule API is disabled (patch4) * support OsIndications, invoking capsule-on-disk only if the variable indicates so (patch#4) * introduced EFI_CAPSULE_ON_DISK_EARLY to invoke capsule-on-disk in U-Boot initialization (patch#4) * detect capsule files only if they are on EFI system partition (patch#4) * use printf, rather than EFI_PRINT, in error cases (patch#4) * use 'header_size' field to retrieve capsule data, adding sanity checks against capsule size (patch#6) * call fmpt driver interfaces with EFI_CALL (patch#6) * remove 'variable update capsule'-related code form mkeficapsule (patch#9) * add a test case of OsIndications not being set properly (patch#10) * adjust test scenario for EFI_CAPSULE_ON_DISK_EARLY (patch#10) * revise pytest scripts (patch#10) Initial release as RFC (March 17, 2020) AKASHI Takahiro (10): efi_loader: disk: add efi_disk_is_system_part() efi_loader: add option to initialise EFI subsystem early efi_loader: define UpdateCapsule api efi_loader: capsule: add capsule_on_disk support efi_loader: capsule: add memory range capsule definitions efi_loader: capsule: support firmware update efi_loader: add simple firmware management protocol for FIT image cmd: add "efidebug capsule" command tools: add mkeficapsule command for UEFI capsule update test test/py: add a test for efi firmware update capsule cmd/efidebug.c | 234 +++++ common/board_r.c | 6 + common/main.c | 4 + include/efi_api.h | 156 ++++ include/efi_loader.h | 35 + lib/efi_loader/Kconfig | 69 ++ lib/efi_loader/Makefile | 2 + lib/efi_loader/efi_capsule.c | 802 ++++++++++++++++++ lib/efi_loader/efi_disk.c | 22 + lib/efi_loader/efi_firmware.c | 191 +++++ lib/efi_loader/efi_runtime.c | 104 ++- lib/efi_loader/efi_setup.c | 44 +- test/py/tests/test_efi_capsule/conftest.py | 73 ++ test/py/tests/test_efi_capsule/defs.py | 24 + .../test_efi_capsule/test_capsule_firmware.py | 198 +++++ test/py/tests/test_efi_capsule/uboot_env.its | 25 + tools/Makefile | 3 + tools/mkeficapsule.c | 209 +++++ 18 files changed, 2150 insertions(+), 51 deletions(-) create mode 100644 lib/efi_loader/efi_capsule.c create mode 100644 lib/efi_loader/efi_firmware.c create mode 100644 test/py/tests/test_efi_capsule/conftest.py create mode 100644 test/py/tests/test_efi_capsule/defs.py create mode 100644 test/py/tests/test_efi_capsule/test_capsule_firmware.py create mode 100644 test/py/tests/test_efi_capsule/uboot_env.its create mode 100644 tools/mkeficapsule.c