.. | .. |
---|
| 1 | +// SPDX-License-Identifier: GPL-2.0-or-later |
---|
1 | 2 | /** |
---|
2 | 3 | * eCryptfs: Linux filesystem encryption layer |
---|
3 | 4 | * |
---|
.. | .. |
---|
6 | 7 | * Copyright (C) 2004-2007 International Business Machines Corp. |
---|
7 | 8 | * Author(s): Michael A. Halcrow <mahalcro@us.ibm.com> |
---|
8 | 9 | * Michael C. Thompson <mcthomps@us.ibm.com> |
---|
9 | | - * |
---|
10 | | - * This program is free software; you can redistribute it and/or |
---|
11 | | - * modify it under the terms of the GNU General Public License as |
---|
12 | | - * published by the Free Software Foundation; either version 2 of the |
---|
13 | | - * License, or (at your option) any later version. |
---|
14 | | - * |
---|
15 | | - * This program is distributed in the hope that it will be useful, but |
---|
16 | | - * WITHOUT ANY WARRANTY; without even the implied warranty of |
---|
17 | | - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU |
---|
18 | | - * General Public License for more details. |
---|
19 | | - * |
---|
20 | | - * You should have received a copy of the GNU General Public License |
---|
21 | | - * along with this program; if not, write to the Free Software |
---|
22 | | - * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA |
---|
23 | | - * 02111-1307, USA. |
---|
24 | 10 | */ |
---|
25 | 11 | |
---|
26 | 12 | #include <crypto/hash.h> |
---|
.. | .. |
---|
37 | 23 | #include <linux/slab.h> |
---|
38 | 24 | #include <asm/unaligned.h> |
---|
39 | 25 | #include <linux/kernel.h> |
---|
| 26 | +#include <linux/xattr.h> |
---|
40 | 27 | #include "ecryptfs_kernel.h" |
---|
41 | 28 | |
---|
42 | 29 | #define DECRYPT 0 |
---|
.. | .. |
---|
61 | 48 | } |
---|
62 | 49 | } |
---|
63 | 50 | |
---|
64 | | -static int ecryptfs_hash_digest(struct crypto_shash *tfm, |
---|
65 | | - char *src, int len, char *dst) |
---|
66 | | -{ |
---|
67 | | - SHASH_DESC_ON_STACK(desc, tfm); |
---|
68 | | - int err; |
---|
69 | | - |
---|
70 | | - desc->tfm = tfm; |
---|
71 | | - desc->flags = CRYPTO_TFM_REQ_MAY_SLEEP; |
---|
72 | | - err = crypto_shash_digest(desc, src, len, dst); |
---|
73 | | - shash_desc_zero(desc); |
---|
74 | | - return err; |
---|
75 | | -} |
---|
76 | | - |
---|
77 | 51 | /** |
---|
78 | 52 | * ecryptfs_calculate_md5 - calculates the md5 of @src |
---|
79 | 53 | * @dst: Pointer to 16 bytes of allocated memory |
---|
.. | .. |
---|
88 | 62 | struct ecryptfs_crypt_stat *crypt_stat, |
---|
89 | 63 | char *src, int len) |
---|
90 | 64 | { |
---|
91 | | - struct crypto_shash *tfm; |
---|
92 | | - int rc = 0; |
---|
| 65 | + int rc = crypto_shash_tfm_digest(crypt_stat->hash_tfm, src, len, dst); |
---|
93 | 66 | |
---|
94 | | - tfm = crypt_stat->hash_tfm; |
---|
95 | | - rc = ecryptfs_hash_digest(tfm, src, len, dst); |
---|
96 | 67 | if (rc) { |
---|
97 | 68 | printk(KERN_ERR |
---|
98 | 69 | "%s: Error computing crypto hash; rc = [%d]\n", |
---|
.. | .. |
---|
610 | 581 | full_alg_name); |
---|
611 | 582 | goto out_free; |
---|
612 | 583 | } |
---|
613 | | - crypto_skcipher_set_flags(crypt_stat->tfm, CRYPTO_TFM_REQ_WEAK_KEY); |
---|
| 584 | + crypto_skcipher_set_flags(crypt_stat->tfm, |
---|
| 585 | + CRYPTO_TFM_REQ_FORBID_WEAK_KEYS); |
---|
614 | 586 | rc = 0; |
---|
615 | 587 | out_free: |
---|
616 | 588 | kfree(full_alg_name); |
---|
.. | .. |
---|
874 | 846 | * @crypt_stat: The cryptographic context |
---|
875 | 847 | * @page_virt: Source data to be parsed |
---|
876 | 848 | * @bytes_read: Updated with the number of bytes read |
---|
877 | | - * |
---|
878 | | - * Returns zero on success; non-zero if the flag set is invalid |
---|
879 | 849 | */ |
---|
880 | | -static int ecryptfs_process_flags(struct ecryptfs_crypt_stat *crypt_stat, |
---|
| 850 | +static void ecryptfs_process_flags(struct ecryptfs_crypt_stat *crypt_stat, |
---|
881 | 851 | char *page_virt, int *bytes_read) |
---|
882 | 852 | { |
---|
883 | | - int rc = 0; |
---|
884 | 853 | int i; |
---|
885 | 854 | u32 flags; |
---|
886 | 855 | |
---|
.. | .. |
---|
893 | 862 | /* Version is in top 8 bits of the 32-bit flag vector */ |
---|
894 | 863 | crypt_stat->file_version = ((flags >> 24) & 0xFF); |
---|
895 | 864 | (*bytes_read) = 4; |
---|
896 | | - return rc; |
---|
897 | 865 | } |
---|
898 | 866 | |
---|
899 | 867 | /** |
---|
.. | .. |
---|
1131 | 1099 | char *page_virt, size_t size) |
---|
1132 | 1100 | { |
---|
1133 | 1101 | int rc; |
---|
| 1102 | + struct dentry *lower_dentry = ecryptfs_dentry_to_lower(ecryptfs_dentry); |
---|
| 1103 | + struct inode *lower_inode = d_inode(lower_dentry); |
---|
1134 | 1104 | |
---|
1135 | | - rc = ecryptfs_setxattr(ecryptfs_dentry, ecryptfs_inode, |
---|
1136 | | - ECRYPTFS_XATTR_NAME, page_virt, size, 0); |
---|
| 1105 | + if (!(lower_inode->i_opflags & IOP_XATTR)) { |
---|
| 1106 | + rc = -EOPNOTSUPP; |
---|
| 1107 | + goto out; |
---|
| 1108 | + } |
---|
| 1109 | + |
---|
| 1110 | + inode_lock(lower_inode); |
---|
| 1111 | + rc = __vfs_setxattr(lower_dentry, lower_inode, ECRYPTFS_XATTR_NAME, |
---|
| 1112 | + page_virt, size, 0); |
---|
| 1113 | + if (!rc && ecryptfs_inode) |
---|
| 1114 | + fsstack_copy_attr_all(ecryptfs_inode, lower_inode); |
---|
| 1115 | + inode_unlock(lower_inode); |
---|
| 1116 | +out: |
---|
1137 | 1117 | return rc; |
---|
1138 | 1118 | } |
---|
1139 | 1119 | |
---|
.. | .. |
---|
1307 | 1287 | if (!(crypt_stat->flags & ECRYPTFS_I_SIZE_INITIALIZED)) |
---|
1308 | 1288 | ecryptfs_i_size_init(page_virt, d_inode(ecryptfs_dentry)); |
---|
1309 | 1289 | offset += MAGIC_ECRYPTFS_MARKER_SIZE_BYTES; |
---|
1310 | | - rc = ecryptfs_process_flags(crypt_stat, (page_virt + offset), |
---|
1311 | | - &bytes_read); |
---|
1312 | | - if (rc) { |
---|
1313 | | - ecryptfs_printk(KERN_WARNING, "Error processing flags\n"); |
---|
1314 | | - goto out; |
---|
1315 | | - } |
---|
| 1290 | + ecryptfs_process_flags(crypt_stat, (page_virt + offset), &bytes_read); |
---|
1316 | 1291 | if (crypt_stat->file_version > ECRYPTFS_SUPPORTED_FILE_VERSION) { |
---|
1317 | 1292 | ecryptfs_printk(KERN_WARNING, "File version is [%d]; only " |
---|
1318 | 1293 | "file version [%d] is supported by this " |
---|
.. | .. |
---|
1594 | 1569 | "[%s]; rc = [%d]\n", full_alg_name, rc); |
---|
1595 | 1570 | goto out; |
---|
1596 | 1571 | } |
---|
1597 | | - crypto_skcipher_set_flags(*key_tfm, CRYPTO_TFM_REQ_WEAK_KEY); |
---|
| 1572 | + crypto_skcipher_set_flags(*key_tfm, CRYPTO_TFM_REQ_FORBID_WEAK_KEYS); |
---|
1598 | 1573 | if (*key_size == 0) |
---|
1599 | | - *key_size = crypto_skcipher_default_keysize(*key_tfm); |
---|
| 1574 | + *key_size = crypto_skcipher_max_keysize(*key_tfm); |
---|
1600 | 1575 | get_random_bytes(dummy_key, *key_size); |
---|
1601 | 1576 | rc = crypto_skcipher_setkey(*key_tfm, dummy_key, *key_size); |
---|
1602 | 1577 | if (rc) { |
---|