diff options
author | Eric W. Biederman <ebiederm@xmission.com> | 2010-03-30 14:31:25 -0400 |
---|---|---|
committer | Greg Kroah-Hartman <gregkh@suse.de> | 2010-05-21 12:37:31 -0400 |
commit | bc451f2058238013e1cdf4acd443c01734d332f0 (patch) | |
tree | 16a1ca2f762edcfbda8f2a4afb6763ba7b090271 /drivers/base | |
parent | ba514a57f5c38d9d79ea15e75059e07f49238726 (diff) |
kobj: Add basic infrastructure for dealing with namespaces.
Move complete knowledge of namespaces into the kobject layer
so we can use that information when reporting kobjects to
userspace.
Signed-off-by: Eric W. Biederman <ebiederm@xmission.com>
Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
Diffstat (limited to 'drivers/base')
-rw-r--r-- | drivers/base/class.c | 9 | ||||
-rw-r--r-- | drivers/base/core.c | 77 |
2 files changed, 72 insertions, 14 deletions
diff --git a/drivers/base/class.c b/drivers/base/class.c index 9c6a0d6408e7..8e231d05b400 100644 --- a/drivers/base/class.c +++ b/drivers/base/class.c | |||
@@ -63,6 +63,14 @@ static void class_release(struct kobject *kobj) | |||
63 | kfree(cp); | 63 | kfree(cp); |
64 | } | 64 | } |
65 | 65 | ||
66 | static const struct kobj_ns_type_operations *class_child_ns_type(struct kobject *kobj) | ||
67 | { | ||
68 | struct class_private *cp = to_class(kobj); | ||
69 | struct class *class = cp->class; | ||
70 | |||
71 | return class->ns_type; | ||
72 | } | ||
73 | |||
66 | static const struct sysfs_ops class_sysfs_ops = { | 74 | static const struct sysfs_ops class_sysfs_ops = { |
67 | .show = class_attr_show, | 75 | .show = class_attr_show, |
68 | .store = class_attr_store, | 76 | .store = class_attr_store, |
@@ -71,6 +79,7 @@ static const struct sysfs_ops class_sysfs_ops = { | |||
71 | static struct kobj_type class_ktype = { | 79 | static struct kobj_type class_ktype = { |
72 | .sysfs_ops = &class_sysfs_ops, | 80 | .sysfs_ops = &class_sysfs_ops, |
73 | .release = class_release, | 81 | .release = class_release, |
82 | .child_ns_type = class_child_ns_type, | ||
74 | }; | 83 | }; |
75 | 84 | ||
76 | /* Hotplug events for classes go to the class class_subsys */ | 85 | /* Hotplug events for classes go to the class class_subsys */ |
diff --git a/drivers/base/core.c b/drivers/base/core.c index 356dd011b8f9..f0699918e2f6 100644 --- a/drivers/base/core.c +++ b/drivers/base/core.c | |||
@@ -131,9 +131,21 @@ static void device_release(struct kobject *kobj) | |||
131 | kfree(p); | 131 | kfree(p); |
132 | } | 132 | } |
133 | 133 | ||
134 | static const void *device_namespace(struct kobject *kobj) | ||
135 | { | ||
136 | struct device *dev = to_dev(kobj); | ||
137 | const void *ns = NULL; | ||
138 | |||
139 | if (dev->class && dev->class->ns_type) | ||
140 | ns = dev->class->namespace(dev); | ||
141 | |||
142 | return ns; | ||
143 | } | ||
144 | |||
134 | static struct kobj_type device_ktype = { | 145 | static struct kobj_type device_ktype = { |
135 | .release = device_release, | 146 | .release = device_release, |
136 | .sysfs_ops = &dev_sysfs_ops, | 147 | .sysfs_ops = &dev_sysfs_ops, |
148 | .namespace = device_namespace, | ||
137 | }; | 149 | }; |
138 | 150 | ||
139 | 151 | ||
@@ -595,11 +607,59 @@ static struct kobject *virtual_device_parent(struct device *dev) | |||
595 | return virtual_dir; | 607 | return virtual_dir; |
596 | } | 608 | } |
597 | 609 | ||
598 | static struct kobject *get_device_parent(struct device *dev, | 610 | struct class_dir { |
599 | struct device *parent) | 611 | struct kobject kobj; |
612 | struct class *class; | ||
613 | }; | ||
614 | |||
615 | #define to_class_dir(obj) container_of(obj, struct class_dir, kobj) | ||
616 | |||
617 | static void class_dir_release(struct kobject *kobj) | ||
618 | { | ||
619 | struct class_dir *dir = to_class_dir(kobj); | ||
620 | kfree(dir); | ||
621 | } | ||
622 | |||
623 | static const | ||
624 | struct kobj_ns_type_operations *class_dir_child_ns_type(struct kobject *kobj) | ||
600 | { | 625 | { |
626 | struct class_dir *dir = to_class_dir(kobj); | ||
627 | return dir->class->ns_type; | ||
628 | } | ||
629 | |||
630 | static struct kobj_type class_dir_ktype = { | ||
631 | .release = class_dir_release, | ||
632 | .sysfs_ops = &kobj_sysfs_ops, | ||
633 | .child_ns_type = class_dir_child_ns_type | ||
634 | }; | ||
635 | |||
636 | static struct kobject * | ||
637 | class_dir_create_and_add(struct class *class, struct kobject *parent_kobj) | ||
638 | { | ||
639 | struct class_dir *dir; | ||
601 | int retval; | 640 | int retval; |
602 | 641 | ||
642 | dir = kzalloc(sizeof(*dir), GFP_KERNEL); | ||
643 | if (!dir) | ||
644 | return NULL; | ||
645 | |||
646 | dir->class = class; | ||
647 | kobject_init(&dir->kobj, &class_dir_ktype); | ||
648 | |||
649 | dir->kobj.kset = &class->p->class_dirs; | ||
650 | |||
651 | retval = kobject_add(&dir->kobj, parent_kobj, "%s", class->name); | ||
652 | if (retval < 0) { | ||
653 | kobject_put(&dir->kobj); | ||
654 | return NULL; | ||
655 | } | ||
656 | return &dir->kobj; | ||
657 | } | ||
658 | |||
659 | |||
660 | static struct kobject *get_device_parent(struct device *dev, | ||
661 | struct device *parent) | ||
662 | { | ||
603 | if (dev->class) { | 663 | if (dev->class) { |
604 | static DEFINE_MUTEX(gdp_mutex); | 664 | static DEFINE_MUTEX(gdp_mutex); |
605 | struct kobject *kobj = NULL; | 665 | struct kobject *kobj = NULL; |
@@ -634,18 +694,7 @@ static struct kobject *get_device_parent(struct device *dev, | |||
634 | } | 694 | } |
635 | 695 | ||
636 | /* or create a new class-directory at the parent device */ | 696 | /* or create a new class-directory at the parent device */ |
637 | k = kobject_create(); | 697 | k = class_dir_create_and_add(dev->class, parent_kobj); |
638 | if (!k) { | ||
639 | mutex_unlock(&gdp_mutex); | ||
640 | return NULL; | ||
641 | } | ||
642 | k->kset = &dev->class->p->class_dirs; | ||
643 | retval = kobject_add(k, parent_kobj, "%s", dev->class->name); | ||
644 | if (retval < 0) { | ||
645 | mutex_unlock(&gdp_mutex); | ||
646 | kobject_put(k); | ||
647 | return NULL; | ||
648 | } | ||
649 | /* do not emit an uevent for this simple "glue" directory */ | 698 | /* do not emit an uevent for this simple "glue" directory */ |
650 | mutex_unlock(&gdp_mutex); | 699 | mutex_unlock(&gdp_mutex); |
651 | return k; | 700 | return k; |