From: Tejun Heo <tj@kernel.org>
To: gregkh@linuxfoundation.org
Cc: linux-kernel@vger.kernel.org, schwidefsky@de.ibm.com,
heiko.carstens@de.ibm.com, stern@rowland.harvard.edu,
JBottomley@parallels.com, bhelgaas@google.com,
Tejun Heo <tj@kernel.org>
Subject: [PATCH 08/14] kernfs: make kernfs_get_active() block if the node is deactivated but not removed
Date: Fri, 10 Jan 2014 08:57:25 -0500 [thread overview]
Message-ID: <1389362251-8128-9-git-send-email-tj@kernel.org> (raw)
In-Reply-To: <1389362251-8128-1-git-send-email-tj@kernel.org>
Currently, kernfs_get_active() fails if the target node is
deactivated. This is fine as a node always gets removed after
deactivation; however, we're gonna add reactivation so the assumption
won't hold. It'd be incorrect for kernfs_get_active() to fail for a
node which was deactivated only temporarily.
This patch makes kernfs_get_active() block if the node is deactivated
but not removed. If the node gets reactivated (not yet implemented),
it will be retried and succeed. If the node gets removed, it will be
woken up and fail.
Signed-off-by: Tejun Heo <tj@kernel.org>
---
fs/kernfs/dir.c | 25 +++++++++++++++++++++----
1 file changed, 21 insertions(+), 4 deletions(-)
diff --git a/fs/kernfs/dir.c b/fs/kernfs/dir.c
index 770d687..37dd640 100644
--- a/fs/kernfs/dir.c
+++ b/fs/kernfs/dir.c
@@ -149,12 +149,25 @@ struct kernfs_node *kernfs_get_active(struct kernfs_node *kn)
if (unlikely(!kn))
return NULL;
- if (!atomic_inc_unless_negative(&kn->active))
- return NULL;
-
if (kernfs_lockdep(kn))
rwsem_acquire_read(&kn->dep_map, 0, 1, _RET_IP_);
- return kn;
+
+ /*
+ * Try to obtain an active ref. If @kn is deactivated, we block
+ * till either it's reactivated or killed.
+ */
+ do {
+ if (atomic_inc_unless_negative(&kn->active))
+ return kn;
+
+ wait_event(kernfs_root(kn)->deactivate_waitq,
+ atomic_read(&kn->active) >= 0 ||
+ RB_EMPTY_NODE(&kn->rb));
+ } while (!RB_EMPTY_NODE(&kn->rb));
+
+ if (kernfs_lockdep(kn))
+ rwsem_release(&kn->dep_map, 1, _RET_IP_);
+ return NULL;
}
/**
@@ -786,6 +799,7 @@ static void __kernfs_deactivate(struct kernfs_node *kn)
static void __kernfs_remove(struct kernfs_node *kn)
{
+ struct kernfs_root *root = kernfs_root(kn);
struct kernfs_node *pos;
lockdep_assert_held(&kernfs_mutex);
@@ -837,6 +851,9 @@ static void __kernfs_remove(struct kernfs_node *kn)
kernfs_put(pos);
} while (pos != kn);
+
+ /* some nodes killed, kick get_active waiters */
+ wake_up_all(&root->deactivate_waitq);
}
/**
--
1.8.4.2
next prev parent reply other threads:[~2014-01-10 14:01 UTC|newest]
Thread overview: 22+ messages / expand[flat|nested] mbox.gz Atom feed top
2014-01-10 13:57 [PATCHSET v3 driver-core-next] kernfs, sysfs, driver-core: implement synchronous self-removal Tejun Heo
2014-01-10 13:57 ` [PATCH 01/14] kernfs: fix get_active failure handling in kernfs_seq_*() Tejun Heo
2014-01-10 13:57 ` [PATCH 02/14] kernfs: replace kernfs_node->u.completion with kernfs_root->deactivate_waitq Tejun Heo
2014-01-10 13:57 ` [PATCH 03/14] kernfs: remove KERNFS_ACTIVE_REF and add kernfs_lockdep() Tejun Heo
2014-01-10 13:57 ` [PATCH 04/14] kernfs: remove KERNFS_REMOVED Tejun Heo
2014-01-10 13:57 ` [PATCH 05/14] kernfs: restructure removal path to fix possible premature return Tejun Heo
2014-01-10 13:57 ` [PATCH 06/14] kernfs: invoke kernfs_unmap_bin_file() directly from __kernfs_remove() Tejun Heo
2014-01-10 13:57 ` [PATCH 07/14] kernfs: remove kernfs_addrm_cxt Tejun Heo
2014-01-10 13:57 ` Tejun Heo [this message]
2014-01-10 13:57 ` [PATCH 09/14] kernfs: implement kernfs_{de|re}activate[_self]() Tejun Heo
2014-01-10 13:57 ` [PATCH 10/14] kernfs, sysfs, driver-core: implement kernfs_remove_self() and its wrappers Tejun Heo
2014-01-10 13:57 ` [PATCH 11/14] pci: use device_remove_file_self() instead of device_schedule_callback() Tejun Heo
2014-01-10 13:57 ` [PATCH 12/14] scsi: " Tejun Heo
2014-01-10 13:57 ` [PATCH 13/14] s390: " Tejun Heo
2014-01-10 13:57 ` [PATCH 14/14] sysfs, driver-core: remove unused {sysfs|device}_schedule_callback_owner() Tejun Heo
2014-01-10 15:08 ` [PATCHSET v3 driver-core-next] kernfs, sysfs, driver-core: implement synchronous self-removal Greg KH
2014-01-11 0:19 ` Greg KH
2014-01-11 18:45 ` Tejun Heo
2014-01-13 21:17 ` Tejun Heo
2014-01-13 22:50 ` Greg KH
2014-01-13 22:54 ` Tejun Heo
-- strict thread matches above, loose matches on Subject: below --
2014-01-10 13:46 [PATCHSET v2 " Tejun Heo
2014-01-10 13:46 ` [PATCH 08/14] kernfs: make kernfs_get_active() block if the node is deactivated but not removed Tejun Heo
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=1389362251-8128-9-git-send-email-tj@kernel.org \
--to=tj@kernel.org \
--cc=JBottomley@parallels.com \
--cc=bhelgaas@google.com \
--cc=gregkh@linuxfoundation.org \
--cc=heiko.carstens@de.ibm.com \
--cc=linux-kernel@vger.kernel.org \
--cc=schwidefsky@de.ibm.com \
--cc=stern@rowland.harvard.edu \
/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