fs/crypto: catch up 4.9-rc6
commit d117b9acaeada0b243f31e0fe83e111fcc9a6644 upstream. Merge tag 'ext4_for_stable' of git://git.kernel.org/pub/scm/linux/kernel/git/tytso/ext4 Pull ext4 fixes from Ted Ts'o: "A security fix (so a maliciously corrupted file system image won't panic the kernel) and some fixes for CONFIG_VMAP_STACK" Signed-off-by: Jaegeuk Kim <jaegeuk@kernel.org>
This commit is contained in:
parent
b3441f8c71
commit
d4ec990d25
7 changed files with 141 additions and 142 deletions
|
@ -28,7 +28,6 @@
|
|||
#include <linux/dcache.h>
|
||||
#include <linux/namei.h>
|
||||
#include <linux/fscrypto.h>
|
||||
#include <linux/ecryptfs.h>
|
||||
|
||||
static unsigned int num_prealloc_crypto_pages = 32;
|
||||
static unsigned int num_prealloc_crypto_ctxs = 128;
|
||||
|
@ -128,11 +127,11 @@ struct fscrypt_ctx *fscrypt_get_ctx(struct inode *inode, gfp_t gfp_flags)
|
|||
EXPORT_SYMBOL(fscrypt_get_ctx);
|
||||
|
||||
/**
|
||||
* fscrypt_complete() - The completion callback for page encryption
|
||||
* @req: The asynchronous encryption request context
|
||||
* @res: The result of the encryption operation
|
||||
* page_crypt_complete() - completion callback for page crypto
|
||||
* @req: The asynchronous cipher request context
|
||||
* @res: The result of the cipher operation
|
||||
*/
|
||||
static void fscrypt_complete(struct crypto_async_request *req, int res)
|
||||
static void page_crypt_complete(struct crypto_async_request *req, int res)
|
||||
{
|
||||
struct fscrypt_completion_result *ecr = req->data;
|
||||
|
||||
|
@ -152,7 +151,10 @@ static int do_page_crypto(struct inode *inode,
|
|||
struct page *src_page, struct page *dest_page,
|
||||
gfp_t gfp_flags)
|
||||
{
|
||||
u8 xts_tweak[FS_XTS_TWEAK_SIZE];
|
||||
struct {
|
||||
__le64 index;
|
||||
u8 padding[FS_XTS_TWEAK_SIZE - sizeof(__le64)];
|
||||
} xts_tweak;
|
||||
struct skcipher_request *req = NULL;
|
||||
DECLARE_FS_COMPLETION_RESULT(ecr);
|
||||
struct scatterlist dst, src;
|
||||
|
@ -170,19 +172,17 @@ static int do_page_crypto(struct inode *inode,
|
|||
|
||||
skcipher_request_set_callback(
|
||||
req, CRYPTO_TFM_REQ_MAY_BACKLOG | CRYPTO_TFM_REQ_MAY_SLEEP,
|
||||
fscrypt_complete, &ecr);
|
||||
page_crypt_complete, &ecr);
|
||||
|
||||
BUILD_BUG_ON(FS_XTS_TWEAK_SIZE < sizeof(index));
|
||||
memcpy(xts_tweak, &index, sizeof(index));
|
||||
memset(&xts_tweak[sizeof(index)], 0,
|
||||
FS_XTS_TWEAK_SIZE - sizeof(index));
|
||||
BUILD_BUG_ON(sizeof(xts_tweak) != FS_XTS_TWEAK_SIZE);
|
||||
xts_tweak.index = cpu_to_le64(index);
|
||||
memset(xts_tweak.padding, 0, sizeof(xts_tweak.padding));
|
||||
|
||||
sg_init_table(&dst, 1);
|
||||
sg_set_page(&dst, dest_page, PAGE_SIZE, 0);
|
||||
sg_init_table(&src, 1);
|
||||
sg_set_page(&src, src_page, PAGE_SIZE, 0);
|
||||
skcipher_request_set_crypt(req, &src, &dst, PAGE_SIZE,
|
||||
xts_tweak);
|
||||
skcipher_request_set_crypt(req, &src, &dst, PAGE_SIZE, &xts_tweak);
|
||||
if (rw == FS_DECRYPT)
|
||||
res = crypto_skcipher_decrypt(req);
|
||||
else
|
||||
|
|
|
@ -10,21 +10,16 @@
|
|||
* This has not yet undergone a rigorous security audit.
|
||||
*/
|
||||
|
||||
#include <keys/encrypted-type.h>
|
||||
#include <keys/user-type.h>
|
||||
#include <linux/scatterlist.h>
|
||||
#include <linux/ratelimit.h>
|
||||
#include <linux/fscrypto.h>
|
||||
|
||||
static u32 size_round_up(size_t size, size_t blksize)
|
||||
{
|
||||
return ((size + blksize - 1) / blksize) * blksize;
|
||||
}
|
||||
|
||||
/**
|
||||
* dir_crypt_complete() -
|
||||
* fname_crypt_complete() - completion callback for filename crypto
|
||||
* @req: The asynchronous cipher request context
|
||||
* @res: The result of the cipher operation
|
||||
*/
|
||||
static void dir_crypt_complete(struct crypto_async_request *req, int res)
|
||||
static void fname_crypt_complete(struct crypto_async_request *req, int res)
|
||||
{
|
||||
struct fscrypt_completion_result *ecr = req->data;
|
||||
|
||||
|
@ -35,90 +30,80 @@ static void dir_crypt_complete(struct crypto_async_request *req, int res)
|
|||
}
|
||||
|
||||
/**
|
||||
* fname_encrypt() -
|
||||
* fname_encrypt() - encrypt a filename
|
||||
*
|
||||
* This function encrypts the input filename, and returns the length of the
|
||||
* ciphertext. Errors are returned as negative numbers. We trust the caller to
|
||||
* allocate sufficient memory to oname string.
|
||||
* The caller must have allocated sufficient memory for the @oname string.
|
||||
*
|
||||
* Return: 0 on success, -errno on failure
|
||||
*/
|
||||
static int fname_encrypt(struct inode *inode,
|
||||
const struct qstr *iname, struct fscrypt_str *oname)
|
||||
{
|
||||
u32 ciphertext_len;
|
||||
struct skcipher_request *req = NULL;
|
||||
DECLARE_FS_COMPLETION_RESULT(ecr);
|
||||
struct fscrypt_info *ci = inode->i_crypt_info;
|
||||
struct crypto_skcipher *tfm = ci->ci_ctfm;
|
||||
int res = 0;
|
||||
char iv[FS_CRYPTO_BLOCK_SIZE];
|
||||
struct scatterlist src_sg, dst_sg;
|
||||
struct scatterlist sg;
|
||||
int padding = 4 << (ci->ci_flags & FS_POLICY_FLAGS_PAD_MASK);
|
||||
char *workbuf, buf[32], *alloc_buf = NULL;
|
||||
unsigned lim;
|
||||
unsigned int lim;
|
||||
unsigned int cryptlen;
|
||||
|
||||
lim = inode->i_sb->s_cop->max_namelen(inode);
|
||||
if (iname->len <= 0 || iname->len > lim)
|
||||
return -EIO;
|
||||
|
||||
ciphertext_len = (iname->len < FS_CRYPTO_BLOCK_SIZE) ?
|
||||
FS_CRYPTO_BLOCK_SIZE : iname->len;
|
||||
ciphertext_len = size_round_up(ciphertext_len, padding);
|
||||
ciphertext_len = (ciphertext_len > lim) ? lim : ciphertext_len;
|
||||
/*
|
||||
* Copy the filename to the output buffer for encrypting in-place and
|
||||
* pad it with the needed number of NUL bytes.
|
||||
*/
|
||||
cryptlen = max_t(unsigned int, iname->len, FS_CRYPTO_BLOCK_SIZE);
|
||||
cryptlen = round_up(cryptlen, padding);
|
||||
cryptlen = min(cryptlen, lim);
|
||||
memcpy(oname->name, iname->name, iname->len);
|
||||
memset(oname->name + iname->len, 0, cryptlen - iname->len);
|
||||
|
||||
if (ciphertext_len <= sizeof(buf)) {
|
||||
workbuf = buf;
|
||||
} else {
|
||||
alloc_buf = kmalloc(ciphertext_len, GFP_NOFS);
|
||||
if (!alloc_buf)
|
||||
return -ENOMEM;
|
||||
workbuf = alloc_buf;
|
||||
}
|
||||
/* Initialize the IV */
|
||||
memset(iv, 0, FS_CRYPTO_BLOCK_SIZE);
|
||||
|
||||
/* Allocate request */
|
||||
/* Set up the encryption request */
|
||||
req = skcipher_request_alloc(tfm, GFP_NOFS);
|
||||
if (!req) {
|
||||
printk_ratelimited(KERN_ERR
|
||||
"%s: crypto_request_alloc() failed\n", __func__);
|
||||
kfree(alloc_buf);
|
||||
"%s: skcipher_request_alloc() failed\n", __func__);
|
||||
return -ENOMEM;
|
||||
}
|
||||
skcipher_request_set_callback(req,
|
||||
CRYPTO_TFM_REQ_MAY_BACKLOG | CRYPTO_TFM_REQ_MAY_SLEEP,
|
||||
dir_crypt_complete, &ecr);
|
||||
fname_crypt_complete, &ecr);
|
||||
sg_init_one(&sg, oname->name, cryptlen);
|
||||
skcipher_request_set_crypt(req, &sg, &sg, cryptlen, iv);
|
||||
|
||||
/* Copy the input */
|
||||
memcpy(workbuf, iname->name, iname->len);
|
||||
if (iname->len < ciphertext_len)
|
||||
memset(workbuf + iname->len, 0, ciphertext_len - iname->len);
|
||||
|
||||
/* Initialize IV */
|
||||
memset(iv, 0, FS_CRYPTO_BLOCK_SIZE);
|
||||
|
||||
/* Create encryption request */
|
||||
sg_init_one(&src_sg, workbuf, ciphertext_len);
|
||||
sg_init_one(&dst_sg, oname->name, ciphertext_len);
|
||||
skcipher_request_set_crypt(req, &src_sg, &dst_sg, ciphertext_len, iv);
|
||||
/* Do the encryption */
|
||||
res = crypto_skcipher_encrypt(req);
|
||||
if (res == -EINPROGRESS || res == -EBUSY) {
|
||||
/* Request is being completed asynchronously; wait for it */
|
||||
wait_for_completion(&ecr.completion);
|
||||
res = ecr.res;
|
||||
}
|
||||
kfree(alloc_buf);
|
||||
skcipher_request_free(req);
|
||||
if (res < 0)
|
||||
if (res < 0) {
|
||||
printk_ratelimited(KERN_ERR
|
||||
"%s: Error (error code %d)\n", __func__, res);
|
||||
|
||||
oname->len = ciphertext_len;
|
||||
return res;
|
||||
}
|
||||
|
||||
oname->len = cryptlen;
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
* fname_decrypt()
|
||||
* This function decrypts the input filename, and returns
|
||||
* the length of the plaintext.
|
||||
* Errors are returned as negative numbers.
|
||||
* We trust the caller to allocate sufficient memory to oname string.
|
||||
/**
|
||||
* fname_decrypt() - decrypt a filename
|
||||
*
|
||||
* The caller must have allocated sufficient memory for the @oname string.
|
||||
*
|
||||
* Return: 0 on success, -errno on failure
|
||||
*/
|
||||
static int fname_decrypt(struct inode *inode,
|
||||
const struct fscrypt_str *iname,
|
||||
|
@ -146,7 +131,7 @@ static int fname_decrypt(struct inode *inode,
|
|||
}
|
||||
skcipher_request_set_callback(req,
|
||||
CRYPTO_TFM_REQ_MAY_BACKLOG | CRYPTO_TFM_REQ_MAY_SLEEP,
|
||||
dir_crypt_complete, &ecr);
|
||||
fname_crypt_complete, &ecr);
|
||||
|
||||
/* Initialize IV */
|
||||
memset(iv, 0, FS_CRYPTO_BLOCK_SIZE);
|
||||
|
@ -168,7 +153,7 @@ static int fname_decrypt(struct inode *inode,
|
|||
}
|
||||
|
||||
oname->len = strnlen(oname->name, iname->len);
|
||||
return oname->len;
|
||||
return 0;
|
||||
}
|
||||
|
||||
static const char *lookup_table =
|
||||
|
@ -231,9 +216,8 @@ u32 fscrypt_fname_encrypted_size(struct inode *inode, u32 ilen)
|
|||
|
||||
if (ci)
|
||||
padding = 4 << (ci->ci_flags & FS_POLICY_FLAGS_PAD_MASK);
|
||||
if (ilen < FS_CRYPTO_BLOCK_SIZE)
|
||||
ilen = FS_CRYPTO_BLOCK_SIZE;
|
||||
return size_round_up(ilen, padding);
|
||||
ilen = max(ilen, (u32)FS_CRYPTO_BLOCK_SIZE);
|
||||
return round_up(ilen, padding);
|
||||
}
|
||||
EXPORT_SYMBOL(fscrypt_fname_encrypted_size);
|
||||
|
||||
|
@ -279,6 +263,10 @@ EXPORT_SYMBOL(fscrypt_fname_free_buffer);
|
|||
/**
|
||||
* fscrypt_fname_disk_to_usr() - converts a filename from disk space to user
|
||||
* space
|
||||
*
|
||||
* The caller must have allocated sufficient memory for the @oname string.
|
||||
*
|
||||
* Return: 0 on success, -errno on failure
|
||||
*/
|
||||
int fscrypt_fname_disk_to_usr(struct inode *inode,
|
||||
u32 hash, u32 minor_hash,
|
||||
|
@ -287,13 +275,12 @@ int fscrypt_fname_disk_to_usr(struct inode *inode,
|
|||
{
|
||||
const struct qstr qname = FSTR_TO_QSTR(iname);
|
||||
char buf[24];
|
||||
int ret;
|
||||
|
||||
if (fscrypt_is_dot_dotdot(&qname)) {
|
||||
oname->name[0] = '.';
|
||||
oname->name[iname->len - 1] = '.';
|
||||
oname->len = iname->len;
|
||||
return oname->len;
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (iname->len < FS_CRYPTO_BLOCK_SIZE)
|
||||
|
@ -303,9 +290,9 @@ int fscrypt_fname_disk_to_usr(struct inode *inode,
|
|||
return fname_decrypt(inode, iname, oname);
|
||||
|
||||
if (iname->len <= FS_FNAME_CRYPTO_DIGEST_SIZE) {
|
||||
ret = digest_encode(iname->name, iname->len, oname->name);
|
||||
oname->len = ret;
|
||||
return ret;
|
||||
oname->len = digest_encode(iname->name, iname->len,
|
||||
oname->name);
|
||||
return 0;
|
||||
}
|
||||
if (hash) {
|
||||
memcpy(buf, &hash, 4);
|
||||
|
@ -315,15 +302,18 @@ int fscrypt_fname_disk_to_usr(struct inode *inode,
|
|||
}
|
||||
memcpy(buf + 8, iname->name + iname->len - 16, 16);
|
||||
oname->name[0] = '_';
|
||||
ret = digest_encode(buf, 24, oname->name + 1);
|
||||
oname->len = ret + 1;
|
||||
return ret + 1;
|
||||
oname->len = 1 + digest_encode(buf, 24, oname->name + 1);
|
||||
return 0;
|
||||
}
|
||||
EXPORT_SYMBOL(fscrypt_fname_disk_to_usr);
|
||||
|
||||
/**
|
||||
* fscrypt_fname_usr_to_disk() - converts a filename from user space to disk
|
||||
* space
|
||||
*
|
||||
* The caller must have allocated sufficient memory for the @oname string.
|
||||
*
|
||||
* Return: 0 on success, -errno on failure
|
||||
*/
|
||||
int fscrypt_fname_usr_to_disk(struct inode *inode,
|
||||
const struct qstr *iname,
|
||||
|
@ -333,7 +323,7 @@ int fscrypt_fname_usr_to_disk(struct inode *inode,
|
|||
oname->name[0] = '.';
|
||||
oname->name[iname->len - 1] = '.';
|
||||
oname->len = iname->len;
|
||||
return oname->len;
|
||||
return 0;
|
||||
}
|
||||
if (inode->i_crypt_info)
|
||||
return fname_encrypt(inode, iname, oname);
|
||||
|
@ -367,10 +357,10 @@ int fscrypt_setup_filename(struct inode *dir, const struct qstr *iname,
|
|||
if (dir->i_crypt_info) {
|
||||
ret = fscrypt_fname_alloc_buffer(dir, iname->len,
|
||||
&fname->crypto_buf);
|
||||
if (ret < 0)
|
||||
if (ret)
|
||||
return ret;
|
||||
ret = fname_encrypt(dir, iname, &fname->crypto_buf);
|
||||
if (ret < 0)
|
||||
if (ret)
|
||||
goto errout;
|
||||
fname->disk_name.name = fname->crypto_buf.name;
|
||||
fname->disk_name.len = fname->crypto_buf.len;
|
||||
|
|
|
@ -8,11 +8,8 @@
|
|||
* Written by Michael Halcrow, Ildar Muslukhov, and Uday Savagaonkar, 2015.
|
||||
*/
|
||||
|
||||
#include <keys/encrypted-type.h>
|
||||
#include <keys/user-type.h>
|
||||
#include <linux/random.h>
|
||||
#include <linux/scatterlist.h>
|
||||
#include <uapi/linux/keyctl.h>
|
||||
#include <linux/fscrypto.h>
|
||||
|
||||
static void derive_crypt_complete(struct crypto_async_request *req, int rc)
|
||||
|
@ -139,6 +136,38 @@ out:
|
|||
return res;
|
||||
}
|
||||
|
||||
static int determine_cipher_type(struct fscrypt_info *ci, struct inode *inode,
|
||||
const char **cipher_str_ret, int *keysize_ret)
|
||||
{
|
||||
if (S_ISREG(inode->i_mode)) {
|
||||
if (ci->ci_data_mode == FS_ENCRYPTION_MODE_AES_256_XTS) {
|
||||
*cipher_str_ret = "xts(aes)";
|
||||
*keysize_ret = FS_AES_256_XTS_KEY_SIZE;
|
||||
return 0;
|
||||
}
|
||||
pr_warn_once("fscrypto: unsupported contents encryption mode "
|
||||
"%d for inode %lu\n",
|
||||
ci->ci_data_mode, inode->i_ino);
|
||||
return -ENOKEY;
|
||||
}
|
||||
|
||||
if (S_ISDIR(inode->i_mode) || S_ISLNK(inode->i_mode)) {
|
||||
if (ci->ci_filename_mode == FS_ENCRYPTION_MODE_AES_256_CTS) {
|
||||
*cipher_str_ret = "cts(cbc(aes))";
|
||||
*keysize_ret = FS_AES_256_CTS_KEY_SIZE;
|
||||
return 0;
|
||||
}
|
||||
pr_warn_once("fscrypto: unsupported filenames encryption mode "
|
||||
"%d for inode %lu\n",
|
||||
ci->ci_filename_mode, inode->i_ino);
|
||||
return -ENOKEY;
|
||||
}
|
||||
|
||||
pr_warn_once("fscrypto: unsupported file type %d for inode %lu\n",
|
||||
(inode->i_mode & S_IFMT), inode->i_ino);
|
||||
return -ENOKEY;
|
||||
}
|
||||
|
||||
static void put_crypt_info(struct fscrypt_info *ci)
|
||||
{
|
||||
if (!ci)
|
||||
|
@ -155,8 +184,8 @@ int get_crypt_info(struct inode *inode)
|
|||
struct fscrypt_context ctx;
|
||||
struct crypto_skcipher *ctfm;
|
||||
const char *cipher_str;
|
||||
u8 raw_key[FS_MAX_KEY_SIZE];
|
||||
u8 mode;
|
||||
int keysize;
|
||||
u8 *raw_key = NULL;
|
||||
int res;
|
||||
|
||||
res = fscrypt_initialize();
|
||||
|
@ -179,13 +208,19 @@ retry:
|
|||
if (res < 0) {
|
||||
if (!fscrypt_dummy_context_enabled(inode))
|
||||
return res;
|
||||
ctx.format = FS_ENCRYPTION_CONTEXT_FORMAT_V1;
|
||||
ctx.contents_encryption_mode = FS_ENCRYPTION_MODE_AES_256_XTS;
|
||||
ctx.filenames_encryption_mode = FS_ENCRYPTION_MODE_AES_256_CTS;
|
||||
ctx.flags = 0;
|
||||
} else if (res != sizeof(ctx)) {
|
||||
return -EINVAL;
|
||||
}
|
||||
res = 0;
|
||||
|
||||
if (ctx.format != FS_ENCRYPTION_CONTEXT_FORMAT_V1)
|
||||
return -EINVAL;
|
||||
|
||||
if (ctx.flags & ~FS_POLICY_FLAGS_VALID)
|
||||
return -EINVAL;
|
||||
|
||||
crypt_info = kmem_cache_alloc(fscrypt_info_cachep, GFP_NOFS);
|
||||
if (!crypt_info)
|
||||
|
@ -198,27 +233,20 @@ retry:
|
|||
crypt_info->ci_keyring_key = NULL;
|
||||
memcpy(crypt_info->ci_master_key, ctx.master_key_descriptor,
|
||||
sizeof(crypt_info->ci_master_key));
|
||||
if (S_ISREG(inode->i_mode))
|
||||
mode = crypt_info->ci_data_mode;
|
||||
else if (S_ISDIR(inode->i_mode) || S_ISLNK(inode->i_mode))
|
||||
mode = crypt_info->ci_filename_mode;
|
||||
else
|
||||
BUG();
|
||||
|
||||
switch (mode) {
|
||||
case FS_ENCRYPTION_MODE_AES_256_XTS:
|
||||
cipher_str = "xts(aes)";
|
||||
break;
|
||||
case FS_ENCRYPTION_MODE_AES_256_CTS:
|
||||
cipher_str = "cts(cbc(aes))";
|
||||
break;
|
||||
default:
|
||||
printk_once(KERN_WARNING
|
||||
"%s: unsupported key mode %d (ino %u)\n",
|
||||
__func__, mode, (unsigned) inode->i_ino);
|
||||
res = -ENOKEY;
|
||||
res = determine_cipher_type(crypt_info, inode, &cipher_str, &keysize);
|
||||
if (res)
|
||||
goto out;
|
||||
}
|
||||
|
||||
/*
|
||||
* This cannot be a stack buffer because it is passed to the scatterlist
|
||||
* crypto API as part of key derivation.
|
||||
*/
|
||||
res = -ENOMEM;
|
||||
raw_key = kmalloc(FS_MAX_KEY_SIZE, GFP_NOFS);
|
||||
if (!raw_key)
|
||||
goto out;
|
||||
|
||||
if (fscrypt_dummy_context_enabled(inode)) {
|
||||
memset(raw_key, 0x42, FS_AES_256_XTS_KEY_SIZE);
|
||||
goto got_key;
|
||||
|
@ -253,11 +281,12 @@ got_key:
|
|||
crypt_info->ci_ctfm = ctfm;
|
||||
crypto_skcipher_clear_flags(ctfm, ~0);
|
||||
crypto_skcipher_set_flags(ctfm, CRYPTO_TFM_REQ_WEAK_KEY);
|
||||
res = crypto_skcipher_setkey(ctfm, raw_key, fscrypt_key_size(mode));
|
||||
res = crypto_skcipher_setkey(ctfm, raw_key, keysize);
|
||||
if (res)
|
||||
goto out;
|
||||
|
||||
memzero_explicit(raw_key, sizeof(raw_key));
|
||||
kzfree(raw_key);
|
||||
raw_key = NULL;
|
||||
if (cmpxchg(&inode->i_crypt_info, NULL, crypt_info) != NULL) {
|
||||
put_crypt_info(crypt_info);
|
||||
goto retry;
|
||||
|
@ -268,7 +297,7 @@ out:
|
|||
if (res == -ENOKEY)
|
||||
res = 0;
|
||||
put_crypt_info(crypt_info);
|
||||
memzero_explicit(raw_key, sizeof(raw_key));
|
||||
kzfree(raw_key);
|
||||
return res;
|
||||
}
|
||||
|
||||
|
|
|
@ -109,6 +109,8 @@ int fscrypt_process_policy(struct file *filp,
|
|||
if (ret)
|
||||
return ret;
|
||||
|
||||
inode_lock(inode);
|
||||
|
||||
if (!inode_has_encryption_context(inode)) {
|
||||
if (!S_ISDIR(inode->i_mode))
|
||||
ret = -EINVAL;
|
||||
|
@ -127,6 +129,8 @@ int fscrypt_process_policy(struct file *filp,
|
|||
ret = -EINVAL;
|
||||
}
|
||||
|
||||
inode_unlock(inode);
|
||||
|
||||
mnt_drop_write_file(filp);
|
||||
return ret;
|
||||
}
|
||||
|
|
|
@ -814,12 +814,12 @@ bool f2fs_fill_dentries(struct dir_context *ctx, struct f2fs_dentry_ptr *d,
|
|||
|
||||
if (f2fs_encrypted_inode(d->inode)) {
|
||||
int save_len = fstr->len;
|
||||
int ret;
|
||||
int err;
|
||||
|
||||
ret = fscrypt_fname_disk_to_usr(d->inode,
|
||||
err = fscrypt_fname_disk_to_usr(d->inode,
|
||||
(u32)de->hash_code, 0,
|
||||
&de_name, fstr);
|
||||
if (ret < 0)
|
||||
if (err)
|
||||
return true;
|
||||
|
||||
de_name = *fstr;
|
||||
|
|
|
@ -451,7 +451,7 @@ static int f2fs_symlink(struct inode *dir, struct dentry *dentry,
|
|||
ostr.name = sd->encrypted_path;
|
||||
ostr.len = disk_link.len;
|
||||
err = fscrypt_fname_usr_to_disk(inode, &istr, &ostr);
|
||||
if (err < 0)
|
||||
if (err)
|
||||
goto err_out;
|
||||
|
||||
sd->len = cpu_to_le16(ostr.len);
|
||||
|
@ -1047,7 +1047,7 @@ static const char *f2fs_encrypted_follow_link(struct dentry *dentry, void **cook
|
|||
goto errout;
|
||||
|
||||
res = fscrypt_fname_disk_to_usr(inode, 0, 0, &cstr, &pstr);
|
||||
if (res < 0)
|
||||
if (res)
|
||||
goto errout;
|
||||
|
||||
/* this is broken symlink case */
|
||||
|
@ -1059,7 +1059,7 @@ static const char *f2fs_encrypted_follow_link(struct dentry *dentry, void **cook
|
|||
paddr = pstr.name;
|
||||
|
||||
/* Null-terminate the name */
|
||||
paddr[res] = '\0';
|
||||
paddr[pstr.len] = '\0';
|
||||
|
||||
put_page(cpage);
|
||||
return *cookie = paddr;
|
||||
|
|
|
@ -111,23 +111,6 @@ struct fscrypt_completion_result {
|
|||
struct fscrypt_completion_result ecr = { \
|
||||
COMPLETION_INITIALIZER((ecr).completion), 0 }
|
||||
|
||||
static inline int fscrypt_key_size(int mode)
|
||||
{
|
||||
switch (mode) {
|
||||
case FS_ENCRYPTION_MODE_AES_256_XTS:
|
||||
return FS_AES_256_XTS_KEY_SIZE;
|
||||
case FS_ENCRYPTION_MODE_AES_256_GCM:
|
||||
return FS_AES_256_GCM_KEY_SIZE;
|
||||
case FS_ENCRYPTION_MODE_AES_256_CBC:
|
||||
return FS_AES_256_CBC_KEY_SIZE;
|
||||
case FS_ENCRYPTION_MODE_AES_256_CTS:
|
||||
return FS_AES_256_CTS_KEY_SIZE;
|
||||
default:
|
||||
BUG();
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
#define FS_FNAME_NUM_SCATTER_ENTRIES 4
|
||||
#define FS_CRYPTO_BLOCK_SIZE 16
|
||||
#define FS_FNAME_CRYPTO_DIGEST_SIZE 32
|
||||
|
@ -202,13 +185,6 @@ static inline bool fscrypt_valid_filenames_enc_mode(u32 mode)
|
|||
return (mode == FS_ENCRYPTION_MODE_AES_256_CTS);
|
||||
}
|
||||
|
||||
static inline u32 fscrypt_validate_encryption_key_size(u32 mode, u32 size)
|
||||
{
|
||||
if (size == fscrypt_key_size(mode))
|
||||
return size;
|
||||
return 0;
|
||||
}
|
||||
|
||||
static inline bool fscrypt_is_dot_dotdot(const struct qstr *str)
|
||||
{
|
||||
if (str->len == 1 && str->name[0] == '.')
|
||||
|
|
Loading…
Add table
Reference in a new issue