Lines Matching +full:composite +full:- +full:in
1 // SPDX-License-Identifier: GPL-2.0+
3 * composite.c - infrastructure for Composite USB Gadgets
5 * Copyright (C) 2006-2008 David Brownell
17 #include <linux/usb/composite.h>
24 * struct usb_os_string - represents OS String to be reported by a gadget
40 * The code in this file is utility code, used to build a gadget driver
43 * with the relevant device-wide data.
49 return (struct usb_gadget_strings **)uc->stash; in get_containers_gs()
53 * function_descriptors() - get function descriptors for speed
72 descriptors = f->ssp_descriptors; in function_descriptors()
77 descriptors = f->ss_descriptors; in function_descriptors()
82 descriptors = f->hs_descriptors; in function_descriptors()
87 descriptors = f->fs_descriptors; in function_descriptors()
99 * next_desc() - advance to the next desc_type descriptor
112 if ((*t)->bDescriptorType == desc_type) in next_desc()
119 * for_each_desc() - iterate over desc_type descriptors in the
130 * config_ep_by_speed_and_alt() - configures the given endpoint
140 * endpoint according to gadget speed and saves it in the
142 * assigned to it - overwrites it with currently corresponding
163 return -EIO; in config_ep_by_speed_and_alt()
166 switch (g->speed) { in config_ep_by_speed_and_alt()
169 speed_desc = f->ssp_descriptors; in config_ep_by_speed_and_alt()
176 speed_desc = f->ss_descriptors; in config_ep_by_speed_and_alt()
183 speed_desc = f->hs_descriptors; in config_ep_by_speed_and_alt()
188 speed_desc = f->fs_descriptors; in config_ep_by_speed_and_alt()
195 if (int_desc->bAlternateSetting == alt) { in config_ep_by_speed_and_alt()
200 return -EIO; in config_ep_by_speed_and_alt()
206 if (chosen_desc->bEndpointAddress == _ep->address) in config_ep_by_speed_and_alt()
209 return -EIO; in config_ep_by_speed_and_alt()
213 _ep->maxpacket = usb_endpoint_maxp(chosen_desc); in config_ep_by_speed_and_alt()
214 _ep->desc = chosen_desc; in config_ep_by_speed_and_alt()
215 _ep->comp_desc = NULL; in config_ep_by_speed_and_alt()
216 _ep->maxburst = 0; in config_ep_by_speed_and_alt()
217 _ep->mult = 1; in config_ep_by_speed_and_alt()
219 if (g->speed == USB_SPEED_HIGH && (usb_endpoint_xfer_isoc(_ep->desc) || in config_ep_by_speed_and_alt()
220 usb_endpoint_xfer_int(_ep->desc))) in config_ep_by_speed_and_alt()
221 _ep->mult = usb_endpoint_maxp_mult(_ep->desc); in config_ep_by_speed_and_alt()
232 (comp_desc->bDescriptorType != USB_DT_SS_ENDPOINT_COMP)) in config_ep_by_speed_and_alt()
233 return -EIO; in config_ep_by_speed_and_alt()
234 _ep->comp_desc = comp_desc; in config_ep_by_speed_and_alt()
235 if (g->speed >= USB_SPEED_SUPER) { in config_ep_by_speed_and_alt()
236 switch (usb_endpoint_type(_ep->desc)) { in config_ep_by_speed_and_alt()
239 _ep->mult = (comp_desc->bmAttributes & 0x3) + 1; in config_ep_by_speed_and_alt()
243 _ep->maxburst = comp_desc->bMaxBurst + 1; in config_ep_by_speed_and_alt()
246 if (comp_desc->bMaxBurst != 0) { in config_ep_by_speed_and_alt()
252 _ep->maxburst = 1; in config_ep_by_speed_and_alt()
261 * config_ep_by_speed() - configures the given endpoint
270 * endpoint according to gadget speed and saves it in the
272 * assigned to it - overwrites it with currently corresponding
287 * usb_add_function() - add a function to a configuration
303 int value = -EINVAL; in usb_add_function()
305 DBG(config->cdev, "adding '%s'/%p to config '%s'/%p\n", in usb_add_function()
306 function->name, function, in usb_add_function()
307 config->label, config); in usb_add_function()
309 if (!function->set_alt || !function->disable) in usb_add_function()
312 function->config = config; in usb_add_function()
313 list_add_tail(&function->list, &config->functions); in usb_add_function()
315 if (function->bind_deactivated) { in usb_add_function()
321 /* REVISIT *require* function->bind? */ in usb_add_function()
322 if (function->bind) { in usb_add_function()
323 value = function->bind(config, function); in usb_add_function()
325 list_del(&function->list); in usb_add_function()
326 function->config = NULL; in usb_add_function()
336 if (!config->fullspeed && function->fs_descriptors) in usb_add_function()
337 config->fullspeed = true; in usb_add_function()
338 if (!config->highspeed && function->hs_descriptors) in usb_add_function()
339 config->highspeed = true; in usb_add_function()
340 if (!config->superspeed && function->ss_descriptors) in usb_add_function()
341 config->superspeed = true; in usb_add_function()
342 if (!config->superspeed_plus && function->ssp_descriptors) in usb_add_function()
343 config->superspeed_plus = true; in usb_add_function()
347 DBG(config->cdev, "adding '%s'/%p --> %d\n", in usb_add_function()
348 function->name, function, value); in usb_add_function()
355 if (f->disable) in usb_remove_function()
356 f->disable(f); in usb_remove_function()
358 bitmap_zero(f->endpoints, 32); in usb_remove_function()
359 list_del(&f->list); in usb_remove_function()
360 if (f->unbind) in usb_remove_function()
361 f->unbind(c, f); in usb_remove_function()
363 if (f->bind_deactivated) in usb_remove_function()
369 * usb_function_deactivate - prevent function and gadget enumeration
389 struct usb_composite_dev *cdev = function->config->cdev; in usb_function_deactivate()
393 spin_lock_irqsave(&cdev->lock, flags); in usb_function_deactivate()
395 if (cdev->deactivations == 0) in usb_function_deactivate()
396 status = usb_gadget_deactivate(cdev->gadget); in usb_function_deactivate()
398 cdev->deactivations++; in usb_function_deactivate()
400 spin_unlock_irqrestore(&cdev->lock, flags); in usb_function_deactivate()
406 * usb_function_activate - allow function and gadget enumeration
417 struct usb_composite_dev *cdev = function->config->cdev; in usb_function_activate()
421 spin_lock_irqsave(&cdev->lock, flags); in usb_function_activate()
423 if (WARN_ON(cdev->deactivations == 0)) in usb_function_activate()
424 status = -EINVAL; in usb_function_activate()
426 cdev->deactivations--; in usb_function_activate()
427 if (cdev->deactivations == 0) in usb_function_activate()
428 status = usb_gadget_activate(cdev->gadget); in usb_function_activate()
431 spin_unlock_irqrestore(&cdev->lock, flags); in usb_function_activate()
437 * usb_interface_id() - allocate an unused interface ID
444 * ID in interface, association, CDC union, and other descriptors. It
447 * also be class-specific or vendor-specific requests to handle.
452 * identifiers are configuration-specific, functions used in more than
453 * one configuration (or more than once in a given configuration) need
456 * Returns the interface ID which was allocated; or -ENODEV if no
462 unsigned id = config->next_interface_id; in usb_interface_id()
465 config->interface[id] = function; in usb_interface_id()
466 config->next_interface_id = id + 1; in usb_interface_id()
469 return -ENODEV; in usb_interface_id()
478 if (c->MaxPower) in encode_bMaxPower()
479 val = c->MaxPower; in encode_bMaxPower()
503 len = USB_COMP_EP0_BUFSIZ - USB_DT_CONFIG_SIZE; in config_buf()
506 c->bLength = USB_DT_CONFIG_SIZE; in config_buf()
507 c->bDescriptorType = type; in config_buf()
509 c->bNumInterfaces = config->next_interface_id; in config_buf()
510 c->bConfigurationValue = config->bConfigurationValue; in config_buf()
511 c->iConfiguration = config->iConfiguration; in config_buf()
512 c->bmAttributes = USB_CONFIG_ATT_ONE | config->bmAttributes; in config_buf()
513 c->bMaxPower = encode_bMaxPower(speed, config); in config_buf()
516 if (config->descriptors) { in config_buf()
518 config->descriptors); in config_buf()
521 len -= status; in config_buf()
526 list_for_each_entry(f, &config->functions, list) { in config_buf()
536 len -= status; in config_buf()
540 len = next - buf; in config_buf()
541 c->wTotalLength = cpu_to_le16(len); in config_buf()
547 struct usb_gadget *gadget = cdev->gadget; in config_desc()
553 if (gadget->speed >= USB_SPEED_SUPER) in config_desc()
554 speed = gadget->speed; in config_desc()
557 if (gadget->speed == USB_SPEED_HIGH) in config_desc()
569 pos = &cdev->configs; in config_desc()
570 c = cdev->os_desc_config; in config_desc()
574 while ((pos = pos->next) != &cdev->configs) { in config_desc()
578 if (c == cdev->os_desc_config) in config_desc()
585 if (!c->superspeed_plus) in config_desc()
589 if (!c->superspeed) in config_desc()
593 if (!c->highspeed) in config_desc()
597 if (!c->fullspeed) in config_desc()
602 return config_buf(c, speed, cdev->req->buf, type); in config_desc()
603 w_value--; in config_desc()
605 return -EINVAL; in config_desc()
610 struct usb_gadget *gadget = cdev->gadget; in count_configs()
618 if (gadget->speed == USB_SPEED_HIGH) in count_configs()
620 if (gadget->speed == USB_SPEED_SUPER) in count_configs()
622 if (gadget->speed == USB_SPEED_SUPER_PLUS) in count_configs()
627 list_for_each_entry(c, &cdev->configs, list) { in count_configs()
630 if (!c->superspeed_plus) in count_configs()
633 if (!c->superspeed) in count_configs()
636 if (!c->highspeed) in count_configs()
639 if (!c->fullspeed) in count_configs()
648 * bos_desc() - prepares the BOS descriptor.
660 struct usb_bos_descriptor *bos = cdev->req->buf; in bos_desc()
663 bos->bLength = USB_DT_BOS_SIZE; in bos_desc()
664 bos->bDescriptorType = USB_DT_BOS; in bos_desc()
666 bos->wTotalLength = cpu_to_le16(USB_DT_BOS_SIZE); in bos_desc()
667 bos->bNumDeviceCaps = 0; in bos_desc()
670 if (cdev->gadget->ops->get_config_params) { in bos_desc()
671 cdev->gadget->ops->get_config_params(cdev->gadget, in bos_desc()
694 * and shall support LPM when operating in USB2.0 HS mode. in bos_desc()
696 usb_ext = cdev->req->buf + le16_to_cpu(bos->wTotalLength); in bos_desc()
697 bos->bNumDeviceCaps++; in bos_desc()
698 le16_add_cpu(&bos->wTotalLength, USB_DT_USB_EXT_CAP_SIZE); in bos_desc()
699 usb_ext->bLength = USB_DT_USB_EXT_CAP_SIZE; in bos_desc()
700 usb_ext->bDescriptorType = USB_DT_DEVICE_CAPABILITY; in bos_desc()
701 usb_ext->bDevCapabilityType = USB_CAP_TYPE_EXT; in bos_desc()
702 usb_ext->bmAttributes = cpu_to_le32(USB_LPM_SUPPORT | in bos_desc()
709 if (gadget_is_superspeed(cdev->gadget)) { in bos_desc()
712 ss_cap = cdev->req->buf + le16_to_cpu(bos->wTotalLength); in bos_desc()
713 bos->bNumDeviceCaps++; in bos_desc()
714 le16_add_cpu(&bos->wTotalLength, USB_DT_USB_SS_CAP_SIZE); in bos_desc()
715 ss_cap->bLength = USB_DT_USB_SS_CAP_SIZE; in bos_desc()
716 ss_cap->bDescriptorType = USB_DT_DEVICE_CAPABILITY; in bos_desc()
717 ss_cap->bDevCapabilityType = USB_SS_CAP_TYPE; in bos_desc()
718 ss_cap->bmAttributes = 0; /* LTM is not supported yet */ in bos_desc()
719 ss_cap->wSpeedSupported = cpu_to_le16(USB_LOW_SPEED_OPERATION | in bos_desc()
723 ss_cap->bFunctionalitySupport = USB_LOW_SPEED_OPERATION; in bos_desc()
724 ss_cap->bU1devExitLat = dcd_config_params.bU1devExitLat; in bos_desc()
725 ss_cap->bU2DevExitLat = dcd_config_params.bU2DevExitLat; in bos_desc()
729 if (gadget_is_superspeed_plus(cdev->gadget)) { in bos_desc()
732 ssp_cap = cdev->req->buf + le16_to_cpu(bos->wTotalLength); in bos_desc()
733 bos->bNumDeviceCaps++; in bos_desc()
739 le16_add_cpu(&bos->wTotalLength, USB_DT_USB_SSP_CAP_SIZE(1)); in bos_desc()
740 ssp_cap->bLength = USB_DT_USB_SSP_CAP_SIZE(1); in bos_desc()
741 ssp_cap->bDescriptorType = USB_DT_DEVICE_CAPABILITY; in bos_desc()
742 ssp_cap->bDevCapabilityType = USB_SSP_CAP_TYPE; in bos_desc()
743 ssp_cap->bReserved = 0; in bos_desc()
744 ssp_cap->wReserved = 0; in bos_desc()
747 ssp_cap->bmAttributes = cpu_to_le32(1); in bos_desc()
750 ssp_cap->wFunctionalitySupport = in bos_desc()
760 ssp_cap->bmSublinkSpeedAttr[0] = in bos_desc()
769 ssp_cap->bmSublinkSpeedAttr[1] = in bos_desc()
774 return le16_to_cpu(bos->wTotalLength); in bos_desc()
779 struct usb_qualifier_descriptor *qual = cdev->req->buf; in device_qual()
781 qual->bLength = sizeof(*qual); in device_qual()
782 qual->bDescriptorType = USB_DT_DEVICE_QUALIFIER; in device_qual()
784 qual->bcdUSB = cdev->desc.bcdUSB; in device_qual()
785 qual->bDeviceClass = cdev->desc.bDeviceClass; in device_qual()
786 qual->bDeviceSubClass = cdev->desc.bDeviceSubClass; in device_qual()
787 qual->bDeviceProtocol = cdev->desc.bDeviceProtocol; in device_qual()
789 qual->bMaxPacketSize0 = cdev->gadget->ep0->maxpacket; in device_qual()
790 qual->bNumConfigurations = count_configs(cdev, USB_DT_DEVICE_QUALIFIER); in device_qual()
791 qual->bRESERVED = 0; in device_qual()
794 /*-------------------------------------------------------------------------*/
802 list_for_each_entry(f, &cdev->config->functions, list) { in reset_config()
803 if (f->disable) in reset_config()
804 f->disable(f); in reset_config()
806 bitmap_zero(f->endpoints, 32); in reset_config()
808 cdev->config = NULL; in reset_config()
809 cdev->delayed_status = 0; in reset_config()
815 struct usb_gadget *gadget = cdev->gadget; in set_config()
817 int result = -EINVAL; in set_config()
822 list_for_each_entry(c, &cdev->configs, list) { in set_config()
823 if (c->bConfigurationValue == number) { in set_config()
829 if (cdev->config) in set_config()
837 } else { /* Zero configuration value - need to reset the config */ in set_config()
838 if (cdev->config) in set_config()
844 usb_speed_string(gadget->speed), in set_config()
845 number, c ? c->label : "unconfigured"); in set_config()
851 cdev->config = c; in set_config()
855 struct usb_function *f = c->interface[tmp]; in set_config()
867 descriptors = function_descriptors(f, gadget->speed); in set_config()
873 if ((*descriptors)->bDescriptorType != USB_DT_ENDPOINT) in set_config()
877 addr = ((ep->bEndpointAddress & 0x80) >> 3) in set_config()
878 | (ep->bEndpointAddress & 0x0f); in set_config()
879 set_bit(addr, f->endpoints); in set_config()
882 result = f->set_alt(f, tmp, 0); in set_config()
884 DBG(cdev, "interface %d (%s/%p) alt 0 --> %d\n", in set_config()
885 tmp, f->name, f, result); in set_config()
894 __func__, tmp, f->name); in set_config()
895 cdev->delayed_status++; in set_config()
897 cdev->delayed_status); in set_config()
902 power = c->MaxPower ? c->MaxPower : CONFIG_USB_GADGET_VBUS_DRAW; in set_config()
903 if (gadget->speed < USB_SPEED_SUPER) in set_config()
914 if (result >= 0 && cdev->delayed_status) in set_config()
924 if (!config->bConfigurationValue) in usb_add_config_only()
925 return -EINVAL; in usb_add_config_only()
928 list_for_each_entry(c, &cdev->configs, list) { in usb_add_config_only()
929 if (c->bConfigurationValue == config->bConfigurationValue) in usb_add_config_only()
930 return -EBUSY; in usb_add_config_only()
933 config->cdev = cdev; in usb_add_config_only()
934 list_add_tail(&config->list, &cdev->configs); in usb_add_config_only()
936 INIT_LIST_HEAD(&config->functions); in usb_add_config_only()
937 config->next_interface_id = 0; in usb_add_config_only()
938 memset(config->interface, 0, sizeof(config->interface)); in usb_add_config_only()
945 * usb_add_config() - add a configuration to a device.
951 * One of the main tasks of a composite @bind() routine is to
956 * assigns global resources including string IDs, and per-configuration
963 int status = -EINVAL; in usb_add_config()
969 config->bConfigurationValue, in usb_add_config()
970 config->label, config); in usb_add_config()
978 while (!list_empty(&config->functions)) { in usb_add_config()
981 f = list_first_entry(&config->functions, in usb_add_config()
983 list_del(&f->list); in usb_add_config()
984 if (f->unbind) { in usb_add_config()
986 f->name, f); in usb_add_config()
987 f->unbind(config, f); in usb_add_config()
991 list_del(&config->list); in usb_add_config()
992 config->cdev = NULL; in usb_add_config()
997 config->bConfigurationValue, config, in usb_add_config()
998 config->superspeed_plus ? " superplus" : "", in usb_add_config()
999 config->superspeed ? " super" : "", in usb_add_config()
1000 config->highspeed ? " high" : "", in usb_add_config()
1001 config->fullspeed in usb_add_config()
1002 ? (gadget_is_dualspeed(cdev->gadget) in usb_add_config()
1008 struct usb_function *f = config->interface[i]; in usb_add_config()
1013 i, f->name, f); in usb_add_config()
1017 /* set_alt(), or next bind(), sets up ep->claimed as needed */ in usb_add_config()
1018 usb_ep_autoconfig_reset(cdev->gadget); in usb_add_config()
1022 DBG(cdev, "added config '%s'/%u --> %d\n", config->label, in usb_add_config()
1023 config->bConfigurationValue, status); in usb_add_config()
1031 while (!list_empty(&config->functions)) { in remove_config()
1034 f = list_first_entry(&config->functions, in remove_config()
1039 list_del(&config->list); in remove_config()
1040 if (config->unbind) { in remove_config()
1041 DBG(cdev, "unbind config '%s'/%p\n", config->label, config); in remove_config()
1042 config->unbind(config); in remove_config()
1048 * usb_remove_config() - remove a configuration from a device.
1061 spin_lock_irqsave(&cdev->lock, flags); in usb_remove_config()
1063 if (cdev->config == config) in usb_remove_config()
1066 spin_unlock_irqrestore(&cdev->lock, flags); in usb_remove_config()
1071 /*-------------------------------------------------------------------------*/
1073 /* We support strings in multiple languages ... string descriptor zero
1087 language = cpu_to_le16(s->language); in collect_langs()
1110 if (s->language != language) in lookup_string()
1116 return -EINVAL; in lookup_string()
1122 struct usb_composite_driver *composite = cdev->driver; in get_string() local
1139 s->bDescriptorType = USB_DT_STRING; in get_string()
1141 sp = composite->strings; in get_string()
1143 collect_langs(sp, s->wData); in get_string()
1145 list_for_each_entry(c, &cdev->configs, list) { in get_string()
1146 sp = c->strings; in get_string()
1148 collect_langs(sp, s->wData); in get_string()
1150 list_for_each_entry(f, &c->functions, list) { in get_string()
1151 sp = f->strings; in get_string()
1153 collect_langs(sp, s->wData); in get_string()
1156 list_for_each_entry(uc, &cdev->gstrings, list) { in get_string()
1160 collect_langs(sp, s->wData); in get_string()
1163 for (len = 0; len <= USB_MAX_STRING_LEN && s->wData[len]; len++) in get_string()
1166 return -EINVAL; in get_string()
1168 s->bLength = 2 * (len + 1); in get_string()
1169 return s->bLength; in get_string()
1172 if (cdev->use_os_string && language == 0 && id == OS_STRING_IDX) { in get_string()
1174 b->bLength = sizeof(*b); in get_string()
1175 b->bDescriptorType = USB_DT_STRING; in get_string()
1177 sizeof(b->qwSignature) == sizeof(cdev->qw_sign), in get_string()
1179 memcpy(&b->qwSignature, cdev->qw_sign, sizeof(b->qwSignature)); in get_string()
1180 b->bMS_VendorCode = cdev->b_vendor_code; in get_string()
1181 b->bPad = 0; in get_string()
1185 list_for_each_entry(uc, &cdev->gstrings, list) { in get_string()
1194 /* String IDs are device-scoped, so we look up each string in get_string()
1196 * simpler-is-better here. in get_string()
1198 if (composite->strings) { in get_string()
1199 len = lookup_string(composite->strings, buf, language, id); in get_string()
1203 list_for_each_entry(c, &cdev->configs, list) { in get_string()
1204 if (c->strings) { in get_string()
1205 len = lookup_string(c->strings, buf, language, id); in get_string()
1209 list_for_each_entry(f, &c->functions, list) { in get_string()
1210 if (!f->strings) in get_string()
1212 len = lookup_string(f->strings, buf, language, id); in get_string()
1217 return -EINVAL; in get_string()
1221 * usb_string_id() - allocate an unused string ID
1227 * then store that ID in the appropriate descriptors and string table.
1236 if (cdev->next_string_id < 254) { in usb_string_id()
1239 /* 255 reserved as well? -- mina86 */ in usb_string_id()
1240 cdev->next_string_id++; in usb_string_id()
1241 return cdev->next_string_id; in usb_string_id()
1243 return -ENODEV; in usb_string_id()
1248 * usb_string_ids_tab() - allocate unused string IDs in batch
1265 int next = cdev->next_string_id; in usb_string_ids_tab()
1267 for (; str->s; ++str) { in usb_string_ids_tab()
1269 return -ENODEV; in usb_string_ids_tab()
1270 str->id = ++next; in usb_string_ids_tab()
1273 cdev->next_string_id = next; in usb_string_ids_tab()
1298 return ERR_PTR(-ENOMEM); in copy_gadget_strings()
1300 stash = uc->stash; in copy_gadget_strings()
1308 gs->language = sp[n_gs]->language; in copy_gadget_strings()
1309 gs->strings = stash; in copy_gadget_strings()
1310 org_s = sp[n_gs]->strings; in copy_gadget_strings()
1315 if (org_s->s) in copy_gadget_strings()
1316 s->s = org_s->s; in copy_gadget_strings()
1318 s->s = ""; in copy_gadget_strings()
1322 s->s = NULL; in copy_gadget_strings()
1331 * usb_gstrings_attach() - attach gadget strings to a cdev and assign ids
1335 * @n_strings: number of entries in each usb_strings array (sp[]->strings)
1341 * The ->language pointer of each struct usb_gadget_strings has to contain the
1343 * For instance: sp[0] is en-US, sp[1] is es-ES. It is expected that the first
1344 * usb_string entry of es-ES contains the translation of the first usb_string
1345 * entry of en-US. Therefore both entries become the same id assign.
1360 return ERR_PTR(-EINVAL); in usb_gstrings_attach()
1367 ret = usb_string_ids_tab(cdev, n_gs[0]->strings); in usb_gstrings_attach()
1376 m_s = n_gs[0]->strings; in usb_gstrings_attach()
1377 s = n_gs[i]->strings; in usb_gstrings_attach()
1379 s->id = m_s->id; in usb_gstrings_attach()
1384 list_add_tail(&uc->list, &cdev->gstrings); in usb_gstrings_attach()
1385 return n_gs[0]->strings; in usb_gstrings_attach()
1393 * usb_string_ids_n() - allocate unused string IDs in batch
1398 * Returns the first requested ID. This ID and next @n-1 IDs are now
1399 * valid IDs. At least provided that @n is non-zero because if it
1404 * then store that ID in the appropriate descriptors and string table.
1413 unsigned next = c->next_string_id; in usb_string_ids_n()
1415 return -ENODEV; in usb_string_ids_n()
1416 c->next_string_id += n; in usb_string_ids_n()
1421 /*-------------------------------------------------------------------------*/
1427 if (req->status || req->actual != req->length) in composite_setup_complete()
1428 DBG((struct usb_composite_dev *) ep->driver_data, in composite_setup_complete()
1429 "setup complete --> %d, %d/%d\n", in composite_setup_complete()
1430 req->status, req->actual, req->length); in composite_setup_complete()
1434 * so they don't have to maintain the same ->complete() stubs. in composite_setup_complete()
1436 * Because of that, we need to check for the validity of ->context in composite_setup_complete()
1439 if (!req->context) in composite_setup_complete()
1442 cdev = req->context; in composite_setup_complete()
1444 if (cdev->req == req) in composite_setup_complete()
1445 cdev->setup_pending = false; in composite_setup_complete()
1446 else if (cdev->os_desc_req == req) in composite_setup_complete()
1447 cdev->os_desc_pending = false; in composite_setup_complete()
1457 ret = usb_ep_queue(cdev->gadget->ep0, req, gfp_flags); in composite_ep0_queue()
1459 if (cdev->req == req) in composite_ep0_queue()
1460 cdev->setup_pending = true; in composite_ep0_queue()
1461 else if (cdev->os_desc_req == req) in composite_ep0_queue()
1462 cdev->os_desc_pending = true; in composite_ep0_queue()
1475 for (i = 0; i < c->next_interface_id; ++i) { in count_ext_compat()
1479 f = c->interface[i]; in count_ext_compat()
1480 for (j = 0; j < f->os_desc_n; ++j) { in count_ext_compat()
1483 if (i != f->os_desc_table[j].if_id) in count_ext_compat()
1485 d = f->os_desc_table[j].os_desc; in count_ext_compat()
1486 if (d && d->ext_compat_id) in count_ext_compat()
1500 for (i = 0; i < c->next_interface_id; ++i) { in fill_ext_compat()
1504 f = c->interface[i]; in fill_ext_compat()
1505 for (j = 0; j < f->os_desc_n; ++j) { in fill_ext_compat()
1508 if (i != f->os_desc_table[j].if_id) in fill_ext_compat()
1510 d = f->os_desc_table[j].os_desc; in fill_ext_compat()
1511 if (d && d->ext_compat_id) { in fill_ext_compat()
1514 memcpy(buf, d->ext_compat_id, 16); in fill_ext_compat()
1535 f = c->interface[interface]; in count_ext_prop()
1536 for (j = 0; j < f->os_desc_n; ++j) { in count_ext_prop()
1539 if (interface != f->os_desc_table[j].if_id) in count_ext_prop()
1541 d = f->os_desc_table[j].os_desc; in count_ext_prop()
1542 if (d && d->ext_compat_id) in count_ext_prop()
1543 return d->ext_prop_count; in count_ext_prop()
1555 f = c->interface[interface]; in len_ext_prop()
1556 for (j = 0; j < f->os_desc_n; ++j) { in len_ext_prop()
1557 if (interface != f->os_desc_table[j].if_id) in len_ext_prop()
1559 d = f->os_desc_table[j].os_desc; in len_ext_prop()
1561 return min(res + d->ext_prop_len, 4096); in len_ext_prop()
1573 f = c->interface[interface]; in fill_ext_prop()
1576 for (j = 0; j < f->os_desc_n; ++j) { in fill_ext_prop()
1577 if (interface != f->os_desc_table[j].if_id) in fill_ext_prop()
1579 d = f->os_desc_table[j].os_desc; in fill_ext_prop()
1581 list_for_each_entry(ext_prop, &d->ext_prop, entry) { in fill_ext_prop()
1582 n = ext_prop->data_len + in fill_ext_prop()
1583 ext_prop->name_len + 14; in fill_ext_prop()
1587 usb_ext_prop_put_type(buf, ext_prop->type); in fill_ext_prop()
1588 ret = usb_ext_prop_put_name(buf, ext_prop->name, in fill_ext_prop()
1589 ext_prop->name_len); in fill_ext_prop()
1592 switch (ext_prop->type) { in fill_ext_prop()
1597 ext_prop->data, in fill_ext_prop()
1598 ext_prop->data_len); in fill_ext_prop()
1602 ext_prop->data, in fill_ext_prop()
1603 ext_prop->data_len); in fill_ext_prop()
1610 return -EINVAL; in fill_ext_prop()
1622 * not handled lower down, in hardware or the hardware driver(like
1625 * the work is in config and function specific setup.
1631 struct usb_request *req = cdev->req; in composite_setup()
1632 int value = -EOPNOTSUPP; in composite_setup()
1634 u16 w_index = le16_to_cpu(ctrl->wIndex); in composite_setup()
1636 u16 w_value = le16_to_cpu(ctrl->wValue); in composite_setup()
1637 u16 w_length = le16_to_cpu(ctrl->wLength); in composite_setup()
1641 /* partial re-init of the response message; the function or the in composite_setup()
1642 * gadget might need to intercept e.g. a control-OUT completion in composite_setup()
1645 req->zero = 0; in composite_setup()
1646 req->context = cdev; in composite_setup()
1647 req->complete = composite_setup_complete; in composite_setup()
1648 req->length = 0; in composite_setup()
1649 gadget->ep0->driver_data = cdev; in composite_setup()
1652 * Don't let non-standard requests match any of the cases below in composite_setup()
1655 if ((ctrl->bRequestType & USB_TYPE_MASK) != USB_TYPE_STANDARD) in composite_setup()
1658 switch (ctrl->bRequest) { in composite_setup()
1662 if (ctrl->bRequestType != USB_DIR_IN) in composite_setup()
1667 cdev->desc.bNumConfigurations = in composite_setup()
1669 cdev->desc.bMaxPacketSize0 = in composite_setup()
1670 cdev->gadget->ep0->maxpacket; in composite_setup()
1672 if (gadget->speed >= USB_SPEED_SUPER) { in composite_setup()
1673 cdev->desc.bcdUSB = cpu_to_le16(0x0320); in composite_setup()
1674 cdev->desc.bMaxPacketSize0 = 9; in composite_setup()
1676 cdev->desc.bcdUSB = cpu_to_le16(0x0210); in composite_setup()
1679 if (gadget->lpm_capable) in composite_setup()
1680 cdev->desc.bcdUSB = cpu_to_le16(0x0201); in composite_setup()
1682 cdev->desc.bcdUSB = cpu_to_le16(0x0200); in composite_setup()
1685 value = min(w_length, (u16) sizeof cdev->desc); in composite_setup()
1686 memcpy(req->buf, &cdev->desc, value); in composite_setup()
1690 gadget->speed >= USB_SPEED_SUPER) in composite_setup()
1698 gadget->speed >= USB_SPEED_SUPER) in composite_setup()
1707 value = get_string(cdev, req->buf, in composite_setup()
1714 gadget->lpm_capable) { in composite_setup()
1724 if (cdev->config) in composite_setup()
1725 config = cdev->config; in composite_setup()
1728 &cdev->configs, in composite_setup()
1733 if (gadget->otg_caps && in composite_setup()
1734 (gadget->otg_caps->otg_rev >= 0x0200)) in composite_setup()
1742 memcpy(req->buf, config->descriptors[0], value); in composite_setup()
1750 if (ctrl->bRequestType != 0) in composite_setup()
1753 if (gadget->a_hnp_support) in composite_setup()
1755 else if (gadget->a_alt_hnp_support) in composite_setup()
1760 spin_lock(&cdev->lock); in composite_setup()
1762 spin_unlock(&cdev->lock); in composite_setup()
1765 if (ctrl->bRequestType != USB_DIR_IN) in composite_setup()
1767 if (cdev->config) in composite_setup()
1768 *(u8 *)req->buf = cdev->config->bConfigurationValue; in composite_setup()
1770 *(u8 *)req->buf = 0; in composite_setup()
1776 if (ctrl->bRequestType != USB_RECIP_INTERFACE) in composite_setup()
1778 if (!cdev->config || intf >= MAX_CONFIG_INTERFACES) in composite_setup()
1780 f = cdev->config->interface[intf]; in composite_setup()
1787 * as we check this in usb_add_function(). in composite_setup()
1789 if (w_value && !f->get_alt) in composite_setup()
1792 spin_lock(&cdev->lock); in composite_setup()
1793 value = f->set_alt(f, w_index, w_value); in composite_setup()
1797 __func__, intf, f->name); in composite_setup()
1798 cdev->delayed_status++; in composite_setup()
1800 cdev->delayed_status); in composite_setup()
1802 spin_unlock(&cdev->lock); in composite_setup()
1805 if (ctrl->bRequestType != (USB_DIR_IN|USB_RECIP_INTERFACE)) in composite_setup()
1807 if (!cdev->config || intf >= MAX_CONFIG_INTERFACES) in composite_setup()
1809 f = cdev->config->interface[intf]; in composite_setup()
1813 value = f->get_alt ? f->get_alt(f, w_index) : 0; in composite_setup()
1816 *((u8 *)req->buf) = value; in composite_setup()
1820 if (gadget_is_otg(gadget) && gadget->hnp_polling_support && in composite_setup()
1822 if (ctrl->bRequestType != (USB_DIR_IN | in composite_setup()
1825 *((u8 *)req->buf) = gadget->host_request_flag; in composite_setup()
1839 if (ctrl->bRequestType != (USB_DIR_IN | USB_RECIP_INTERFACE)) in composite_setup()
1842 put_unaligned_le16(0, req->buf); in composite_setup()
1843 if (!cdev->config || intf >= MAX_CONFIG_INTERFACES) in composite_setup()
1845 f = cdev->config->interface[intf]; in composite_setup()
1848 status = f->get_status ? f->get_status(f) : 0; in composite_setup()
1851 put_unaligned_le16(status & 0x0000ffff, req->buf); in composite_setup()
1862 if (ctrl->bRequestType != (USB_DIR_OUT | USB_RECIP_INTERFACE)) in composite_setup()
1866 if (!cdev->config || intf >= MAX_CONFIG_INTERFACES) in composite_setup()
1868 f = cdev->config->interface[intf]; in composite_setup()
1872 if (f->func_suspend) in composite_setup()
1873 value = f->func_suspend(f, w_index >> 8); in composite_setup()
1888 if (cdev->use_os_string && cdev->os_desc_config && in composite_setup()
1889 (ctrl->bRequestType & USB_TYPE_VENDOR) && in composite_setup()
1890 ctrl->bRequest == cdev->b_vendor_code) { in composite_setup()
1896 req = cdev->os_desc_req; in composite_setup()
1897 req->context = cdev; in composite_setup()
1898 req->complete = composite_setup_complete; in composite_setup()
1899 buf = req->buf; in composite_setup()
1900 os_desc_cfg = cdev->os_desc_config; in composite_setup()
1904 switch (ctrl->bRequestType & USB_RECIP_MASK) { in composite_setup()
1946 "non-core control req%02x.%02x v%04x i%04x l%d\n", in composite_setup()
1947 ctrl->bRequestType, ctrl->bRequest, in composite_setup()
1954 if (cdev->config) { in composite_setup()
1955 list_for_each_entry(f, &cdev->config->functions, list) in composite_setup()
1956 if (f->req_match && in composite_setup()
1957 f->req_match(f, ctrl, false)) in composite_setup()
1961 list_for_each_entry(c, &cdev->configs, list) in composite_setup()
1962 list_for_each_entry(f, &c->functions, list) in composite_setup()
1963 if (f->req_match && in composite_setup()
1964 f->req_match(f, ctrl, true)) in composite_setup()
1969 switch (ctrl->bRequestType & USB_RECIP_MASK) { in composite_setup()
1971 if (!cdev->config || intf >= MAX_CONFIG_INTERFACES) in composite_setup()
1973 f = cdev->config->interface[intf]; in composite_setup()
1977 if (!cdev->config) in composite_setup()
1980 list_for_each_entry(f, &cdev->config->functions, list) { in composite_setup()
1981 if (test_bit(endp, f->endpoints)) in composite_setup()
1984 if (&f->list == &cdev->config->functions) in composite_setup()
1989 if (f && f->setup) in composite_setup()
1990 value = f->setup(f, ctrl); in composite_setup()
1994 c = cdev->config; in composite_setup()
1999 if (c->setup) { in composite_setup()
2000 value = c->setup(c, ctrl); in composite_setup()
2004 /* try the only function in the current config */ in composite_setup()
2005 if (!list_is_singular(&c->functions)) in composite_setup()
2007 f = list_first_entry(&c->functions, struct usb_function, in composite_setup()
2009 if (f->setup) in composite_setup()
2010 value = f->setup(f, ctrl); in composite_setup()
2019 req->length = value; in composite_setup()
2020 req->context = cdev; in composite_setup()
2021 req->zero = value < w_length; in composite_setup()
2024 DBG(cdev, "ep_queue --> %d\n", value); in composite_setup()
2025 req->status = 0; in composite_setup()
2026 composite_setup_complete(gadget->ep0, req); in composite_setup()
2047 spin_lock_irqsave(&cdev->lock, flags); in composite_disconnect()
2048 cdev->suspended = 0; in composite_disconnect()
2049 if (cdev->config) in composite_disconnect()
2051 if (cdev->driver->disconnect) in composite_disconnect()
2052 cdev->driver->disconnect(cdev); in composite_disconnect()
2053 spin_unlock_irqrestore(&cdev->lock, flags); in composite_disconnect()
2056 /*-------------------------------------------------------------------------*/
2064 return sprintf(buf, "%d\n", cdev->suspended); in suspended_show()
2071 struct usb_gadget_strings *gstr = cdev->driver->strings[0]; in __composite_unbind()
2072 struct usb_string *dev_str = gstr->strings; in __composite_unbind()
2077 * state protected by cdev->lock. in __composite_unbind()
2079 WARN_ON(cdev->config); in __composite_unbind()
2081 while (!list_empty(&cdev->configs)) { in __composite_unbind()
2083 c = list_first_entry(&cdev->configs, in __composite_unbind()
2087 if (cdev->driver->unbind && unbind_driver) in __composite_unbind()
2088 cdev->driver->unbind(cdev); in __composite_unbind()
2092 if (dev_str[USB_GADGET_MANUFACTURER_IDX].s == cdev->def_manufacturer) in __composite_unbind()
2095 kfree(cdev->def_manufacturer); in __composite_unbind()
2116 * these variables may have been set in in update_unchanged_dev_desc()
2119 idVendor = new->idVendor; in update_unchanged_dev_desc()
2120 idProduct = new->idProduct; in update_unchanged_dev_desc()
2121 bcdDevice = new->bcdDevice; in update_unchanged_dev_desc()
2122 iSerialNumber = new->iSerialNumber; in update_unchanged_dev_desc()
2123 iManufacturer = new->iManufacturer; in update_unchanged_dev_desc()
2124 iProduct = new->iProduct; in update_unchanged_dev_desc()
2128 new->idVendor = idVendor; in update_unchanged_dev_desc()
2130 new->idProduct = idProduct; in update_unchanged_dev_desc()
2132 new->bcdDevice = bcdDevice; in update_unchanged_dev_desc()
2134 new->bcdDevice = cpu_to_le16(get_default_bcdDevice()); in update_unchanged_dev_desc()
2136 new->iSerialNumber = iSerialNumber; in update_unchanged_dev_desc()
2138 new->iManufacturer = iManufacturer; in update_unchanged_dev_desc()
2140 new->iProduct = iProduct; in update_unchanged_dev_desc()
2143 int composite_dev_prepare(struct usb_composite_driver *composite, in composite_dev_prepare() argument
2146 struct usb_gadget *gadget = cdev->gadget; in composite_dev_prepare()
2147 int ret = -ENOMEM; in composite_dev_prepare()
2150 cdev->req = usb_ep_alloc_request(gadget->ep0, GFP_KERNEL); in composite_dev_prepare()
2151 if (!cdev->req) in composite_dev_prepare()
2152 return -ENOMEM; in composite_dev_prepare()
2154 cdev->req->buf = kmalloc(USB_COMP_EP0_BUFSIZ, GFP_KERNEL); in composite_dev_prepare()
2155 if (!cdev->req->buf) in composite_dev_prepare()
2158 ret = device_create_file(&gadget->dev, &dev_attr_suspended); in composite_dev_prepare()
2162 cdev->req->complete = composite_setup_complete; in composite_dev_prepare()
2163 cdev->req->context = cdev; in composite_dev_prepare()
2164 gadget->ep0->driver_data = cdev; in composite_dev_prepare()
2166 cdev->driver = composite; in composite_dev_prepare()
2170 * more than 100mA from USB must report itself as bus-powered in in composite_dev_prepare()
2178 * drivers will zero ep->driver_data. in composite_dev_prepare()
2183 kfree(cdev->req->buf); in composite_dev_prepare()
2185 usb_ep_free_request(gadget->ep0, cdev->req); in composite_dev_prepare()
2186 cdev->req = NULL; in composite_dev_prepare()
2195 cdev->os_desc_req = usb_ep_alloc_request(ep0, GFP_KERNEL); in composite_os_desc_req_prepare()
2196 if (!cdev->os_desc_req) { in composite_os_desc_req_prepare()
2197 ret = -ENOMEM; in composite_os_desc_req_prepare()
2201 cdev->os_desc_req->buf = kmalloc(USB_COMP_EP0_OS_DESC_BUFSIZ, in composite_os_desc_req_prepare()
2203 if (!cdev->os_desc_req->buf) { in composite_os_desc_req_prepare()
2204 ret = -ENOMEM; in composite_os_desc_req_prepare()
2205 usb_ep_free_request(ep0, cdev->os_desc_req); in composite_os_desc_req_prepare()
2208 cdev->os_desc_req->context = cdev; in composite_os_desc_req_prepare()
2209 cdev->os_desc_req->complete = composite_setup_complete; in composite_os_desc_req_prepare()
2219 list_for_each_entry_safe(uc, tmp, &cdev->gstrings, list) { in composite_dev_cleanup()
2220 list_del(&uc->list); in composite_dev_cleanup()
2223 if (cdev->os_desc_req) { in composite_dev_cleanup()
2224 if (cdev->os_desc_pending) in composite_dev_cleanup()
2225 usb_ep_dequeue(cdev->gadget->ep0, cdev->os_desc_req); in composite_dev_cleanup()
2227 kfree(cdev->os_desc_req->buf); in composite_dev_cleanup()
2228 cdev->os_desc_req->buf = NULL; in composite_dev_cleanup()
2229 usb_ep_free_request(cdev->gadget->ep0, cdev->os_desc_req); in composite_dev_cleanup()
2230 cdev->os_desc_req = NULL; in composite_dev_cleanup()
2232 if (cdev->req) { in composite_dev_cleanup()
2233 if (cdev->setup_pending) in composite_dev_cleanup()
2234 usb_ep_dequeue(cdev->gadget->ep0, cdev->req); in composite_dev_cleanup()
2236 kfree(cdev->req->buf); in composite_dev_cleanup()
2237 cdev->req->buf = NULL; in composite_dev_cleanup()
2238 usb_ep_free_request(cdev->gadget->ep0, cdev->req); in composite_dev_cleanup()
2239 cdev->req = NULL; in composite_dev_cleanup()
2241 cdev->next_string_id = 0; in composite_dev_cleanup()
2242 device_remove_file(&cdev->gadget->dev, &dev_attr_suspended); in composite_dev_cleanup()
2247 * In that case, the dispose() callback is used to notify the in composite_dev_cleanup()
2248 * backend that the EPs are no longer in use. in composite_dev_cleanup()
2254 &cdev->gadget->ep_list, ep_list) { in composite_dev_cleanup()
2255 if (ep->ops->dispose) in composite_dev_cleanup()
2256 ep->ops->dispose(ep); in composite_dev_cleanup()
2264 struct usb_composite_driver *composite = to_cdriver(gdriver); in composite_bind() local
2265 int status = -ENOMEM; in composite_bind()
2271 spin_lock_init(&cdev->lock); in composite_bind()
2272 cdev->gadget = gadget; in composite_bind()
2274 INIT_LIST_HEAD(&cdev->configs); in composite_bind()
2275 INIT_LIST_HEAD(&cdev->gstrings); in composite_bind()
2277 status = composite_dev_prepare(composite, cdev); in composite_bind()
2281 /* composite gadget needs to assign strings for whole device (like in composite_bind()
2285 status = composite->bind(cdev); in composite_bind()
2289 if (cdev->use_os_string) { in composite_bind()
2290 status = composite_os_desc_req_prepare(cdev, gadget->ep0); in composite_bind()
2295 update_unchanged_dev_desc(&cdev->desc, composite->dev); in composite_bind()
2298 if (composite->needs_serial && !cdev->desc.iSerialNumber) in composite_bind()
2301 INFO(cdev, "%s ready\n", composite->name); in composite_bind()
2309 /*-------------------------------------------------------------------------*/
2320 if (cdev->config) { in composite_suspend()
2321 list_for_each_entry(f, &cdev->config->functions, list) { in composite_suspend()
2322 if (f->suspend) in composite_suspend()
2323 f->suspend(f); in composite_suspend()
2326 if (cdev->driver->suspend) in composite_suspend()
2327 cdev->driver->suspend(cdev); in composite_suspend()
2329 cdev->suspended = 1; in composite_suspend()
2345 if (cdev->driver->resume) in composite_resume()
2346 cdev->driver->resume(cdev); in composite_resume()
2347 if (cdev->config) { in composite_resume()
2348 list_for_each_entry(f, &cdev->config->functions, list) { in composite_resume()
2349 if (f->resume) in composite_resume()
2350 f->resume(f); in composite_resume()
2353 maxpower = cdev->config->MaxPower ? in composite_resume()
2354 cdev->config->MaxPower : CONFIG_USB_GADGET_VBUS_DRAW; in composite_resume()
2355 if (gadget->speed < USB_SPEED_SUPER) in composite_resume()
2366 cdev->suspended = 0; in composite_resume()
2369 /*-------------------------------------------------------------------------*/
2388 * usb_composite_probe() - register a composite driver
2393 * This function is used to register drivers using the composite driver
2400 * while it was binding. That would usually be done in order to wait for
2407 if (!driver || !driver->dev || !driver->bind) in usb_composite_probe()
2408 return -EINVAL; in usb_composite_probe()
2410 if (!driver->name) in usb_composite_probe()
2411 driver->name = "composite"; in usb_composite_probe()
2413 driver->gadget_driver = composite_driver_template; in usb_composite_probe()
2414 gadget_driver = &driver->gadget_driver; in usb_composite_probe()
2416 gadget_driver->function = (char *) driver->name; in usb_composite_probe()
2417 gadget_driver->driver.name = driver->name; in usb_composite_probe()
2418 gadget_driver->max_speed = driver->max_speed; in usb_composite_probe()
2425 * usb_composite_unregister() - unregister a composite driver
2428 * This function is used to unregister drivers using the composite
2433 usb_gadget_unregister_driver(&driver->gadget_driver); in usb_composite_unregister()
2438 * usb_composite_setup_continue() - Continue with the control transfer
2439 * @cdev: the composite device who's control transfer was kept waiting
2442 * with the control transfer's data/status stage in case it had requested to
2444 * can request the composite framework to delay the setup request's data/status
2450 struct usb_request *req = cdev->req; in usb_composite_setup_continue()
2454 spin_lock_irqsave(&cdev->lock, flags); in usb_composite_setup_continue()
2456 if (cdev->delayed_status == 0) { in usb_composite_setup_continue()
2459 } else if (--cdev->delayed_status == 0) { in usb_composite_setup_continue()
2461 req->length = 0; in usb_composite_setup_continue()
2462 req->context = cdev; in usb_composite_setup_continue()
2465 DBG(cdev, "ep_queue --> %d\n", value); in usb_composite_setup_continue()
2466 req->status = 0; in usb_composite_setup_continue()
2467 composite_setup_complete(cdev->gadget->ep0, req); in usb_composite_setup_continue()
2471 spin_unlock_irqrestore(&cdev->lock, flags); in usb_composite_setup_continue()
2477 return kasprintf(GFP_KERNEL, "%s %s with %s", init_utsname()->sysname, in composite_default_mfr()
2478 init_utsname()->release, gadget->name); in composite_default_mfr()
2484 struct usb_device_descriptor *desc = &cdev->desc; in usb_composite_overwrite_options()
2485 struct usb_gadget_strings *gstr = cdev->driver->strings[0]; in usb_composite_overwrite_options()
2486 struct usb_string *dev_str = gstr->strings; in usb_composite_overwrite_options()
2488 if (covr->idVendor) in usb_composite_overwrite_options()
2489 desc->idVendor = cpu_to_le16(covr->idVendor); in usb_composite_overwrite_options()
2491 if (covr->idProduct) in usb_composite_overwrite_options()
2492 desc->idProduct = cpu_to_le16(covr->idProduct); in usb_composite_overwrite_options()
2494 if (covr->bcdDevice) in usb_composite_overwrite_options()
2495 desc->bcdDevice = cpu_to_le16(covr->bcdDevice); in usb_composite_overwrite_options()
2497 if (covr->serial_number) { in usb_composite_overwrite_options()
2498 desc->iSerialNumber = dev_str[USB_GADGET_SERIAL_IDX].id; in usb_composite_overwrite_options()
2499 dev_str[USB_GADGET_SERIAL_IDX].s = covr->serial_number; in usb_composite_overwrite_options()
2501 if (covr->manufacturer) { in usb_composite_overwrite_options()
2502 desc->iManufacturer = dev_str[USB_GADGET_MANUFACTURER_IDX].id; in usb_composite_overwrite_options()
2503 dev_str[USB_GADGET_MANUFACTURER_IDX].s = covr->manufacturer; in usb_composite_overwrite_options()
2506 desc->iManufacturer = dev_str[USB_GADGET_MANUFACTURER_IDX].id; in usb_composite_overwrite_options()
2507 cdev->def_manufacturer = composite_default_mfr(cdev->gadget); in usb_composite_overwrite_options()
2508 dev_str[USB_GADGET_MANUFACTURER_IDX].s = cdev->def_manufacturer; in usb_composite_overwrite_options()
2511 if (covr->product) { in usb_composite_overwrite_options()
2512 desc->iProduct = dev_str[USB_GADGET_PRODUCT_IDX].id; in usb_composite_overwrite_options()
2513 dev_str[USB_GADGET_PRODUCT_IDX].s = covr->product; in usb_composite_overwrite_options()