| .. | .. |
|---|
| 1 | +// SPDX-License-Identifier: GPL-2.0-only |
|---|
| 1 | 2 | /* |
|---|
| 2 | 3 | * Copyright (C) 2010 IBM Corporation |
|---|
| 3 | 4 | * Copyright (C) 2010 Politecnico di Torino, Italy |
|---|
| 4 | | - * TORSEC group -- http://security.polito.it |
|---|
| 5 | + * TORSEC group -- https://security.polito.it |
|---|
| 5 | 6 | * |
|---|
| 6 | 7 | * Authors: |
|---|
| 7 | 8 | * Mimi Zohar <zohar@us.ibm.com> |
|---|
| 8 | 9 | * Roberto Sassu <roberto.sassu@polito.it> |
|---|
| 9 | | - * |
|---|
| 10 | | - * This program is free software; you can redistribute it and/or modify |
|---|
| 11 | | - * it under the terms of the GNU General Public License as published by |
|---|
| 12 | | - * the Free Software Foundation, version 2 of the License. |
|---|
| 13 | 10 | * |
|---|
| 14 | 11 | * See Documentation/security/keys/trusted-encrypted.rst |
|---|
| 15 | 12 | */ |
|---|
| .. | .. |
|---|
| 45 | 42 | static const char blkcipher_alg[] = "cbc(aes)"; |
|---|
| 46 | 43 | static const char key_format_default[] = "default"; |
|---|
| 47 | 44 | static const char key_format_ecryptfs[] = "ecryptfs"; |
|---|
| 45 | +static const char key_format_enc32[] = "enc32"; |
|---|
| 48 | 46 | static unsigned int ivsize; |
|---|
| 49 | 47 | static int blksize; |
|---|
| 50 | 48 | |
|---|
| .. | .. |
|---|
| 54 | 52 | #define HASH_SIZE SHA256_DIGEST_SIZE |
|---|
| 55 | 53 | #define MAX_DATA_SIZE 4096 |
|---|
| 56 | 54 | #define MIN_DATA_SIZE 20 |
|---|
| 55 | +#define KEY_ENC32_PAYLOAD_LEN 32 |
|---|
| 57 | 56 | |
|---|
| 58 | 57 | static struct crypto_shash *hash_tfm; |
|---|
| 59 | 58 | |
|---|
| 60 | 59 | enum { |
|---|
| 61 | | - Opt_err = -1, Opt_new, Opt_load, Opt_update |
|---|
| 60 | + Opt_new, Opt_load, Opt_update, Opt_err |
|---|
| 62 | 61 | }; |
|---|
| 63 | 62 | |
|---|
| 64 | 63 | enum { |
|---|
| 65 | | - Opt_error = -1, Opt_default, Opt_ecryptfs |
|---|
| 64 | + Opt_default, Opt_ecryptfs, Opt_enc32, Opt_error |
|---|
| 66 | 65 | }; |
|---|
| 67 | 66 | |
|---|
| 68 | 67 | static const match_table_t key_format_tokens = { |
|---|
| 69 | 68 | {Opt_default, "default"}, |
|---|
| 70 | 69 | {Opt_ecryptfs, "ecryptfs"}, |
|---|
| 70 | + {Opt_enc32, "enc32"}, |
|---|
| 71 | 71 | {Opt_error, NULL} |
|---|
| 72 | 72 | }; |
|---|
| 73 | 73 | |
|---|
| .. | .. |
|---|
| 195 | 195 | key_format = match_token(p, key_format_tokens, args); |
|---|
| 196 | 196 | switch (key_format) { |
|---|
| 197 | 197 | case Opt_ecryptfs: |
|---|
| 198 | + case Opt_enc32: |
|---|
| 198 | 199 | case Opt_default: |
|---|
| 199 | 200 | *format = p; |
|---|
| 200 | 201 | *master_desc = strsep(&datablob, " \t"); |
|---|
| .. | .. |
|---|
| 322 | 323 | return ukey; |
|---|
| 323 | 324 | } |
|---|
| 324 | 325 | |
|---|
| 325 | | -static int calc_hash(struct crypto_shash *tfm, u8 *digest, |
|---|
| 326 | | - const u8 *buf, unsigned int buflen) |
|---|
| 327 | | -{ |
|---|
| 328 | | - SHASH_DESC_ON_STACK(desc, tfm); |
|---|
| 329 | | - int err; |
|---|
| 330 | | - |
|---|
| 331 | | - desc->tfm = tfm; |
|---|
| 332 | | - desc->flags = 0; |
|---|
| 333 | | - |
|---|
| 334 | | - err = crypto_shash_digest(desc, buf, buflen, digest); |
|---|
| 335 | | - shash_desc_zero(desc); |
|---|
| 336 | | - return err; |
|---|
| 337 | | -} |
|---|
| 338 | | - |
|---|
| 339 | 326 | static int calc_hmac(u8 *digest, const u8 *key, unsigned int keylen, |
|---|
| 340 | 327 | const u8 *buf, unsigned int buflen) |
|---|
| 341 | 328 | { |
|---|
| 342 | 329 | struct crypto_shash *tfm; |
|---|
| 343 | 330 | int err; |
|---|
| 344 | 331 | |
|---|
| 345 | | - tfm = crypto_alloc_shash(hmac_alg, 0, CRYPTO_ALG_ASYNC); |
|---|
| 332 | + tfm = crypto_alloc_shash(hmac_alg, 0, 0); |
|---|
| 346 | 333 | if (IS_ERR(tfm)) { |
|---|
| 347 | 334 | pr_err("encrypted_key: can't alloc %s transform: %ld\n", |
|---|
| 348 | 335 | hmac_alg, PTR_ERR(tfm)); |
|---|
| .. | .. |
|---|
| 351 | 338 | |
|---|
| 352 | 339 | err = crypto_shash_setkey(tfm, key, keylen); |
|---|
| 353 | 340 | if (!err) |
|---|
| 354 | | - err = calc_hash(tfm, digest, buf, buflen); |
|---|
| 341 | + err = crypto_shash_tfm_digest(tfm, buf, buflen, digest); |
|---|
| 355 | 342 | crypto_free_shash(tfm); |
|---|
| 356 | 343 | return err; |
|---|
| 357 | 344 | } |
|---|
| .. | .. |
|---|
| 381 | 368 | |
|---|
| 382 | 369 | memcpy(derived_buf + strlen(derived_buf) + 1, master_key, |
|---|
| 383 | 370 | master_keylen); |
|---|
| 384 | | - ret = calc_hash(hash_tfm, derived_key, derived_buf, derived_buf_len); |
|---|
| 385 | | - kzfree(derived_buf); |
|---|
| 371 | + ret = crypto_shash_tfm_digest(hash_tfm, derived_buf, derived_buf_len, |
|---|
| 372 | + derived_key); |
|---|
| 373 | + kfree_sensitive(derived_buf); |
|---|
| 386 | 374 | return ret; |
|---|
| 387 | 375 | } |
|---|
| 388 | 376 | |
|---|
| .. | .. |
|---|
| 625 | 613 | format_len = (!format) ? strlen(key_format_default) : strlen(format); |
|---|
| 626 | 614 | decrypted_datalen = dlen; |
|---|
| 627 | 615 | payload_datalen = decrypted_datalen; |
|---|
| 628 | | - if (format && !strcmp(format, key_format_ecryptfs)) { |
|---|
| 629 | | - if (dlen != ECRYPTFS_MAX_KEY_BYTES) { |
|---|
| 630 | | - pr_err("encrypted_key: keylen for the ecryptfs format " |
|---|
| 631 | | - "must be equal to %d bytes\n", |
|---|
| 632 | | - ECRYPTFS_MAX_KEY_BYTES); |
|---|
| 633 | | - return ERR_PTR(-EINVAL); |
|---|
| 616 | + if (format) { |
|---|
| 617 | + if (!strcmp(format, key_format_ecryptfs)) { |
|---|
| 618 | + if (dlen != ECRYPTFS_MAX_KEY_BYTES) { |
|---|
| 619 | + pr_err("encrypted_key: keylen for the ecryptfs format must be equal to %d bytes\n", |
|---|
| 620 | + ECRYPTFS_MAX_KEY_BYTES); |
|---|
| 621 | + return ERR_PTR(-EINVAL); |
|---|
| 622 | + } |
|---|
| 623 | + decrypted_datalen = ECRYPTFS_MAX_KEY_BYTES; |
|---|
| 624 | + payload_datalen = sizeof(struct ecryptfs_auth_tok); |
|---|
| 625 | + } else if (!strcmp(format, key_format_enc32)) { |
|---|
| 626 | + if (decrypted_datalen != KEY_ENC32_PAYLOAD_LEN) { |
|---|
| 627 | + pr_err("encrypted_key: enc32 key payload incorrect length: %d\n", |
|---|
| 628 | + decrypted_datalen); |
|---|
| 629 | + return ERR_PTR(-EINVAL); |
|---|
| 630 | + } |
|---|
| 634 | 631 | } |
|---|
| 635 | | - decrypted_datalen = ECRYPTFS_MAX_KEY_BYTES; |
|---|
| 636 | | - payload_datalen = sizeof(struct ecryptfs_auth_tok); |
|---|
| 637 | 632 | } |
|---|
| 638 | 633 | |
|---|
| 639 | 634 | encrypted_datalen = roundup(decrypted_datalen, blksize); |
|---|
| .. | .. |
|---|
| 817 | 812 | ret = encrypted_init(epayload, key->description, format, master_desc, |
|---|
| 818 | 813 | decrypted_datalen, hex_encoded_iv); |
|---|
| 819 | 814 | if (ret < 0) { |
|---|
| 820 | | - kzfree(epayload); |
|---|
| 815 | + kfree_sensitive(epayload); |
|---|
| 821 | 816 | goto out; |
|---|
| 822 | 817 | } |
|---|
| 823 | 818 | |
|---|
| 824 | 819 | rcu_assign_keypointer(key, epayload); |
|---|
| 825 | 820 | out: |
|---|
| 826 | | - kzfree(datablob); |
|---|
| 821 | + kfree_sensitive(datablob); |
|---|
| 827 | 822 | return ret; |
|---|
| 828 | 823 | } |
|---|
| 829 | 824 | |
|---|
| .. | .. |
|---|
| 832 | 827 | struct encrypted_key_payload *epayload; |
|---|
| 833 | 828 | |
|---|
| 834 | 829 | epayload = container_of(rcu, struct encrypted_key_payload, rcu); |
|---|
| 835 | | - kzfree(epayload); |
|---|
| 830 | + kfree_sensitive(epayload); |
|---|
| 836 | 831 | } |
|---|
| 837 | 832 | |
|---|
| 838 | 833 | /* |
|---|
| .. | .. |
|---|
| 890 | 885 | rcu_assign_keypointer(key, new_epayload); |
|---|
| 891 | 886 | call_rcu(&epayload->rcu, encrypted_rcu_free); |
|---|
| 892 | 887 | out: |
|---|
| 893 | | - kzfree(buf); |
|---|
| 888 | + kfree_sensitive(buf); |
|---|
| 894 | 889 | return ret; |
|---|
| 895 | 890 | } |
|---|
| 896 | 891 | |
|---|
| .. | .. |
|---|
| 951 | 946 | memzero_explicit(derived_key, sizeof(derived_key)); |
|---|
| 952 | 947 | |
|---|
| 953 | 948 | memcpy(buffer, ascii_buf, asciiblob_len); |
|---|
| 954 | | - kzfree(ascii_buf); |
|---|
| 949 | + kfree_sensitive(ascii_buf); |
|---|
| 955 | 950 | |
|---|
| 956 | 951 | return asciiblob_len; |
|---|
| 957 | 952 | out: |
|---|
| .. | .. |
|---|
| 966 | 961 | */ |
|---|
| 967 | 962 | static void encrypted_destroy(struct key *key) |
|---|
| 968 | 963 | { |
|---|
| 969 | | - kzfree(key->payload.data[0]); |
|---|
| 964 | + kfree_sensitive(key->payload.data[0]); |
|---|
| 970 | 965 | } |
|---|
| 971 | 966 | |
|---|
| 972 | 967 | struct key_type key_type_encrypted = { |
|---|
| .. | .. |
|---|
| 983 | 978 | { |
|---|
| 984 | 979 | int ret; |
|---|
| 985 | 980 | |
|---|
| 986 | | - hash_tfm = crypto_alloc_shash(hash_alg, 0, CRYPTO_ALG_ASYNC); |
|---|
| 981 | + hash_tfm = crypto_alloc_shash(hash_alg, 0, 0); |
|---|
| 987 | 982 | if (IS_ERR(hash_tfm)) { |
|---|
| 988 | 983 | pr_err("encrypted_key: can't allocate %s transform: %ld\n", |
|---|
| 989 | 984 | hash_alg, PTR_ERR(hash_tfm)); |
|---|