diff options
author | Tyler Hicks <tyhicks@canonical.com> | 2013-04-06 02:26:22 -0400 |
---|---|---|
committer | Tyler Hicks <tyhicks@canonical.com> | 2013-06-07 20:28:26 -0400 |
commit | 00a699400a707953368e970b37bb8765fdb08015 (patch) | |
tree | 5f0d915de16b024814d17fb1cd941db855b3bd99 /fs/ecryptfs/crypto.c | |
parent | 9c6043f41222b448a314b0b8370f33b579f777ea (diff) |
eCryptfs: Combine encrypt_scatterlist() and decrypt_scatterlist()
These two functions are identical except for a debug printk and whether
they call crypto_ablkcipher_encrypt() or crypto_ablkcipher_decrypt(), so
they can be safely merged if the caller can indicate if encryption or
decryption should occur.
The debug printk is useless so it is removed.
Two new #define's are created to indicate if an ENCRYPT or DECRYPT
operation is desired.
Signed-off-by: Tyler Hicks <tyhicks@canonical.com>
Diffstat (limited to 'fs/ecryptfs/crypto.c')
-rw-r--r-- | fs/ecryptfs/crypto.c | 106 |
1 files changed, 20 insertions, 86 deletions
diff --git a/fs/ecryptfs/crypto.c b/fs/ecryptfs/crypto.c index 35b409bda841..fb54a0182f2e 100644 --- a/fs/ecryptfs/crypto.c +++ b/fs/ecryptfs/crypto.c | |||
@@ -37,6 +37,9 @@ | |||
37 | #include <asm/unaligned.h> | 37 | #include <asm/unaligned.h> |
38 | #include "ecryptfs_kernel.h" | 38 | #include "ecryptfs_kernel.h" |
39 | 39 | ||
40 | #define DECRYPT 0 | ||
41 | #define ENCRYPT 1 | ||
42 | |||
40 | static int | 43 | static int |
41 | ecryptfs_decrypt_page_offset(struct ecryptfs_crypt_stat *crypt_stat, | 44 | ecryptfs_decrypt_page_offset(struct ecryptfs_crypt_stat *crypt_stat, |
42 | struct page *dst_page, struct page *src_page, | 45 | struct page *dst_page, struct page *src_page, |
@@ -334,19 +337,20 @@ static void extent_crypt_complete(struct crypto_async_request *req, int rc) | |||
334 | } | 337 | } |
335 | 338 | ||
336 | /** | 339 | /** |
337 | * encrypt_scatterlist | 340 | * crypt_scatterlist |
338 | * @crypt_stat: Pointer to the crypt_stat struct to initialize. | 341 | * @crypt_stat: Pointer to the crypt_stat struct to initialize. |
339 | * @dest_sg: Destination of encrypted data | 342 | * @dest_sg: Destination of the data after performing the crypto operation |
340 | * @src_sg: Data to be encrypted | 343 | * @src_sg: Data to be encrypted or decrypted |
341 | * @size: Length of data to be encrypted | 344 | * @size: Length of data |
342 | * @iv: iv to use during encryption | 345 | * @iv: IV to use |
346 | * @op: ENCRYPT or DECRYPT to indicate the desired operation | ||
343 | * | 347 | * |
344 | * Returns the number of bytes encrypted; negative value on error | 348 | * Returns the number of bytes encrypted or decrypted; negative value on error |
345 | */ | 349 | */ |
346 | static int encrypt_scatterlist(struct ecryptfs_crypt_stat *crypt_stat, | 350 | static int crypt_scatterlist(struct ecryptfs_crypt_stat *crypt_stat, |
347 | struct scatterlist *dest_sg, | 351 | struct scatterlist *dest_sg, |
348 | struct scatterlist *src_sg, int size, | 352 | struct scatterlist *src_sg, int size, |
349 | unsigned char *iv) | 353 | unsigned char *iv, int op) |
350 | { | 354 | { |
351 | struct ablkcipher_request *req = NULL; | 355 | struct ablkcipher_request *req = NULL; |
352 | struct extent_crypt_result ecr; | 356 | struct extent_crypt_result ecr; |
@@ -389,9 +393,9 @@ static int encrypt_scatterlist(struct ecryptfs_crypt_stat *crypt_stat, | |||
389 | crypt_stat->flags |= ECRYPTFS_KEY_SET; | 393 | crypt_stat->flags |= ECRYPTFS_KEY_SET; |
390 | } | 394 | } |
391 | mutex_unlock(&crypt_stat->cs_tfm_mutex); | 395 | mutex_unlock(&crypt_stat->cs_tfm_mutex); |
392 | ecryptfs_printk(KERN_DEBUG, "Encrypting [%d] bytes.\n", size); | ||
393 | ablkcipher_request_set_crypt(req, src_sg, dest_sg, size, iv); | 396 | ablkcipher_request_set_crypt(req, src_sg, dest_sg, size, iv); |
394 | rc = crypto_ablkcipher_encrypt(req); | 397 | rc = op == ENCRYPT ? crypto_ablkcipher_encrypt(req) : |
398 | crypto_ablkcipher_decrypt(req); | ||
395 | if (rc == -EINPROGRESS || rc == -EBUSY) { | 399 | if (rc == -EINPROGRESS || rc == -EBUSY) { |
396 | struct extent_crypt_result *ecr = req->base.data; | 400 | struct extent_crypt_result *ecr = req->base.data; |
397 | 401 | ||
@@ -624,78 +628,6 @@ out: | |||
624 | } | 628 | } |
625 | 629 | ||
626 | /** | 630 | /** |
627 | * decrypt_scatterlist | ||
628 | * @crypt_stat: Cryptographic context | ||
629 | * @dest_sg: The destination scatterlist to decrypt into | ||
630 | * @src_sg: The source scatterlist to decrypt from | ||
631 | * @size: The number of bytes to decrypt | ||
632 | * @iv: The initialization vector to use for the decryption | ||
633 | * | ||
634 | * Returns the number of bytes decrypted; negative value on error | ||
635 | */ | ||
636 | static int decrypt_scatterlist(struct ecryptfs_crypt_stat *crypt_stat, | ||
637 | struct scatterlist *dest_sg, | ||
638 | struct scatterlist *src_sg, int size, | ||
639 | unsigned char *iv) | ||
640 | { | ||
641 | struct ablkcipher_request *req = NULL; | ||
642 | struct extent_crypt_result ecr; | ||
643 | int rc = 0; | ||
644 | |||
645 | BUG_ON(!crypt_stat || !crypt_stat->tfm | ||
646 | || !(crypt_stat->flags & ECRYPTFS_STRUCT_INITIALIZED)); | ||
647 | if (unlikely(ecryptfs_verbosity > 0)) { | ||
648 | ecryptfs_printk(KERN_DEBUG, "Key size [%zd]; key:\n", | ||
649 | crypt_stat->key_size); | ||
650 | ecryptfs_dump_hex(crypt_stat->key, | ||
651 | crypt_stat->key_size); | ||
652 | } | ||
653 | |||
654 | init_completion(&ecr.completion); | ||
655 | |||
656 | mutex_lock(&crypt_stat->cs_tfm_mutex); | ||
657 | req = ablkcipher_request_alloc(crypt_stat->tfm, GFP_NOFS); | ||
658 | if (!req) { | ||
659 | mutex_unlock(&crypt_stat->cs_tfm_mutex); | ||
660 | rc = -ENOMEM; | ||
661 | goto out; | ||
662 | } | ||
663 | |||
664 | ablkcipher_request_set_callback(req, | ||
665 | CRYPTO_TFM_REQ_MAY_BACKLOG | CRYPTO_TFM_REQ_MAY_SLEEP, | ||
666 | extent_crypt_complete, &ecr); | ||
667 | /* Consider doing this once, when the file is opened */ | ||
668 | if (!(crypt_stat->flags & ECRYPTFS_KEY_SET)) { | ||
669 | rc = crypto_ablkcipher_setkey(crypt_stat->tfm, crypt_stat->key, | ||
670 | crypt_stat->key_size); | ||
671 | if (rc) { | ||
672 | ecryptfs_printk(KERN_ERR, | ||
673 | "Error setting key; rc = [%d]\n", | ||
674 | rc); | ||
675 | mutex_unlock(&crypt_stat->cs_tfm_mutex); | ||
676 | rc = -EINVAL; | ||
677 | goto out; | ||
678 | } | ||
679 | crypt_stat->flags |= ECRYPTFS_KEY_SET; | ||
680 | } | ||
681 | mutex_unlock(&crypt_stat->cs_tfm_mutex); | ||
682 | ecryptfs_printk(KERN_DEBUG, "Decrypting [%d] bytes.\n", size); | ||
683 | ablkcipher_request_set_crypt(req, src_sg, dest_sg, size, iv); | ||
684 | rc = crypto_ablkcipher_decrypt(req); | ||
685 | if (rc == -EINPROGRESS || rc == -EBUSY) { | ||
686 | struct extent_crypt_result *ecr = req->base.data; | ||
687 | |||
688 | wait_for_completion(&ecr->completion); | ||
689 | rc = ecr->rc; | ||
690 | INIT_COMPLETION(ecr->completion); | ||
691 | } | ||
692 | out: | ||
693 | ablkcipher_request_free(req); | ||
694 | return rc; | ||
695 | |||
696 | } | ||
697 | |||
698 | /** | ||
699 | * ecryptfs_encrypt_page_offset | 631 | * ecryptfs_encrypt_page_offset |
700 | * @crypt_stat: The cryptographic context | 632 | * @crypt_stat: The cryptographic context |
701 | * @dst_page: The page to encrypt into | 633 | * @dst_page: The page to encrypt into |
@@ -718,7 +650,8 @@ ecryptfs_encrypt_page_offset(struct ecryptfs_crypt_stat *crypt_stat, | |||
718 | 650 | ||
719 | sg_set_page(&src_sg, src_page, size, offset); | 651 | sg_set_page(&src_sg, src_page, size, offset); |
720 | sg_set_page(&dst_sg, dst_page, size, offset); | 652 | sg_set_page(&dst_sg, dst_page, size, offset); |
721 | return encrypt_scatterlist(crypt_stat, &dst_sg, &src_sg, size, iv); | 653 | return crypt_scatterlist(crypt_stat, &dst_sg, &src_sg, |
654 | size, iv, ENCRYPT); | ||
722 | } | 655 | } |
723 | 656 | ||
724 | /** | 657 | /** |
@@ -745,7 +678,8 @@ ecryptfs_decrypt_page_offset(struct ecryptfs_crypt_stat *crypt_stat, | |||
745 | sg_init_table(&dst_sg, 1); | 678 | sg_init_table(&dst_sg, 1); |
746 | sg_set_page(&dst_sg, dst_page, size, offset); | 679 | sg_set_page(&dst_sg, dst_page, size, offset); |
747 | 680 | ||
748 | return decrypt_scatterlist(crypt_stat, &dst_sg, &src_sg, size, iv); | 681 | return crypt_scatterlist(crypt_stat, &dst_sg, &src_sg, |
682 | size, iv, DECRYPT); | ||
749 | } | 683 | } |
750 | 684 | ||
751 | #define ECRYPTFS_MAX_SCATTERLIST_LEN 4 | 685 | #define ECRYPTFS_MAX_SCATTERLIST_LEN 4 |