|
@@ -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 = {
|