Signed-off-by: Andrzej Pietrasiewicz <andrzej.p@xxxxxxxxxxx> Signed-off-by: Kyungmin Park <kyungmin.park@xxxxxxxxxxx> --- drivers/usb/gadget/f_mass_storage.c | 135 +++++++++++++++-------------------- drivers/usb/gadget/f_mass_storage.h | 4 +- 2 files changed, 58 insertions(+), 81 deletions(-) diff --git a/drivers/usb/gadget/f_mass_storage.c b/drivers/usb/gadget/f_mass_storage.c index 0c3d817..b244ddc 100644 --- a/drivers/usb/gadget/f_mass_storage.c +++ b/drivers/usb/gadget/f_mass_storage.c @@ -2521,78 +2521,31 @@ void fsg_common_put(struct fsg_common *common) } EXPORT_SYMBOL(fsg_common_put); -struct fsg_common *fsg_common_init(struct fsg_common *common, - struct usb_composite_dev *cdev, - struct fsg_config *cfg) +struct fsg_common *fsg_common_init(struct fsg_common *common) { - struct usb_gadget *gadget = cdev->gadget; struct fsg_buffhd *bh; - struct fsg_lun *curlun; - struct fsg_lun_config *lcfg; - int nluns, i, rc; - char *pathbuf; + int i, rc; rc = fsg_num_buffers_validate(); if (rc != 0) return ERR_PTR(rc); - /* Find out how many LUNs there should be */ - nluns = cfg->nluns; - if (nluns < 1 || nluns > FSG_MAX_LUNS) { - dev_err(&gadget->dev, "invalid number of LUNs: %u\n", nluns); + /* TODO: move it somewhere else */ + /*if (common->nluns < 1 || common->nluns > FSG_MAX_LUNS) { + printk("invalid number of LUNs: %u\n", nluns); return ERR_PTR(-EINVAL); - } - - /* Allocate? */ - if (!common) { - common = kzalloc(sizeof *common, GFP_KERNEL); - if (!common) - return ERR_PTR(-ENOMEM); - common->free_storage_on_release = 1; - } else { - memset(common, 0, sizeof *common); - common->free_storage_on_release = 0; - } + }*/ common->buffhds = kcalloc(fsg_num_buffers, sizeof *(common->buffhds), GFP_KERNEL); - if (!common->buffhds) { - if (common->free_storage_on_release) - kfree(common); + if (!common->buffhds) return ERR_PTR(-ENOMEM); - } - - common->ops = cfg->ops; - common->private_data = cfg->private_data; - - common->gadget = gadget; - common->ep0 = gadget->ep0; - common->ep0req = cdev->req; - common->cdev = cdev; - /* Maybe allocate device-global string IDs, and patch descriptors */ - if (fsg_strings[FSG_STRING_INTERFACE].id == 0) { - rc = usb_string_id(cdev); - if (unlikely(rc < 0)) - goto error_release; - fsg_strings[FSG_STRING_INTERFACE].id = rc; - fsg_intf_desc.iInterface = rc; - } - - /* - * Create the LUNs, open their backing files, and register the - * LUN devices in sysfs. - */ - curlun = kcalloc(nluns, sizeof(*curlun), GFP_KERNEL); - if (unlikely(!curlun)) { - rc = -ENOMEM; - goto error_release; - } - common->luns = curlun; + common->ops = NULL; + common->private_data = NULL; init_rwsem(&common->filesem); - /* Data buffers cyclic list */ bh = common->buffhds; i = fsg_num_buffers; @@ -2609,24 +2562,6 @@ buffhds_first_it: } while (--i); bh->next = common->buffhds; - /* Prepare inquiryString */ - i = get_default_bcdDevice(); - snprintf(common->inquiry_string, sizeof common->inquiry_string, - "%-8s%-16s%04x", cfg->vendor_name ?: "Linux", - /* Assume product name dependent on the first LUN */ - cfg->product_name ?: (common->luns->cdrom - ? "File-Stor Gadget" - : "File-CD Gadget"), - i); - - /* - * Some peripheral controllers are known not to be able to - * halt bulk endpoints correctly. If one of them is present, - * disable stalls. - */ - common->can_stall = cfg->can_stall && - !(gadget_is_at91(common->gadget)); - spin_lock_init(&common->lock); kref_init(&common->ref); @@ -2641,8 +2576,10 @@ buffhds_first_it: init_waitqueue_head(&common->fsg_wait); /* Information */ + pr_info(FSG_DRIVER_DESC ", version: " FSG_DRIVER_VERSION "\n"); + pr_info("Number of LUNs=%d\n", common->nluns); - DBG(common, "I/O thread pid: %d\n", task_pid_nr(common->thread_task)); + pr_info("I/O thread pid: %d\n", task_pid_nr(common->thread_task)); wake_up_process(common->thread_task); @@ -2656,6 +2593,51 @@ error_release: } EXPORT_SYMBOL(fsg_common_init); +static struct fsg_common *fsg_common_init_cdev(struct fsg_common *common, + struct usb_composite_dev *cdev) +{ + struct usb_gadget *gadget = cdev->gadget; + int rc, i; + + common->gadget = gadget; + common->ep0 = gadget->ep0; + common->ep0req = cdev->req; + common->cdev = cdev; + + /* Maybe allocate device-global string IDs, and patch descriptors */ + if (fsg_strings[FSG_STRING_INTERFACE].id == 0) { + rc = usb_string_id(cdev); + if (unlikely(rc < 0)) + goto error_release; + fsg_strings[FSG_STRING_INTERFACE].id = rc; + fsg_intf_desc.iInterface = rc; + } + + /* Prepare inquiryString */ + i = get_default_bcdDevice(); + snprintf(common->inquiry_string, sizeof common->inquiry_string, + "%-8s%-16s%04x", "Linux", + /* Assume product name dependent on the first LUN */ + /* TODO: actually check first child's "cdrom" flag */ + "USB mass storage", i); + + /* + * Some peripheral controllers are known not to be able to + * halt bulk endpoints correctly. If one of them is present, + * disable stalls. + */ + common->can_stall = common->can_stall && + !(gadget_is_at91(common->gadget)); + + return common; + +error_release: + common->state = FSG_STATE_TERMINATED; /* The thread is dead */ + /* Call fsg_common_release() directly, ref might be not initialised. */ + fsg_common_release(&common->ref); + return ERR_PTR(rc); +} + static void fsg_common_release(struct kref *ref) { struct fsg_common *common = container_of(ref, struct fsg_common, ref); @@ -2680,11 +2662,8 @@ static void fsg_common_release(struct kref *ref) } kfree(common->buffhds); - if (common->free_storage_on_release) - kfree(common); } - /*-------------------------------------------------------------------------*/ static void fsg_unbind(struct usb_configuration *c, struct usb_function *f) diff --git a/drivers/usb/gadget/f_mass_storage.h b/drivers/usb/gadget/f_mass_storage.h index 8c0e885..f81a0e0 100644 --- a/drivers/usb/gadget/f_mass_storage.h +++ b/drivers/usb/gadget/f_mass_storage.h @@ -88,9 +88,7 @@ struct fsg_common { struct kref ref; }; -struct fsg_common *fsg_common_init(struct fsg_common *common, - struct usb_composite_dev *cdev, - struct fsg_config *cfg); +struct fsg_common *fsg_common_init(struct fsg_common *common); void fsg_common_get(struct fsg_common *common); void fsg_common_put(struct fsg_common *common); -- 1.7.0.4 -- To unsubscribe from this list: send the line "unsubscribe linux-usb" in the body of a message to majordomo@xxxxxxxxxxxxxxx More majordomo info at http://vger.kernel.org/majordomo-info.html