]> Gentwo Git Trees - linux/.git/commitdiff
ext4: add mext_check_validity() to do basic check
authorZhang Yi <yi.zhang@huawei.com>
Mon, 13 Oct 2025 01:51:22 +0000 (09:51 +0800)
committerTheodore Ts'o <tytso@mit.edu>
Thu, 6 Nov 2025 15:44:39 +0000 (10:44 -0500)
Currently, the basic validation checks during the move extent operation
are scattered across __ext4_ioctl() and ext4_move_extents(), which makes
the code somewhat disorganized. Introduce a new helper,
mext_check_validity(), to handle these checks. This change involves only
code relocation without any logical modifications.

Signed-off-by: Zhang Yi <yi.zhang@huawei.com>
Reviewed-by: Jan Kara <jack@suse.cz>
Message-ID: <20251013015128.499308-7-yi.zhang@huaweicloud.com>
Signed-off-by: Theodore Ts'o <tytso@mit.edu>
fs/ext4/ioctl.c
fs/ext4/move_extent.c

index a93a7baae990cc5580d2ddb3ffcc72fe15246978..366a9b615bf085b6a1a0d25fece1d92d3b4c01a2 100644 (file)
@@ -1641,16 +1641,6 @@ static long __ext4_ioctl(struct file *filp, unsigned int cmd, unsigned long arg)
                if (!(fd_file(donor)->f_mode & FMODE_WRITE))
                        return -EBADF;
 
-               if (ext4_has_feature_bigalloc(sb)) {
-                       ext4_msg(sb, KERN_ERR,
-                                "Online defrag not supported with bigalloc");
-                       return -EOPNOTSUPP;
-               } else if (IS_DAX(inode)) {
-                       ext4_msg(sb, KERN_ERR,
-                                "Online defrag not supported with DAX");
-                       return -EOPNOTSUPP;
-               }
-
                err = mnt_want_write_file(filp);
                if (err)
                        return err;
index 6175906c711947d7951fe5e9b2123dc03c6dd547..cdd175d5c1f3f6dbb5fda2ba9b90cfae1745a724 100644 (file)
@@ -442,6 +442,68 @@ move_extent_per_page(struct file *o_filp, struct inode *donor_inode,
        goto unlock_folios;
 }
 
+/*
+ * Check the validity of the basic filesystem environment and the
+ * inodes' support status.
+ */
+static int mext_check_validity(struct inode *orig_inode,
+                              struct inode *donor_inode)
+{
+       struct super_block *sb = orig_inode->i_sb;
+
+       /* origin and donor should be different inodes */
+       if (orig_inode == donor_inode) {
+               ext4_debug("ext4 move extent: The argument files should not be same inode [ino:orig %lu, donor %lu]\n",
+                          orig_inode->i_ino, donor_inode->i_ino);
+               return -EINVAL;
+       }
+
+       /* origin and donor should belone to the same filesystem */
+       if (orig_inode->i_sb != donor_inode->i_sb) {
+               ext4_debug("ext4 move extent: The argument files should be in same FS [ino:orig %lu, donor %lu]\n",
+                          orig_inode->i_ino, donor_inode->i_ino);
+               return -EINVAL;
+       }
+
+       /* Regular file check */
+       if (!S_ISREG(orig_inode->i_mode) || !S_ISREG(donor_inode->i_mode)) {
+               ext4_debug("ext4 move extent: The argument files should be regular file [ino:orig %lu, donor %lu]\n",
+                          orig_inode->i_ino, donor_inode->i_ino);
+               return -EINVAL;
+       }
+
+       if (ext4_has_feature_bigalloc(sb)) {
+               ext4_msg(sb, KERN_ERR,
+                        "Online defrag not supported with bigalloc");
+               return -EOPNOTSUPP;
+       }
+
+       if (IS_DAX(orig_inode)) {
+               ext4_msg(sb, KERN_ERR,
+                        "Online defrag not supported with DAX");
+               return -EOPNOTSUPP;
+       }
+
+       /*
+        * TODO: it's not obvious how to swap blocks for inodes with full
+        * journaling enabled.
+        */
+       if (ext4_should_journal_data(orig_inode) ||
+           ext4_should_journal_data(donor_inode)) {
+               ext4_msg(sb, KERN_ERR,
+                        "Online defrag not supported with data journaling");
+               return -EOPNOTSUPP;
+       }
+
+       if (IS_ENCRYPTED(orig_inode) || IS_ENCRYPTED(donor_inode)) {
+               ext4_msg(sb, KERN_ERR,
+                        "Online defrag not supported for encrypted files");
+               return -EOPNOTSUPP;
+       }
+
+       return 0;
+}
+
 /**
  * mext_check_arguments - Check whether move extent can be done
  *
@@ -567,43 +629,9 @@ ext4_move_extents(struct file *o_filp, struct file *d_filp, __u64 orig_blk,
        ext4_lblk_t d_start = donor_blk;
        int ret;
 
-       if (orig_inode->i_sb != donor_inode->i_sb) {
-               ext4_debug("ext4 move extent: The argument files "
-                       "should be in same FS [ino:orig %lu, donor %lu]\n",
-                       orig_inode->i_ino, donor_inode->i_ino);
-               return -EINVAL;
-       }
-
-       /* orig and donor should be different inodes */
-       if (orig_inode == donor_inode) {
-               ext4_debug("ext4 move extent: The argument files should not "
-                       "be same inode [ino:orig %lu, donor %lu]\n",
-                       orig_inode->i_ino, donor_inode->i_ino);
-               return -EINVAL;
-       }
-
-       /* Regular file check */
-       if (!S_ISREG(orig_inode->i_mode) || !S_ISREG(donor_inode->i_mode)) {
-               ext4_debug("ext4 move extent: The argument files should be "
-                       "regular file [ino:orig %lu, donor %lu]\n",
-                       orig_inode->i_ino, donor_inode->i_ino);
-               return -EINVAL;
-       }
-
-       /* TODO: it's not obvious how to swap blocks for inodes with full
-          journaling enabled */
-       if (ext4_should_journal_data(orig_inode) ||
-           ext4_should_journal_data(donor_inode)) {
-               ext4_msg(orig_inode->i_sb, KERN_ERR,
-                        "Online defrag not supported with data journaling");
-               return -EOPNOTSUPP;
-       }
-
-       if (IS_ENCRYPTED(orig_inode) || IS_ENCRYPTED(donor_inode)) {
-               ext4_msg(orig_inode->i_sb, KERN_ERR,
-                        "Online defrag not supported for encrypted files");
-               return -EOPNOTSUPP;
-       }
+       ret = mext_check_validity(orig_inode, donor_inode);
+       if (ret)
+               return ret;
 
        /* Protect orig and donor inodes against a truncate */
        lock_two_nondirectories(orig_inode, donor_inode);