fs: remove get_super_thawed and get_super_exclusive_thawed

Just open code the wait in the only caller of both functions.

Signed-off-by: Christoph Hellwig <hch@lst.de>
Reviewed-by: Jan Kara <jack@suse.cz>
Reviewed-by: Hannes Reinecke <hare@suse.de>
Signed-off-by: Jens Axboe <axboe@kernel.dk>
This commit is contained in:
Christoph Hellwig 2020-11-16 15:21:18 +01:00 committed by Jens Axboe
parent 5df1a67269
commit 60b498852b
4 changed files with 29 additions and 59 deletions

View File

@ -114,7 +114,9 @@ extern struct file *alloc_empty_file_noaccount(int, const struct cred *);
*/ */
extern int reconfigure_super(struct fs_context *); extern int reconfigure_super(struct fs_context *);
extern bool trylock_super(struct super_block *sb); extern bool trylock_super(struct super_block *sb);
struct super_block *__get_super(struct block_device *bdev, bool excl);
extern struct super_block *user_get_super(dev_t); extern struct super_block *user_get_super(dev_t);
void put_super(struct super_block *sb);
extern bool mount_capable(struct fs_context *); extern bool mount_capable(struct fs_context *);
/* /*

View File

@ -20,6 +20,7 @@
#include <linux/writeback.h> #include <linux/writeback.h>
#include <linux/nospec.h> #include <linux/nospec.h>
#include "compat.h" #include "compat.h"
#include "../internal.h"
static int check_quotactl_permission(struct super_block *sb, int type, int cmd, static int check_quotactl_permission(struct super_block *sb, int type, int cmd,
qid_t id) qid_t id)
@ -868,6 +869,7 @@ static struct super_block *quotactl_block(const char __user *special, int cmd)
struct block_device *bdev; struct block_device *bdev;
struct super_block *sb; struct super_block *sb;
struct filename *tmp = getname(special); struct filename *tmp = getname(special);
bool excl = false, thawed = false;
if (IS_ERR(tmp)) if (IS_ERR(tmp))
return ERR_CAST(tmp); return ERR_CAST(tmp);
@ -875,17 +877,32 @@ static struct super_block *quotactl_block(const char __user *special, int cmd)
putname(tmp); putname(tmp);
if (IS_ERR(bdev)) if (IS_ERR(bdev))
return ERR_CAST(bdev); return ERR_CAST(bdev);
if (quotactl_cmd_onoff(cmd))
sb = get_super_exclusive_thawed(bdev); if (quotactl_cmd_onoff(cmd)) {
else if (quotactl_cmd_write(cmd)) excl = true;
sb = get_super_thawed(bdev); thawed = true;
else } else if (quotactl_cmd_write(cmd)) {
sb = get_super(bdev); thawed = true;
}
retry:
sb = __get_super(bdev, excl);
if (thawed && sb && sb->s_writers.frozen != SB_UNFROZEN) {
if (excl)
up_write(&sb->s_umount);
else
up_read(&sb->s_umount);
wait_event(sb->s_writers.wait_unfrozen,
sb->s_writers.frozen == SB_UNFROZEN);
put_super(sb);
goto retry;
}
bdput(bdev); bdput(bdev);
if (!sb) if (!sb)
return ERR_PTR(-ENODEV); return ERR_PTR(-ENODEV);
return sb; return sb;
#else #else
return ERR_PTR(-ENODEV); return ERR_PTR(-ENODEV);
#endif #endif

View File

@ -307,7 +307,7 @@ static void __put_super(struct super_block *s)
* Drops a temporary reference, frees superblock if there's no * Drops a temporary reference, frees superblock if there's no
* references left. * references left.
*/ */
static void put_super(struct super_block *sb) void put_super(struct super_block *sb)
{ {
spin_lock(&sb_lock); spin_lock(&sb_lock);
__put_super(sb); __put_super(sb);
@ -740,7 +740,7 @@ void iterate_supers_type(struct file_system_type *type,
EXPORT_SYMBOL(iterate_supers_type); EXPORT_SYMBOL(iterate_supers_type);
static struct super_block *__get_super(struct block_device *bdev, bool excl) struct super_block *__get_super(struct block_device *bdev, bool excl)
{ {
struct super_block *sb; struct super_block *sb;
@ -789,53 +789,6 @@ struct super_block *get_super(struct block_device *bdev)
} }
EXPORT_SYMBOL(get_super); EXPORT_SYMBOL(get_super);
static struct super_block *__get_super_thawed(struct block_device *bdev,
bool excl)
{
while (1) {
struct super_block *s = __get_super(bdev, excl);
if (!s || s->s_writers.frozen == SB_UNFROZEN)
return s;
if (!excl)
up_read(&s->s_umount);
else
up_write(&s->s_umount);
wait_event(s->s_writers.wait_unfrozen,
s->s_writers.frozen == SB_UNFROZEN);
put_super(s);
}
}
/**
* get_super_thawed - get thawed superblock of a device
* @bdev: device to get the superblock for
*
* Scans the superblock list and finds the superblock of the file system
* mounted on the device. The superblock is returned once it is thawed
* (or immediately if it was not frozen). %NULL is returned if no match
* is found.
*/
struct super_block *get_super_thawed(struct block_device *bdev)
{
return __get_super_thawed(bdev, false);
}
EXPORT_SYMBOL(get_super_thawed);
/**
* get_super_exclusive_thawed - get thawed superblock of a device
* @bdev: device to get the superblock for
*
* Scans the superblock list and finds the superblock of the file system
* mounted on the device. The superblock is returned once it is thawed
* (or immediately if it was not frozen) and s_umount semaphore is held
* in exclusive mode. %NULL is returned if no match is found.
*/
struct super_block *get_super_exclusive_thawed(struct block_device *bdev)
{
return __get_super_thawed(bdev, true);
}
EXPORT_SYMBOL(get_super_exclusive_thawed);
/** /**
* get_active_super - get an active reference to the superblock of a device * get_active_super - get an active reference to the superblock of a device
* @bdev: device to get the superblock for * @bdev: device to get the superblock for

View File

@ -1409,7 +1409,7 @@ enum {
struct sb_writers { struct sb_writers {
int frozen; /* Is sb frozen? */ int frozen; /* Is sb frozen? */
wait_queue_head_t wait_unfrozen; /* for get_super_thawed() */ wait_queue_head_t wait_unfrozen; /* wait for thaw */
struct percpu_rw_semaphore rw_sem[SB_FREEZE_LEVELS]; struct percpu_rw_semaphore rw_sem[SB_FREEZE_LEVELS];
}; };
@ -3132,8 +3132,6 @@ extern struct file_system_type *get_filesystem(struct file_system_type *fs);
extern void put_filesystem(struct file_system_type *fs); extern void put_filesystem(struct file_system_type *fs);
extern struct file_system_type *get_fs_type(const char *name); extern struct file_system_type *get_fs_type(const char *name);
extern struct super_block *get_super(struct block_device *); extern struct super_block *get_super(struct block_device *);
extern struct super_block *get_super_thawed(struct block_device *);
extern struct super_block *get_super_exclusive_thawed(struct block_device *bdev);
extern struct super_block *get_active_super(struct block_device *bdev); extern struct super_block *get_active_super(struct block_device *bdev);
extern void drop_super(struct super_block *sb); extern void drop_super(struct super_block *sb);
extern void drop_super_exclusive(struct super_block *sb); extern void drop_super_exclusive(struct super_block *sb);