}
static struct kobj_type dynamic_kobj_ktype = {
- .release = dynamic_kobj_release,
+ .release = dynamic_kobj_release,
+ .sysfs_ops = &kobj_sysfs_ops,
};
-/*
+/**
* kobject_create - create a struct kobject dynamically
*
* This function creates a kobject structure dynamically and sets it up
* to be a "dynamic" kobject with a default release function set up.
*
* If the kobject was not able to be created, NULL will be returned.
+ * The kobject structure returned from here must be cleaned up with a
+ * call to kobject_put() and not kfree(), as kobject_init_ng() has
+ * already been called on this structure.
*/
-static struct kobject *kobject_create(void)
+struct kobject *kobject_create(void)
{
struct kobject *kobj;
}
EXPORT_SYMBOL_GPL(kobject_create_and_add);
-/**
- * kobject_kset_add_dir - add sub directory of object.
- * @kset: kset the directory is belongs to.
- * @parent: object in which a directory is created.
- * @name: directory name.
- *
- * Add a plain directory object as child of given object.
- */
-struct kobject *kobject_kset_add_dir(struct kset *kset,
- struct kobject *parent, const char *name)
-{
- struct kobject *k;
- int ret;
-
- k = kobject_create();
- if (!k)
- return NULL;
-
- k->kset = kset;
- ret = kobject_add_ng(k, parent, "%s", name);
- if (ret < 0) {
- printk(KERN_WARNING "%s: kobject_add error: %d\n",
- __func__, ret);
- kobject_put(k);
- k = NULL;
- }
-
- return k;
-}
-
/**
* kset_init - initialize a kset for use
* @k: kset
spin_lock_init(&k->list_lock);
}
+/* default kobject attribute operations */
+static ssize_t kobj_attr_show(struct kobject *kobj, struct attribute *attr,
+ char *buf)
+{
+ struct kobj_attribute *kattr;
+ ssize_t ret = -EIO;
+
+ kattr = container_of(attr, struct kobj_attribute, attr);
+ if (kattr->show)
+ ret = kattr->show(kobj, kattr, buf);
+ return ret;
+}
+
+static ssize_t kobj_attr_store(struct kobject *kobj, struct attribute *attr,
+ const char *buf, size_t count)
+{
+ struct kobj_attribute *kattr;
+ ssize_t ret = -EIO;
+
+ kattr = container_of(attr, struct kobj_attribute, attr);
+ if (kattr->store)
+ ret = kattr->store(kobj, kattr, buf, count);
+ return ret;
+}
+
+struct sysfs_ops kobj_sysfs_ops = {
+ .show = kobj_attr_show,
+ .store = kobj_attr_store,
+};
/**
* kset_add - add a kset object to the hierarchy.
kset_unregister(s);
}
-/**
- * subsystem_create_file - export sysfs attribute file.
- * @s: subsystem.
- * @a: subsystem attribute descriptor.
- */
-
-int subsys_create_file(struct kset *s, struct subsys_attribute *a)
-{
- int error = 0;
-
- if (!s || !a)
- return -EINVAL;
-
- if (kset_get(s)) {
- error = sysfs_create_file(&s->kobj, &a->attr);
- kset_put(s);
- }
- return error;
-}
-
static void kset_release(struct kobject *kobj)
{
struct kset *kset = container_of(kobj, struct kset, kobj);
kfree(kset);
}
-static struct kobj_type kset_type = {
+static struct kobj_type kset_ktype = {
+ .sysfs_ops = &kobj_sysfs_ops,
.release = kset_release,
};
kset->kobj.parent = parent_kobj;
/*
- * The kobject of this kset will have a type of kset_type and belong to
+ * The kobject of this kset will have a type of kset_ktype and belong to
* no kset itself. That way we can properly free it when it is
* finished being used.
*/
- kset->kobj.ktype = &kset_type;
+ kset->kobj.ktype = &kset_ktype;
kset->kobj.kset = NULL;
return kset;
EXPORT_SYMBOL(subsystem_register);
EXPORT_SYMBOL(subsystem_unregister);
-EXPORT_SYMBOL(subsys_create_file);