Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

usb: gadget: add usb_gadget_activate/deactivate functions

These functions allows to deactivate gadget to make it not visible to
host and make it active again when gadget driver is finally ready.

They are needed to fix usb_function_activate() and usb_function_deactivate()
functions which currently are not working as usb_gadget_connect() is
called immediately after function bind regardless to previous calls of
usb_gadget_disconnect() function.

Signed-off-by: Robert Baldyga <r.baldyga@samsung.com>
Signed-off-by: Felipe Balbi <balbi@ti.com>

authored by

Robert Baldyga and committed by
Felipe Balbi
ccdf138f 35116993

+95 -7
+95 -7
include/linux/usb/gadget.h
··· 526 526 * @quirk_ep_out_aligned_size: epout requires buffer size to be aligned to 527 527 * MaxPacketSize. 528 528 * @is_selfpowered: if the gadget is self-powered. 529 + * @deactivated: True if gadget is deactivated - in deactivated state it cannot 530 + * be connected. 531 + * @connected: True if gadget is connected. 529 532 * 530 533 * Gadgets have a mostly-portable "gadget driver" implementing device 531 534 * functions, handling all usb configurations and interfaces. Gadget ··· 571 568 unsigned a_alt_hnp_support:1; 572 569 unsigned quirk_ep_out_aligned_size:1; 573 570 unsigned is_selfpowered:1; 571 + unsigned deactivated:1; 572 + unsigned connected:1; 574 573 }; 575 574 #define work_to_gadget(w) (container_of((w), struct usb_gadget, work)) 576 575 ··· 776 771 */ 777 772 static inline int usb_gadget_connect(struct usb_gadget *gadget) 778 773 { 774 + int ret; 775 + 779 776 if (!gadget->ops->pullup) 780 777 return -EOPNOTSUPP; 781 - return gadget->ops->pullup(gadget, 1); 778 + 779 + if (gadget->deactivated) { 780 + /* 781 + * If gadget is deactivated we only save new state. 782 + * Gadget will be connected automatically after activation. 783 + */ 784 + gadget->connected = true; 785 + return 0; 786 + } 787 + 788 + ret = gadget->ops->pullup(gadget, 1); 789 + if (!ret) 790 + gadget->connected = 1; 791 + return ret; 782 792 } 783 793 784 794 /** ··· 804 784 * as a disconnect (when a VBUS session is active). Not all systems 805 785 * support software pullup controls. 806 786 * 807 - * This routine may be used during the gadget driver bind() call to prevent 808 - * the peripheral from ever being visible to the USB host, unless later 809 - * usb_gadget_connect() is called. For example, user mode components may 810 - * need to be activated before the system can talk to hosts. 811 - * 812 787 * Returns zero on success, else negative errno. 813 788 */ 814 789 static inline int usb_gadget_disconnect(struct usb_gadget *gadget) 815 790 { 791 + int ret; 792 + 816 793 if (!gadget->ops->pullup) 817 794 return -EOPNOTSUPP; 818 - return gadget->ops->pullup(gadget, 0); 795 + 796 + if (gadget->deactivated) { 797 + /* 798 + * If gadget is deactivated we only save new state. 799 + * Gadget will stay disconnected after activation. 800 + */ 801 + gadget->connected = false; 802 + return 0; 803 + } 804 + 805 + ret = gadget->ops->pullup(gadget, 0); 806 + if (!ret) 807 + gadget->connected = 0; 808 + return ret; 819 809 } 820 810 811 + /** 812 + * usb_gadget_deactivate - deactivate function which is not ready to work 813 + * @gadget: the peripheral being deactivated 814 + * 815 + * This routine may be used during the gadget driver bind() call to prevent 816 + * the peripheral from ever being visible to the USB host, unless later 817 + * usb_gadget_activate() is called. For example, user mode components may 818 + * need to be activated before the system can talk to hosts. 819 + * 820 + * Returns zero on success, else negative errno. 821 + */ 822 + static inline int usb_gadget_deactivate(struct usb_gadget *gadget) 823 + { 824 + int ret; 825 + 826 + if (gadget->deactivated) 827 + return 0; 828 + 829 + if (gadget->connected) { 830 + ret = usb_gadget_disconnect(gadget); 831 + if (ret) 832 + return ret; 833 + /* 834 + * If gadget was being connected before deactivation, we want 835 + * to reconnect it in usb_gadget_activate(). 836 + */ 837 + gadget->connected = true; 838 + } 839 + gadget->deactivated = true; 840 + 841 + return 0; 842 + } 843 + 844 + /** 845 + * usb_gadget_activate - activate function which is not ready to work 846 + * @gadget: the peripheral being activated 847 + * 848 + * This routine activates gadget which was previously deactivated with 849 + * usb_gadget_deactivate() call. It calls usb_gadget_connect() if needed. 850 + * 851 + * Returns zero on success, else negative errno. 852 + */ 853 + static inline int usb_gadget_activate(struct usb_gadget *gadget) 854 + { 855 + if (!gadget->deactivated) 856 + return 0; 857 + 858 + gadget->deactivated = false; 859 + 860 + /* 861 + * If gadget has been connected before deactivation, or became connected 862 + * while it was being deactivated, we call usb_gadget_connect(). 863 + */ 864 + if (gadget->connected) 865 + return usb_gadget_connect(gadget); 866 + 867 + return 0; 868 + } 821 869 822 870 /*-------------------------------------------------------------------------*/ 823 871