embassy-rs / embassy

Modern embedded framework, using Rust and async.
https://embassy.dev
Apache License 2.0
5.67k stars 790 forks source link

STM32F4: USB HID Keyboard not working in BIOS (before Linux start) #2997

Open dariogoetz opened 6 months ago

dariogoetz commented 6 months ago

MCU: STM32F401CC

I have written an embassy-based keyboard firmware for a keyboard. The firmware works well in Linux. However, the keyboard does not produce anything when the laptop asks for a system password when booting (before Linux starts).

I could reproduce the issue with the code from the examples directory examples/stm32f4/src/bin/usb_hid_keyboard.rs (adjusted for clocks of the STM32F401CC, otherwise vanilla): Within my Linux system, it produces an a when pulling PC13 up. In the password prompt before starting Linux, however, nothing happens.

I have another firmware based on rtic, stm32f4xx-hal, and usb-device that does not have this issue, so I would exclude it being a hardware issue.

Any ideas, what the issue could be?

joelsa commented 5 months ago

Any ideas, what the issue could be?

If the device implements the boot protocol, the device subclass needs to be set to 0x01, see page 8 of the USB HID specification: https://www.usb.org/sites/default/files/documents/hid1_11.pdf

So as a bare minimum, this line here needs to be set to 0x01:

https://github.com/embassy-rs/embassy/blob/26e660722cca9151e5a9331c328421145509ab20/examples/stm32f4/src/bin/usb_hid_keyboard.rs#L77C12-L77C28

Of course, this should only be set to 0x01 if your device supports the boot protocol. See Appendix F and G of above document for information on what's needed to implement it.

Depending on the rest of your Code chances are, that you do not need to do anything apart from changing the referenced line with the subClass, so you might try that out.

dariogoetz commented 4 months ago

Thank you very much for the feedback. I tried various different combinations, also setting different values for config.device_class (the default value and 0x03) and config.composite_with_iads while fixing config.device_sub_class=0x01. None worked, unfortunately.

When you wrote "f your device supports the boot protocol", what is the "device" you speak of? I am using an STM32F401CCU6 black pill board. Is that what you mean? Apart from that, the various requirements described in the F and G sections of the document that you linked refer to software-related things that are (or should be) implemented in embassy-usb. Maybe I got that wrong, though.