diff --git a/drivers/usb/gadget/epautoconf.c b/drivers/usb/gadget/epautoconf.c index 71b15c65b90f..744b8336003d 100644 --- a/drivers/usb/gadget/epautoconf.c +++ b/drivers/usb/gadget/epautoconf.c @@ -205,3 +205,41 @@ void usb_ep_autoconfig_reset (struct usb_gadget *gadget) gadget->out_epnum = 0; } EXPORT_SYMBOL_GPL(usb_ep_autoconfig_reset); + +/** + * usb_ep_autoconfig_by_name - Used to pick the endpoint by name. eg ep1in-gsi + * @gadget: The device to which the endpoint must belong. + * @desc: Endpoint descriptor, with endpoint direction and transfer mode + * initialized. + * @ep_name: EP name that is to be searched. + * + */ +struct usb_ep *usb_ep_autoconfig_by_name( + struct usb_gadget *gadget, + struct usb_endpoint_descriptor *desc, + const char *ep_name +) +{ + struct usb_ep *ep; + bool ep_found = false; + + list_for_each_entry(ep, &gadget->ep_list, ep_list) + if (strcmp(ep->name, ep_name) == 0 && !ep->driver_data) { + ep_found = true; + break; + } + + if (ep_found) { + desc->bEndpointAddress &= USB_DIR_IN; + desc->bEndpointAddress |= ep->ep_num; + ep->address = desc->bEndpointAddress; + pr_debug("Allocating ep address:%x\n", ep->address); + ep->desc = NULL; + ep->comp_desc = NULL; + return ep; + } + + pr_err("%s:error finding ep %s\n", __func__, ep_name); + return NULL; +} +EXPORT_SYMBOL_GPL(usb_ep_autoconfig_by_name); diff --git a/include/linux/usb/gadget.h b/include/linux/usb/gadget.h index e5cd84a0f84a..fe5ab51ac304 100644 --- a/include/linux/usb/gadget.h +++ b/include/linux/usb/gadget.h @@ -184,6 +184,11 @@ struct usb_ep_caps { .dir_out = !!(_dir & USB_EP_CAPS_DIR_OUT), \ } +enum ep_type { + EP_TYPE_NORMAL = 0, + EP_TYPE_GSI, +}; + /** * struct usb_ep - device side representation of USB endpoint * @name:identifier for the endpoint, such as "ep-a" or "ep9in-bulk" @@ -209,6 +214,11 @@ struct usb_ep_caps { * enabled and remains valid until the endpoint is disabled. * @comp_desc: In case of SuperSpeed support, this is the endpoint companion * descriptor that is used to configure the endpoint + * @ep_type: Used to specify type of EP eg. normal vs h/w accelerated. + * @ep_num: Used EP number + * @ep_intr_num: Interrupter number for EP. + * @endless: In case where endless transfer is being initiated, this is set + * to disable usb event interrupt for few events. * * the bus controller driver lists all the general purpose endpoints in * gadget->ep_list. the control endpoint (gadget->ep0) is not in that list, @@ -232,6 +242,10 @@ struct usb_ep { u8 address; const struct usb_endpoint_descriptor *desc; const struct usb_ss_ep_comp_descriptor *comp_desc; + enum ep_type ep_type; + u8 ep_num; + u8 ep_intr_num; + bool endless; }; /*-------------------------------------------------------------------------*/ @@ -883,5 +897,8 @@ extern struct usb_ep *usb_ep_autoconfig_ss(struct usb_gadget *, extern void usb_ep_autoconfig_release(struct usb_ep *); extern void usb_ep_autoconfig_reset(struct usb_gadget *); +extern struct usb_ep *usb_ep_autoconfig_by_name(struct usb_gadget *gadget, + struct usb_endpoint_descriptor *desc, + const char *ep_name); #endif /* __LINUX_USB_GADGET_H */