|| pstart < 0 || plength < 0)
                                        return -EINVAL;
                        }
-                       /* partition number in use? */
+
                        mutex_lock(&bdev->bd_mutex);
-                       if (disk->part[part - 1]) {
-                               mutex_unlock(&bdev->bd_mutex);
-                               return -EBUSY;
-                       }
+
                        /* overlap? */
                        for (i = 0; i < disk->minors - 1; i++) {
                                struct hd_struct *s = disk->part[i];
 
        .release        = part_release,
 };
 
-static inline void partition_sysfs_add_subdir(struct hd_struct *p)
-{
-       struct kobject *k;
-
-       k = kobject_get(&p->dev.kobj);
-       p->holder_dir = kobject_create_and_add("holders", k);
-       kobject_put(k);
-}
-
 static inline void disk_sysfs_add_subdirs(struct gendisk *disk)
 {
        struct kobject *k;
        struct hd_struct *p;
        int err;
 
+       if (disk->part[part - 1])
+               return -EBUSY;
+
        p = kzalloc(sizeof(*p), GFP_KERNEL);
        if (!p)
                return -ENOMEM;
 
        if (!init_part_stats(p)) {
                err = -ENOMEM;
-               goto out0;
+               goto out_free;
        }
        p->start_sect = start;
        p->nr_sects = len;
        p->dev.class = &block_class;
        p->dev.type = &part_type;
        p->dev.parent = &disk->dev;
-       disk->part[part-1] = p;
 
        /* delay uevent until 'holders' subdir is created */
        p->dev.uevent_suppress = 1;
        err = device_add(&p->dev);
        if (err)
-               goto out1;
-       partition_sysfs_add_subdir(p);
+               goto out_put;
+
+       err = -ENOMEM;
+       p->holder_dir = kobject_create_and_add("holders", &p->dev.kobj);
+       if (!p->holder_dir)
+               goto out_del;
+
        p->dev.uevent_suppress = 0;
        if (flags & ADDPART_FLAG_WHOLEDISK) {
                err = device_create_file(&p->dev, &dev_attr_whole_disk);
                if (err)
-                       goto out2;
+                       goto out_del;
        }
 
+       /* everything is up and running, commence */
+       disk->part[part - 1] = p;
+
        /* suppress uevent if the disk supresses it */
        if (!disk->dev.uevent_suppress)
                kobject_uevent(&p->dev.kobj, KOBJ_ADD);
 
        return 0;
 
-out2:
+out_free:
+       kfree(p);
+       return err;
+out_del:
+       kobject_put(p->holder_dir);
        device_del(&p->dev);
-out1:
+out_put:
        put_device(&p->dev);
-       free_part_stats(p);
-out0:
-       kfree(p);
        return err;
 }