Groups | Search | Server Info | Keyboard shortcuts | Login | Register [http] [https] [nntp] [nntps]
Groups > linux.kernel > #1621404
| From | Niranjan Dighe <niranjan.dighe@gmail.com> |
|---|---|
| Newsgroups | linux.kernel |
| Subject | [PATCH] chipidea: Fix issue in reconnecing gadget without insmod/rmmod |
| Date | 2017-04-11 17:20 +0200 |
| Message-ID | <tv5Ki-gG-13@gated-at.bofh.it> (permalink) |
| Organization | linux.* mail to news gateway |
Currently usb_gadget_connect() is called only through gadget
registration via composite_driver_probe(). As a result, after a
disconnection, if the role transitions to host and back to gadget,
the gadget is not recognized by the host anymore.
This is a typical scenario with an iAP device in the following
usecase -
conn iAP dev -> send roleswitch command -> roleswitch ourself
to gadget -> disconnect iAP device -> roleswitch back to host to
enumerate the device again -> reconnect device -> resend the
roleswitch command -> roleswitch ourself to gadget -> ISSUE.
To workaround this, do the following -
1. Restart OTG FSM on SLi interrupt and on switching role to gadget
so that device transitions to B_IDLE state from B_PERIPHERAL state.
A transition from B_IDLE to B_PERIPHERAL is needed to enable
interrups and restore the correct state of the chipidea controller
so that communication with host is possible
2. usb_gadget_connect() after roleswitch to gadget so that
gadget->ops->pullup() is called and D+ line is asserted. This
causes host to "see" the device and enumeration can happen.
Signed-off-by: Niranjan Dighe <niranjan.dighe@gmail.com>
---
drivers/usb/chipidea/debug.c | 10 +++++++++-
drivers/usb/chipidea/udc.c | 3 +++
2 files changed, 12 insertions(+), 1 deletion(-)
diff --git a/drivers/usb/chipidea/debug.c b/drivers/usb/chipidea/debug.c
index a4f7db2..66c1485 100644
--- a/drivers/usb/chipidea/debug.c
+++ b/drivers/usb/chipidea/debug.c
@@ -16,7 +16,7 @@
#include "udc.h"
#include "bits.h"
#include "otg.h"
-
+extern void ci_hdrc_otg_fsm_restart(struct ci_hdrc *);
/**
* ci_device_show: prints information about device capabilities and status
*/
@@ -325,6 +325,14 @@ static ssize_t ci_role_write(struct file *file, const char __user *ubuf,
ci_role_stop(ci);
ret = ci_role_start(ci, role);
enable_irq(ci->irq);
+
+ /* REVISIT - Avoid repeated FSM restart*/
+
+ if (role == CI_ROLE_GADGET) {
+ ci_hdrc_otg_fsm_restart(ci);
+ usb_gadget_connect(&ci->gadget);
+ }
+
pm_runtime_put_sync(ci->dev);
return ret ? ret : count;
diff --git a/drivers/usb/chipidea/udc.c b/drivers/usb/chipidea/udc.c
index a0accd5..1e3b827 100644
--- a/drivers/usb/chipidea/udc.c
+++ b/drivers/usb/chipidea/udc.c
@@ -29,6 +29,8 @@
#include "otg.h"
#include "otg_fsm.h"
+extern void ci_hdrc_otg_fsm_restart(struct ci_hdrc *);
+
/* control endpoint description */
static const struct usb_endpoint_descriptor
ctrl_endpt_out_desc = {
@@ -1881,6 +1883,7 @@ static irqreturn_t udc_irq(struct ci_hdrc *ci)
ci->driver->suspend(&ci->gadget);
usb_gadget_set_state(&ci->gadget,
USB_STATE_SUSPENDED);
+ ci_hdrc_otg_fsm_restart(ci);
spin_lock(&ci->lock);
}
}
--
2.1.4
Back to linux.kernel | Previous | Next — Next in thread | Find similar | Unroll thread
[PATCH] chipidea: Fix issue in reconnecing gadget without insmod/rmmod Niranjan Dighe <niranjan.dighe@gmail.com> - 2017-04-11 17:20 +0200
Re: [PATCH] chipidea: Fix issue in reconnecing gadget without insmod/rmmod kbuild test robot <lkp@intel.com> - 2017-04-11 20:30 +0200
Re: [PATCH] chipidea: Fix issue in reconnecing gadget without insmod/rmmod Peter Chen <hzpeterchen@gmail.com> - 2017-04-12 14:00 +0200
Re: [PATCH] chipidea: Fix issue in reconnecing gadget without insmod/rmmod Niranjan Dighe <niranjan.dighe@gmail.com> - 2017-04-12 14:50 +0200
Re: [PATCH] chipidea: Fix issue in reconnecing gadget without insmod/rmmod Peter Chen <hzpeterchen@gmail.com> - 2017-04-14 11:40 +0200
csiph-web