[PATCH v4 2/6] tpm: print all PCRs from pcr_read
Ilias Apalodimas
ilias.apalodimas at linaro.org
Wed Jul 1 13:05:39 CEST 2026
On Mon, 29 Jun 2026 at 11:02, Ludwig Nussel <ludwig.nussel at siemens.com> wrote:
>
> Output is now more similar to the Linux userspace tool "tpm2_pcrread".
>
> The old semantics that require specifying one PCR number are
> retained. In addition with no arguments the command now prints
> contents of all PCR registers.
>
> Signed-off-by: Ludwig Nussel <ludwig.nussel at siemens.com>
>
> ---
Acked-by: Ilias Apalodimas <ilias.apalodimas at linaro.org>
>
> (no changes since v3)
>
> Changes in v3:
> - fix test failure
>
> Changes in v2:
> - fix return value handling
>
> cmd/tpm-v2.c | 69 +++++++++++++++++++++++++++-----------
> test/py/tests/test_tpm2.py | 9 ++---
> 2 files changed, 53 insertions(+), 25 deletions(-)
>
> diff --git a/cmd/tpm-v2.c b/cmd/tpm-v2.c
> index 847b2691581..e9f4bc24e33 100644
> --- a/cmd/tpm-v2.c
> +++ b/cmd/tpm-v2.c
> @@ -8,6 +8,7 @@
> #include <dm.h>
> #include <log.h>
> #include <mapmem.h>
> +#include <malloc.h>
> #include <tpm-common.h>
> #include <tpm-v2.h>
> #include "tpm-user-utils.h"
> @@ -150,10 +151,11 @@ static int do_tpm_pcr_read(struct cmd_tbl *cmdtp, int flag, int argc,
> u32 index, rc;
> int algo_len;
> unsigned int updates;
> - void *data;
> + u8 *data;
> int ret;
> + u32 pcr_start, pcr_end;
>
> - if (argc < 3 || argc > 4)
> + if (argc > 4)
> return CMD_RET_USAGE;
> if (argc == 4) {
> algo = tpm2_name_to_algorithm(argv[3]);
> @@ -168,25 +170,51 @@ static int do_tpm_pcr_read(struct cmd_tbl *cmdtp, int flag, int argc,
>
> priv = dev_get_uclass_priv(dev);
> if (!priv)
> - return -EINVAL;
> -
> - index = simple_strtoul(argv[1], NULL, 0);
> - if (index >= priv->pcr_count)
> - return -EINVAL;
> + return CMD_RET_FAILURE;
>
> - data = map_sysmem(simple_strtoul(argv[2], NULL, 0), 0);
> + if (argc >= 2) {
> + pcr_start = simple_strtoul(argv[1], NULL, 0);
> + if (pcr_start >= priv->pcr_count) {
> + log_err("Index %u out of range (max %u)\n", pcr_start, priv->pcr_count - 1);
> + return CMD_RET_FAILURE;
> + }
> + pcr_end = pcr_start + 1;
> + } else {
> + pcr_start = 0;
> + pcr_end = priv->pcr_count;
> + }
>
> - rc = tpm2_pcr_read(dev, index, priv->pcr_select_min, algo,
> - data, algo_len, &updates);
> - if (!rc) {
> - printf("PCR #%u %s %d byte content (%u known updates):\n", index,
> - tpm2_algorithm_name(algo), algo_len, updates);
> - print_byte_string(data, algo_len);
> + if (argc >= 3) {
> + data = map_sysmem(simple_strtoul(argv[2], NULL, 0), 0);
> + } else {
> + data = malloc(algo_len);
> + if (!data) {
> + log_err("Failed to allocate %u bytes for PCR data\n", algo_len);
> + return CMD_RET_FAILURE;
> + }
> }
>
> - unmap_sysmem(data);
> + printf("%8s:\n", tpm2_algorithm_name(algo));
> + for (index = pcr_start; index < pcr_end; ++index) {
> + printf("%6u: ", index);
> + rc = tpm2_pcr_read(dev, index, priv->pcr_select_min, algo,
> + data, algo_len, &updates);
> + if (rc == 0) {
> + printf("0x");
> + for (int i = 0; i < algo_len; ++i)
> + printf("%02X", data[i]);
> + printf(" (%u known updates)\n", updates);
> + } else {
> + log_err("PCR #%u read failed: %d\n", index, rc);
> + ret = report_return_code(rc);
> + }
> + }
> + if (argc >= 3)
> + unmap_sysmem(data);
> + else
> + free(data);
>
> - return report_return_code(rc);
> + return ret;
> }
>
> static int do_tpm_get_capability(struct cmd_tbl *cmdtp, int flag, int argc,
> @@ -548,10 +576,13 @@ U_BOOT_CMD(tpm2, CONFIG_SYS_MAXARGS, 1, do_tpm, "Issue a TPMv2.x command",
> " Extend PCR #<pcr> with digest at <digest_addr> with digest_algo.\n"
> " <pcr>: index of the PCR\n"
> " <digest_addr>: address of digest of digest_algo type (defaults to SHA256)\n"
> -"pcr_read <pcr> <digest_addr> [<digest_algo>]\n"
> +"pcr_read [<pcr> [<digest_addr> [<digest_algo>]]]\n"
> " Read PCR #<pcr> to memory address <digest_addr> with <digest_algo>.\n"
> -" <pcr>: index of the PCR\n"
> -" <digest_addr>: address of digest of digest_algo type (defaults to SHA256)\n"
> +" With no arguments, print all PCR registers.\n"
> +" If only <pcr> is specified, a buffer is allocated internally.\n"
> +" <pcr>: index of the PCR (optional, defaults to all PCRs)\n"
> +" <digest_addr>: address of digest of digest_algo type (optional)\n"
> +" <digest_algo>: digest algorithm type (defaults to SHA256)\n"
> "get_capability <capability> <property> <addr> <count>\n"
> " Read and display <count> entries indexed by <capability>/<property>.\n"
> " Values are 4 bytes long and are written at <addr>.\n"
> diff --git a/test/py/tests/test_tpm2.py b/test/py/tests/test_tpm2.py
> index 9be85999d46..1baf86dd065 100644
> --- a/test/py/tests/test_tpm2.py
> +++ b/test/py/tests/test_tpm2.py
> @@ -198,8 +198,7 @@ def test_tpm2_pcr_read(ubman):
> updates = int(re.findall(r'\d+', str)[0])
>
> # Check the output value
> - assert 'PCR #10 sha256 32 byte content' in read_pcr
> - assert '00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00' in read_pcr
> + assert 'sha256:\r\r\n 10: 0x0000000000000000000000000000000000000000000000000000000000000000' in read_pcr
>
> @pytest.mark.buildconfigspec('cmd_tpm_v2')
> @pytest.mark.notbuildconfigspec('target_chromebook_coral')
> @@ -230,8 +229,7 @@ def test_tpm2_pcr_extend(ubman):
> read_pcr = ubman.run_command('tpm2 pcr_read 10 0x%x' % (ram + 0x20))
> output = ubman.run_command('echo $?')
> assert output.endswith('0')
> - assert 'f5 a5 fd 42 d1 6a 20 30 27 98 ef 6e d3 09 97 9b' in read_pcr
> - assert '43 00 3d 23 20 d9 f0 e8 ea 98 31 a9 27 59 fb 4b' in read_pcr
> + assert 'sha256:\r\r\n 10: 0xF5A5FD42D16A20302798EF6ED309979B43003D2320D9F0E8EA9831A92759FB4B' in read_pcr
>
> str = re.findall(r'\d+ known updates', read_pcr)[0]
> new_updates = int(re.findall(r'\d+', str)[0])
> @@ -244,8 +242,7 @@ def test_tpm2_pcr_extend(ubman):
> read_pcr = ubman.run_command('tpm2 pcr_read 10 0x%x' % (ram + 0x20))
> output = ubman.run_command('echo $?')
> assert output.endswith('0')
> - assert '7a 05 01 f5 95 7b df 9c b3 a8 ff 49 66 f0 22 65' in read_pcr
> - assert 'f9 68 65 8b 7a 9c 62 64 2c ba 11 65 e8 66 42 f5' in read_pcr
> + assert '10: 0x7A0501F5957BDF9CB3A8FF4966F02265F968658B7A9C62642CBA1165E86642F5' in read_pcr
>
> str = re.findall(r'\d+ known updates', read_pcr)[0]
> new_updates = int(re.findall(r'\d+', str)[0])
> --
> 2.43.0
>
More information about the U-Boot
mailing list