Message ID | 1350867440-6109-1-git-send-email-dmitry.torokhov@gmail.com (mailing list archive) |
---|---|
State | New, archived |
Headers | show |
This series looks good to me, and looks to fix the issue about as cleanly as it can. Al, holler if you have any concerns, but I'm planning on applying it ASAP, Linus On Mon, Oct 22, 2012 at 3:57 AM, Dmitry Torokhov <dmitry.torokhov@gmail.com> wrote: > In certain cases (for example when a cdev structure is embedded into > another object whose lifetime is controlled by a separate kobject) it is > beneficial to tie lifetime of another object to the lifetime of character > device so that related object is not freed until after char_dev object is > freed. To achieve this let's pin kobject's parent when doing cdev_add() > and unpin when last reference to cdev structure is being released. -- To unsubscribe from this list: send the line "unsubscribe linux-input" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
On Mon, Oct 22, 2012 at 08:02:12AM +0300, Linus Torvalds wrote: > This series looks good to me, and looks to fix the issue about as > cleanly as it can. Al, holler if you have any concerns, but I'm > planning on applying it ASAP, Add my ACKed-by. And from the look of it, we'll need something similar at least in drivers/mtd/ubi in addition to evdev patch. -- To unsubscribe from this list: send the line "unsubscribe linux-input" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
diff --git a/fs/char_dev.c b/fs/char_dev.c index 3f152b9..afc2bb6 100644 --- a/fs/char_dev.c +++ b/fs/char_dev.c @@ -471,9 +471,19 @@ static int exact_lock(dev_t dev, void *data) */ int cdev_add(struct cdev *p, dev_t dev, unsigned count) { + int error; + p->dev = dev; p->count = count; - return kobj_map(cdev_map, dev, count, NULL, exact_match, exact_lock, p); + + error = kobj_map(cdev_map, dev, count, NULL, + exact_match, exact_lock, p); + if (error) + return error; + + kobject_get(p->kobj.parent); + + return 0; } static void cdev_unmap(dev_t dev, unsigned count) @@ -498,14 +508,20 @@ void cdev_del(struct cdev *p) static void cdev_default_release(struct kobject *kobj) { struct cdev *p = container_of(kobj, struct cdev, kobj); + struct kobject *parent = kobj->parent; + cdev_purge(p); + kobject_put(parent); } static void cdev_dynamic_release(struct kobject *kobj) { struct cdev *p = container_of(kobj, struct cdev, kobj); + struct kobject *parent = kobj->parent; + cdev_purge(p); kfree(p); + kobject_put(parent); } static struct kobj_type ktype_cdev_default = {
In certain cases (for example when a cdev structure is embedded into another object whose lifetime is controlled by a separate kobject) it is beneficial to tie lifetime of another object to the lifetime of character device so that related object is not freed until after char_dev object is freed. To achieve this let's pin kobject's parent when doing cdev_add() and unpin when last reference to cdev structure is being released. Signed-off-by: Dmitry Torokhov <dmitry.torokhov@gmail.com> --- OK, so it looks like cdev kobject's parent is unused so we can just have users set themselves as parents of character device and have cdev_add() pin it. fs/char_dev.c | 18 +++++++++++++++++- 1 file changed, 17 insertions(+), 1 deletion(-)