cancel
Showing results for 
Search instead for 
Did you mean: 

USB ethernet gadget stops working after replugging cable

BillR
Associate III

Not sure if this is the best forum for this question but I am using the USB OTG port in device mode as ethernet gadget. It works fine if plugged in from boot, or first plug in anytime after.

But if unplugged and plugged in again it will not come back without a board reboot:

[  46.766872] dwc2 49000000.usb-otg: new device is high-speed
[  46.771014] dwc2 49000000.usb-otg: dwc2_hsotg_enqueue_setup: failed queue (-11)

Error -11 is something like "resource temporarily unavailable". Ever seen this before?

1 ACCEPTED SOLUTION

Accepted Solutions
BillR
Associate III

I decided it was time to take the dive into the kernel and then confirmed there is no disconnect interrupt in device mode, only suspend due to no activity on D lines.  

0693W00000Lvm1AQAR.pngThis isn't a problem on the DK2 I believe because its using the STMUSB1600 which gives disconnected indication. Since we only needed device mode and that chip was not available, we thought it wouldn't be a problem to leave out.

So, in

drivers/usb/dwc2/core_intr.c

we have the following:

/*
 * Change to L2 (suspend) state before releasing
 * spinlock
 */
hsotg->lx_state = DWC2_L2;
 
/* Call gadget suspend callback */
call_gadget(hsotg, suspend);

Change to:

dwc2_hsotg_disconnect(hsotg); 

I am going to test this next week.

Bill

View solution in original post

12 REPLIES 12
Olivier GALLIEN
ST Employee

Hi @BillR​ ,

Yes, it can be due to wrong DTS setting which depends on your software version.

Can you please share the OpenSTLinux version you are using and kernel dts ?

Thanks

Olivier

Olivier GALLIEN
In order to give better visibility on the answered topics, please click on 'Accept as Solution' on the reply which solved your issue or answered your question.
Kevin HUBER
ST Employee

Hello @BillR​ ,

In top of the request of Olivier, I will also need to know the content of your shell script that makes the configuration of USB Gadget.

Below you have the wiki page with an example script "stm32_usbotg_eth_config.sh" :

https://wiki.st.com/stm32mpu/wiki/USB_overview#How_to_configure_USB_Gadget_through_configfs

Can I also have your complete bootlog traces please.

Regards,

Kevin

In order to give better visibility on the answered topics, please click on 'Accept as Solution' on the reply which solved your issue or answered your question.
BillR
Associate III

Thanks for the responses so far. I am away from the project for a few days and will be getting back to this next week. I did notice that calling the script with stop and then start, it will work again. I'll get back to you with some info soon, thanks!

BillR
Associate III

I am using the kernel from OpenSTLinux 5.4 Dunfell 20-06-24.

Attached is a zip file with kernel config, boot log, shell script, and kernel device tree.

If I run the script (stm32_usbotg_eth_config.sh) with stop and start, that will restart the RNDIS OK but no udev unplug or plug event is detected so I wouldn't know when to run the script to restart it.

Thanks!

BillR
Associate III

0693W00000Lvct2QAB.pngI don't think I mentioned that we are only using this Type C port as device role. I notice other designs use a USB1600 chip to support dual role for Type C. I don't understand why the driver wouldn't be able to know that the cable gets unplugged, just by the removal of Vbus from the host or something.

-Bill

BillR
Associate III

I compared to a DK2 using udevadm and we see a 'remove' event. I do not get this event on my board.

root@stm32mp1:~# udevadm monitor -u
monitor will print the received events for:
UDEV - the event which udev sends out after rule processing
 
UDEV  [72314.380603] remove   /devices/platform/soc/5c002000.i2c/i2c-1/1-0028/typec/port0/port0-partner (typec)
 

BillR
Associate III

I decided it was time to take the dive into the kernel and then confirmed there is no disconnect interrupt in device mode, only suspend due to no activity on D lines.  

0693W00000Lvm1AQAR.pngThis isn't a problem on the DK2 I believe because its using the STMUSB1600 which gives disconnected indication. Since we only needed device mode and that chip was not available, we thought it wouldn't be a problem to leave out.

So, in

drivers/usb/dwc2/core_intr.c

we have the following:

/*
 * Change to L2 (suspend) state before releasing
 * spinlock
 */
hsotg->lx_state = DWC2_L2;
 
/* Call gadget suspend callback */
call_gadget(hsotg, suspend);

Change to:

dwc2_hsotg_disconnect(hsotg); 

I am going to test this next week.

Bill

BillR
Associate III

The above kernel patch works but does not completely solve the problem on its own. Also required is a daemon program to poll on:

/sys/class/udc/49000000.usb-otg/state

and when it now changes from "configured" to "not attached" (as a result of above kernel patch) that gives the indication to stop and start the script, and then ethernet gadget works fine now.

/sbin/stm32_usbotg_eth_config.sh stop
/sbin/stm32_usbotg_eth_config.sh start

This is the best I can come up with at this time, I don't have time to figure out a more proper kernel-only solution.

Bill

Kevin HUBER
ST Employee

Hello @BillR​ ,

I am not an USB expert, but I think I found something for you.

You are right, the USB DISC_INT is not available in device mode as explained in the refman.

But since you are able to detect the suspend operation and call the modified part of code that you made, it is because there is an interrupt.

in "drivers/usb/dwc2/core_intr.c"

The function that you changed "dwc2_handle_usb_suspend_intr" is called on an interrupt

#define GINTSTS_USBSUSP			BIT(11)

This interrupt is described in the refman v5.0 page 3168: https://www.st.com/resource/en/reference_manual/DM00327659-.pdf

0693W00000LwqKwQAJ.png 

And then you can see in the function "dwc2_handle_usb_suspend_intr" that you called your code when the status register "DSTS" has its bit DSTS_SUSPSTS to 1.

This register is described page 3208 of the refman v5.0:

0693W00000LwqMEQAZ.png 

So like the usb driver, you can watch this interrupt and verify the status of the register "DSTS" to know if you need to stop and start your usbotg shell script.

I think this is cleaner than changing an existing device.

Hope it helps,

Regards,

Kevin

In order to give better visibility on the answered topics, please click on 'Accept as Solution' on the reply which solved your issue or answered your question.