From: "Fernando Luis Vázquez Cao" <fernando_b1@lab.ntt.co.jp>
To: Al Viro <viro@zeniv.linux.org.uk>
Cc: Josef Bacik <jbacik@fusionio.com>,
Eric Sandeen <sandeen@redhat.com>,
Dave Chinner <dchinner@redhat.com>,
Christoph Hellwig <hch@infradead.org>, Jan Kara <jack@suse.cz>,
Luiz Capitulino <lcapitulino@redhat.com>,
linux-fsdevel@vger.kernel.org
Subject: [PATCH 1/17] vfs: add __iterate_supers() and helpers around it
Date: Mon, 07 Jan 2013 20:21:01 +0900 [thread overview]
Message-ID: <1357557661.8183.2.camel@nexus.lab.ntt.co.jp> (raw)
In-Reply-To: <1357557492.8183.1.camel@nexus.lab.ntt.co.jp>
iterate_supers() calls a function provided by the caller with the s_umount
semaphore taken in read mode. However, there may be cases where write mode
is preferable, so we add __iterate_supers(), which lets one
specify the mode of the lock, and replace iterate_supers with two helpers
around __iterate_supers(), iterate_supers_read() and iterate_supers_write().
This will be used to fix the emergency thaw (filesystem unfreeze) code, which
iterates over the list of superblocks but needs to hold the s_umount semaphore
in _write_ mode bebore carrying out the actual thaw operation.
This patch introduces no semantic changes since current iterate_supers()
callers are just updated to use iterate_supers_read() instead.
Cc: linux-fsdevel@vger.kernel.org
Cc: Josef Bacik <jbacik@fusionio.com>
Cc: Eric Sandeen <sandeen@redhat.com>
Cc: Christoph Hellwig <hch@infradead.org>
Cc: Dave Chinner <dchinner@redhat.com>
Cc: Luiz Capitulino <lcapitulino@redhat.com>
Reviewed-by: Jan Kara <jack@suse.cz>
Signed-off-by: Fernando Luis Vazquez Cao <fernando@oss.ntt.co.jp>
---
diff -urNp linux-3.8-rc1-orig/fs/buffer.c linux-3.8-rc1/fs/buffer.c
--- linux-3.8-rc1-orig/fs/buffer.c 2012-12-25 10:27:41.166737000 +0900
+++ linux-3.8-rc1/fs/buffer.c 2012-12-25 11:14:41.304018000 +0900
@@ -520,7 +520,7 @@ static void do_thaw_one(struct super_blo
static void do_thaw_all(struct work_struct *work)
{
- iterate_supers(do_thaw_one, NULL);
+ iterate_supers_read(do_thaw_one, NULL);
kfree(work);
printk(KERN_WARNING "Emergency Thaw complete\n");
}
diff -urNp linux-3.8-rc1-orig/fs/drop_caches.c linux-3.8-rc1/fs/drop_caches.c
--- linux-3.8-rc1-orig/fs/drop_caches.c 2012-12-11 12:30:57.000000000 +0900
+++ linux-3.8-rc1/fs/drop_caches.c 2012-12-25 11:14:41.304018000 +0900
@@ -59,7 +59,7 @@ int drop_caches_sysctl_handler(ctl_table
return ret;
if (write) {
if (sysctl_drop_caches & 1)
- iterate_supers(drop_pagecache_sb, NULL);
+ iterate_supers_read(drop_pagecache_sb, NULL);
if (sysctl_drop_caches & 2)
drop_slab();
}
diff -urNp linux-3.8-rc1-orig/fs/quota/quota.c linux-3.8-rc1/fs/quota/quota.c
--- linux-3.8-rc1-orig/fs/quota/quota.c 2012-12-25 10:27:42.034737000 +0900
+++ linux-3.8-rc1/fs/quota/quota.c 2012-12-25 11:14:41.304018000 +0900
@@ -58,7 +58,7 @@ static int quota_sync_all(int type)
return -EINVAL;
ret = security_quotactl(Q_SYNC, type, 0, NULL);
if (!ret)
- iterate_supers(quota_sync_one, &type);
+ iterate_supers_read(quota_sync_one, &type);
return ret;
}
diff -urNp linux-3.8-rc1-orig/fs/super.c linux-3.8-rc1/fs/super.c
--- linux-3.8-rc1-orig/fs/super.c 2012-12-11 12:30:57.000000000 +0900
+++ linux-3.8-rc1/fs/super.c 2012-12-25 11:14:41.308018000 +0900
@@ -508,14 +508,16 @@ void drop_super(struct super_block *sb)
EXPORT_SYMBOL(drop_super);
/**
- * iterate_supers - call function for all active superblocks
+ * __iterate_supers - call function for all active superblocks
* @f: function to call
* @arg: argument to pass to it
+ * @wlock: mode of superblock lock (false->read lock, true->write lock)
*
* Scans the superblock list and calls given function, passing it
* locked superblock and given argument.
*/
-void iterate_supers(void (*f)(struct super_block *, void *), void *arg)
+static void __iterate_supers(void (*f)(struct super_block *, void *), void *arg,
+ bool wlock)
{
struct super_block *sb, *p = NULL;
@@ -526,10 +528,18 @@ void iterate_supers(void (*f)(struct sup
sb->s_count++;
spin_unlock(&sb_lock);
- down_read(&sb->s_umount);
+ if (wlock)
+ down_write(&sb->s_umount);
+ else
+ down_read(&sb->s_umount);
+
if (sb->s_root && (sb->s_flags & MS_BORN))
f(sb, arg);
- up_read(&sb->s_umount);
+
+ if (wlock)
+ up_write(&sb->s_umount);
+ else
+ up_read(&sb->s_umount);
spin_lock(&sb_lock);
if (p)
@@ -542,6 +552,34 @@ void iterate_supers(void (*f)(struct sup
}
/**
+ * iterate_supers_read - call function for all active superblocks
+ * @f: function to call
+ * @arg: argument to pass to it
+ *
+ * Scans the superblock list and calls given function, passing it
+ * a superblock locked in _read_ mode and given argument. The lock
+ * is automatically relased after the function returns.
+ */
+void iterate_supers_read(void (*f)(struct super_block *, void *), void *arg)
+{
+ __iterate_supers(f, arg , false);
+}
+
+/**
+ * iterate_supers_write - call function for all active superblocks
+ * @f: function to call
+ * @arg: argument to pass to it
+ *
+ * Scans the superblock list and calls given function, passing it
+ * a superblock locked in _write_ mode and given argument. The lock
+ * is automatically relased after the function returns.
+ */
+void iterate_supers_write(void (*f)(struct super_block *, void *), void *arg)
+{
+ __iterate_supers(f, arg , true);
+}
+
+/**
* iterate_supers_type - call function for superblocks of given type
* @type: fs type
* @f: function to call
diff -urNp linux-3.8-rc1-orig/fs/sync.c linux-3.8-rc1/fs/sync.c
--- linux-3.8-rc1-orig/fs/sync.c 2012-12-11 12:30:57.000000000 +0900
+++ linux-3.8-rc1/fs/sync.c 2012-12-25 11:14:41.312018000 +0900
@@ -104,9 +104,9 @@ SYSCALL_DEFINE0(sync)
int nowait = 0, wait = 1;
wakeup_flusher_threads(0, WB_REASON_SYNC);
- iterate_supers(sync_inodes_one_sb, NULL);
- iterate_supers(sync_fs_one_sb, &nowait);
- iterate_supers(sync_fs_one_sb, &wait);
+ iterate_supers_read(sync_inodes_one_sb, NULL);
+ iterate_supers_read(sync_fs_one_sb, &nowait);
+ iterate_supers_read(sync_fs_one_sb, &wait);
iterate_bdevs(fdatawrite_one_bdev, NULL);
iterate_bdevs(fdatawait_one_bdev, NULL);
if (unlikely(laptop_mode))
@@ -122,11 +122,11 @@ static void do_sync_work(struct work_str
* Sync twice to reduce the possibility we skipped some inodes / pages
* because they were temporarily locked
*/
- iterate_supers(sync_inodes_one_sb, &nowait);
- iterate_supers(sync_fs_one_sb, &nowait);
+ iterate_supers_read(sync_inodes_one_sb, &nowait);
+ iterate_supers_read(sync_fs_one_sb, &nowait);
iterate_bdevs(fdatawrite_one_bdev, NULL);
- iterate_supers(sync_inodes_one_sb, &nowait);
- iterate_supers(sync_fs_one_sb, &nowait);
+ iterate_supers_read(sync_inodes_one_sb, &nowait);
+ iterate_supers_read(sync_fs_one_sb, &nowait);
iterate_bdevs(fdatawrite_one_bdev, NULL);
printk("Emergency Sync complete\n");
kfree(work);
diff -urNp linux-3.8-rc1-orig/include/linux/fs.h linux-3.8-rc1/include/linux/fs.h
--- linux-3.8-rc1-orig/include/linux/fs.h 2012-12-25 10:27:42.198737000 +0900
+++ linux-3.8-rc1/include/linux/fs.h 2012-12-25 11:14:41.312018000 +0900
@@ -2494,7 +2494,8 @@ extern struct super_block *get_super(str
extern struct super_block *get_super_thawed(struct block_device *);
extern struct super_block *get_active_super(struct block_device *bdev);
extern void drop_super(struct super_block *sb);
-extern void iterate_supers(void (*)(struct super_block *, void *), void *);
+extern void iterate_supers_read(void (*)(struct super_block *, void *), void *);
+extern void iterate_supers_write(void (*)(struct super_block *, void *), void *);
extern void iterate_supers_type(struct file_system_type *,
void (*)(struct super_block *, void *), void *);
diff -urNp linux-3.8-rc1-orig/security/selinux/hooks.c linux-3.8-rc1/security/selinux/hooks.c
--- linux-3.8-rc1-orig/security/selinux/hooks.c 2012-12-11 12:30:57.000000000 +0900
+++ linux-3.8-rc1/security/selinux/hooks.c 2012-12-25 11:14:41.312018000 +0900
@@ -5720,7 +5720,7 @@ void selinux_complete_init(void)
/* Set up any superblocks initialized prior to the policy load. */
printk(KERN_DEBUG "SELinux: Setting up existing superblocks.\n");
- iterate_supers(delayed_superblock_init, NULL);
+ iterate_supers_read(delayed_superblock_init, NULL);
}
/* SELinux requires early initialization in order to label
next prev parent reply other threads:[~2013-01-07 12:13 UTC|newest]
Thread overview: 27+ messages / expand[flat|nested] mbox.gz Atom feed top
2013-01-07 11:18 [PATCH v6 0/17] fsfreeze: miscellaneous fixes and cleanups Fernando Luis Vázquez Cao
2013-01-07 11:21 ` Fernando Luis Vázquez Cao [this message]
2013-01-07 11:22 ` [PATCH 2/17] fsfreeze: add unlocked version of thaw_super Fernando Luis Vázquez Cao
2013-01-07 11:23 ` [PATCH 3/17] fsfreeze: fix emergency thaw infinite loop Fernando Luis Vázquez Cao
2013-01-07 11:26 ` [PATCH 4/17] fsfreeze: emergency thaw will deadlock on s_umount Fernando Luis Vázquez Cao
2013-01-09 16:12 ` Jan Kara
2013-01-07 11:27 ` [PATCH 5/17] xfs: switch to using super methods for fsfreeze Fernando Luis Vázquez Cao
2013-01-07 11:29 ` [PATCH 6/17] fsfreeze: move emergency thaw code to fs/super.c Fernando Luis Vázquez Cao
2013-01-07 11:30 ` [PATCH 7/17] fsfreeze: fix nested freezing of sb-less bdevs Fernando Luis Vázquez Cao
2013-01-09 16:24 ` Jan Kara
2013-01-07 11:32 ` [PATCH 8/17] fsfreeze: allow bdev level thaws when the sb is unfrozen Fernando Luis Vázquez Cao
2013-01-09 16:26 ` Jan Kara
2013-01-07 11:34 ` [PATCH 9/17] fsfreeze: freeze_super and thaw_bdev don't play well together Fernando Luis Vázquez Cao
2013-01-07 11:35 ` [PATCH 10/17] fsfreeze: automatically thaw on umount Fernando Luis Vázquez Cao
2013-01-09 17:20 ` Jan Kara
2013-01-10 9:14 ` Fernando Luis Vazquez Cao
2013-01-07 11:36 ` [PATCH 11/17] fsfreeze: add thaw_super_force Fernando Luis Vázquez Cao
2013-01-07 11:38 ` [PATCH 12/17] fsfreeze: sb-level/bdev-level fsfreeze integration Fernando Luis Vázquez Cao
2013-01-09 16:37 ` Jan Kara
2013-01-10 9:57 ` Fernando Luis Vazquez Cao
2013-01-07 11:39 ` [PATCH 13/17] fsfreeze: unfreeze bdevs in addition to filesystems during emergency thaw Fernando Luis Vázquez Cao
2013-01-09 16:41 ` Jan Kara
2013-01-07 11:41 ` [PATCH 14/17] vfs: leverage bd_super in get_super and get_active_super Fernando Luis Vázquez Cao
2013-01-09 16:44 ` Jan Kara
2013-01-07 11:42 ` [PATCH 15/17] btrfs: store pointer to superblock in bd_super Fernando Luis Vázquez Cao
2013-01-07 11:43 ` [PATCH 16/17] fsfreeze: allow freeze counter lock nesting Fernando Luis Vázquez Cao
2013-01-07 11:44 ` [PATCH 17/17] fsfreeze: export freeze_count through mountinfo Fernando Luis Vázquez Cao
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=1357557661.8183.2.camel@nexus.lab.ntt.co.jp \
--to=fernando_b1@lab.ntt.co.jp \
--cc=dchinner@redhat.com \
--cc=hch@infradead.org \
--cc=jack@suse.cz \
--cc=jbacik@fusionio.com \
--cc=lcapitulino@redhat.com \
--cc=linux-fsdevel@vger.kernel.org \
--cc=sandeen@redhat.com \
--cc=viro@zeniv.linux.org.uk \
/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).