-
Notifications
You must be signed in to change notification settings - Fork 8.3k
subsys: usb: host: support for usb host cdc-ecm class #100289
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: main
Are you sure you want to change the base?
subsys: usb: host: support for usb host cdc-ecm class #100289
Conversation
Add a "struct usbh_status" that contains a bitmask of flags to keep track of the global state of the host context, like done for the device_next implementation. Signed-off-by: Josuah Demangeon <[email protected]>
Add missing copyright notice for the linker script to help with check_compliance.py. Signed-off-by: Josuah Demangeon <[email protected]>
Add a "struct usbh_class_api" for the host implementation, and move all the function poitners to it. Add more fields to "struct usbh_class_data". Signed-off-by: Josuah Demangeon <[email protected]>
Add API wrappers around the function pointers in struct usbh_class_api, while also documenting the USB host class internal API. Signed-off-by: Josuah Demangeon <[email protected]>
Add functions to probe/remove all classes as part of a new usbh_class.c and a matching usbh_class.h. These functions are called from the function usbh_init_device_intl() in usbh_core.c to initialize every class upon connection of a device. Every class driver provide filters to match the interfaces of the device. Co-authored-by: Aiden Hu <[email protected]> Signed-off-by: Josuah Demangeon <[email protected]>
Move the UVC header with all the definitions from the UVC standard to share it between USB host and device class implementation. Signed-off-by: Josuah Demangeon <[email protected]>
Add tests making sure the USB Host class APIs introduced build and run as expected. Signed-off-by: Josuah Demangeon <[email protected]>
Add tests making sure the USB Host class APIs introduced build and run as expected. Signed-off-by: Josuah Demangeon <[email protected]>
Move the UVC header with all the definitions from the UVC standard to share it between USB host and device class implementation. Signed-off-by: Josuah Demangeon <[email protected]>
Move UVC helper functions to a file shared between UVC host and device. The arrays are not visible anymore from either USB host or device, but instead accessed through a front-end funciton. Signed-off-by: Josuah Demangeon <[email protected]>
The USB control size field was wrong for UVC_PU_CONTRAST_CONTROL. Correct it to the correct value from the standard. Signed-off-by: Josuah Demangeon <[email protected]>
Loop through each of the VideoStreaming and VideoControl descriptor to parse them. This is meant as a stub for the purpose of testing the class API. Signed-off-by: Josuah Demangeon <[email protected]>
Add a test to run the USB Video Class host support by using the existing Zephyr USB Video Class device support. This allows running implementing the host side from the device side. A draft implementation of UVC is added leveraging this test. Signed-off-by: Josuah Demangeon <[email protected]>
The public API file <zephyr/usb/class/usbd_uvc.h> lacked an include to <zephyr/drivers/video.h> making it fail depending on the order of the includes. Signed-off-by: Josuah Demangeon <[email protected]>
Modify the USB device int sequence to read the device descriptor only after setting a valid device address. Signed-off-by: Santhosh Charles <[email protected]>
When hub is used, need to consider about multiple devices are attached. Signed-off-by: Aiden Hu <[email protected]>
add usbh_device_get_root and usbh_device_is_root function to check root device Signed-off-by: Aiden Hu <[email protected]>
For usb xfer, set endpoint type and interval by the selected endpoint desc. Signed-off-by: Aiden Hu <[email protected]>
Convert xfer's interval to actual value because mcux_ep->interval is already calculated. Signed-off-by: Aiden Hu <[email protected]>
maxPacketSize and numberPerUframe of pipe should be set considering additional transactions. Signed-off-by: Aiden Hu <[email protected]>
Add two functions: usbh_connect_device() for device connection usbh_disconnect_device() for device disconnection These functions centralize the logic for device attach/detach, including class probe and remove handling. They can be invoked by the hub class as well as dev_connected_handler and dev_removed_handler, improving code clarity and reuse. Signed-off-by: Aiden Hu <[email protected]>
Add support for the USB CDC ECM (Ethernet Control Model) class to the USB host subsystem. This implementation enables Ethernet functionality for USB host. Signed-off-by: Santhosh Charles <[email protected]>
Add devicetree binding file describing the USB Host CDC Ethernet Control Model (ECM) implementation for Zephyr. Signed-off-by: Santhosh Charles <[email protected]>
Introduce subsys/usb/common as a new directory intended to hold sources and configuration that are shared between USB host and device implementations. Integrate the new common directory into the build system. Signed-off-by: Santhosh Charles <[email protected]> Signed-off-by: Josuah Demangeon <[email protected]>
This reverts commit a01c220.
Add missing include for usbh_class.h header file in usbh_core.c to fix implicit declaration of function 'usbh_class_init_all' in usbh_core.c Signed-off-by: Dv Alan <[email protected]>
Add usbh_req_desc_str() helper function to retrieve USB string descriptors from a device. This function wraps the generic descriptor request with proper handling for string descriptors, including memory allocation, data copying, and endianness conversion for the bString field. Signed-off-by: Dv Alan <[email protected]>
Add Ethernet Statistics Feature Selector enumeration defining all standard CDC ECM statistics counters (XMIT_OK, RCV_OK, etc.) as per the USB CDC specification. Add CDC notification packet structure for handling device notifications. Add CONNECTION_SPEED_CHANGE notification code and Ethernet Power Management Pattern activation constants. Signed-off-by: Dv Alan <[email protected]>
Complete rewrite of the USB host CDC-ECM (Ethernet Control Model) driver with improved architecture and functionality: - Restructure driver to use proper Ethernet API with ETH_NET_DEVICE_DT_INST_DEFINE - Implement asynchronous RX handling using k_poll signals and dedicated thread - Add support for fragmented network buffers with linearization - Implement proper packet filter management (promiscuous, multicast, broadcast) - Add support for connection speed change notifications and link capabilities - Implement MAC address retrieval from USB string descriptors with multi-language support - Add comprehensive CDC-ECM class requests (SET_ETHERNET_PACKET_FILTER, GET_ETHERNET_STATISTIC, SET_ETHERNET_MULTICAST_FILTERS, etc.) - Use separate buffer pools for TX and RX data transfers - Add proper ZLP (Zero Length Packet) handling for bulk transfers - Implement automatic RX restart mechanism with error recovery - Add network interface up/down state management - Update Kconfig with configurable buffer counts and stack size - Rename Kconfig file from Kconfig.cdc_ecm_host to Kconfig.cdc_ecm - Change DT compatible from "zephyr,usbh-cdc-ecm" to "zephyr,cdc-ecm-host" - Mark driver as EXPERIMENTAL in Kconfig The rewritten driver provides better error handling, improved performance through asynchronous operations, and more complete CDC-ECM feature support. Signed-off-by: Dv Alan <[email protected]>
Rename the CDC-ECM host device tree binding file from zephyr,usbh-cdc-ecm.yaml to zephyr,cdc-ecm-host.yaml to align with the updated compatible string used in the rewritten driver. Update the binding description to clarify that each CDC-ECM instance represents an ethernet interface visible to Zephyr's networking stack. Remove the local-mac-address property as MAC address retrieval is now handled directly from USB string descriptors in the driver implementation. Signed-off-by: Dv Alan <[email protected]>
|
| @@ -0,0 +1,1157 @@ | |||
| /* | |||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
this is a ethernet driver, so it belongs in drivers/ethernet/. I know there are already others there, but these should probably be moved too. I don't like ethernet drivers and its api be scattered all over the tree. (should be limited to the ethernet and wifi drivers and the net subsystem)
| net_if_carrier_off(priv->iface); | ||
|
|
||
| usbh_cdc_ecm_stop_auto_rx(priv); | ||
|
|
||
| ret = net_if_down(priv->iface); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
net_if_down should not be used from the ethernet driver, it is only for the user and the networking subsys. net_if_carrier_off should only be used. It is there to signal to the networking subsystem, that there is no connection.
| priv->caps = 0; | ||
| (void)atomic_clear(&priv->eth_pkt_filter_bitmap); | ||
|
|
||
| ret = net_if_down(priv->iface); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
we normally don't do net_if_down or net_if_up from the ethernet driver. Please try to get rid of them.
| goto cleanup; | ||
| } | ||
|
|
||
| ret = net_mgmt(NET_REQUEST_ETHERNET_SET_MAC_ADDRESS, data->iface, ð_req_params, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
don't use net_mgmt inside a ethernet driver to control itself. use net_if_set_link_addr directly for example.
| case USB_CDC_CONNECTION_SPEED_CHANGE: | ||
| if (xfer->buf->len != (sizeof(struct cdc_notification_packet) + 8)) { | ||
| ret = -EBADMSG; | ||
| goto cleanup; | ||
| } | ||
|
|
||
| link_speeds = (uint32_t *)(notif + 1); | ||
|
|
||
| for (size_t i = 0; i < 2; i++) { | ||
| link_speeds[i] = sys_le32_to_cpu(link_speeds[i]); | ||
| switch (link_speeds[i]) { | ||
| case 2500 * 1000000U: | ||
| priv->caps |= ETHERNET_LINK_2500BASE; | ||
| case 1000 * 1000000U: | ||
| priv->caps |= ETHERNET_LINK_1000BASE; | ||
| case 100 * 1000000U: | ||
| priv->caps |= ETHERNET_LINK_100BASE; | ||
| case 10 * 1000000U: | ||
| priv->caps |= ETHERNET_LINK_10BASE; | ||
| break; | ||
| default: | ||
| break; | ||
| } | ||
| } | ||
| break; | ||
| default: | ||
| break; | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
the caps are just for the generally supported speeds of the device, not of the current speeds. if you want to expose this to the user, use the ethernet phy api.




Dependencies:
This implementation contains all commits from #99775 & some necessary commits from #99097 and in addition:
samples/net/dhcpv4_client(CDC-ECM feature can be verified at boardrd_rw612_bga)It is fixed & improved the implementation in #99097: