On Wed, Aug 18, 2021 at 5:27 PM Icenowy Zheng <icenowy@xxxxxxx> wrote: > > > > 于 2021年8月18日 GMT+08:00 下午4:02:24, Kyle Tso <kyletso@xxxxxxxxxx> 写到: > >On Tue, Aug 17, 2021 at 11:13 PM Guenter Roeck <linux@xxxxxxxxxxxx> wrote: > >> > >> On 8/17/21 2:36 AM, Heikki Krogerus wrote: > >> > On Fri, Aug 13, 2021 at 12:31:31PM +0800, Icenowy Zheng wrote: > >> >> Currently, TCPM code omits discover when swapping to gadget, and assume > >> >> that no altmodes are available when swapping from gadget. However, we do > >> >> send discover when we get attached as gadget -- this leads to modes to be > >> >> discovered twice when attached as gadget and then swap to host. > >> >> > >> >> Always re-send discover when swapping DR, regardless of what change is > >> >> being made; and because of this, the assumption that no altmodes are > >> >> registered with gadget role is broken, and altmodes de-registeration is > >> >> always needed now. > >> >> > >> >> Signed-off-by: Icenowy Zheng <icenowy@xxxxxxx> > >> >> --- > >> >> drivers/usb/typec/tcpm/tcpm.c | 9 ++++----- > >> >> 1 file changed, 4 insertions(+), 5 deletions(-) > >> >> > >> >> diff --git a/drivers/usb/typec/tcpm/tcpm.c b/drivers/usb/typec/tcpm/tcpm.c > >> >> index b9bb63d749ec..ab6d0d51ee1c 100644 > >> >> --- a/drivers/usb/typec/tcpm/tcpm.c > >> >> +++ b/drivers/usb/typec/tcpm/tcpm.c > >> >> @@ -4495,15 +4495,14 @@ static void run_state_machine(struct tcpm_port *port) > >> >> tcpm_set_state(port, ready_state(port), 0); > >> >> break; > >> >> case DR_SWAP_CHANGE_DR: > >> >> - if (port->data_role == TYPEC_HOST) { > >> >> - tcpm_unregister_altmodes(port); > >> >> + tcpm_unregister_altmodes(port); > >> >> + if (port->data_role == TYPEC_HOST) > >> >> tcpm_set_roles(port, true, port->pwr_role, > >> >> TYPEC_DEVICE); > >> >> - } else { > >> >> + else > >> >> tcpm_set_roles(port, true, port->pwr_role, > >> >> TYPEC_HOST); > >> >> - port->send_discover = true; > >> >> - } > >> >> + port->send_discover = true; > >> >> tcpm_ams_finish(port); > >> >> tcpm_set_state(port, ready_state(port), 0); > >> >> break; > >> > > >> > Why is it necessary to do discovery with data role swap in general? > >> > > >> > thanks, > >> > > >> > >> Additional question: There are two patches pending related to DR_SWAP > >> and discovery. Are they both needed, or do they both solve the same > >> problem ? > >> > >> Thanks, > >> Guenter > > > >Hi, I just noticed this patch. > > > >Part of this patch and part of my patch > >https://lore.kernel.org/r/20210816075449.2236547-1-kyletso@xxxxxxxxxx > >are to solve the same problem that Discover_Identity is not sent in a > >case where the port becomes UFP after DR_SWAP while in PD3. > > > >The difference (for the DR_SWAP part) is that my patch does not set > >the flag "send_discover" if the port becomes UFP after PD2 DR_SWAP. > >That is because in PD2 Spec, UFP is not allowed to be the SVDM > >Initiator. > > > >This patch indeed solves another problem where > >tcpm_unregister_altmodes should be called during PD3 DR_SWAP because > >the port partner may return mode data in the latest Discover_Mode. For > >the PD2 case, I don't think it needs to be called because PD2 DFP will > >always return NAK for Discover_Mode. However it is fine because it is > > It sounds like my dock is doing something against the specification... > > It sends altmodes rather than NAK when my board gets attached as > UFP and send bogus discovers (because of bugs of current TCPM > code). These altmodes are then registered in TCPM and never get > cleaned up within it, which leads to conflict when the dock is > removed and then re-inserted. > Could you provide more details? 1. Is the connection in PD3 ? 2. Could you provide the tcpm logs? > (BTW is it neceesary for data role and power role to be the same > when attaching? My board now gets attached as UFP to drain > power, and then do DR_SWAP to become USB host.) > Either Sink/UFP or Source/DFP in the beginning. Then DR_SWAP is okay when both ports are in ready state. Your dock looks like a Sourcing Device. Type-C Spec: ``` 4.8.4 Sourcing Device A Sourcing Device is a special sub-class of a DRP that is capable of supplying power, but is not capable of acting as a USB host. For example a hub’s UFP or a monitor’s UFP that operates as a device but not as a host. The Sourcing Device shall follow the rules for a DRP (See Section 4.5.1.4 and Figure 4-15). It shall also follow the requirements for the Source as Power Source (See Section 4.8.1). The Sourcing Device shall support USB PD and shall support the DR_Swap command in order to enable the Source to assume the UFP data role. ``` thanks, Kyle > >safe to call tcpm_unregister_altmodes even if there is no mode data. > > > >In fact, when I was tracing the code I found another bug. PD2 UFP is > >not allowed to send Discover_Identity and Discover_Mode. I can send > >another patch to address this problem. > > > >thanks, > >Kyle