aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorEric Biggers2017-06-08 08:49:18 -0500
committerJames Morris2017-06-08 22:29:48 -0500
commitee618b4619b72527aaed765f0f0b74072b281159 (patch)
tree7a01f2a757a88fab95d9acf6353494a6e8e1a32e
parenta9dd74b252e04b7e41ffe78d418b896b33b70a13 (diff)
downloadlinux-phy-ee618b4619b72527aaed765f0f0b74072b281159.tar.gz
linux-phy-ee618b4619b72527aaed765f0f0b74072b281159.tar.xz
linux-phy-ee618b4619b72527aaed765f0f0b74072b281159.zip
KEYS: trusted: sanitize all key material
As the previous patch did for encrypted-keys, zero sensitive any potentially sensitive data related to the "trusted" key type before it is freed. Notably, we were not zeroing the tpm_buf structures in which the actual key is stored for TPM seal and unseal, nor were we zeroing the trusted_key_payload in certain error paths. Cc: Mimi Zohar <zohar@linux.vnet.ibm.com> Cc: David Safford <safford@us.ibm.com> Signed-off-by: Eric Biggers <ebiggers@google.com> Signed-off-by: David Howells <dhowells@redhat.com> Signed-off-by: James Morris <james.l.morris@oracle.com>
-rw-r--r--security/keys/trusted.c50
1 files changed, 22 insertions, 28 deletions
diff --git a/security/keys/trusted.c b/security/keys/trusted.c
index 2ae31c5a87de..435e86e13879 100644
--- a/security/keys/trusted.c
+++ b/security/keys/trusted.c
@@ -70,7 +70,7 @@ static int TSS_sha1(const unsigned char *data, unsigned int datalen,
70 } 70 }
71 71
72 ret = crypto_shash_digest(&sdesc->shash, data, datalen, digest); 72 ret = crypto_shash_digest(&sdesc->shash, data, datalen, digest);
73 kfree(sdesc); 73 kzfree(sdesc);
74 return ret; 74 return ret;
75} 75}
76 76
@@ -114,7 +114,7 @@ static int TSS_rawhmac(unsigned char *digest, const unsigned char *key,
114 if (!ret) 114 if (!ret)
115 ret = crypto_shash_final(&sdesc->shash, digest); 115 ret = crypto_shash_final(&sdesc->shash, digest);
116out: 116out:
117 kfree(sdesc); 117 kzfree(sdesc);
118 return ret; 118 return ret;
119} 119}
120 120
@@ -165,7 +165,7 @@ static int TSS_authhmac(unsigned char *digest, const unsigned char *key,
165 paramdigest, TPM_NONCE_SIZE, h1, 165 paramdigest, TPM_NONCE_SIZE, h1,
166 TPM_NONCE_SIZE, h2, 1, &c, 0, 0); 166 TPM_NONCE_SIZE, h2, 1, &c, 0, 0);
167out: 167out:
168 kfree(sdesc); 168 kzfree(sdesc);
169 return ret; 169 return ret;
170} 170}
171 171
@@ -246,7 +246,7 @@ static int TSS_checkhmac1(unsigned char *buffer,
246 if (memcmp(testhmac, authdata, SHA1_DIGEST_SIZE)) 246 if (memcmp(testhmac, authdata, SHA1_DIGEST_SIZE))
247 ret = -EINVAL; 247 ret = -EINVAL;
248out: 248out:
249 kfree(sdesc); 249 kzfree(sdesc);
250 return ret; 250 return ret;
251} 251}
252 252
@@ -347,7 +347,7 @@ static int TSS_checkhmac2(unsigned char *buffer,
347 if (memcmp(testhmac2, authdata2, SHA1_DIGEST_SIZE)) 347 if (memcmp(testhmac2, authdata2, SHA1_DIGEST_SIZE))
348 ret = -EINVAL; 348 ret = -EINVAL;
349out: 349out:
350 kfree(sdesc); 350 kzfree(sdesc);
351 return ret; 351 return ret;
352} 352}
353 353
@@ -564,7 +564,7 @@ static int tpm_seal(struct tpm_buf *tb, uint16_t keytype,
564 *bloblen = storedsize; 564 *bloblen = storedsize;
565 } 565 }
566out: 566out:
567 kfree(td); 567 kzfree(td);
568 return ret; 568 return ret;
569} 569}
570 570
@@ -678,7 +678,7 @@ static int key_seal(struct trusted_key_payload *p,
678 if (ret < 0) 678 if (ret < 0)
679 pr_info("trusted_key: srkseal failed (%d)\n", ret); 679 pr_info("trusted_key: srkseal failed (%d)\n", ret);
680 680
681 kfree(tb); 681 kzfree(tb);
682 return ret; 682 return ret;
683} 683}
684 684
@@ -703,7 +703,7 @@ static int key_unseal(struct trusted_key_payload *p,
703 /* pull migratable flag out of sealed key */ 703 /* pull migratable flag out of sealed key */
704 p->migratable = p->key[--p->key_len]; 704 p->migratable = p->key[--p->key_len];
705 705
706 kfree(tb); 706 kzfree(tb);
707 return ret; 707 return ret;
708} 708}
709 709
@@ -1037,12 +1037,12 @@ static int trusted_instantiate(struct key *key,
1037 if (!ret && options->pcrlock) 1037 if (!ret && options->pcrlock)
1038 ret = pcrlock(options->pcrlock); 1038 ret = pcrlock(options->pcrlock);
1039out: 1039out:
1040 kfree(datablob); 1040 kzfree(datablob);
1041 kfree(options); 1041 kzfree(options);
1042 if (!ret) 1042 if (!ret)
1043 rcu_assign_keypointer(key, payload); 1043 rcu_assign_keypointer(key, payload);
1044 else 1044 else
1045 kfree(payload); 1045 kzfree(payload);
1046 return ret; 1046 return ret;
1047} 1047}
1048 1048
@@ -1051,8 +1051,7 @@ static void trusted_rcu_free(struct rcu_head *rcu)
1051 struct trusted_key_payload *p; 1051 struct trusted_key_payload *p;
1052 1052
1053 p = container_of(rcu, struct trusted_key_payload, rcu); 1053 p = container_of(rcu, struct trusted_key_payload, rcu);
1054 memset(p->key, 0, p->key_len); 1054 kzfree(p);
1055 kfree(p);
1056} 1055}
1057 1056
1058/* 1057/*
@@ -1094,13 +1093,13 @@ static int trusted_update(struct key *key, struct key_preparsed_payload *prep)
1094 ret = datablob_parse(datablob, new_p, new_o); 1093 ret = datablob_parse(datablob, new_p, new_o);
1095 if (ret != Opt_update) { 1094 if (ret != Opt_update) {
1096 ret = -EINVAL; 1095 ret = -EINVAL;
1097 kfree(new_p); 1096 kzfree(new_p);
1098 goto out; 1097 goto out;
1099 } 1098 }
1100 1099
1101 if (!new_o->keyhandle) { 1100 if (!new_o->keyhandle) {
1102 ret = -EINVAL; 1101 ret = -EINVAL;
1103 kfree(new_p); 1102 kzfree(new_p);
1104 goto out; 1103 goto out;
1105 } 1104 }
1106 1105
@@ -1114,22 +1113,22 @@ static int trusted_update(struct key *key, struct key_preparsed_payload *prep)
1114 ret = key_seal(new_p, new_o); 1113 ret = key_seal(new_p, new_o);
1115 if (ret < 0) { 1114 if (ret < 0) {
1116 pr_info("trusted_key: key_seal failed (%d)\n", ret); 1115 pr_info("trusted_key: key_seal failed (%d)\n", ret);
1117 kfree(new_p); 1116 kzfree(new_p);
1118 goto out; 1117 goto out;
1119 } 1118 }
1120 if (new_o->pcrlock) { 1119 if (new_o->pcrlock) {
1121 ret = pcrlock(new_o->pcrlock); 1120 ret = pcrlock(new_o->pcrlock);
1122 if (ret < 0) { 1121 if (ret < 0) {
1123 pr_info("trusted_key: pcrlock failed (%d)\n", ret); 1122 pr_info("trusted_key: pcrlock failed (%d)\n", ret);
1124 kfree(new_p); 1123 kzfree(new_p);
1125 goto out; 1124 goto out;
1126 } 1125 }
1127 } 1126 }
1128 rcu_assign_keypointer(key, new_p); 1127 rcu_assign_keypointer(key, new_p);
1129 call_rcu(&p->rcu, trusted_rcu_free); 1128 call_rcu(&p->rcu, trusted_rcu_free);
1130out: 1129out:
1131 kfree(datablob); 1130 kzfree(datablob);
1132 kfree(new_o); 1131 kzfree(new_o);
1133 return ret; 1132 return ret;
1134} 1133}
1135 1134
@@ -1158,24 +1157,19 @@ static long trusted_read(const struct key *key, char __user *buffer,
1158 for (i = 0; i < p->blob_len; i++) 1157 for (i = 0; i < p->blob_len; i++)
1159 bufp = hex_byte_pack(bufp, p->blob[i]); 1158 bufp = hex_byte_pack(bufp, p->blob[i]);
1160 if ((copy_to_user(buffer, ascii_buf, 2 * p->blob_len)) != 0) { 1159 if ((copy_to_user(buffer, ascii_buf, 2 * p->blob_len)) != 0) {
1161 kfree(ascii_buf); 1160 kzfree(ascii_buf);
1162 return -EFAULT; 1161 return -EFAULT;
1163 } 1162 }
1164 kfree(ascii_buf); 1163 kzfree(ascii_buf);
1165 return 2 * p->blob_len; 1164 return 2 * p->blob_len;
1166} 1165}
1167 1166
1168/* 1167/*
1169 * trusted_destroy - before freeing the key, clear the decrypted data 1168 * trusted_destroy - clear and free the key's payload
1170 */ 1169 */
1171static void trusted_destroy(struct key *key) 1170static void trusted_destroy(struct key *key)
1172{ 1171{
1173 struct trusted_key_payload *p = key->payload.data[0]; 1172 kzfree(key->payload.data[0]);
1174
1175 if (!p)
1176 return;
1177 memset(p->key, 0, p->key_len);
1178 kfree(key->payload.data[0]);
1179} 1173}
1180 1174
1181struct key_type key_type_trusted = { 1175struct key_type key_type_trusted = {