{
unsigned long flags;
- if (ctx->bounce_page) {
+ if (ctx->flags & F2FS_WRITE_PATH_FL && ctx->w.bounce_page) {
if (ctx->flags & F2FS_BOUNCE_PAGE_REQUIRES_FREE_ENCRYPT_FL)
- __free_page(ctx->bounce_page);
+ __free_page(ctx->w.bounce_page);
else
- mempool_free(ctx->bounce_page, f2fs_bounce_page_pool);
- ctx->bounce_page = NULL;
+ mempool_free(ctx->w.bounce_page, f2fs_bounce_page_pool);
+ ctx->w.bounce_page = NULL;
}
- ctx->control_page = NULL;
+ ctx->w.control_page = NULL;
if (ctx->flags & F2FS_CTX_REQUIRES_FREE_ENCRYPT_FL) {
if (ctx->tfm)
crypto_free_tfm(ctx->tfm);
} else {
ctx->flags &= ~F2FS_CTX_REQUIRES_FREE_ENCRYPT_FL;
}
+ ctx->flags &= ~F2FS_WRITE_PATH_FL;
/*
* Allocate a new Crypto API context if we don't already have
}
BUG_ON(ci->ci_size != f2fs_encryption_key_size(ci->ci_data_mode));
- /*
- * There shouldn't be a bounce page attached to the crypto
- * context at this point.
- */
- BUG_ON(ctx->bounce_page);
-
out:
if (res) {
if (!IS_ERR_OR_NULL(ctx))
static void completion_pages(struct work_struct *work)
{
struct f2fs_crypto_ctx *ctx =
- container_of(work, struct f2fs_crypto_ctx, work);
- struct bio *bio = ctx->bio;
+ container_of(work, struct f2fs_crypto_ctx, r.work);
+ struct bio *bio = ctx->r.bio;
struct bio_vec *bv;
int i;
void f2fs_end_io_crypto_work(struct f2fs_crypto_ctx *ctx, struct bio *bio)
{
- INIT_WORK(&ctx->work, completion_pages);
- ctx->bio = bio;
- queue_work(f2fs_read_workqueue, &ctx->work);
+ INIT_WORK(&ctx->r.work, completion_pages);
+ ctx->r.bio = bio;
+ queue_work(f2fs_read_workqueue, &ctx->r.work);
}
/**
struct f2fs_crypto_ctx *pos, *n;
list_for_each_entry_safe(pos, n, &f2fs_free_crypto_ctxs, free_list) {
- if (pos->bounce_page) {
+ if (pos->w.bounce_page) {
if (pos->flags &
F2FS_BOUNCE_PAGE_REQUIRES_FREE_ENCRYPT_FL)
- __free_page(pos->bounce_page);
+ __free_page(pos->w.bounce_page);
else
- mempool_free(pos->bounce_page,
+ mempool_free(pos->w.bounce_page,
f2fs_bounce_page_pool);
}
if (pos->tfm)
ctx = (struct f2fs_crypto_ctx *)page_private(bounce_page);
/* restore control page */
- *page = ctx->control_page;
+ *page = ctx->w.control_page;
f2fs_restore_control_page(bounce_page);
}
} else {
ctx->flags |= F2FS_BOUNCE_PAGE_REQUIRES_FREE_ENCRYPT_FL;
}
- ctx->bounce_page = ciphertext_page;
- ctx->control_page = plaintext_page;
+ ctx->flags |= F2FS_WRITE_PATH_FL;
+ ctx->w.bounce_page = ciphertext_page;
+ ctx->w.control_page = plaintext_page;
err = f2fs_page_crypto(ctx, inode, F2FS_ENCRYPT, plaintext_page->index,
plaintext_page, ciphertext_page);
if (err) {
#define F2FS_CTX_REQUIRES_FREE_ENCRYPT_FL 0x00000001
#define F2FS_BOUNCE_PAGE_REQUIRES_FREE_ENCRYPT_FL 0x00000002
+#define F2FS_WRITE_PATH_FL 0x00000004
struct f2fs_crypto_ctx {
struct crypto_tfm *tfm; /* Crypto API context */
- struct page *bounce_page; /* Ciphertext page on write path */
- struct page *control_page; /* Original page on write path */
- struct bio *bio; /* The bio for this context */
- struct work_struct work; /* Work queue for read complete path */
- struct list_head free_list; /* Free list */
- int flags; /* Flags */
- int mode; /* Encryption mode for tfm */
+ union {
+ struct {
+ struct page *bounce_page; /* Ciphertext page */
+ struct page *control_page; /* Original page */
+ } w;
+ struct {
+ struct bio *bio;
+ struct work_struct work;
+ } r;
+ struct list_head free_list; /* Free list */
+ };
+ char flags; /* Flags */
+ char mode; /* Encryption mode for tfm */
};
struct f2fs_completion_result {