nilclass / usbh

WIP USB host abstraction for embedded targets
MIT License
9 stars 1 forks source link

Hardware support for: ESP32-S3-USB-OTG #2

Open paulyoung opened 2 months ago

paulyoung commented 2 months ago

ESP32-S2/S3 chips have built-in USB-OTG peripherals, which support USB host mode.

I specifically have a ESP32-S3-USB-OTG board that I would like to use as a USB host.

I think esp-rs/esp-idf-sys and these USB host examples could be useful.

paulyoung commented 2 months ago

https://docs.rs/esp32s3/latest/esp32s3/usb0/index.html

paulyoung commented 2 months ago

https://docs.espressif.com/projects/esp-idf/en/latest/esp32s3/api-reference/peripherals/usb_host.html

paulyoung commented 2 months ago

https://docs.espressif.com/projects/esp-iot-solution/en/latest/usb/usb_overview/usb_host_solutions.html

paulyoung commented 2 months ago

https://docs.rs/esp32s3/latest/esp32s3/struct.USB0.html

paulyoung commented 2 months ago

I’m a bit out of my depth here but I think the idea is that I would implement usbh::bus::HostBus using esp32-idf-sys by referring to the file below.

https://github.com/espressif/esp-idf/blob/59e18382702b6986be3d3f55e9ac7763c1397cf7/components/usb/usb_host.c

paulyoung commented 2 months ago

Or perhaps this one https://github.com/espressif/esp-idf/blob/59e18382702b6986be3d3f55e9ac7763c1397cf7/components/usb/hcd_dwc.c

nilclass commented 2 months ago

Hey @paulyoung, that sounds like an interesting device to try.

I’m a bit out of my depth here but I think the idea is that I would implement usbh::bus::HostBus using esp32-idf-sys by referring to the file below.

Yes, ideally that is all you need to do. In practice it may turn out to be hard or impossible -- in that case we would need to change the HostBus trait a bit. Ostensibly it's easy to implement on any hardware, but since so far it's only implemented for the RP2040 I don't know what "easy" means yet :)

nilclass commented 2 months ago

I took a peek at the docs for esp32-s3, unfortunately the registers aren't documented: https://www.espressif.com/sites/default/files/documentation/esp32-s3_technical_reference_manual_en.pdf#subsection.32.5

When I wrote the code for the rp2040, the register docs were a huge help.

This SVD file has a list of all the registers & their fields though, so that can be a start: https://raw.githubusercontent.com/esp-rs/esp-pacs/main/esp32s3/svd/esp32s3.base.svd (I'm using the openocd-svd viewer to browse SVD files, not sure if there's something better?)

What I would do is go through the registers, and try to guess what they might do, skipping those where I have no clue. Like this one, I guess could mean "Embedded Host ENable"? :shrug: image

Or it might not.

Then I would write a sketch to log some register fields to see if they change, and maybe mess with some of them to see if it changes anything:

// read EHEN field from the GOTGTCL register of the USB0 peripheral
writeln!(uart0, "ehen: {}", peripherals.USB0.gotgctl().read().ehen().bit()).unwrap();
// write EHEN bit
peripherals.USB0.gotgctl().write(|w| w.ehen().set_bit());
// or:
peripherals.USB0.gotgctl().write(|w| w.ehen().clear_bit());

There's a bunch of registers that start with "HC", maybe that means "Host Controller"? image

Another good source could be the esp-hal code for device mode support in embassy: https://github.com/esp-rs/esp-hal/blob/main/esp-hal/src/otg_fs.rs Support for the UsbBus trait from usb-device seems to be implemented here: https://github.com/esp-rs-compat/synopsys-usb-otg/blob/esp32sx/src/bus.rs

If nothing else, those sources can tell you what not do to as a host, like force device mode.

For the record, I'm out of my depth here too :smile: