ext4: move check under lock scope to close a race.
authorDavide Italiano <dccitaliano@gmail.com>
Sun, 3 May 2015 03:21:15 +0000 (23:21 -0400)
committerTheodore Ts'o <tytso@mit.edu>
Sun, 3 May 2015 03:21:15 +0000 (23:21 -0400)
fallocate() checks that the file is extent-based and returns
EOPNOTSUPP in case is not. Other tasks can convert from and to
indirect and extent so it's safe to check only after grabbing
the inode mutex.

Signed-off-by: Davide Italiano <dccitaliano@gmail.com>
Signed-off-by: Theodore Ts'o <tytso@mit.edu>
Cc: stable@vger.kernel.org
fs/ext4/extents.c

index 973816bfe4a9d115a11270a1689a1cecd6fd1dec..d74e08029643d3e5eeb1f8a14d9a78c290549863 100644 (file)
@@ -4927,13 +4927,6 @@ long ext4_fallocate(struct file *file, int mode, loff_t offset, loff_t len)
        if (ret)
                return ret;
 
-       /*
-        * currently supporting (pre)allocate mode for extent-based
-        * files _only_
-        */
-       if (!(ext4_test_inode_flag(inode, EXT4_INODE_EXTENTS)))
-               return -EOPNOTSUPP;
-
        if (mode & FALLOC_FL_COLLAPSE_RANGE)
                return ext4_collapse_range(inode, offset, len);
 
@@ -4955,6 +4948,14 @@ long ext4_fallocate(struct file *file, int mode, loff_t offset, loff_t len)
 
        mutex_lock(&inode->i_mutex);
 
+       /*
+        * We only support preallocation for extent-based files only
+        */
+       if (!(ext4_test_inode_flag(inode, EXT4_INODE_EXTENTS))) {
+               ret = -EOPNOTSUPP;
+               goto out;
+       }
+
        if (!(mode & FALLOC_FL_KEEP_SIZE) &&
             offset + len > i_size_read(inode)) {
                new_size = offset + len;