Re: [PATCH v9 6/6] tpm: pass an array of tpm_extend_digest structures to tpm_pcr_extend()
From: Roberto Sassu <roberto.sassu@huawei.com>
Date: 2019-02-05 10:02:50
Also in:
keyrings, linux-integrity, lkml
On 2/1/2019 8:15 PM, Mimi Zohar wrote:
Hi Roberto, Sorry for the delayed review. A few comments inline below, minor suggestions.quoted
diff --git a/security/integrity/ima/ima.h b/security/integrity/ima/ima.h index cc12f3449a72..e6b2dcb0846a 100644 --- a/security/integrity/ima/ima.h +++ b/security/integrity/ima/ima.h@@ -56,6 +56,7 @@ extern int ima_policy_flag; extern int ima_hash_algo; extern int ima_appraise; extern struct tpm_chip *ima_tpm_chip; +extern struct tpm_digest *digests; /* IMA event related data */ struct ima_event_data {diff --git a/security/integrity/ima/ima_init.c b/security/integrity/ima/ima_init.c index 6bb42a9c5e47..296a965b11ef 100644 --- a/security/integrity/ima/ima_init.c +++ b/security/integrity/ima/ima_init.c@@ -27,6 +27,7 @@ /* name for boot aggregate entry */ static const char boot_aggregate_name[] = "boot_aggregate"; struct tpm_chip *ima_tpm_chip; +struct tpm_digest *digests;"digests" is used in the new ima_init_digests() and in ima_pcr_extend(). It's nice that the initialization routines are grouped together here in ima_init.c, but wouldn't it better to define "digests" in ima_queued.c, where it is currently being used? "digests" could then be defined as static.quoted
/* Add the boot aggregate to the IMA measurement list and extend * the PCR register.@@ -104,6 +105,24 @@ void __init ima_load_x509(void) } #endif +int __init ima_init_digests(void) +{ + int i; + + if (!ima_tpm_chip) + return 0; + + digests = kcalloc(ima_tpm_chip->nr_allocated_banks, sizeof(*digests), + GFP_NOFS); + if (!digests) + return -ENOMEM; + + for (i = 0; i < ima_tpm_chip->nr_allocated_banks; i++) + digests[i].alg_id = ima_tpm_chip->allocated_banks[i].alg_id; + + return 0; +} + int __init ima_init(void) { int rc;@@ -125,6 +144,9 @@ int __init ima_init(void) ima_load_kexec_buffer(); + rc = ima_init_digests();Ok. Getting the tpm chip is at the beginning of this function. Deferring allocating "digests" to here, avoids having to free memory on failure.
If I understood the code correctly, ima_init() does not undo the actions of previous functions. For example, if ima_init_template() fails, ima_shash_tfm is not freed. Probably, this can be improved later. Roberto
ima_load_kexec_buffer() restores prior measurements, but doesn't extend the TPM. For anyone reading the code, a short comment above ima_load_kexec_buffer() would make sense. Mimiquoted
+ if (rc != 0) + return rc; rc = ima_add_boot_aggregate(); /* boot aggregate must be first entry */ if (rc != 0) return rc;diff --git a/security/integrity/ima/ima_queue.c b/security/integrity/ima/ima_queue.c index 0e41dc1df1d4..719e88ca58f6 100644 --- a/security/integrity/ima/ima_queue.c +++ b/security/integrity/ima/ima_queue.c@@ -140,11 +140,15 @@ unsigned long ima_get_binary_runtime_size(void) static int ima_pcr_extend(const u8 *hash, int pcr) { int result = 0; + int i; if (!ima_tpm_chip) return result; - result = tpm_pcr_extend(ima_tpm_chip, pcr, hash); + for (i = 0; i < ima_tpm_chip->nr_allocated_banks; i++) + memcpy(digests[i].digest, hash, TPM_DIGEST_SIZE); + + result = tpm_pcr_extend(ima_tpm_chip, pcr, digests); if (result != 0) pr_err("Error Communicating to TPM chip, result: %d\n", result); return result;
-- HUAWEI TECHNOLOGIES Duesseldorf GmbH, HRB 56063 Managing Director: Bo PENG, Jian LI, Yanli SHI