From 2ec16342082a0ac4dddbca1475a124fe574f5661 Mon Sep 17 00:00:00 2001 From: Thomas Gleixner Date: Sun, 19 Jul 2009 08:44:27 -0500 Subject: [PATCH] fs: namespace preemption fix commit ce5c9d0cfb49aadeac6fe322035c4f73bbc5ef85 in tip. On RT we cannot loop with preemption disabled here as mnt_make_readonly() might have been preempted. Instead we block on vfsmount_lock which is held by mnt_make_readonly(). Works for !RT as well. Signed-off-by: Thomas Gleixner Signed-off-by: Paul Gortmaker --- fs/namespace.c | 17 ++++++++++++----- 1 files changed, 12 insertions(+), 5 deletions(-) diff --git a/fs/namespace.c b/fs/namespace.c index f20cb57..b42380a 100644 --- a/fs/namespace.c +++ b/fs/namespace.c @@ -264,8 +264,16 @@ int mnt_want_write(struct vfsmount *mnt) * incremented count after it has set MNT_WRITE_HOLD. */ smp_mb(); - while (mnt->mnt_flags & MNT_WRITE_HOLD) - cpu_relax(); + preempt_enable(); + /* + * HACK ALERT. on RT we can not spin here with cpu_relax() and + * preemption disabled so we block on the vfsmount lock which is + * held by mnt_make_readonly(). Works on !RT as well. + */ + while (mnt->mnt_flags & MNT_WRITE_HOLD) { + spin_lock(&vfsmount_lock); + spin_unlock(&vfsmount_lock); + } /* * After the slowpath clears MNT_WRITE_HOLD, mnt_is_readonly will * be set to match its requirements. So we must not load that until @@ -273,12 +281,11 @@ int mnt_want_write(struct vfsmount *mnt) */ smp_rmb(); if (__mnt_is_readonly(mnt)) { + preempt_disable(); dec_mnt_writers(mnt); + preempt_enable(); ret = -EROFS; - goto out; } -out: - preempt_enable(); return ret; } EXPORT_SYMBOL_GPL(mnt_want_write); -- 1.7.0.4