Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 27211598 authored by Andrey Markovytch's avatar Andrey Markovytch
Browse files

eCryptfs: fixed some major bugs



1. Fixed bug which didn't allow several threads to work simultaneously
on files in eCryptfs mounted folder

2. Fixed bug where PFK close callback was invoked multiple times when
files was opened and closed multiple times. Now it is invoked just once
when files is closed for the last time

Change-Id: Iaa3ada03500e5a12752918b5d2bb4a852ddca5f0
Signed-off-by: default avatarAndrey Markovytch <andreym@codeaurora.org>
parent 1a45a811
Loading
Loading
Loading
Loading
+6 −2
Original line number Diff line number Diff line
@@ -471,6 +471,8 @@ out:
static void init_ecryption_parameters(bool *hw_crypt, bool *cipher_supported,
				struct ecryptfs_crypt_stat *crypt_stat)
{
	unsigned char final[2*ECRYPTFS_MAX_CIPHER_NAME_SIZE+1];

	if (!hw_crypt || !cipher_supported)
		return;

@@ -481,7 +483,7 @@ static void init_ecryption_parameters(bool *hw_crypt, bool *cipher_supported,
		*cipher_supported =
			get_events()->is_cipher_supported_cb(
				ecryptfs_get_full_cipher(crypt_stat->cipher,
				crypt_stat->cipher_mode));
				crypt_stat->cipher_mode, final, sizeof(final)));
		if (*cipher_supported) {
			/**
			 * we should apply external algorythm
@@ -806,10 +808,12 @@ static void ecryptfs_generate_new_key(struct ecryptfs_crypt_stat *crypt_stat)
static int ecryptfs_generate_new_salt(struct ecryptfs_crypt_stat *crypt_stat)
{
	size_t salt_size = 0;
	unsigned char final[2*ECRYPTFS_MAX_CIPHER_NAME_SIZE+1];

	salt_size = ecryptfs_get_salt_size_for_cipher(
			ecryptfs_get_full_cipher(crypt_stat->cipher,
						 crypt_stat->cipher_mode));
						 crypt_stat->cipher_mode,
						 final, sizeof(final)));

	if (0 == salt_size)
		return 0;
+6 −5
Original line number Diff line number Diff line
@@ -535,16 +535,17 @@ ecryptfs_dentry_to_lower_path(struct dentry *dentry)
 * concatenates them to create a new string of
 * <cipher>_<mode> format.
 */
static inline char *ecryptfs_get_full_cipher(
	char *cipher, char *mode)
static inline unsigned char *ecryptfs_get_full_cipher(
	unsigned char *cipher, unsigned char *mode,
	unsigned char *final, size_t final_size)
{
	static char final[2*ECRYPTFS_MAX_CIPHER_NAME_SIZE+1];
	memset(final, 0, final_size);

	if (strlen(mode) > 0) {
		memset(final, 0, sizeof(final));
		snprintf(final, sizeof(final), "%s_%s", cipher, mode);
		snprintf(final, final_size, "%s_%s", cipher, mode);
		return final;
	}

	return cipher;
}

+6 −3
Original line number Diff line number Diff line
@@ -176,6 +176,7 @@ size_t ecryptfs_get_key_size(void *data)
size_t ecryptfs_get_salt_size(void *data)
{
	struct ecryptfs_crypt_stat *stat = NULL;
	unsigned char final[2*ECRYPTFS_MAX_CIPHER_NAME_SIZE+1];

	if (!data) {
		ecryptfs_printk(KERN_ERR,
@@ -186,7 +187,8 @@ size_t ecryptfs_get_salt_size(void *data)
	stat = (struct ecryptfs_crypt_stat *)data;
	return ecryptfs_get_salt_size_for_cipher(
			ecryptfs_get_full_cipher(stat->cipher,
						 stat->cipher_mode));
						 stat->cipher_mode,
						 final, sizeof(final)));

}

@@ -196,7 +198,7 @@ size_t ecryptfs_get_salt_size(void *data)
 */
const unsigned char *ecryptfs_get_cipher(void *data)
{

	unsigned char final[2*ECRYPTFS_MAX_CIPHER_NAME_SIZE+1];
	struct ecryptfs_crypt_stat *stat = NULL;

	if (!data) {
@@ -205,7 +207,8 @@ const unsigned char *ecryptfs_get_cipher(void *data)
		return NULL;
	}
	stat = (struct ecryptfs_crypt_stat *)data;
	return ecryptfs_get_full_cipher(stat->cipher, stat->cipher_mode);
	return ecryptfs_get_full_cipher(stat->cipher, stat->cipher_mode,
			final, sizeof(final));
}

/**
+0 −3
Original line number Diff line number Diff line
@@ -298,9 +298,6 @@ static int ecryptfs_release(struct inode *inode, struct file *file)
	if (ret)
		pr_err("failed to sync file ret = %d.\n", ret);

	if (get_events() && get_events()->release_cb)
		get_events()->release_cb(ecryptfs_inode_to_lower(inode));

	ecryptfs_put_lower_file(inode);
	kmem_cache_free(ecryptfs_file_info_cache,
			ecryptfs_file_to_private(file));
+12 −5
Original line number Diff line number Diff line
@@ -1695,6 +1695,8 @@ static int
decrypt_passphrase_encrypted_session_key(struct ecryptfs_auth_tok *auth_tok,
					 struct ecryptfs_crypt_stat *crypt_stat)
{

	unsigned char final[2*ECRYPTFS_MAX_CIPHER_NAME_SIZE+1];
	struct scatterlist dst_sg[2];
	struct scatterlist src_sg[2];
	struct mutex *tfm_mutex;
@@ -1775,7 +1777,8 @@ decrypt_passphrase_encrypted_session_key(struct ecryptfs_auth_tok *auth_tok,
				  crypt_stat->key_size);
		ecryptfs_dump_salt_hex(crypt_stat->key, crypt_stat->key_size,
				ecryptfs_get_full_cipher(crypt_stat->cipher,
					crypt_stat->cipher_mode));
					crypt_stat->cipher_mode,
					final, sizeof(final)));
	}
out:
	return rc;
@@ -2012,12 +2015,14 @@ pki_encrypt_session_key(struct key *auth_tok_key,
	size_t payload_len = 0;
	struct ecryptfs_message *msg;
	int rc;
	unsigned char final[2*ECRYPTFS_MAX_CIPHER_NAME_SIZE+1];

	rc = write_tag_66_packet(auth_tok->token.private_key.signature,
			ecryptfs_code_for_cipher_string(
					ecryptfs_get_full_cipher(
						crypt_stat->cipher,
						crypt_stat->cipher_mode),
						crypt_stat->cipher_mode,
						final, sizeof(final)),
					ecryptfs_get_key_size_to_enc_data(
						crypt_stat)),
					crypt_stat, &payload, &payload_len);
@@ -2232,6 +2237,7 @@ write_tag_3_packet(char *dest, size_t *remaining_bytes,
	u8 cipher_code;
	size_t packet_size_length;
	size_t max_packet_size;
	unsigned char final[2*ECRYPTFS_MAX_CIPHER_NAME_SIZE+1];
	struct ecryptfs_mount_crypt_stat *mount_crypt_stat =
		crypt_stat->mount_crypt_stat;
	struct blkcipher_desc desc = {
@@ -2343,7 +2349,8 @@ write_tag_3_packet(char *dest, size_t *remaining_bytes,
	ecryptfs_printk(KERN_DEBUG, "Encrypting [%zd] bytes of the salt key\n",
		ecryptfs_get_salt_size_for_cipher(
			ecryptfs_get_full_cipher(crypt_stat->cipher,
				crypt_stat->cipher_mode)));
				crypt_stat->cipher_mode,
				final, sizeof(final))));
	rc = crypto_blkcipher_encrypt(&desc, dst_sg, src_sg,
				      (*key_rec).enc_key_size);
	mutex_unlock(tfm_mutex);
@@ -2399,7 +2406,7 @@ encrypted_session_key_set:
	 * specified with strings */
	cipher_code = ecryptfs_code_for_cipher_string(
			ecryptfs_get_full_cipher(crypt_stat->cipher,
				crypt_stat->cipher_mode),
				crypt_stat->cipher_mode, final, sizeof(final)),
			crypt_stat->key_size);
	if (cipher_code == 0) {
		ecryptfs_printk(KERN_WARNING, "Unable to generate code for "
Loading