linux-btrfs.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
From: Josef Bacik <josef@toxicpanda.com>
To: linux-btrfs@vger.kernel.org, kernel-team@fb.com
Subject: [PATCH v5 40/52] btrfs: add test_dummy_encryption support
Date: Wed, 24 Jan 2024 12:19:02 -0500	[thread overview]
Message-ID: <77449ee5a882db2945429946c74ea7e796122328.1706116485.git.josef@toxicpanda.com> (raw)
In-Reply-To: <cover.1706116485.git.josef@toxicpanda.com>

In order to enable more thorough testing of fscrypt enable the
test_dummy_encryption mount option.  This is used by fscrypt users to
easily enable fscrypt on the file system for testing without needing to
do the key setup and everything.

The only deviation from other file systems we make is we only support
the fsparam_flag version of this mount option, as it defaults to v2.  We
don't want to have to bother with rejecting v1 related mount options.

Signed-off-by: Josef Bacik <josef@toxicpanda.com>
---
 fs/btrfs/disk-io.c |  1 +
 fs/btrfs/fs.h      |  3 +++
 fs/btrfs/fscrypt.c |  6 +++++
 fs/btrfs/super.c   | 64 ++++++++++++++++++++++++++++++++++++++++++++++
 4 files changed, 74 insertions(+)

diff --git a/fs/btrfs/disk-io.c b/fs/btrfs/disk-io.c
index 51c6127508af..70e33df8f975 100644
--- a/fs/btrfs/disk-io.c
+++ b/fs/btrfs/disk-io.c
@@ -1290,6 +1290,7 @@ void btrfs_free_fs_info(struct btrfs_fs_info *fs_info)
 	kfree(fs_info->super_copy);
 	kfree(fs_info->super_for_commit);
 	kfree(fs_info->subpage_info);
+	fscrypt_free_dummy_policy(&fs_info->dummy_enc_policy);
 	kvfree(fs_info);
 }
 
diff --git a/fs/btrfs/fs.h b/fs/btrfs/fs.h
index 1340e71d026c..74752204f3ab 100644
--- a/fs/btrfs/fs.h
+++ b/fs/btrfs/fs.h
@@ -7,6 +7,7 @@
 #include <linux/fs.h>
 #include <linux/btrfs_tree.h>
 #include <linux/sizes.h>
+#include <linux/fscrypt.h>
 #include "extent-io-tree.h"
 #include "extent_map.h"
 #include "async-thread.h"
@@ -189,6 +190,7 @@ enum {
 	BTRFS_MOUNT_IGNOREDATACSUMS		= (1UL << 28),
 	BTRFS_MOUNT_NODISCARD			= (1UL << 29),
 	BTRFS_MOUNT_NOSPACECACHE		= (1UL << 30),
+	BTRFS_MOUNT_TEST_DUMMY_ENCRYPTION	= (1UL << 31),
 };
 
 /*
@@ -828,6 +830,7 @@ struct btrfs_fs_info {
 	spinlock_t eb_leak_lock;
 	struct list_head allocated_ebs;
 #endif
+	struct fscrypt_dummy_policy dummy_enc_policy;
 };
 
 static inline u64 btrfs_get_fs_generation(const struct btrfs_fs_info *fs_info)
diff --git a/fs/btrfs/fscrypt.c b/fs/btrfs/fscrypt.c
index 560243d732e7..6a6ecf4a49e2 100644
--- a/fs/btrfs/fscrypt.c
+++ b/fs/btrfs/fscrypt.c
@@ -243,6 +243,11 @@ static blk_status_t btrfs_process_encrypted_bio(struct bio *orig_bio,
 	return btrfs_csum_one_bio(bbio, enc_bio);
 }
 
+static const union fscrypt_policy *btrfs_get_dummy_policy(struct super_block *sb)
+{
+	return btrfs_sb(sb)->dummy_enc_policy.policy;
+}
+
 int btrfs_fscrypt_load_extent_info(struct btrfs_inode *inode,
 				   struct extent_map *em,
 				   struct btrfs_fscrypt_ctx *ctx)
@@ -367,4 +372,5 @@ const struct fscrypt_operations btrfs_fscrypt_ops = {
 	.empty_dir = btrfs_fscrypt_empty_dir,
 	.get_devices = btrfs_fscrypt_get_devices,
 	.process_bio = btrfs_process_encrypted_bio,
+	.get_dummy_policy = btrfs_get_dummy_policy,
 };
diff --git a/fs/btrfs/super.c b/fs/btrfs/super.c
index 28fbe366717e..861fbf48456a 100644
--- a/fs/btrfs/super.c
+++ b/fs/btrfs/super.c
@@ -88,6 +88,7 @@ struct btrfs_fs_context {
 	unsigned long compress_type:4;
 	unsigned int compress_level;
 	refcount_t refs;
+	struct fscrypt_dummy_policy dummy_enc_policy;
 };
 
 enum {
@@ -122,6 +123,7 @@ enum {
 	Opt_thread_pool,
 	Opt_treelog,
 	Opt_user_subvol_rm_allowed,
+	Opt_test_dummy_encryption,
 
 	/* Rescue options */
 	Opt_rescue,
@@ -253,6 +255,10 @@ static const struct fs_parameter_spec btrfs_fs_parameters[] = {
 	fsparam_flag_no("enospc_debug", Opt_enospc_debug),
 #ifdef CONFIG_BTRFS_DEBUG
 	fsparam_enum("fragment", Opt_fragment, btrfs_parameter_fragment),
+
+	fsparam_flag("test_dummy_encryption", Opt_test_dummy_encryption),
+	fsparam_string("test_dummy_encryption", Opt_test_dummy_encryption),
+
 #endif
 #ifdef CONFIG_BTRFS_FS_REF_VERIFY
 	fsparam_flag("ref_verify", Opt_ref_verify),
@@ -271,6 +277,7 @@ static int btrfs_parse_param(struct fs_context *fc, struct fs_parameter *param)
 	struct btrfs_fs_context *ctx = fc->fs_private;
 	struct fs_parse_result result;
 	int opt;
+	int ret;
 
 	opt = fs_parse(fc, btrfs_fs_parameters, param, &result);
 	if (opt < 0)
@@ -598,6 +605,22 @@ static int btrfs_parse_param(struct fs_context *fc, struct fs_parameter *param)
 			return -EINVAL;
 		}
 		break;
+	case Opt_test_dummy_encryption:
+		/*
+		 * We only support v2, so reject any v1 policies.
+		 */
+		if (param->type == fs_value_is_string && *param->string &&
+		    !strcmp(param->string, "v1")) {
+			btrfs_info(NULL, "v1 encryption isn't supported");
+			return -EINVAL;
+		}
+
+		btrfs_set_opt(ctx->mount_opt, TEST_DUMMY_ENCRYPTION);
+		ret = fscrypt_parse_test_dummy_encryption(param,
+							  &ctx->dummy_enc_policy);
+		if (ret)
+			return ret;
+		break;
 #endif
 #ifdef CONFIG_BTRFS_FS_REF_VERIFY
 	case Opt_ref_verify:
@@ -945,6 +968,9 @@ static int btrfs_fill_super(struct super_block *sb,
 		return err;
 	}
 
+	if (fscrypt_is_dummy_policy_set(&fs_info->dummy_enc_policy))
+		btrfs_set_fs_incompat(fs_info, ENCRYPT);
+
 	inode = btrfs_iget(sb, BTRFS_FIRST_FREE_OBJECTID, fs_info->fs_root);
 	if (IS_ERR(inode)) {
 		err = PTR_ERR(inode);
@@ -1101,6 +1127,9 @@ static int btrfs_show_options(struct seq_file *seq, struct dentry *dentry)
 #endif
 	if (btrfs_test_opt(info, REF_VERIFY))
 		seq_puts(seq, ",ref_verify");
+	if (btrfs_test_opt(info, TEST_DUMMY_ENCRYPTION))
+		fscrypt_show_test_dummy_encryption(seq, ',', dentry->d_sb);
+
 	seq_printf(seq, ",subvolid=%llu",
 		  BTRFS_I(d_inode(dentry))->root->root_key.objectid);
 	subvol_name = btrfs_get_subvol_name_from_objectid(info,
@@ -1368,6 +1397,18 @@ static void btrfs_ctx_to_info(struct btrfs_fs_info *fs_info, struct btrfs_fs_con
 	fs_info->mount_opt = ctx->mount_opt;
 	fs_info->compress_type = ctx->compress_type;
 	fs_info->compress_level = ctx->compress_level;
+
+	/*
+	 * If there's nothing set, or if the fs_info already has one set, don't
+	 * do anything.  If the fs_info is set we'll free the dummy one when we
+	 * free the ctx.
+	 */
+	if (!fscrypt_is_dummy_policy_set(&ctx->dummy_enc_policy) ||
+	    fscrypt_is_dummy_policy_set(&fs_info->dummy_enc_policy))
+		return;
+
+	fs_info->dummy_enc_policy = ctx->dummy_enc_policy;
+	memset(&ctx->dummy_enc_policy, 0, sizeof(ctx->dummy_enc_policy));
 }
 
 static void btrfs_info_to_ctx(struct btrfs_fs_info *fs_info, struct btrfs_fs_context *ctx)
@@ -1419,6 +1460,7 @@ static void btrfs_emit_options(struct btrfs_fs_info *info,
 	btrfs_info_if_set(info, old, USEBACKUPROOT, "trying to use backup root at mount time");
 	btrfs_info_if_set(info, old, IGNOREBADROOTS, "ignoring bad roots");
 	btrfs_info_if_set(info, old, IGNOREDATACSUMS, "ignoring data csums");
+	btrfs_info_if_set(info, old, TEST_DUMMY_ENCRYPTION, "test dummy encryption mode enabled");
 
 	btrfs_info_if_unset(info, old, NODATACOW, "setting datacow");
 	btrfs_info_if_unset(info, old, SSD, "not using ssd optimizations");
@@ -1448,6 +1490,23 @@ static void btrfs_emit_options(struct btrfs_fs_info *info,
 		btrfs_info(info, "max_inline set to %llu", info->max_inline);
 }
 
+static bool btrfs_check_test_dummy_encryption(struct fs_context *fc)
+{
+	struct btrfs_fs_context *ctx = fc->fs_private;
+	struct btrfs_fs_info *fs_info = btrfs_sb(fc->root->d_sb);
+
+	if (!fscrypt_is_dummy_policy_set(&ctx->dummy_enc_policy))
+		return true;
+
+	if (fscrypt_dummy_policies_equal(&fs_info->dummy_enc_policy,
+					 &ctx->dummy_enc_policy))
+		return true;
+
+	btrfs_warn(fs_info,
+		   "Can't set or change test_dummy_encryption on remount");
+	return false;
+}
+
 static int btrfs_reconfigure(struct fs_context *fc)
 {
 	struct super_block *sb = fc->root->d_sb;
@@ -1474,6 +1533,10 @@ static int btrfs_reconfigure(struct fs_context *fc)
 	    !btrfs_check_options(fs_info, &ctx->mount_opt, fc->sb_flags))
 		return -EINVAL;
 
+	if (!mount_reconfigure &&
+	    !btrfs_check_test_dummy_encryption(fc))
+		return -EINVAL;
+
 	ret = btrfs_check_features(fs_info, !(fc->sb_flags & SB_RDONLY));
 	if (ret < 0)
 		return ret;
@@ -2105,6 +2168,7 @@ static void btrfs_free_fs_context(struct fs_context *fc)
 		btrfs_free_fs_info(fs_info);
 
 	if (ctx && refcount_dec_and_test(&ctx->refs)) {
+		fscrypt_free_dummy_policy(&ctx->dummy_enc_policy);
 		kfree(ctx->subvol_name);
 		kfree(ctx);
 	}
-- 
2.43.0


  parent reply	other threads:[~2024-01-24 17:20 UTC|newest]

Thread overview: 59+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2024-01-24 17:18 [PATCH v5 00/52] btrfs: add fscrypt support Josef Bacik
2024-01-24 17:18 ` [PATCH v5 01/52] fscrypt: add per-extent encryption support Josef Bacik
2024-01-24 17:18 ` [PATCH v5 02/52] fscrypt: allow inline encryption for extent based encryption Josef Bacik
2024-01-24 17:18 ` [PATCH v5 03/52] fscrypt: add a fscrypt_inode_open helper Josef Bacik
2024-01-24 17:18 ` [PATCH v5 04/52] fscrypt: conditionally don't wipe mk secret until the last active user is done Josef Bacik
2024-01-24 17:18 ` [PATCH v5 05/52] blk-crypto: add a process bio callback Josef Bacik
2024-01-24 17:18 ` [PATCH v5 06/52] fscrypt: add a process_bio hook to fscrypt_operations Josef Bacik
2024-01-24 17:18 ` [PATCH v5 07/52] fscrypt: expose fscrypt_nokey_name Josef Bacik
2024-01-24 17:18 ` [PATCH v5 08/52] fscrypt: add documentation about extent encryption Josef Bacik
2024-01-24 17:18 ` [PATCH v5 09/52] btrfs: add infrastructure for safe em freeing Josef Bacik
2024-01-24 19:49   ` Boris Burkov
2024-01-24 17:18 ` [PATCH v5 10/52] btrfs: disable various operations on encrypted inodes Josef Bacik
2024-01-24 19:53   ` Boris Burkov
2024-01-24 17:18 ` [PATCH v5 11/52] btrfs: disable verity " Josef Bacik
2024-01-24 19:53   ` Boris Burkov
2024-01-24 17:18 ` [PATCH v5 12/52] btrfs: start using fscrypt hooks Josef Bacik
2024-01-24 17:18 ` [PATCH v5 13/52] btrfs: add inode encryption contexts Josef Bacik
2024-01-24 17:18 ` [PATCH v5 14/52] btrfs: add new FEATURE_INCOMPAT_ENCRYPT flag Josef Bacik
2024-01-24 17:18 ` [PATCH v5 15/52] btrfs: adapt readdir for encrypted and nokey names Josef Bacik
2024-01-24 17:18 ` [PATCH v5 16/52] btrfs: handle " Josef Bacik
2024-01-24 17:18 ` [PATCH v5 17/52] btrfs: implement fscrypt ioctls Josef Bacik
2024-01-24 17:18 ` [PATCH v5 18/52] btrfs: gate encryption behind BTRFS_DEBUG Josef Bacik
2024-01-24 17:18 ` [PATCH v5 19/52] btrfs: select encryption dependencies if FS_ENCRYPTION Josef Bacik
2024-01-24 17:18 ` [PATCH v5 20/52] btrfs: add get_devices hook for fscrypt Josef Bacik
2024-01-24 17:18 ` [PATCH v5 21/52] btrfs: set file extent encryption excplicitly Josef Bacik
2024-01-24 17:18 ` [PATCH v5 22/52] btrfs: add fscrypt_info and encryption_type to extent_map Josef Bacik
2024-01-24 17:18 ` [PATCH v5 23/52] btrfs: add fscrypt_info and encryption_type to ordered_extent Josef Bacik
2024-01-24 17:18 ` [PATCH v5 24/52] btrfs: plumb through setting the fscrypt_info for ordered extents Josef Bacik
2024-01-24 17:18 ` [PATCH v5 25/52] btrfs: plumb the fscrypt extent context through create_io_em Josef Bacik
2024-01-24 17:18 ` [PATCH v5 26/52] btrfs: populate the ordered_extent with the fscrypt context Josef Bacik
2024-01-24 17:18 ` [PATCH v5 27/52] btrfs: keep track of fscrypt info and orig_start for dio reads Josef Bacik
2024-01-24 17:18 ` [PATCH v5 28/52] btrfs: add an optional encryption context to the end of file extents Josef Bacik
2024-01-24 17:18 ` [PATCH v5 29/52] btrfs: explicitly track file extent length for replace and drop Josef Bacik
2024-01-24 17:18 ` [PATCH v5 30/52] btrfs: pass through fscrypt_extent_info to the file extent helpers Josef Bacik
2024-01-24 17:18 ` [PATCH v5 31/52] btrfs: implement the fscrypt extent encryption hooks Josef Bacik
2024-01-24 17:18 ` [PATCH v5 32/52] btrfs: setup fscrypt_extent_info for new extents Josef Bacik
2024-01-24 17:18 ` [PATCH v5 33/52] btrfs: populate ordered_extent with the orig offset Josef Bacik
2024-01-24 17:18 ` [PATCH v5 34/52] btrfs: set the bio fscrypt context when applicable Josef Bacik
2024-01-24 17:18 ` [PATCH v5 35/52] btrfs: add a bio argument to btrfs_csum_one_bio Josef Bacik
2024-01-24 17:18 ` [PATCH v5 36/52] btrfs: add orig_logical to btrfs_bio Josef Bacik
2024-01-24 17:18 ` [PATCH v5 37/52] btrfs: limit encrypted writes to 256 segments Josef Bacik
2024-01-24 17:19 ` [PATCH v5 38/52] btrfs: implement process_bio cb for fscrypt Josef Bacik
2024-01-24 17:19 ` [PATCH v5 39/52] btrfs: implement read repair for encryption Josef Bacik
2024-01-24 17:19 ` Josef Bacik [this message]
2024-01-24 17:19 ` [PATCH v5 41/52] btrfs: don't rewrite ret from inode_permission Josef Bacik
2024-01-24 17:19 ` [PATCH v5 42/52] btrfs: move inode_to_path higher in backref.c Josef Bacik
2024-01-24 17:19 ` [PATCH v5 43/52] btrfs: make btrfs_ref_to_path handle encrypted filenames Josef Bacik
2024-01-24 17:19 ` [PATCH v5 44/52] btrfs: don't search back for dir inode item in INO_LOOKUP_USER Josef Bacik
2024-01-24 17:19 ` [PATCH v5 45/52] btrfs: deal with encrypted symlinks in send Josef Bacik
2024-01-24 17:19 ` [PATCH v5 46/52] btrfs: decrypt file names for send Josef Bacik
2024-01-24 17:19 ` [PATCH v5 47/52] btrfs: load the inode context before sending writes Josef Bacik
2024-01-24 17:19 ` [PATCH v5 48/52] btrfs: set the appropriate free space settings in reconfigure Josef Bacik
2024-01-24 17:19 ` [PATCH v5 49/52] btrfs: support encryption with log replay Josef Bacik
2024-01-24 17:19 ` [PATCH v5 50/52] btrfs: disable auto defrag on encrypted files Josef Bacik
2024-01-24 17:19 ` [PATCH v5 51/52] btrfs: disable encryption on RAID5/6 Josef Bacik
2024-01-24 17:19 ` [PATCH v5 52/52] btrfs: disable send if we have encryption enabled Josef Bacik
2024-01-24 19:28   ` Boris Burkov
2024-01-24 19:18 ` [PATCH v5 00/52] btrfs: add fscrypt support Neal Gompa
2024-01-24 19:58   ` Josef Bacik

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=77449ee5a882db2945429946c74ea7e796122328.1706116485.git.josef@toxicpanda.com \
    --to=josef@toxicpanda.com \
    --cc=kernel-team@fb.com \
    --cc=linux-btrfs@vger.kernel.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).